X-Git-Url: https://git.lyx.org/gitweb/?a=blobdiff_plain;f=development%2FPAINTING_ANALYSIS;h=4934c5e1b6b10289c3511545fe3f58eaac3512f8;hb=78eaf8333bacec8d735eae06c0745163d06a5122;hp=08afa500ed7c84a59b7a73c24358438df52e0e08;hpb=c4da9b9e37848909a0f6be2053c5d49225c1a641;p=lyx.git diff --git a/development/PAINTING_ANALYSIS b/development/PAINTING_ANALYSIS index 08afa500ed..4934c5e1b6 100644 --- a/development/PAINTING_ANALYSIS +++ b/development/PAINTING_ANALYSIS @@ -33,38 +33,102 @@ is acted on. ** Buffer::change issues When calling Buffer::changed outside of bv::processUpdateFlags, -how do we now that the update strategy is set correctly? It is +how do we know that the update strategy is set correctly? It is possible to reset the strategy at the end of bv::draw. What would be a good value? NoScreenUpdate? On a related note, what is the semantics of a call to Buffer::changed(false)? What does the caller mean? -** What happens with FitCursor when the cursor is already OK? +** How to avoid redraw with FitCursor when the cursor is already OK? -In this case, we invoke Buffer::change(false) with drawing disabled, -which means that the paint machinery is invoked to update inset -positions. +In this case, we invoke Buffer::change(false) with drawing disabled +and NoScreenUpdate strategy. -Actually, this was added as part of the horizontal scrolling GSoC -work. We need to investigate how costly this is. +In the draw phase, bv::checkCursorScrollOffset (the horizontal +scrolling machinery) will change the strategy to FullScreenUpdate if +the current row needs further scrolling. + +When the update strategy it kept to NoScreenUpdate, there is currently +a no-draw full repaint, which should not be necessary. It would be +possible to avoid that if the call to checkCursorScrollOffset was done +in bv::processUpdateFlags instead of bv::draw. + +The global idea would be to extend FitCursor to cover also horizontal +cursor. * Proposals -** get rid of pm::insetDimension. +* Clean-up of drawing code + +The goal is to make painting with drawing disable fast enough that it +can be used after every metrics computation. Then we can separate real +drawing from metrics. + +** DONE RowPainter + +Inset position is set in paintInset, paintOnlyInsets, and paintText. +This should be done only once in paintInset + +** DONE TextMetrics::drawParagraph + +We can really simplify the code when drawing is disabled only +paintInset needs to be called. + + do right at the start when drawing is already disabled + + do it in the loop for rows that are not visible on screen. + +The only thing we want to do here is to set inset positions (for +text). The other insets still use the painter with drawing disabled. + +** Painter::text + +We cannot remove (or make private) the version that uses a +FontInfo because it is used by PainterInfo::draw. Document this and +remove unused arguments rtl and double spacing. This would become a specialized helper. +Proposed solution: keep the existing function, but private and without +optional arguments. -The information contained there is already in bv::coordCache. +Avoid to return (and thus compute) the width of strings? + + used by InsetSpecialChar (fixable) + + used by textDecoration() in text(): more difficult to fix -Effect: only code simplification. +Idea: add a version of text where wordspacing and textwidth (giving +the width of strings) are required parameters and remove optional +version. -** set inset position during metrics phase +==> more versions, no optional parameters. -This implies to set inset positions relative to outer isnet during -metrics phase and then in a second loop to descend into insets and -update positions correctly. +** Set inset position during metrics phase -Effect: avoid going through the painter machinery when it is not necessary. +In order to do that, a no-paint drawing will be initiated after every +redoParagraph. This code path will need to be made as fast as possible. + +Effect: avoid depending on actual drawing having taken place. In turn, +it will allow to do drawing on paint events, like any reasonable +application would do. + +** Cleanup after complete metrics + Then the following can be done: + + remove hack in InsetMathNest::drawSelection + + remove painting when not inside in drawParagraph + + remove Cursor::inCoordCache? + +** Use Row for MathData + +It may not be so difficult. Implement x2pos and pos2x from +the TM:cursorX and TM::getPosNearX, and use them for both text and +math. + +Will the strings display OK if drawing string-wise? + +Then it would be possible to streamline drawing with disabled painter. + +** Paint directly to screen + +Instead of using an intermediary pixmap. I have no idea of how +difficult it will prove. +One benefit will be that subpixel aliasing will work again (#9972) ** Merging bv::updateMetrics and tm::metrics @@ -73,26 +137,21 @@ paragraphs that are rebroken, the version that is used for inner inset does not try any such optimization. This can be very bad for very tall insets. We should re-use the bv::updateMetrics logic: + transfer all the logic of bv::updateMetrics to tm. - + Main InsetText should not be special. + + Main InsetText should not be special. -** Metrics outside of visible area +The difficuly for a tall table cell for example, is that it may be +necessary to break the whole contents to know the width of the cell. -Currently metrics are computed for current visible paet of text, the -page above and the page below. It should be possible to compute hidden -rows ony on demand, although it might be a bit slow. -There was a proposal to always compute _all_ rows, but this may become -expensive for large files. This would though help scrolling. +* Description of current drawing mechanism - -* Two phase drawing +** Two stage drawing There are two parts to drawing the work area: + the metrics phase computes the size of insets and breaks the paragraphs into rows. It stores the dimension of insets (both - normal and math) in bv::coordCache, and the size of normal - insets in pm::insetDimension. + normal and math) in bv::coordCache. + the drawing phase draws the contents and caches the inset positions. Since the caching of positions is useful in itself, @@ -100,7 +159,6 @@ There are two parts to drawing the work area: thing we want is to cache inset positions (Painter::setDrawingEnabled). - The machinery is controlled via bv::processUpdateFlags. This method is called at the end of bv::mouseEventDispatch and in GuiApplication::dispatch, via the updateCurrentView method. There are @@ -122,7 +180,7 @@ The screen is drawn (with appropriate update strategy), except when update flag is Update::None. -* Metrics computation +** Metrics computation This is triggered by bv::updateMetrics, which calls tm::redoParagraph for + all visible paragraphs @@ -137,7 +195,7 @@ of text insets, this will invoke recursively tm::metrics, which redoes all the paragraphs of the inset. -* Drawing the work area. +** Drawing the work area. This is done in bv::draw. This method is triggered mainly by Buffer::changed, which draws all the work areas that show the given buffer.