Bugs in AbstractIntegerField [message #1767916] |
Wed, 12 July 2017 07:02 |
Urs Beeli Messages: 573 Registered: October 2012 Location: Bern, Switzerland |
Senior Member |
|
|
I've stumbled across a couple of bugs in the behaviour of the AbstractIntegerField. (We're using Scout 6.1.0.B009, I haven't testet if a nightly 6.1.0 build or Scout 7.0 behaves differently).
Bug 1: German validation message on minimum or maximum value only
If I use getConfiguredMinValue() and getConfiguredMaxValue() and then enter a value outside this range, the message is correct in German: "Der Wert ist zu klein/gross: Muss zwischen <min> und <max> liegen".
However, if I use only one of the two (getConfiguredMinValue() *or* getConfiguredMaxValue()), the German validation message is incorrect:
"Der Wert ist zu klein: muss grösser als <min> sein" --> correct would be "Der Wert ist zu klein: muss grösser gleich <min> sein".
"Der Wert ist zu gross: muss kleiner als <max> sein" --> correct would be "Der Wert ist zu gross: muss kleiner gleich <max> sein".
The attached code shows this behaviour in the "MinField" (try entering -4) and "MaxField" (try entering 444) fields. I have only tested this with German, I don't know if the English (or other language) texts are correct.
Bug 2: MaxIntegerDigits also crop out of range numbers
If I use getConfiguredMaxValue() and getConfiguredMaxIntegerDigits() and then enter a number that is too large and has more digits than were configured, the number gets cropped to the specified number of digits and an error message is shown about the number being too large. However, the number shown can be smaller than the upper limit, so the error text makes no sense to the user.
To see this demonstrated use the "MinMaxDigit" field in the code below and enter the value "888". This will be cropped to "88" and the error text will be "Der Wert ist zu gross: muss kleiner als 99 sein". However, 88 *is* smaller than "99" so to the user that will be pretty confusing.
The reason for this seems to be that AbstractValueField.setValue() on line 328-330 catches ProcessingExceptions and then calls updateDisplayText(rawValue) which eventually leads to AbstractNumberField.formatValueInternal() being called which then calls getFormatInternal().format(value). However, the format being returned by getFormatInternal() has had the maximum number of digits applied thus cropping any extraneous digits...
I don't see an easy fix for this, but in effect it renders getConfiguredMaxIntegerDigits() pretty useless in conjunction with getConfiguredMaxValue()...
public class TestForm extends AbstractForm {
@Override
protected String getConfiguredTitle() {
return "Integer Field Tests";
}
@Override
public void start() throws ProcessingException {
startInternal(new NullFormHandler());
}
@Order(10.0)
public class MainBox extends AbstractGroupBox {
@Order(10.0)
public class IntegerField extends AbstractIntegerField {
@Override
protected String getConfiguredLabel() {
return getClass().getSimpleName();
}
}
@Order(20.0)
public class MinField extends AbstractIntegerField {
@Override
protected String getConfiguredLabel() {
return getClass().getSimpleName();
}
@Override
protected Integer getConfiguredMinValue() {
return 0;
}
}
@Order(30.0)
public class MaxField extends AbstractIntegerField {
@Override
protected String getConfiguredLabel() {
return getClass().getSimpleName();
}
@Override
protected Integer getConfiguredMaxValue() {
return 99;
}
}
@Order(40.0)
public class MinMaxField extends AbstractIntegerField {
@Override
protected String getConfiguredLabel() {
return getClass().getSimpleName();
}
@Override
protected Integer getConfiguredMinValue() {
return 0;
}
@Override
protected Integer getConfiguredMaxValue() {
return 99;
}
}
@Order(50.0)
public class MinMaxDigitField extends AbstractIntegerField {
@Override
protected String getConfiguredLabel() {
return getClass().getSimpleName();
}
@Override
protected Integer getConfiguredMinValue() {
return 0;
}
@Override
protected Integer getConfiguredMaxValue() {
return 99;
}
@Override
protected int getConfiguredMaxIntegerDigits() {
return 2;
}
}
@Order(60.0)
public class DigitField extends AbstractIntegerField {
@Override
protected String getConfiguredLabel() {
return getClass().getSimpleName();
}
@Override
protected int getConfiguredMaxIntegerDigits() {
return 2;
}
}
@Order(1000.0)
public class CloseButton extends AbstractCloseButton {
}
}
}
|
|
|
|
|
Re: Bugs in AbstractIntegerField [message #1773235 is a reply to message #1771325] |
Mon, 25 September 2017 08:30 |
|
Urs,
Thank you very much for your analysis and the example form.
1. Wrong message
Yes, this validation message is confusing and technically wrong. Apparently, no one noticed this in the past 10 years or so. :-) Can you open a bug for this? It will take a while to fix it, as the same text is used in a number of languages. A similar validation message occurs when both the min and max value are restricted ("value must be between X and Y"). It is also not 100% clear if the lower and upper bound are included in the valid range. Do you have a suggestion on how to improve this message?
Be the way: to quickly fix this in your application, you can just register your own ITextProviderService, provide your own Texts.properties file and re-define the text key.
2. and 3. Min/max number of digits
This is clearly a very confusing behavior. However, is it really necessary to use both properties simultaneously? My suggested quick-fix would be to limit the maximum value or the maximum number of digits. Also, you should always be able to override execValidateValue() and implement your own logic.
The min/max number of digits is implemented using the standard Java DateFormat. Apparently, these properties are only used to format and parse, not validate. Maybe this does not really match Scout's validation cycle, or maybe the JavaDoc is just not clear enough. I cannot give you a definitive answer here, so I suggest, you create a bugzilla for this issue as well.
Regards,
Beat
|
|
|
|
Powered by
FUDForum. Page generated in 0.02696 seconds