Given a TcxDateEdit (or DB-aware, or grid-column) with InputKind=ikMask:
Setting EditFormat from code instead of the designer gives the wrong type of EditMask - the generated one is a regular expression from TcxCustomDateEditProperties.BuildEditMask or thereabouts. Before the date is set (via the drop-down calendar), the text in the control is:
"([ 12]?[1- ]|[123] |31)'.'(( ?[1- ]|1[ 12])|('j n'|'feb'|'m r'|' pr'|'m i'|'jun'|'ju '|' ug'|'sep'|'okt'|'nov'|'des'))'.'dddd' '([ 1]?d|2[ -3]):[ -5]?d"
The control also behaves as if InputKind=ikRegExpr. Typing in the middle of the text will remove the trailing characters, instead of overwriting one character.
See the attached file for an example.
Other minor notes about TcxDateEditProperties:
-
UseDisplayFormatWhenEditing appears not to be honored. It isn't published, but it is documented, and can thus only be set from code. Perhaps it isn't meant to be used.
-
The property Nullstring has a lower-case "s", which looks out of place when seen next to UseNullString :)
Hello,
I have reproduced this behavior. We will examine it and get back to you once we have any results or need additional information. Thank you for your patience.
Do you mind if we make this report public, so that other customers can learn from it?
Posted by DataGrafikk:
The solution does not address the issue with InputKind=ikMask.
The change ensures that GetInputKind can never return ikMask when EditFormat is set, effectively removing ikMask support. (What use would a masked edit be without a means to set the format?)
If you open the sample project with the hotfix applied, the following change occurs:
Before opening:
object cxDateEdit1: TcxDateEdit
Left = 16
Top = 40
Properties.AutoSelect = False
Properties.EditFormat = 'dd.MM.yyyy hh:nn'
Properties.InputKind = ikMask
Properties.Kind = ckDateTime
TabOrder = 0
Width = 153
end
…
object cxDateEdit2: TcxDateEdit
Left = 16
Top = 104
Properties.AutoSelect = False
Properties.InputKind = ikMask
Properties.Kind = ckDateTime
TabOrder = 1
Width = 153
end
After opening:
object cxDateEdit1: TcxDateEdit
Left = 16
Top = 40
Properties.AutoSelect = False
Properties.EditFormat = 'dd.MM.yyyy hh:nn'
Properties.InputKind = ikRegExpr <-- InputKind changed by hotfix to ikRegExpr, because EditFormat is set.
Properties.Kind = ckDateTime
TabOrder = 0
Width = 153
end
…
object cxDateEdit2: TcxDateEdit
Left = 16
Top = 104
Properties.AutoSelect = False
Properties.InputKind = ikMask
Properties.Kind = ckDateTime
TabOrder = 1
Width = 153
end
If you compile and run the project, the text in the second dateedit is still the regex-generated editmask "([ 12]?[1- ]|[123] |31)'.'(( ?[1- ]|1[ 12])|('j n'|'feb'|'m r'|' pr'|'m i'|'jun'|'ju '|' ug'|'sep'|'okt'|'nov'|'des'))'.'dddd' '([ 1]?d|2[ -3]):[ -5]?d"
Hello,
I apologize for this inconvenience. It seems that you are right, the issue is incompletely fixed. I have forwarded this ticket to developers for further research.
Hello again,
Would you please try the following patch on your side:
cxCalendar: procedure TcxCustomDateEditProperties.BuildEditMask; begin LockUpdate(True); try if EditFormat = '' then case InputKind of ikMask: begin MaskKind := emkStandard; if Kind = ckDateTime then EditMask := cxFormatController.StandardDateTimeEditMask else EditMask := cxFormatController.StandardDateEditMask; end; ikRegExpr: begin MaskKind := emkRegExprEx; if Kind = ckDateTime then EditMask := cxFormatController.RegExprDateTimeEditMask else EditMask := cxFormatController.RegExprDateEditMask; end; else EditMask := ''; end else begin MaskKind := emkRegExprEx; EditMask := cxFormatController.RegExprCustomDateEditMask(EditFormat); end; finally LockUpdate(False); end; end; //.......... function TcxCustomDateEditProperties.GetInputKind: TcxInputKind; begin if not cxIsGregorianCalendar then Result := ikStandard else begin if AssignedValues.EditFormat and (Length(EditMask) > 0) then Result := ikRegExpr else begin if AssignedValues.InputKind then Result := FInputKind else Result := GetDefaultInputKind; end; end; end;
It should fix the issue.
Technically speaking, the "weird text in the control" bug is gone.
We are, however, still wondering if it is (or would be) possible to combine EditFormat with InputKind=ikMask, since the patch ensures that setting EditFormat will always change InputKind to ikRegExpr.
As a side effect, it is not possible to change ikMask when AssignedValues.EditFormat=True, which will probably be confusing.
The behaviour in the current cxDateEdit implementation is such that one can set DisplayFormat and EditFormat. EditMask is always automatically generated by the control, even when the property is set. Changing EditMask triggers DoChanged, which regenerates EditMask from EditFormat.
Ideally (for us), cxDateEdit with InputKind=ikMask would resemble cxMaskEdit with a drop-down calendar. This might be accomplished if BuildEditMask could be modified to generate an EditMask for the case where InputKind=ikMask, instead of forcing InputKind=ikRegExpr and making a RegExpr EditMask.
Hello,
This behavior (using ikRegExpr with EditFormat in any way) is designed specifics (limitation) of our Date editors. The problem was that the check on whether or not to apply ikRegExpr was incomplete.
May we suggest a change along the lines of the attached patch, which enables EditFormat support for InputKind=ikMask? It is a quite trivial change.
I am afraid that it is not acceptable. Not all formats can be implemented using standard masks, so we have to use regular expressions. Otherwise, complicated formats will not work.
Understandable.
Can you make the following four functions protected & virtual, so it is possible to subclass and override this? The GetInputKind change broke our earlier overridden functions.
TcxCustomDateEditProperties.BuildEditMask
TcxCustomDateEditProperties.GetInputKind
TcxCustomDateEditProperties.GetEmptyDisplayValue
TcxCustomDateEditProperties.GetTimeZoneInfo
I have created a separate ticket to implement this change with future releases (TcxCustomDateEditProperties - make the BuildEditMask, GetInputKind, GetEmptyDisplayValue, and GetTimeZoneInfo methods virtual ).