<?xml version="1.0"?>
<?XML-stylesheet href="layout.css" type="text/css"?>
<!DOCTYPE Documentation>

<Documentation xmlns:html="http://www.w3.org/TR/REC-HTML40">

<Title>Gecko Layout Engine</Title>
<Author xml:link="simple" show="new" href="mailto:troy@netscape.com">Troy Chevalier</Author>
<UpdateDate>8 August 1999</UpdateDate>

<SectionHeading>Overview</SectionHeading>
<Body>Gecko is Mozilla's new layout engine. It is based on the HTML4, CSS1, XML 1.0,
and DOM Internet standards, and it is built using a modular XPCOM-based
architecture.</Body>

<Body>When we talk about layout, we're referring to the formatting process that applies
presentation styles to a source document. The formatting process is controlled
by the style specification.</Body>

<SectionHeading>Components</SectionHeading>
<Body>Here are a list of components and terms that will be referenced by this document.</Body>

<Components>
<Term>Parser</Term>
<Definition>Either the <A xml:link="simple" show="replace" href="http://www.mozilla.org/newlayout/doc/parser.html">HTML</A>
or XML parser. Processes the document and makes calls to the content sink.</Definition>

<Term>Content sink</Term>
<Definition>Called by the parser. Responsible for building the content model.</Definition>

<Term><A xml:link="simple" show="replace" href="http://www.mozilla.org/newlayout/doc/contentmodel.html">Content model</A></Term>
<Definition>Consists of document object and a tree of content objects. Changes to the
content model result in modifications of the frame model.</Definition>

<Term>Frame model</Term>
<Definition><A xml:link="simple" show="replace" href="#Frames">Frames</A> are formatting
objects. Each frame defines a particular set of formatting characteristics.</Definition>

<Term><A xml:link="simple" show="replace" href="#Reflow">Reflow</A></Term>
<Definition>The formatting process. Reflow of the frame model defines the visual appearance
of the formatted document.</Definition>

<Term><A xml:link="simple" show="replace" href="#FrameConstruction">Frame construction</A></Term>
<Definition>Initial creation and updating of the frame model in response to changes to the
content model and changes to the style data.</Definition>

<Term><A xml:link="simple" show="replace" href="http://www.mozilla.org/newlayout/doc/style.html">Style system</A></Term>
<Definition>Provide the mapping and management of style data onto document content in a given
presentation. Major components are style set, style sheets, style sheet and
rules, style context, and style sheet loader.</Definition>

<Term>Presentation shell</Term>
<Definition>Controlling point for managing the presentation of a document.</Definition>

<Term><A xml:link="simple" show="replace" href="http://www.mozilla.org/newlayout/doc/viewsystem.html">View system</A></Term>
<Definition>Consists of a view manager and view objects arranged in a tree hierarchy.
Views support overlapped positioning, z-order sorting, and opacity levels.</Definition>
</Components>

<SectionHeading>Document Loading</SectionHeading>
<Body>The basic flow of control is as follows: as the parser encounters tokens it notifies
the content sink that a new node (or child node) is encountered. The content sink
creates the appropriate type content object and inserts it into the content model.</Body>

<Body>Whenever the content model changes the document's observers are notified. The presentation
shell is one of the document observers. The presentation shell forwards the document
change notification to the style set object</Body>

<Body>The style set passes the notification to the frame construction code, the
frame construction code creates new frames and inserts them into the frame model. The
document is reflowed, and the formatted changes are displayed.
</Body>

<Body>
The actual interfaces involved are:
<Interfaces>
<Interface>nsIDocument</Interface>
<Interface>nsIDocumentObserver</Interface>
<Interface>nsIPresShell</Interface>
<Interface>nsIStyleSet</Interface>
<Interface>nsIStyleFrameConstruction</Interface>
<Interface>nsIFrame</Interface>
</Interfaces>
</Body>

<Body>All of the interface files are located in the mozilla/layout/base/public
directory.</Body>

<SectionHeading>Object Lifetimes</SectionHeading>
<Body>Gecko supports multiple views of the same document. This means you can print the
same document that you're viewing on the screen, and there's only one content
model. Because there's just a single content model, each of the content objects
is referenced counted. The document holds a reference to the root content object,
and each content node holds a reference to its child content nodes.</Body>

<Body>Each view of the document has a separate presentation shell, style manager,
style set, and frame hierarchy. The presentation shell is the controlling point for
the presentation of a document, and it holds a reference to the document object.</Body>

<Body>Frames and views are not referenced counted. The lifetime of the frame hierarchy
is bounded by the lifetime of the presentation shell which owns the frames. The
lifetime of the view hierarchy is bounded by the lifetime of the view manager
that owns the views.</Body>

<SectionHeading><html:a name="Frames">Frames</html:a></SectionHeading>
<Body>Each frame defines a particular set of formatting characteristics. Frames have
the opportunity to:
<Characteristics>
<Characteristic>reflow (format) their child frames</Characteristic>
<Characteristic>render their appearance</Characteristic>
<Characteristic>handle mouse and keyboard events</Characteristic>
<Characteristic>display a cursor</Characteristic>
<Characteristic>have an associated view object</Characteristic>
</Characteristics>
</Body>

<Body>Frames can have multiple child lists, the default unnamed child list
(referred to as the principal child list) and additional named child lists.
There is an ordering of frames within a child list, but no ordering
between frames in different child lists of the same parent frame.</Body>

<Body>The principal child list contains the flowed children, and the additional
child lists are for out-of-flow frames like floated elements and absolutely
positioned elements.</Body>

<Body>Child frames are linked together in a singly linked list. Each frame
defines its own local coordinate space. Frame bounding rects are in twips,
and the origin is relative to the upper-left corner of its parent frame.
The bounding rect includes the content area, borders, and padding.</Body>

<SectionHeading><html:a name="FrameConstruction">Frame Construction</html:a></SectionHeading>
<Body>The frame construction process begins with a notification that content
has been added or removed or that style has changed.</Body>

<Body>The first step is to resolve style information for the content element.
This process creates a style context that is stored in the frame (see
nsIStyleContext).</Body>

<Body>Once style is resolved construction rules are used to decide the type of
frame to create. First we look at the element's tag and special case some
things like IMG elements. If we don't create a frame that way, then we use
the 'display' property to dictate what type of frame to create. Typically
it's a block or inline frame.</Body>

<Body>For a 'display' value of 'none' no frame is created. For elements that are
out of the flow (for example, a floated element or an absolutely positioned
element), a placeholder frame is also created. The placeholder frame is inserted
into the flow exactly where the out-of-flow frame would have been inserted.
The out-of-flow frame is then inserted as a child of its containing block in
one of the additional child lists. Floated frames are inserted into the
"Floater-list" and absolutely positioned frames are inserted into the
"Absolute-list".</Body>

<SectionHeading>Frame Manager</SectionHeading>
<Body>The frame manager is owned by the presentation shell and used by both the
presentation shell and the frame construction code. It serves two main
purposes:
<Purposes>
<Purpose>provides a service for mapping from content object to frame and from out-of-flow
frame to placeholder frame</Purpose>
<Purpose>coordinates structural modifications to the frame model</Purpose>
</Purposes>
</Body>

<Body>In many places in the frame code we need to find the frame associated with
a particular content object. In order to quickly implement this operation we
maintain a mapping from content objects to frames. The frame construction adds
and removes entries from the map as frames are created and destroyed.</Body>

<Body>When creating new frames and removing existing frames, the frame construction
code doesn't directly modify the frame hierarchy. Instead if informs the frame
manager and has it coordinate the request. If the frame model lock is available,
the change is processed immediately; otherwise, the request is queued and
processed later.</Body>

<Body>The frame manager also coordinates processing of replaced elements that can't
be rendered (for example, an IMG or OBJECT element), and it allows client to
register to be notified when a particular frame is being destroyed. This is
needed because frames are not reference counted. It's used by the event manager
and other clients to ensure that any outstanding references to the frame are
cleaned up.</Body>

<SectionHeading><html:a name="Reflow">Reflow</html:a> Process</SectionHeading>
<Note>The fact that are two reflow interfaces reflects an early
goal of having core layout and HTML specific layout. The core reflow process would
be the same for all frames, and each class of formatting objects (for
example, CSS and DSSSL) would have their own reflow additions.</Note>

<Body>The reflow process is a top-down protocol where a frame is given some
available space and asked to reflow its child frames and return a desired
size.</Body>

<Body>The reflow process is not part of the nsIFrame interface. The generic reflow
interface is defined in the nsIFrameReflow interface, and the HTML/CSS specific
reflow interface is defined in the nsIHTMLReflow interface.</Body>

<Body>An important part of the reflow process is the calculation of the computed
values for the CSS properties. This includes things like 'width', 'height',
and 'margin', and involves calculation of the containing block width and height
and percentage based values and properties whose value is inherited.</Body>

<Body>This process is encapsulated in the HTML specific reflow state struct
(struct nsHTMLReflowState) that is passed in as part of reflow. The reflow
states are linked together with the reflow state for a child frame pointing
to its parent frame's reflow state. This allows us to walk up the reflow state
structures and calculate containing block width and height and percentage
based values.</Body>

<Body>In addition to the computed values for the CSS box model properties, the
following items are also included:
<Items>
<Item>reflow reason that indicates why the frame is being reflowed</Item>
<Item>a rendering context that can be used to measure text</Item>
<Item>reflow command (only used for incremental reflow)</Item>
<Item>space manager</Item>
</Items>
</Body>

<Body>The most common reflow reasons are 'eReflowReason_Resize' (the viewport
has changed size) and 'eReflowReason_Incremental' (processing of an incremental
reflow command).</Body>

<Body>Reflow commands (see nsIReflowCommand in mozilla/layout/base/public) are used
to kick off an incremental reflow. They're generated either by the style system
(in response to a style change) or by a frame itself (for example, if a frame has
dirty child frames that need to be reflowed it will generate a reflow command).</Body>

<Body>Reflow commands are queued by the presentation shell and then dispatched. Reflow
commands have a target frame, which is the frame for which the reflow command
is destined. In the example above the target frame is the frame with dirty child
frames that need to be reflowed. Reflow command processing follows a path from
the root frame down to the target frame.</Body>

<Body>The space manager (see nsISpaceManager in mozilla/layout/base/public) is used
when flowing text around floated elements. It has an API for managing bands of
unavailable space (space that is reserved for a floated element). Internally it
organizes the band data similar to how a region data structure works.</Body>

<SectionHeading>Frame Classes</SectionHeading>
<Body>There are four main categories of frame classes, all of which are located
in mozilla/layout/html/src:

<Categories>
<Category>core frame classes</Category>
<Category>table frame classes</Category>
<Category>form frame classes</Category>
<Category>frameset frame classes</Category>
</Categories>
</Body>

<Body><RunIn>The core frame classes</RunIn> implement the CSS viewport abstraction, scrolling,
block and inline display of flowed elements, floaters, and absolute positioning.</Body>

<Body>For more information on block layout, click 
<A xml:link="simple" show="replace" href="block.html">here</A>. For more information about
line layout, click <A xml:link="simple" show="replace" href="line-layout.html">here</A>.</Body>

<Body><RunIn>The table frame classes</RunIn> correspond to the HTML4 table spec, and in addition
to the table frame there are row group frames, row frames, column group frames,
column frames, and cell frames. There is an "outer" table frame as well that's
really an anonymous frame that contains the caption frame and the table frame
itself.</Body>

<Body>Table layout is determined in a 3-step process. In the first step, the table
is flowed into an infinitely wide and tall space. This gives us the minimum and
desired sizes for every cell in the table. In the second step, the table constraints
are factored in and widths are assigned to every cell. In the third step, heights are
assigned to every cell based on the computed width constraint. The results of the first
step are cached and only need to be recomputed when content or constraints are changed.</Body>

<SectionHeading>Event Manager</SectionHeading>
<Body>To be written</Body>

</Documentation>
