One of the questions that is asked from time to time while working on Personas projects is how to make certain fields mandatory on screens. Usually there are multiple ways in the backend to do this, either via IMG configuration options, transaction / screen variants or application-specific features (for example the incompletion procedure in case of sales documents). If such a solution exists, it is generally best to fulfill the requirement using them. Another method could be some coding that takes advantage of a BAdI, enhancement spot or user exit. However, in some cases there may not be an easy way to solve the issue if none of the mentioned methods is available.
Let’s see how it is possible to achieve this goal with the use of an SAP Screen Personas flavor. I’m going to use the Create Sales Order (VA01) application as an example and want to make the “Sales office” field on the first screen a required entry.
The flavor editor offers a way to show a field seem as required. This visual option is available by setting the ‘Suggested’ attribute, after which the field will appear as required, displaying a red asterisk in the front.
Unfortunately, this will not actually enforce entering a value like a usual mandatory field. To do this, we must employ some scripting.
This check should happen after user interaction, like pressing Enter or selecting a menu option etc. Therefore, we need to perform this validation tied to the onBeforeRefresh screen event which is the last one before control is passed to the backend. Our goal is to interrupt processing if the “Sales office” field is left blank and issue an error message. However, there are some actions which we must not interrupt, because they are performing a standard navigation or user action.
We can use the following script snippet to do just that:
/* globals caller triggerType vkey */
switch(triggerType) {
case session.findById("wnd[0]").EVENT_VCOMP:
// If Back, Cancel or Exit pressed:
if (caller && (caller === "wnd[0]/tbar[0]/btn[12]" || caller === "wnd[0]/tbar[0]/btn[15]" || caller === "wnd[0]/tbar[0]/btn[3]")) {
// leave it to backend processing
return;
}
break;
case session.findById("wnd[0]").EVENT_VKEY:
if ( vkey === 4 ) {
// F4 Search Help
return;
}
break;
}
This will first verify if the user selected one of the actions we do not want to interrupt and pass the control to the backend to continue as usual if either the Back, Cancel or Exit button is pressed or search help was requested.
In all other cases, our check logic should run to ensure that the “Sales office” field is populated. So, let’s add this to our script:
if (session.findById("wnd[0]/usr/ctxtVBAK-VKBUR").text == "") {
session.findById("wnd[0]/sbar").setMessage("Fill out all required fields", "E");
session.findById("wnd[0]/usr/ctxtVBAK-VKBUR").setFocus(); //set cursor to the empty required field
return true; //interrupt screen processing
}
Now if we assign this script to the onBeforeRefresh screen event, it will work exactly as we want, and it doesn’t let the user go to the next screen without specifying the “Sales office” value.
If we have multiple languages to deal with, we can certainly use a language-dependent error message instead of the hard coded one above, and use something like this to turn the text into a variable:
session.findById("wnd[0]/sbar").setMessage("$FLVRT:ER1", "E");
This variable is translatable via Flavor Administration to all languages we support.
In case we have more than one field on the screen that should be mandatory, we can optimize our script, so we don’t repeat the same logic for each. Let’s say, we also want the “Sales group” field to be mandatory, besides “Sales office”. So then, the second part of the script could look like the following:
if (isEmpty("wnd[0]/usr/ctxtVBAK-VKBUR") || isEmpty("wnd[0]/usr/ctxtVBAK-VKGRP")) {
return true; //interrupt screen processing
}
function isEmpty(fieldID) {
if (session.findById(fieldID).text == "") {
session.findById("wnd[0]/sbar").setMessage("Fill out all required fields", "E");
session.findById(fieldID).setFocus(); //set cursor to the field
return true; //indicate an empty required field
}
}
As mentioned earlier, the preferred way is to use backend features to make fields required, since that will also work for users who are not running a Personas flavor. This method is there if no such option is available. In addition, the above scripted solution can be useful if fields should be turned to be mandatory in a dynamic fashion. Like in this case, we could enforce entry in these fields only for certain order types.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
User | Count |
---|---|
19 | |
11 | |
9 | |
7 | |
7 | |
6 | |
6 | |
5 | |
5 | |
4 |