With the validate option set to "key", we will activate the entry validation that gets triggered on any content modification. The value is "none" by default, which means that there is no validation.
Other possible values are "focusin" and "focusout", which validate when the widget gets or loses the focus, respectively, or simply "focus" to validate in both cases. Alternatively, we can use the "all" value to validate in all situations.
The validatecommand function is called each time the validation is triggered, and it should return true if the new content is valid, and false otherwise.
Since we need more information to determine whether the content is valid or not, we create a Tcl wrapper around our Python function using the register method of the Widget class. Then, you can add the percent substitution for each parameter that will be passed to the Python function. Finally, we will group these values as a Python tuple. This corresponds to the following line from our example:
vcmd = (self.register(self.validate_username), "%i", "%P")
In general, you can use any of the following substitutions:
- %d: Type of action; 1 for insertion, 0 for deletion, and -1 otherwise
- %i: Index of the string being inserted or deleted
- %P: Value of the entry if the modification is allowed
- %s: Value of the entry before the modification
- %S: String content that is being inserted or deleted
- %v: The type of validation currently set
- %V: Type of validation that triggered the action
- %W: The name of the Entry widget
The invalidcommand option takes a function that is invoked when validatecommand returns false. The same percent substitutions can be applied to this option, but in our example, we directly passed the print_error() method of our class.