Skip to main content
Post a question

Notifications

Announcements

No record found.

Customizing D365 with event handlers

Sukrut Parab Profile Picture Sukrut Parab 71,673 Moderator

With Dynamics 365 release we have to do most of the things using extensions and event handlers. You still have an option to over layer code. While creating new package if you choose select existing packages and modified any standard object which belongs to that package, you are doing overlaying.  In previous versions it was not a big  issue but with new release we should stop doing that and instead embrace a practice of doing customizations using extensions and event handlers.

Source code and metadata of model elements can be extended without an over-layering using extensions.

Today I will share some code snippets about how to  do few things while using event handlers which are going to help you while doing common scenarios like how to get form datasource , form controls etc.. in event handlers.

How to get Form Datasource

If you copy form event handler here is how you can get form datasource from XFormRun

  1. [FormEventHandler(formStr(HcmPosition), FormEventType::Initialized)]
  2. public static void HcmPosition_OnInitialized(xFormRun sender, FormEventArgs e)
  3. {
  4.  
  5. FormDataSource hcmosition_ds = sender.dataSource(formDataSourceStr(HcmPosition, HcmPosition));
  6. Or
  7. FormDataSource hcmosition_ds = sender.dataSource('HcmPosition');
  8. }


If you copy form datasource event you can get form run object from datasource  as below. Once you get form run you can call any form method available on the form.

  1. [FormDataSourceEventHandler(formDataSourceStr(HcmPosition, HcmPosition), FormDataSourceEventType::Created)]
  2. public static void HcmPosition_OnCreated(FormDataSource sender, FormDataSourceEventArgs e)
  3. {
  4.  
  5. FormRun formRun = sender.formRun() as FormRun;
  6. }

 

Similarly you can get formrun on a from control event handler using FormControl

  1. [FormControlEventHandler(formControlStr(HcmPosition, HcmPosition_PositionId1), FormControlEventType::Modified)]
  2. public static void HcmPosition_PositionId1_OnModified(FormControl sender, FormControlEventArgs e)
  3. {
  4. FormRun formRun = sender.formRun() as FormRun;
  5.  
  6. }

To get control on a form  and make it editable or non-editable

  1. [FormEventHandler(formStr(HcmPosition), FormEventType::Initialized)]
  2. public static void HcmPosition_OnInitialized(xFormRun sender, FormEventArgs e)
  3. {
  4. sender.design().controlName(formControlStr(HcmPosition, HcmPositionNewPosition)).AllowEdit(false);
  5. // to get form open Mode
  6. OpenMode openMode = sender.args().openMode();
  7. }

 

Getting  current record

Hcmposition is first datasource  on HcmPosition form  that’s why  gave 1 in datasource.

  1. [FormControlEventHandler(formControlStr(HcmPosition, HcmPositionNewPosition), FormControlEventType::Clicked)]
  2. public static void HcmPositionNewPosition_OnClicked(FormControl sender, FormControlEventArgs e)
  3. {
  4.  
  5. HcmPosition hcmposition = sender.formRun().dataSource(1).cursor();
  6. }

 

Using DataEventArgs to send Validation result

  1. [DataEventHandler(tableStr(CategoryTable), DataEventType::ValidatingDelete)]
  2. public static void CategoryTable_onValidatingDelete(Common _sender, DataEventArgs _e)
  3. {
  4. CategoryTable categoryTable = _sender as CategoryTable;
  5. ValidateEventArgs validateEventArgs = _e as ValidateEventArgs;
  6. boolean ret = true;
  7.  
  8. if (categoryTable.UseInProject)
  9. {
  10. ProjCategory projCategory = ProjCategory::find(categoryTable.CategoryId);
  11. ret = projCategory.validateDelete();
  12. }
  13.  
  14. if (ret && categoryTable.UseInExpense)
  15. {
  16. TrvCostType trvCostType = TrvCostType::find(categoryTable.CategoryId);
  17. ret = trvCostType.validateDelete();
  18. }
  19. if (!ret)
  20. {
  21. validateEventArgs.parmValidateResult(false);
  22. }
  23. }

 

Similarly you can use on ValidateFieldValueEventArgs  to send validation result back to Validate Field method

  1. [DataEventHandler(tableStr(LedgerParameters), DataEventType::ValidatingFieldValue)]
  2. public static void LedgerParameters_onValidatingFieldValue(Common sender, DataEventArgs e)
  3. {
  4. ValidateFieldValueEventArgs ve = e;
  5. boolean isValid = true;
  6. LedgerParameters ledgerParameters = sender as LedgerParameters;
  7. #isoCountryRegionCodes
  8. if (ve.parmFieldName() == fieldStr(LedgerParameters, ChineseVoucher_CN)
  9. && SysCountryRegionCode::isLegalEntityInCountryRegion([#isoCN]))
  10. {
  11. if ((select firstonly RecId from LedgerJournalTrans
  12. where LedgerJournalTrans.LedgerVoucherType_CN != 0
  13. || LedgerJournalTrans.Voucher_CN != '').RecId != 0)
  14. {
  15. // The general journal needs to be empty in order to modify the setup for the Chinese voucher system.
  16. isValid = checkFailed("@GLS54497");
  17. }
  18. ve.parmValidateResult(isValid);
  19. }
  20. }

 

More information about customizing using extensions can be found here

 

Comments

*This post is locked for comments

  • CAHE4KA Profile Picture CAHE4KA 10
    Posted 08 Nov 2019 at 23:39:42
    Ann2015, right-click the Event in the Form designer and select Find event handlers
  • Ann2015 Profile Picture Ann2015 1,122
    Posted 18 Jan 2019 at 16:24:43

    if there is already a custom code in the method, how can I see that ?

    I know I can copy and create a new event handlers but how do I know what's in the code already? Is there any way to view it? Thank u . Ann