Wednesday, October 5, 2011

Using the do_config_determination to change a screen layout

Sometimes, you run in to a requirement where you would like to change the layout of the screen based on another field, for instance if a dropdownbox contains a certain value, you would like to show different input fields from when the dropdown box contains another value, or in some cases the existence of a value in one field might require input in another field.

There are several ways to implement this, where one of the most flexible ways is implementing the DO_CONFIG_DETERMINATION. Standard SAP does not contain many implementations of this class, but the best example is probably in component BP_HEAD in the AccountDetails view.

If you look at the code, the do_config_determination first reads the values from the typed_context.
You can of course read values directly from the context, or first retrieve them from the relations.
Then, using a simple method call, the values are sent to the config keys:

  me->set_config_keys( iv_object_type          = lv_object_type
                       iv_object_sub_type      = lv_subtype
                       iv_propagate_2_children = abap_true ).

As you can see in the BP_HEAD/AccountDetails view, the object_type and subobject_type are set. You can only use the object_type and subobject_types that are available in the system, so, in the example, SAP uses BP_ACCOUNT, INDIVIDUAL and GROUP. So, the logic to determine the object type in this case is hardcoded.

Another good example of variable configuration determination can be seen in BT126H_APPT. Here, SAP decided not to use the do_config_determination of a particular view, but to implement it in the window BT126H_APPT/MainWindow.

The downside of using the configuration determination using the object_type and object_subtype, is that while adding new configurations, the values that are available are limited to what has been defined in the hardcoded valuehelp.

If you want to be implement dynamic configuration determination independent of hardcoded objects and subobjects, you can use the field 'Component Usage'. If you move the value from a field to the component usage, you will be able to differentiate in the configuration based on the value you have entered in the screen. If the values in the screen are limited to a few values (for instance in a radiobutton, or a dropdown listbox), this could be a perfect solution to your requirement.
If you want to check whether a value is present in a field or not, do not move the exact value to the component usage, but move 'X' or 'Blank' to the field for instance. Otherwise, you would have to create configurations for all possible entries in the field.

You can set the component usage in the do_config_determination, by implementing the following statement: 

ME->CONFIGURATION_DESCR->SET_COMPONENT_USAGE( [your variable] ).

As the do_config_determination is called on every roundtrip, you can choose to force a roundtrip after changing the value in a DDLB or a radiobutton by implementing an event as described here. You do not necessarily have to implement the actual corresponding event handler, as all you want to do is force a roundtrip.

For ordinary input fields, a roundtrip is triggered upon enter.

Using this dynamic usage determination, you are able to move for instance the user status of an object to the component usage field, and then differentiate in the view configuration per status. In some cases you might have different mandatory fields for different statusses.

2 comments: