On Nov 23, 2006, at 12:14, [EMAIL PROTECTED] wrote:
<snip />
An excellent idea. However, before I go any further with implementing
anything I'd like to make sure that I actually understand what's going
on at the moment and (more importantly) what should be going on.
As I understand it, objects in the fo tree describe the structure
of the
document and relate directly to the xsl:fo input.
100% correct. I myself am very much in favor of not having an
identity relationship between the FOTree and the source document, but
already perform some normalizing there (since there are possibly
different FO structures, yielding the exact same result), and thus
making the layoutengine's job a bit easier.
But OK, that's another story: your base assumption is correct.
All these objects descend from FONode and all have a number of
distinct properties which
relate in some way to the input document and which may or may not have
some bearing on the output (e.g. aural and accessibility properties
don't
have any impact whilst font and text properties do).
Also correct, and the set of properties for which each FO has members
corresponds to the properties that are mentioned as applicable to
that type of FO.
All the property
classes are supposed to be immutable even though some of them
aren't and
none of them use final members. Is this all correct so far?
True, and this could be much improved, I'd say...
What I'm less clear on is the use of PropertyList and PropertyMaker.
AFAIU, way back when, the situation was far worse than it is now:
Instead of having members for only the applicable properties
described in the XSL-FO Rec., each FONode used to have one
PropertyList as an instance member. PropertyLists however, require
space for *all* possible properties even if they don't directly apply
to the FONode (see the implementation of StaticPropertyList which
allocates space for two arrays with a number of elements equal to the
number of all properties; since about 70%, if not 85%, of those
elements will be null anyway, it's a big waste to keep those lists
alive much longer than is absolutely necessary).
This was changed, and the PropertyList should currently only be
available as a temporary window during FOTree building, only used for
converting the Attributes into Property objects. In FONode.bind()
these properties are transferred to the instance member slots. By the
time layout kicks in, ideally, there should be no PropertyLists alive
in the FOTree, with the exception of those lists for markers/retrieve-
markers (currently the latter also means keeping a reference to
parentPropertyLists, so the ideal is not yet reached).
WRT the last remark: possible solution would be to create a
PropertyList subtype that is able to collapse the tree of lists --
dump all available properties into its own instance member arrays--
and sever the link to the parentPropertyList.
Some properties such as KeepProperty or EnumProperty have makers
as static inner classes.
That's the general idea. As far as I get the picture, external Makers
are used when there is no compelling reason to create a whole new
Property subclass (see FontSizePropertyMaker: there is no
FontSizeProperty, since the LengthProperty infrastructure suffices
for the rest)
Don't know if you've already taken a look at
org.apache.fop.fo.FOPropertyMapping. Very helpful class to see how
the properties map to the Maker-types.
Some properties such as SpaceProperty have both
an inner static class and an external maker class.
That's a bit of an exception. The external Maker descends from
CorrespondingPropertyMaker, and seems to be used only for computing
the space-* properties from the corresponding margin-* properties.
The internal Maker descends from CompoundPropertyMaker and is
responsible for creating the space-* properties themselves (from
scratch).
Some properties such
as PercentLength don't seem to have any makers at all. Why?
Good question. Best explanation I can think of is that PercentLength
simply relies on LengthProperty.Maker. Apparently, there was no need
to override the Maker as well...
It occurs to me that the best strategy for handling these would be to
turn all Makers into singletons and use use them as flyweight
factories,
introducing a new factory for the Common* property classes. What do
you
think?
Seems like a fine idea. The Makers will then become responsible for
checking whether an identical Property was already instantiated
earlier, and create a new one only if there wasn't.
As for the Common* property classes, I guess it would then become
possible to replace all the currently unused bundles --such as for
the CommonAural properties, that would be identical for a very large
number of FOs-- with one instance, shared by the different FOs.
Would already make a neat difference, I think...
Cheers,
Andreas