diff --git a/platform-dao/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDatesDao.java b/platform-dao/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDatesDao.java index f0d84e3c7ce..b51cd4b0daf 100644 --- a/platform-dao/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDatesDao.java +++ b/platform-dao/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDatesDao.java @@ -22,7 +22,7 @@ public TgEntityWithTimeZoneDatesDao(final IFilter filter) { @Override protected IFetchProvider createFetchProvider() { - return super.createFetchProvider().with("key", "dateProp", "datePropUtc"); + return super.createFetchProvider().with("key", "dateProp", "datePropUtc", "datePropDependent"); } } \ No newline at end of file diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/criteria/generator/impl/CriteriaGenerator.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/criteria/generator/impl/CriteriaGenerator.java index b953600a19c..16656fd0d49 100644 --- a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/criteria/generator/impl/CriteriaGenerator.java +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/criteria/generator/impl/CriteriaGenerator.java @@ -215,15 +215,10 @@ private static List generateCriteriaProperties(final Class copyDateAnnotations(final Class managedType, final String propertyName) { - return of(DateOnly.class, TimeOnly.class, PersistentType.class) + return of(DateOnly.class, TimeOnly.class, PersistentType.class, DependentTimeZoneMode.class) .map(annotationType -> getPropertyAnnotationOptionally(annotationType, managedType, propertyName)) .flatMap(annotation -> annotation.isPresent() ? of(annotation.get()) : empty()) .map(annotation -> { @@ -231,8 +226,10 @@ private static List copyDateAnnotations(final Class managedType, return newDateOnlyAnnotation(); } else if (annotation instanceof TimeOnly) { return newTimeOnlyAnnotation(); - } else { + } else if (annotation instanceof PersistentType) { return newUtcAnnotation(); + } else { + return newDependentTimeZoneModeAnnotation(); } }) .collect(toList()); diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/DependentTimeZoneMode.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/DependentTimeZoneMode.java new file mode 100644 index 00000000000..adf8d56d108 --- /dev/null +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/DependentTimeZoneMode.java @@ -0,0 +1,35 @@ +package ua.com.fielden.platform.entity.annotation; + +import ua.com.fielden.platform.utils.IDates; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; +import java.util.Date; + +/// An annotation for properties of type [java.util.Date] to enforce dependent time-zone mode in Web UI logic. +/// +/// Please note, that appropriate [IDates#now()] and [IDates#zoned(Date)] method variations are required in server-side logic. +/// I.e. it may not be sufficient to annotate the properties with this annotation. +/// +/// ```java +///static DateTime now(final IDates dates) { +/// return new DateTime(getTimeZone(dates)); +///} +///static DateTime zoned(final Date date, fina IDates dates) { +/// return new DateTime(date, getTimeZone(dates)); +///} +///private static DateTimeZone getTimeZone(final IDates dates) { +/// if (dates.requestTimeZone().isEmpty()) { +/// throw failure(ERR_TIME_ZONE_IS_MISSING); +/// } +/// return dates.requestTimeZone().get(); +///} +/// ``` +/// +@Retention(RetentionPolicy.RUNTIME) +@Target({ ElementType.FIELD }) +public @interface DependentTimeZoneMode { + +} diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/factory/DateAnnotations.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/factory/DateAnnotations.java index 5aa37d51693..4396a9a2ea0 100644 --- a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/factory/DateAnnotations.java +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/entity/annotation/factory/DateAnnotations.java @@ -1,25 +1,19 @@ package ua.com.fielden.platform.entity.annotation.factory; -import java.lang.annotation.Annotation; - import ua.com.fielden.platform.entity.annotation.DateOnly; +import ua.com.fielden.platform.entity.annotation.DependentTimeZoneMode; import ua.com.fielden.platform.entity.annotation.PersistentType; import ua.com.fielden.platform.entity.annotation.TimeOnly; import ua.com.fielden.platform.types.markers.IUtcDateTimeType; -/** - * Factory for date annotations. - * - * @author TG Team - * - */ +import java.lang.annotation.Annotation; + +/// Factory for date annotations. +/// public class DateAnnotations { - /** - * Instantiates {@link DateOnly} annotation. - * - * @return - */ + /// Instantiates [DateOnly] annotation. + /// public static DateOnly newDateOnlyAnnotation() { return new DateOnly() { @Override @@ -29,11 +23,8 @@ public Class annotationType() { }; } - /** - * Instantiates {@link TimeOnly} annotation. - * - * @return - */ + /// Instantiates [TimeOnly] annotation. + /// public static TimeOnly newTimeOnlyAnnotation() { return new TimeOnly() { @Override @@ -43,11 +34,8 @@ public Class annotationType() { }; } - /** - * Instantiates marker annotation for UTC date properties. - * - * @return - */ + /// Instantiates marker annotation for UTC date properties. + /// public static PersistentType newUtcAnnotation() { return new PersistentType() { @Override @@ -66,5 +54,16 @@ public Class userType() { } }; } - + + /// Instantiates [DependentTimeZoneMode] annotation. + /// + public static DependentTimeZoneMode newDependentTimeZoneModeAnnotation() { + return new DependentTimeZoneMode() { + @Override + public Class annotationType() { + return DependentTimeZoneMode.class; + } + }; + } + } \ No newline at end of file diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDates.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDates.java index b9e1a2c7245..a6412dd0c26 100644 --- a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDates.java +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/sample/domain/TgEntityWithTimeZoneDates.java @@ -4,6 +4,7 @@ import ua.com.fielden.platform.entity.AbstractPersistentEntity; import ua.com.fielden.platform.entity.annotation.CompanionObject; +import ua.com.fielden.platform.entity.annotation.DependentTimeZoneMode; import ua.com.fielden.platform.entity.annotation.IsProperty; import ua.com.fielden.platform.entity.annotation.KeyTitle; import ua.com.fielden.platform.entity.annotation.KeyType; @@ -41,6 +42,22 @@ public class TgEntityWithTimeZoneDates extends AbstractPersistentEntity @AfterChange(UtcDatesToLocalDefiner.class) private Date datePropUtc; + @IsProperty + @MapTo + @Title("Date Prop Dependent") + @DependentTimeZoneMode + private Date datePropDependent; + + @Observable + public TgEntityWithTimeZoneDates setDatePropDependent(final Date datePropDependent) { + this.datePropDependent = datePropDependent; + return this; + } + + public Date getDatePropDependent() { + return datePropDependent; + } + @Observable public TgEntityWithTimeZoneDates setDatePropUtc(final Date datePropUtc) { this.datePropUtc = datePropUtc; diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/DefaultValueContract.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/DefaultValueContract.java index edb5be8b8b1..2bbe8c7d794 100644 --- a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/DefaultValueContract.java +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/DefaultValueContract.java @@ -1,19 +1,5 @@ package ua.com.fielden.platform.serialisation.jackson; -import static java.lang.Boolean.FALSE; -import static java.util.Optional.empty; -import static java.util.Optional.of; -import static ua.com.fielden.platform.entity.annotation.IsProperty.DEFAULT_DISPLAY_AS; -import static ua.com.fielden.platform.entity.annotation.IsProperty.DEFAULT_LENGTH; -import static ua.com.fielden.platform.entity.annotation.IsProperty.DEFAULT_PRECISION; -import static ua.com.fielden.platform.entity.annotation.IsProperty.DEFAULT_SCALE; -import static ua.com.fielden.platform.entity.annotation.IsProperty.DEFAULT_TRAILING_ZEROS; -import static ua.com.fielden.platform.reflection.TitlesDescsGetter.getDefaultEntityTitleAndDesc; -import static ua.com.fielden.platform.types.tuples.T2.t2; -import static ua.com.fielden.platform.utils.EntityUtils.equalsEx; - -import java.util.Optional; - import ua.com.fielden.platform.entity.AbstractEntity; import ua.com.fielden.platform.entity.annotation.DateOnly; import ua.com.fielden.platform.entity.annotation.PersistentType; @@ -26,15 +12,24 @@ import ua.com.fielden.platform.types.markers.IUtcDateTimeType; import ua.com.fielden.platform.types.tuples.T2; -/** - * A set of utilities to determine if the value of some property or meta-info is default. It is used internally for Jackson entity serialiser to significantly reduce the amount of - * the information to be serialised. - * - * @author TG Team - * - */ +import java.util.Optional; + +import static java.lang.Boolean.FALSE; +import static java.util.Optional.empty; +import static java.util.Optional.of; +import static ua.com.fielden.platform.entity.annotation.IsProperty.*; +import static ua.com.fielden.platform.reflection.AnnotationReflector.isPropertyAnnotationPresent; +import static ua.com.fielden.platform.reflection.TitlesDescsGetter.getDefaultEntityTitleAndDesc; +import static ua.com.fielden.platform.types.tuples.T2.t2; +import static ua.com.fielden.platform.utils.EntityUtils.equalsEx; + +/// A set of utilities to determine if the value of some property or meta-info is default. +/// It is used internally for Jackson entity serialiser to significantly reduce the amount of the information to be serialised. +/// public class DefaultValueContract { private static final String UTC = "UTC"; + public static final String DATE_ONLY = "DATE"; + public static final String TIME_ONLY = "TIME"; private DefaultValueContract() { } @@ -134,18 +129,14 @@ public static boolean isUtc(final Class entityType, final String propertyName return UTC.equals(getTimeZone(entityType, propertyName)); } - /** - * Returns the value that indicates what portion of date property to display. - * - * @param entityType - * @param propertyName - * @return - */ + /// Returns the value that indicates which portion of date property to display. + /// public static String getTimePortionToDisplay(final Class entityType, final String propertyName) { - if (AnnotationReflector.isPropertyAnnotationPresent(DateOnly.class, entityType, propertyName)) { - return "DATE"; - } else if (AnnotationReflector.isPropertyAnnotationPresent(TimeOnly.class, entityType, propertyName)) { - return "TIME"; + if (isPropertyAnnotationPresent(DateOnly.class, entityType, propertyName)) { + return DATE_ONLY; + } + else if (isPropertyAnnotationPresent(TimeOnly.class, entityType, propertyName)) { + return TIME_ONLY; } return null; } diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntitySerialiser.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntitySerialiser.java index bc8ea007c92..c785258a104 100644 --- a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntitySerialiser.java +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntitySerialiser.java @@ -199,12 +199,16 @@ private static > EntityType createEntityTypeInfo(fin if (!isIgnoreDefault(ignore)) { entityTypeProp.set_ignore(ignore); } - if (isPropertyAnnotationPresent(DateOnly.class, type, name)) { + final var timePortion = getTimePortionToDisplay(type, name); + if (DATE_ONLY.equals(timePortion)) { entityTypeProp.set_date(TRUE); } - if (isPropertyAnnotationPresent(TimeOnly.class, type, name)) { + else if (TIME_ONLY.equals(timePortion)) { entityTypeProp.set_time(TRUE); } + if (isPropertyAnnotationPresent(DependentTimeZoneMode.class, type, name)) { + entityTypeProp.set_dependentTimeZoneMode(TRUE); + } final IsProperty isPropertyAnnotation = AnnotationReflector.getPropertyAnnotation(IsProperty.class, type, name); if (isPropertyAnnotation != null) { final Long length = Long.valueOf(isPropertyAnnotation.length()); diff --git a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntityTypeProp.java b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntityTypeProp.java index 9e882f50900..74f9dbf5c33 100644 --- a/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntityTypeProp.java +++ b/platform-pojo-bl/src/main/java/ua/com/fielden/platform/serialisation/jackson/EntityTypeProp.java @@ -58,6 +58,10 @@ public class EntityTypeProp extends AbstractEntity { @Title(value = "TimeZone", desc = "TimeZone of date-typed property.") private String _timeZone; + @IsProperty + @Title(value = "Dependent Time-zone Mode", desc = "Dependent Time-zone Mode of date-typed property.") + private Boolean _dependentTimeZoneMode; + @IsProperty @Title(value = "Is Date Only?", desc = "Should display only date portion?") private Boolean _date; @@ -156,6 +160,16 @@ public Boolean get_date() { return _date; } + @Observable + public EntityTypeProp set_dependentTimeZoneMode(final Boolean _dependentTimeZoneMode) { + this._dependentTimeZoneMode = _dependentTimeZoneMode; + return this; + } + + public Boolean get_dependentTimeZoneMode() { + return _dependentTimeZoneMode; + } + @Observable public EntityTypeProp set_timeZone(final String _timeZone) { this._timeZone = _timeZone; diff --git a/platform-web-resources/src/main/java/ua/com/fielden/platform/web/test/server/config/TgEntityWithTimeZoneDatesWebUiConfig.java b/platform-web-resources/src/main/java/ua/com/fielden/platform/web/test/server/config/TgEntityWithTimeZoneDatesWebUiConfig.java index f1815034424..b9b5b249fbe 100644 --- a/platform-web-resources/src/main/java/ua/com/fielden/platform/web/test/server/config/TgEntityWithTimeZoneDatesWebUiConfig.java +++ b/platform-web-resources/src/main/java/ua/com/fielden/platform/web/test/server/config/TgEntityWithTimeZoneDatesWebUiConfig.java @@ -68,7 +68,8 @@ private EntityCentre createCentre(final Injector inje .withSummary("total_count_", "COUNT(SELF)", "Count:The total number of matching TgEntityWithTimeZoneDates.") .withAction(standardEditAction).also() .addProp("dateProp").minWidth(100).also() - .addProp("datePropUtc").minWidth(100) + .addProp("datePropUtc").minWidth(100).also() + .addProp("datePropDependent").minWidth(100) .addPrimaryAction(standardEditAction) .build(); @@ -76,11 +77,12 @@ private EntityCentre createCentre(final Injector inje return entityCentre; } private EntityMaster createMaster(final Injector injector) { - final String layout = LayoutComposer.mkGridForMaster(640, 1, 2); + final String layout = LayoutComposer.mkGridForMaster(960, 1, 3); final IMaster masterConfig = new SimpleMasterBuilder().forEntity(TgEntityWithTimeZoneDates.class) .addProp("dateProp").asDateTimePicker().also() .addProp("datePropUtc").asDateTimePicker().also() + .addProp("datePropDependent").asDateTimePicker().also() .addAction(MasterActions.REFRESH).shortDesc("Cancel").longDesc("Cancel action") .addAction(MasterActions.SAVE) .setActionBarLayoutFor(Device.DESKTOP, Optional.empty(), LayoutComposer.mkActionLayoutForMaster()) diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateCriterionWidget.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateCriterionWidget.java index 3e0bdb6174c..d7caad20f26 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateCriterionWidget.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateCriterionWidget.java @@ -1,41 +1,29 @@ package ua.com.fielden.platform.web.centre.api.crit.impl; -import java.util.Map; - import ua.com.fielden.platform.entity.AbstractEntity; -import ua.com.fielden.platform.serialisation.jackson.DefaultValueContract; import ua.com.fielden.platform.web.view.master.api.widgets.datetimepicker.impl.DateTimePickerWidget; -/** - * An implementation for date double-editor criterion. - * - * @author TG Team - * - */ +import java.util.Map; + +/// An implementation for date double-editor criterion. +/// public class DateCriterionWidget extends AbstractRangeCriterionWidget { - /** - * Creates an instance of {@link DateCriterionWidget} for specified entity type and property name. - * - * @param criteriaType - * @param propertyName - */ + /// Creates an instance of [DateCriterionWidget] for specified entity type and property name. + /// public DateCriterionWidget(final Class> root, final Class managedType, final String propertyName) { super(root, "centre/criterion/multi/range/tg-date-range-criterion", propertyName, - new DateTimePickerWidget( - AbstractCriterionWidget.generateTitleDesc(root, managedType, propertyName).getKey(), - AbstractCriterionWidget.generateNames(root, managedType, propertyName).getKey(), - false, - DefaultValueContract.getTimeZone(managedType, propertyName), - DefaultValueContract.getTimePortionToDisplay(managedType, propertyName) - ), - new DateTimePickerWidget( - AbstractCriterionWidget.generateTitleDesc(root, managedType, propertyName).getValue(), - AbstractCriterionWidget.generateNames(root, managedType, propertyName).getValue(), - true, - DefaultValueContract.getTimeZone(managedType, propertyName), - DefaultValueContract.getTimePortionToDisplay(managedType, propertyName) - )); + new DateTimePickerWidget( + generateTitleDesc(root, managedType, propertyName).getKey(), + generateNames(root, managedType, propertyName).getKey(), + false + ), + new DateTimePickerWidget( + generateTitleDesc(root, managedType, propertyName).getValue(), + generateNames(root, managedType, propertyName).getValue(), + true + ) + ); } @Override diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateSingleCriterionWidget.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateSingleCriterionWidget.java index 7a88e0a974d..30c62fe4892 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateSingleCriterionWidget.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/crit/impl/DateSingleCriterionWidget.java @@ -1,31 +1,19 @@ package ua.com.fielden.platform.web.centre.api.crit.impl; import ua.com.fielden.platform.entity.AbstractEntity; -import ua.com.fielden.platform.serialisation.jackson.DefaultValueContract; import ua.com.fielden.platform.web.view.master.api.widgets.datetimepicker.impl.DateTimePickerWidget; -/** - * An implementation for date single-editor criterion. - * - * @author TG Team - * - */ +/// An implementation for date single-editor criterion. +/// public class DateSingleCriterionWidget extends AbstractSingleCriterionWidget { - /** - * Creates an instance of {@link DateSingleCriterionWidget} for specified entity type and property name. - * - * @param criteriaType - * @param propertyName - */ + /// Creates an instance of [DateSingleCriterionWidget] for specified entity type and property name. + /// public DateSingleCriterionWidget(final Class> root, final Class managedType, final String propertyName) { - super(root, propertyName, - new DateTimePickerWidget( - AbstractCriterionWidget.generateSingleTitleDesc(root, managedType, propertyName), - AbstractCriterionWidget.generateSingleName(root, managedType, propertyName), - false, - DefaultValueContract.getTimeZone(managedType, propertyName), - DefaultValueContract.getTimePortionToDisplay(managedType, propertyName) - )); + super(root, propertyName, new DateTimePickerWidget( + generateSingleTitleDesc(root, managedType, propertyName), + generateSingleName(root, managedType, propertyName), + false + )); } } diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/impl/ResultSetBuilder.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/impl/ResultSetBuilder.java index f46e88c4f37..2a3641afc4c 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/impl/ResultSetBuilder.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/centre/api/impl/ResultSetBuilder.java @@ -7,7 +7,6 @@ import ua.com.fielden.platform.entity.fetch.IFetchProvider; import ua.com.fielden.platform.reflection.PropertyTypeDeterminator; import ua.com.fielden.platform.reflection.TitlesDescsGetter; -import ua.com.fielden.platform.serialisation.jackson.DefaultValueContract; import ua.com.fielden.platform.types.Colour; import ua.com.fielden.platform.types.Hyperlink; import ua.com.fielden.platform.types.Money; @@ -161,9 +160,7 @@ private Optional createWidget(final String propName) { } else if (isBoolean(propertyType)) { return of(new CheckboxWidget(pair("", TitlesDescsGetter.getTitleAndDesc(propName, root).getValue()), propName)); } else if (isDate(propertyType)) { - return of(new DateTimePickerWidget(pair("", TitlesDescsGetter.getTitleAndDesc(propName, root).getValue()), propName, false, - DefaultValueContract.getTimeZone(root, propName), - DefaultValueContract.getTimePortionToDisplay(root, propName))); + return of(new DateTimePickerWidget(pair("", TitlesDescsGetter.getTitleAndDesc(propName, root).getValue()), propName, false)); } else if (isCollectional(propertyType)) { return of(new CollectionalRepresentorWidget(pair("", TitlesDescsGetter.getTitleAndDesc(propName, root).getValue()),propName)); } diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/helpers/impl/WidgetSelector.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/helpers/impl/WidgetSelector.java index 8044b2caa04..d17450a0057 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/helpers/impl/WidgetSelector.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/helpers/impl/WidgetSelector.java @@ -5,8 +5,6 @@ import ua.com.fielden.platform.entity.annotation.DateOnly; import ua.com.fielden.platform.entity.annotation.TimeOnly; import ua.com.fielden.platform.reflection.PropertyTypeDeterminator; -import ua.com.fielden.platform.reflection.TitlesDescsGetter; -import ua.com.fielden.platform.serialisation.jackson.DefaultValueContract; import ua.com.fielden.platform.web.view.master.api.helpers.IWidgetSelector; import ua.com.fielden.platform.web.view.master.api.impl.SimpleMasterBuilder; import ua.com.fielden.platform.web.view.master.api.widgets.*; @@ -29,7 +27,8 @@ import java.util.Optional; import static java.lang.String.format; -import static ua.com.fielden.platform.serialisation.jackson.DefaultValueContract.getTimePortionToDisplay; +import static ua.com.fielden.platform.reflection.TitlesDescsGetter.getTitleAndDesc; +import static ua.com.fielden.platform.serialisation.jackson.DefaultValueContract.*; public class WidgetSelector> implements IWidgetSelector { @@ -79,15 +78,15 @@ public static > EntityAutocompletionWidget createAut final var declaredPropType = StringUtils.isEmpty(propertyName) ? entityType : PropertyTypeDeterminator.determinePropertyType(entityType, propertyName); return optPropType.map(propType -> { if (String.class.isAssignableFrom(declaredPropType)) { - return new EntityAutocompletionWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, entityType), propertyName, propType, true); + return new EntityAutocompletionWidget(getTitleAndDesc(propertyName, entityType), propertyName, propType, true); } else if (propType.equals(declaredPropType)) { - return new EntityAutocompletionWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, entityType), propertyName, propType, false); + return new EntityAutocompletionWidget(getTitleAndDesc(propertyName, entityType), propertyName, propType, false); } else { throw new EntityMasterConfigurationException(format(ERR_INVALID_AUTOCOMPLETER_TYPE, propType.getTypeName(), entityType.getSimpleName(), propertyName, declaredPropType.getTypeName())); } }).orElseGet(() -> { if (AbstractEntity.class.isAssignableFrom(declaredPropType)) { - return new EntityAutocompletionWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, entityType), propertyName, (Class>) declaredPropType, false); + return new EntityAutocompletionWidget(getTitleAndDesc(propertyName, entityType), propertyName, (Class>) declaredPropType, false); } else { throw new EntityMasterConfigurationException(format(ERR_INVALID_PROPERTY_FOR_AUTOCOMPLETION, entityType.getSimpleName(), propertyName, declaredPropType.getTypeName())); } @@ -96,31 +95,31 @@ public static > EntityAutocompletionWidget createAut @Override public ISinglelineTextConfig asSinglelineText() { - widget = new SinglelineTextWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new SinglelineTextWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new SinglelineTextConfig<>((SinglelineTextWidget) widget, smBuilder); } @Override public ICollectionalRepresentorConfig asCollectionalRepresentor() { - widget = new CollectionalRepresentorWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new CollectionalRepresentorWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new CollectionalRepresentorConfig<>((CollectionalRepresentorWidget) widget, smBuilder); } @Override public ICollectionalEditorConfig asCollectionalEditor() { - widget = new CollectionalEditorWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new CollectionalEditorWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new CollectionalEditorConfig<>((CollectionalEditorWidget) widget, smBuilder); } @Override public IMultilineTextConfig asMultilineText() { - widget = new MultilineTextWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), smBuilder.getEntityType(), propertyName); + widget = new MultilineTextWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), smBuilder.getEntityType(), propertyName); return new MultilineTextConfig<>((MultilineTextWidget) widget, smBuilder); } @Override public IRichTextConfig asRichText() { - widget = new RichTextWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), smBuilder.getEntityType(), propertyName); + widget = new RichTextWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), smBuilder.getEntityType(), propertyName); return new RichTextConfig<>((RichTextWidget)widget, smBuilder); } @@ -138,13 +137,7 @@ public IFileConfig asFile() { public IDateTimePickerConfig asDateTimePicker() { final String timePortion = getTimePortionToDisplay(smBuilder.getEntityType(), propertyName); if (timePortion == null) { - widget = new DateTimePickerWidget( - TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), - propertyName, - false, - DefaultValueContract.getTimeZone(smBuilder.getEntityType(), propertyName), - null - ); + widget = new DateTimePickerWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName, false); return new DateTimePickerConfig<>((DateTimePickerWidget) widget, smBuilder); } throw new EntityMasterConfigurationException(format(ERR_INVALID_DATEPICKER_CHOICE, @@ -153,15 +146,8 @@ public IDateTimePickerConfig asDateTimePicker() { @Override public IDatePickerConfig asDatePicker() { - final String DATE_ONLY = "DATE"; if (DATE_ONLY.equals(getTimePortionToDisplay(smBuilder.getEntityType(), propertyName))) { - widget = new DateTimePickerWidget( - TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), - propertyName, - false, - DefaultValueContract.getTimeZone(smBuilder.getEntityType(), propertyName), - DATE_ONLY - ); + widget = new DateTimePickerWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName, false); return new DatePickerConfig<>((DateTimePickerWidget) widget, smBuilder); } throw new EntityMasterConfigurationException(format(ERR_INVALID_DATEPICKER_CHOICE, propertyName, smBuilder.getEntityType().getSimpleName(), DateOnly.class.getSimpleName())); @@ -169,15 +155,8 @@ public IDatePickerConfig asDatePicker() { @Override public ITimePickerConfig asTimePicker() { - final String TIME_ONLY = "TIME"; if (TIME_ONLY.equals(getTimePortionToDisplay(smBuilder.getEntityType(), propertyName))) { - widget = new DateTimePickerWidget( - TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), - propertyName, - false, - DefaultValueContract.getTimeZone(smBuilder.getEntityType(), propertyName), - TIME_ONLY - ); + widget = new DateTimePickerWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName, false); return new TimePickerConfig<>((DateTimePickerWidget) widget, smBuilder); } throw new EntityMasterConfigurationException(format(ERR_INVALID_DATEPICKER_CHOICE, propertyName, smBuilder.getEntityType().getSimpleName(), TimeOnly.class.getSimpleName())); @@ -185,13 +164,13 @@ public ITimePickerConfig asTimePicker() { @Override public IDecimalConfig asDecimal() { - widget = new DecimalWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new DecimalWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new DecimalConfig<>((DecimalWidget) widget, smBuilder); } @Override public ISpinnerConfig asSpinner() { - widget = new SpinnerWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new SpinnerWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new SpinnerConfig<>((SpinnerWidget) widget, smBuilder); } @@ -202,13 +181,13 @@ public ISpinnerConfig asInteger() { @Override public IMoneyConfig asMoney() { - widget = new MoneyWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new MoneyWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new MoneyConfig<>((MoneyWidget) widget, smBuilder); } @Override public ICheckboxConfig asCheckbox() { - widget = new CheckboxWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new CheckboxWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new CheckboxConfig<>((CheckboxWidget) widget, smBuilder); } @@ -224,13 +203,13 @@ public IEmailConfig asEmail() { @Override public IColourConfig asColour() { - widget = new ColourWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new ColourWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new ColourConfig<>((ColourWidget) widget, smBuilder); } @Override public IHyperlinkConfig asHyperlink() { - widget = new HyperlinkWidget(TitlesDescsGetter.getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); + widget = new HyperlinkWidget(getTitleAndDesc(propertyName, smBuilder.getEntityType()), propertyName); return new HyperlinkConfig<>((HyperlinkWidget) widget, smBuilder); } diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/widgets/datetimepicker/impl/DateTimePickerWidget.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/widgets/datetimepicker/impl/DateTimePickerWidget.java index b4c405a9912..12122a2770c 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/widgets/datetimepicker/impl/DateTimePickerWidget.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/api/widgets/datetimepicker/impl/DateTimePickerWidget.java @@ -1,44 +1,26 @@ package ua.com.fielden.platform.web.view.master.api.widgets.datetimepicker.impl; -import java.util.Map; - import ua.com.fielden.platform.utils.Pair; import ua.com.fielden.platform.web.view.master.api.widgets.impl.AbstractWidget; -/** - * The implementation for web date-time picker widgets. - * - * @author TG Team - * - */ +import java.util.Map; + +/// The implementation for Web UI date-time picker widgets. +/// public class DateTimePickerWidget extends AbstractWidget { private final boolean timePortionToBecomeEndOfDay; - private final String timeZone; - private final String datePortion; - /** - * Creates an instance of {@link DateTimePickerWidget} for specified entity type and property name. - * - * @param titleDesc - * @param propertyName - */ - public DateTimePickerWidget(final Pair titleDesc, final String propertyName, final boolean timePortionToBecomeEndOfDay, final String timeZone, final String datePortion) { + /// Creates an instance of [DateTimePickerWidget] for specified entity type and property name. + /// + public DateTimePickerWidget(final Pair titleDesc, final String propertyName, final boolean timePortionToBecomeEndOfDay) { super("editors/tg-datetime-picker", titleDesc, propertyName); this.timePortionToBecomeEndOfDay = timePortionToBecomeEndOfDay; - this.timeZone = timeZone; - this.datePortion = datePortion; } @Override protected Map createCustomAttributes() { final Map customAttr = super.createCustomAttributes(); customAttr.put("time-portion-to-become-end-of-day", timePortionToBecomeEndOfDay); - if (timeZone != null) { - customAttr.put("time-zone", timeZone); - } - if (datePortion != null) { - customAttr.put("date-portion", datePortion); - } return customAttr; } diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/chart/decker/api/impl/ChartDeckerMaster.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/chart/decker/api/impl/ChartDeckerMaster.java index ca901e70895..c58a9b5e03c 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/chart/decker/api/impl/ChartDeckerMaster.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/chart/decker/api/impl/ChartDeckerMaster.java @@ -21,11 +21,8 @@ import java.util.function.Function; import java.util.stream.Stream; -import static java.util.Optional.ofNullable; import static org.apache.commons.lang3.StringUtils.isEmpty; import static org.apache.commons.lang3.StringUtils.join; -import static ua.com.fielden.platform.serialisation.jackson.DefaultValueContract.getTimePortionToDisplay; -import static ua.com.fielden.platform.serialisation.jackson.DefaultValueContract.getTimeZone; import static ua.com.fielden.platform.web.centre.EntityCentre.IMPORTS; import static ua.com.fielden.platform.web.centre.api.resultset.impl.FunctionalActionKind.PRIMARY_RESULT_SET; import static ua.com.fielden.platform.web.view.master.EntityMaster.ENTITY_TYPE; @@ -119,9 +116,9 @@ private String readyCallback(final IChartDeckerConfig deckerConfig) { + " },\n" + " lines: " + generateListOfValues(deck.getLines(), l -> generateLine(l)) + ",\n" + " dataPropertyNames: {\n" - + " groupKeyProp: " + generateValueAccessor(deck.getEntityType(), deck.getPropertyType(), deck.getGroupKeyProp()) + ",\n" + + " groupKeyProp: " + generateValueAccessor(deck.getPropertyType(), deck.getGroupKeyProp()) + ",\n" + " groupDescProp: '" + deck.getGroupDescProperty() + "',\n" - + " valueProps: " + generateListOfValues(deck.getSeries(), s -> generateValueAccessor(s.getEntityType(), s.getPropertyType(), s.getPropertyName())) + "\n" + + " valueProps: " + generateListOfValues(deck.getSeries(), s -> generateValueAccessor(s.getPropertyType(), s.getPropertyName())) + "\n" + " },\n" + " colours: " + generateListOfValues(deck.getSeries(), s -> "'" + s.getColour().getColourValue() + "'") + ",\n" + " barColour: (d, i) => self.barOptions[" + deckIndex + "].colours[i],\n" @@ -129,8 +126,8 @@ private String readyCallback(final IChartDeckerConfig deckerConfig) { + " propertyTypes: " + generateListOfValues(deck.getSeries(), s -> "'" + s.getPropertyType().getSimpleName() + "'") + ",\n" + " barLabel: (d, i) => this._labelFormatter(d, i, self.barOptions[" + deckIndex + "].propertyNames, self.barOptions[" + deckIndex + "].propertyTypes, self.barOptions[" + deckIndex + "].mode),\n" + " tooltip: (d, i) => this._tooltip(d, " - + generateValueAccessor(deck.getEntityType(), deck.getPropertyType(), deck.getGroupKeyProp()) + ", " - + generateValueAccessor(deck.getEntityType(), String.class, deck.getGroupDescProperty()) + ", " + + generateValueAccessor(deck.getPropertyType(), deck.getGroupKeyProp()) + ", " + + generateValueAccessor(String.class, deck.getGroupDescProperty()) + ", " + "self.barOptions[" + deckIndex + "].propertyNames[i], " + "self.barOptions[" + deckIndex + "].propertyTypes[i], " + "self.legendItems[" + deckIndex + "][i].title, " + deckIndex + ", i),\n" @@ -147,7 +144,7 @@ private String generateLineLegendItem(final ChartLine line) { } private String generateLine(final ChartLine line) { - return "{property: " + generateValueAccessor(line.getEntityType(), line.getPropertyType(), line.getProperty()) + ", title: '" + line.getTitle() + "', colour: '" + line.getColour().getColourValue() + "'}"; + return "{property: " + generateValueAccessor(line.getPropertyType(), line.getProperty()) + ", title: '" + line.getTitle() + "', colour: '" + line.getColour().getColourValue() + "'}"; } private String generateListOfValues(final List series, final Function func) { @@ -167,14 +164,11 @@ private String generateLegendItem(final ChartSeries series) { return "{title: '" + (isEmpty(series.getTitle()) ? "" : series.getTitle()) + "', colour: '" + series.getColour().getColourValue() + "'}"; } - private String generateValueAccessor(final Class deckType, final Class propertyType, final String aggregationProperty) { + private String generateValueAccessor(final Class propertyType, final String aggregationProperty) { if (Money.class.isAssignableFrom(propertyType)) { return "this._moneyPropAccessor('" + aggregationProperty + "')"; } else if (EntityUtils.isDate(propertyType)) { - final Optional timeZone = ofNullable(getTimeZone(deckType, aggregationProperty)); - final Optional timePortion = ofNullable(getTimePortionToDisplay(deckType, aggregationProperty)); - final String typeSpec = "Date:" + timeZone.orElse(":") + timePortion.orElse(""); - return "this._datePropAccessor('" + aggregationProperty + "', '" + typeSpec + "')"; + return "this._datePropAccessor('" + aggregationProperty + "')"; } return "'" + aggregationProperty + "'"; } diff --git a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/scatterplot/api/implementation/ScatterPlotMaster.java b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/scatterplot/api/implementation/ScatterPlotMaster.java index b928407155f..5ab5730d51b 100644 --- a/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/scatterplot/api/implementation/ScatterPlotMaster.java +++ b/platform-web-ui/src/main/java/ua/com/fielden/platform/web/view/master/scatterplot/api/implementation/ScatterPlotMaster.java @@ -24,9 +24,8 @@ import static java.util.Optional.*; import static org.apache.commons.lang3.StringUtils.isEmpty; import static org.apache.commons.lang3.StringUtils.join; -import static ua.com.fielden.platform.reflection.TitlesDescsGetter.*; -import static ua.com.fielden.platform.serialisation.jackson.DefaultValueContract.getTimePortionToDisplay; -import static ua.com.fielden.platform.serialisation.jackson.DefaultValueContract.getTimeZone; +import static ua.com.fielden.platform.reflection.TitlesDescsGetter.getEntityTitleAndDesc; +import static ua.com.fielden.platform.reflection.TitlesDescsGetter.getTitleAndDesc; import static ua.com.fielden.platform.web.centre.EntityCentre.IMPORTS; import static ua.com.fielden.platform.web.centre.api.resultset.impl.FunctionalActionKind.PRIMARY_RESULT_SET; import static ua.com.fielden.platform.web.view.master.EntityMaster.ENTITY_TYPE; @@ -154,10 +153,7 @@ private String generateValueAccessor(Class> entityTy if (Money.class.isAssignableFrom(propertyType)) { return "this._moneyPropAccessor('" + propertyName + "')"; } else if (EntityUtils.isDate(propertyType)) { - final Optional timeZone = ofNullable(getTimeZone(entityType, propertyName)); - final Optional timePortion = ofNullable(getTimePortionToDisplay(entityType, propertyName)); - final String typeSpec = "Date:" + timeZone.orElse(":") + timePortion.orElse(""); - return "this._datePropAccessor('" + propertyName + "', '" + typeSpec + "')"; + return "this._datePropAccessor('" + propertyName + "')"; } return "'" + propertyName + "'"; } diff --git a/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/chart-decker/tg-chart-decker-template-behavior.js b/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/chart-decker/tg-chart-decker-template-behavior.js index dca048d2317..c930075ab11 100644 --- a/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/chart-decker/tg-chart-decker-template-behavior.js +++ b/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/chart-decker/tg-chart-decker-template-behavior.js @@ -2,7 +2,6 @@ import { TgAppConfig } from '/app/tg-app-config.js'; import { TgEntityMasterTemplateBehavior} from '/resources/master/tg-entity-master-template-behavior.js'; import { tearDownEvent } from '/resources/reflection/tg-polymer-utils.js'; -import {_momentTz, _millisDateRepresentation} from '/resources/reflection/tg-date-utils.js'; const generateActionTooltip = function (action) { const shortDesc = "" + action.shortDesc + ""; @@ -75,13 +74,12 @@ const TgChartDeckerTemplateBehaviorImpl = { tearDownEvent(event); }, - _datePropAccessor: function (propertyName, dateType) { - return function (entity, value) { + _datePropAccessor: function (propertyName) { + return (entity, value) => { if (!value) { - const splitedType = dateType.split(':'); - return _millisDateRepresentation(entity.get(propertyName), splitedType[1] || null, splitedType[2] || null); + return this._reflector().tg_toString(entity.get(propertyName), entity.type(), propertyName, { display: true }); } - } + }; }, _moneyPropAccessor: function (propertyName) { diff --git a/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/tg-calendar.js b/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/tg-calendar.js index 4ed3f4fce02..06a74b1317d 100644 --- a/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/tg-calendar.js +++ b/platform-web-ui/src/main/web/ua/com/fielden/platform/web/components/tg-calendar.js @@ -13,8 +13,8 @@ import '/resources/components/tg-month-selector.js'; import {Polymer} from '/resources/polymer/@polymer/polymer/lib/legacy/polymer-fn.js'; import {html} from '/resources/polymer/@polymer/polymer/lib/utils/html-tag.js'; -import moment from '/resources/polymer/lib/moment-lib.js'; // used for moment.localeData(). ... -import {_momentTz} from '/resources/reflection/tg-date-utils.js'; +import moment from '/resources/polymer/lib/moment-lib.js'; // used for moment.localeData() and moment.monthsShort(). +import { _momentTz } from '/resources/reflection/tg-date-utils.js'; const template = html`