// License: GPL. For details, see LICENSE file.
package org.openstreetmap.josm.gui.dialogs.changeset.query;
import static org.openstreetmap.josm.tools.I18n.tr;
import java.time.LocalTime;
import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeParseException;
import java.time.format.FormatStyle;
import javax.swing.text.JTextComponent;
import org.openstreetmap.josm.Main;
import org.openstreetmap.josm.gui.widgets.AbstractTextComponentValidator;
/**
* Validates time values entered as text in a {@link JTextComponent}. Validates the input
* on the fly and gives feedback about whether the time value is valid or not.
*
* Time values can be entered in one of four standard formats defined for the current locale.
* @since 11326 (extracted from AdvancedChangesetQueryPanel)
*/
public class TimeValidator extends AbstractTextComponentValidator {
/**
* Constructs a new {@code TimeValidator} for the given text component.
* @param tc text component
*/
public TimeValidator(JTextComponent tc) {
super(tc);
}
/**
* Decorates the given text component.
* @param tc text component to decorate
* @return new time validator attached to {@code tc}
*/
public static TimeValidator decorate(JTextComponent tc) {
return new TimeValidator(tc);
}
@Override
public boolean isValid() {
if (getComponent().getText().trim().isEmpty())
return true;
return getTime() != null;
}
/**
* Returns the standard tooltip text as HTML.
* @return the standard tooltip text as HTML
*/
public String getStandardTooltipTextAsHtml() {
return "<html>" + getStandardTooltipText() + "</html>";
}
/**
* Returns the standard tooltip text.
* @return the standard tooltip text
*/
public String getStandardTooltipText() {
final ZonedDateTime now = ZonedDateTime.now();
return tr(
"Please enter a valid time in the usual format for your locale.<br>"
+ "Example: {0}<br>"
+ "Example: {1}<br>"
+ "Example: {2}<br>"
+ "Example: {3}<br>",
DateTimeFormatter.ofLocalizedTime(FormatStyle.SHORT).format(now),
DateTimeFormatter.ofLocalizedTime(FormatStyle.MEDIUM).format(now),
DateTimeFormatter.ofLocalizedTime(FormatStyle.LONG).format(now),
DateTimeFormatter.ofLocalizedTime(FormatStyle.FULL).format(now)
);
}
@Override
public void validate() {
if (!isValid()) {
String msg = "<html>The current value isn't a valid time.<br>" + getStandardTooltipText() + "</html>";
feedbackInvalid(msg);
return;
} else {
String msg = "<html>" + getStandardTooltipText() + "</html>";
feedbackValid(msg);
}
}
/**
* Returns the time.
* @return the time
*/
public LocalTime getTime() {
if (getComponent().getText().trim().isEmpty())
return LocalTime.MIDNIGHT;
for (final FormatStyle format: FormatStyle.values()) {
DateTimeFormatter df = DateTimeFormatter.ofLocalizedTime(format);
try {
return LocalTime.parse(getComponent().getText(), df);
} catch (DateTimeParseException e) {
// Try next format
Main.trace(e);
}
}
return LocalTime.MIDNIGHT;
}
}