wxMaxima
Loading...
Searching...
No Matches
Data Structures | Public Member Functions
WorksheetLayout Class Reference

The layout/recalculation engine of a worksheet. More...

#include <WorksheetLayout.h>

Data Structures

struct  ScrollAnchor
 The point of the worksheet the cursor sits at, for ArmScrollCompensation(). More...
 

Public Member Functions

 WorksheetLayout (Configuration *config, WorksheetView &view, std::function< GroupCell *()> getTree, std::function< GroupCell *()> getLastCell)
 Construct the engine.
 
 WorksheetLayout (const WorksheetLayout &)=delete
 
WorksheetLayout & operator= (const WorksheetLayout &)=delete
 
void RequestRecalculation (Cell *start)
 Schedule a recalculation of the worksheet starting with the cell start.
 
void RequestFullRecalculation ()
 Schedule a recalculation of the whole worksheet.
 
bool RecalculateIfNeeded (bool timeout=false, long timeSliceMs=50)
 Perform the scheduled recalculation, if one is pending.
 
void AdjustSize ()
 Adjust the virtual size and scrollbars to the document's extent.
 
void GetMaxPoint (int *width, int *height)
 Get the coordinates of the bottom right point of the worksheet.
 
void UpdateConfigurationClientSize ()
 Inform the configuration about the view's current client size.
 
int GroupCellWidthWithMargins (int cellWidth) const
 The horizontal space a group cell of the given width occupies.
 
int GetScrollUnit () const
 The scroll granularity (device px per scroll unit) AdjustSize() last applied.
 
void RequestAdjustSize ()
 Flag the virtual (scroll) size as needing re-adjustment.
 
void CancelPendingRecalculation ()
 Drop any pending recalculation (e.g. when the document is cleared).
 
void SetScrollAnchorCallback (std::function< ScrollAnchor()> callback)
 Tells the engine where the cursor currently is.
 
void ArmScrollCompensation ()
 Keep the cursor still on screen across the next layout pass.
 
bool ScrollCompensationArmed () const
 Is a scroll compensation waiting for the next layout pass to finish?
 
int GetLastCellsVisited () const
 GroupCells walked by the most recent RecalculateIfNeeded() pass (visited includes cheap reposition-only cells; recalculated counts only the cells that actually needed the expensive re-layout). Exposed for tests and diagnostics: a localized change should recalculate very few cells, so a large count on a small edit signals an over-broad recalculation.
 
int GetLastCellsRecalculated () const
 

Detailed Description

The layout/recalculation engine of a worksheet.

Talks to the cell tree via the callbacks handed to the constructor, to the window via a WorksheetView and to the Configuration for metrics and the canvas size. Worksheet holds one instance and forwards its layout entry points here; the headless unit test drives an instance without any window.

Constructor & Destructor Documentation

◆ WorksheetLayout()

WorksheetLayout::WorksheetLayout ( Configuration *  config,
WorksheetView &  view,
std::function< GroupCell *()>  getTree,
std::function< GroupCell *()>  getLastCell 
)

Construct the engine.

Parameters
configThe Configuration supplying metrics, the canvas size and the recalculation drawing context.
viewThe window surface (real Worksheet or a test mock). Held by reference: must outlive this object.
getTreeReturns the first GroupCell of the worksheet (or null).
getLastCellReturns the last GroupCell of the worksheet (or null).

Member Function Documentation

◆ AdjustSize()

void WorksheetLayout::AdjustSize ( )

Adjust the virtual size and scrollbars to the document's extent.

Defers (via RequestAdjustSize()) while a recalculation is still pending, since the cell positions it reads would be stale - see the implementation comment for the full story.

◆ ArmScrollCompensation()

void WorksheetLayout::ArmScrollCompensation ( )

Keep the cursor still on screen across the next layout pass.

Called just before output is appended to a cell: the cells below it are about to move down, the cursor with them if it sits below the changed cell. This remembers where the cursor's cell is now; once the pass has laid everything out, the view is scrolled by however far that cell moved - to the pixel, see ComputeScrollCompensation() - so the cursor, and everything around it, stays where the user was looking.

Only ever arms once per pass: a second append before the pass has run would measure positions that aren't on screen yet. The caller is expected to only arm if the cursor is visible - scrolling to keep an invisible point still would move the part of the worksheet the user actually is looking at.

◆ GetMaxPoint()

void WorksheetLayout::GetMaxPoint ( int *  width,
int *  height 
)

Get the coordinates of the bottom right point of the worksheet.

Only valid once no recalculation is pending; asserts on that.

◆ GetScrollUnit()

int WorksheetLayout::GetScrollUnit ( ) const
inline

The scroll granularity (device px per scroll unit) AdjustSize() last applied.

Worksheet's scroll handlers read it to convert scroll positions to pixels.

◆ GroupCellWidthWithMargins()

int WorksheetLayout::GroupCellWidthWithMargins ( int  cellWidth) const

The horizontal space a group cell of the given width occupies.

That is the cell's own width plus the equal left and right margins the worksheet reserves around every group cell. Used both when measuring the document width (GetMaxPoint) and while walking the recalculation.

◆ RecalculateIfNeeded()

bool WorksheetLayout::RecalculateIfNeeded ( bool  timeout = false,
long  timeSliceMs = 50 
)

Perform the scheduled recalculation, if one is pending.

One walk from the scheduled start point drives both modes: with timeout set the pass is time-sliced (yields after timeSliceMs, resuming on the next call); otherwise the whole scheduled range is laid out in one go. Ends by adjusting the virtual size once the cell positions are valid.

Returns
true if any layout work was done or remains pending.

◆ RequestAdjustSize()

void WorksheetLayout::RequestAdjustSize ( )
inline

Flag the virtual (scroll) size as needing re-adjustment.

Set when a cell changed height (via the callback Worksheet registers on the Configuration, so cells can flag it without depending on the view) or when layout is scheduled; consumed by RecalculateIfNeeded(), which calls AdjustSize() once the cell positions are valid.

◆ RequestFullRecalculation()

void WorksheetLayout::RequestFullRecalculation ( )

Schedule a recalculation of the whole worksheet.

For changes that potentially dirty cells at arbitrary positions (zoom, font or configuration changes, window resizes): the dirty range becomes "the first cell to the end of the document", so the next layout pass may not stop early. An operation that changes one known cell should call RequestRecalculation(cell) instead.

◆ RequestRecalculation()

void WorksheetLayout::RequestRecalculation ( Cell *  start)

Schedule a recalculation of the worksheet starting with the cell start.

This only records where the next layout pass has to start (it marks the group dirty and extends the pending dirty range [m_recalculateStart, m_recalculateEnd]); it does not size or position any cell. The actual work - and, crucially, AdjustSize() once the cell positions are correct - happens in RecalculateIfNeeded(). Calling AdjustSize() (or otherwise reading cell geometry) right after this, without a RecalculateIfNeeded() in between, reads stale positions.

◆ SetScrollAnchorCallback()

void WorksheetLayout::SetScrollAnchorCallback ( std::function< ScrollAnchor()>  callback)
inline

Tells the engine where the cursor currently is.

Queried by ArmScrollCompensation() and again once the layout pass has run, so a compensation is dropped if the cursor moved in between: the point to keep still is then a different one. Worksheet sets this; without it (the headless tests) no compensation is ever armed.


The documentation for this class was generated from the following files: