Thanks for the example. In general when we have this kind of thing we have done
exactly what you describe--a raw element to parse the data and an inputValueCalc
element calculate the value.
This type of non-base-10 scaling isn't too uncommon, so I could imagine one
option would be to replace dfdl:binaryDecimalVirtualPoint with a more generic
scale property. E.g.
<xs:element name="SomeElement" type="xs:decimal"
dfdl:binaryDecimalScale="1.40625" ... />
And parse/unparse would just scale the value automatically.
I think it's also not uncommon for formats that have a scale to also have an
offset. So if we wanted to generalize a bit more we could add a
dfdl:binaryDecimalOffset="..." property. Then the value put in the infoset would
be modified by:
parseValue * binaryDecimalScale + binaryDecimalOffset
And unparse would reverse this.
It makes things a bit more generic and is probably sufficient for most formats.
Though I'm not sure how many formats really need this. The raw/inputValueCalc
approach is probably what we recommend for this, it does at a bit of messiness,
but is very flexible.
Note that we used to have something call typeValueCalc, which let you define a
"representation type" and then apply arbitrary expressions to adjust that to
create a "logical value". For example
<xs:simpleType name="uint8" type="xs:unsignedInt"
dfdl:lengthKind="explicit" dfdl:length="8" dfdl:lenghtUnits="bits" />
<xs:element name="degrees" type="xs:float"
dfdlx:repType="uint8"
dfdlx:inputTypeCalc="{ dfdlx:repTypeValue() * 1.40625 }"
dfdlx:outputTypeCalc="{ dfdlx:logicalTypeValue() div 1.40625 }"
/>
So to get the degrees value we first parse it as a uint8, then evaluate the
inputTypeCalc expression to convert the raw value to a logical float. And on
unparse we evaluate outputTypeCalc to convert the float back to a uint8 for
unparsing.
However, we ended up removing this feature due to it not really being used and
adding extra complexity. We still support repType, but only support converting
that to one of a list of enumeration values. We could maybe consider bringing
this back, or maybe something that acheives a similar result.
On 2025-10-18 08:18 AM, Sean Callahan wrote:
Good Afternoon Steve,
I appreciate the quick response. If I were dealing with powers of 10, the
solution you suggest would be perfect, but unfortunately, I’m not that
lucky. Instead, we have scores of fixed-point types with deltas such as 360
degrees encoded in 8 bits (i.e. 360/(2^8). To define such a type, we use
the technique below:
<schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:dfdl="
http://www.ogf.org/dfdl/dfdl-1.0/">
<simpleType name="SomeElementType">
<restriction base="xs:float">
<minInclusive value="0.0"/>
<maxInclusive value="358.59375"/>
</restriction>
</simpleType>
<complexType name="SomeComplexType">
<sequence>
<group dfdl:hiddenGroupRef="HiddenSomeComplexTypeSomeElementGroup"/>
<element name="SomeElement" type="SomeElementType">
<annotation>
<appinfo source="http:www.ogf.org/dfdl/">
<dfdl:element inputValueCalc="{xs:float(../RawValue * 1.40625)}"/>
</appinfo>
</annotation>
</element>
</sequence>
</complexType>
<group name="HiddenSomeComplexTypeSomeElementGroup">
<sequence>
<element name="RawValue" type="xs:unsignedInt">
<annotation>
<appinfo source="http:www.ogf.org/dfdl/">
<dfdl:element length="8" lengthKind="explicit" lengthUnits="bits"
outputValueCalc="{xs:unsignedInt(../SomeElement div 1.40625)}"/>
</appinfo>
</annotation>
</element>
</sequence>
</group>
</schema>
It would be ideal to reduce this to something similar to:
<schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:dfdl="
http://www.ogf.org/dfdl/dfdl-1.0/">
<simpleType name="SomeElementType">
<restriction base="xs:float">
<minInclusive value="0.0"/>
<maxInclusive value="358.59375"/>
</restriction>
</simpleType>
<complexType name="SomeComplexType">
<sequence>
<sequence dfdlx:layer="FixedPointLayer"
dfdl:newVariableInstance ref="fixed_point_layer:delta"
defaultValue="1.40625">
<element name="SomeElement" type="SomeElementType"/>
</sequence>
</sequence>
</complexType>
</schema>
Thanks,
Sean
From: *Steve Lawrence* <*[email protected] <[email protected]>*>
Date: Thu, Oct 16, 2025 at 1:45 PM
Subject: RE: Fixed-Point Layer
To: <*[email protected] <[email protected]>*>
CC: Sean Callahan <*[email protected] <[email protected]>*>
Are you able to use dfdl:binaryDecimalVirtualPoint? For example:
<element name="cost" type="xs:decimal"
dfdl:representation="binary"
dfdl:binaryNumberRep="binary"
dfdl:byteOrder="bigEndian"
dfdl:lengthKind="explicit"
dfdl:length="4"
dfdl:lengthUnits="bytes"
dfdl:binaryDecimalVirtualPoint="2" />
This parses a 4-byte binary integer that represents a cost in cents. The
binaryDecimalVirtualPoint="2" then shifts the decimal to the left by 2 so
the
value in the infoset becomes dollars and cents. For example, 12345 becomes
123.45
If you're looking for something different, can you give an example?
(I've CC'd you directly since you're not subscribed to the list. You may
want to
join to see any follow-up discussion.)
On 2025/10/16 11:24:13 Sean Callahan wrote:
Good Morning Folks,
If it hasn’t already been suggested, a fixed-point (vs floating-point)
layer would be an excellent addition to the distribution. Currently, the
only alternative is hidden groups, which isn’t intuitive and quickly
clutters a schema.
Thanks,
Sean Callahan