On Sat, June 11, 2011 11:34, Jeremy Sanders wrote:
> Benjamin K. Stuhl wrote:
>
>> Longer term, having a more intelligent update model would be valuable for
>> multiple reasons. I've had occasion recently to ask Veusz to plot several
>> hundred thousand points, and while it can do so, it's still pretty slow,
>> at least with antialiasing turned on. One way to speed things up a lot
>> would be to change the rendering system so that each widget is its own
>> layer, which is only updated on demand, and then the drawing code simply
>> composites the layers together. Right now, changing an axis label also
>> prompts a redraw of every curve; caching layers would circumvent this.
>> This might not be _too_ hard to implement naively: each widget redraws its
>> layer whenever it settings are changed, while the plotwindow give the
>> widgets new layers whenever the zoom is changed. Of course, decent export
>> still wants all the drawing to happen directly, rather than through a
>> series of composited layers. (Though that in turn has the problem that my
>> printer choked on the ~30 MB of postscript that the print driver produced,
>> so...)
>
> Seems a good goal. Each widget would need to know its dependencies much
> better to know when to be updated. Maybe it would be possible to do
> rendering in multiple threads if Qt allows it, and the widgets were
> independent.

I've got a branch that I think implements this at 
https://github.com/bks/veusz/tree/layered-widgets
The idea is that by improving the change-tracking of the document datasets and
each widget's settings, it should now be possible to know when a cached layer
is out-of-date. Take a look. I've opened all the example documents with the 
branch
and I'm using it for real work, so it's not critically broken -- but I did
have to change most of the Operations to not directly write to document.data,
so there's definitely room for breakage.

The next step is to actually generate cached images and composite them together,
but that needs some design thought: which component is responsible for 
maintaining
the rendering hierarchy? Is it the PlotWindow, since that's the only component
that actually wants cached images rather than a full redraw? Does each widget
composite itself? Or does each parent widget composite its children? (And
can we use the cached rendering tree to eliminate the special Painters that
the PlotWindow currently uses?)

> I've thought about whether it is possible to offload rendering to a non-UI
> thread. For the rendering thread to get a consistent view, we'd need to
> either "snapshot" the document before rendering (maybe some sort of clever
> copy on write scheme could be used for modifications), copy the document
> before rendering (probably slow), or batch modifications until rendering has
> finished (difficult to keep the UI showing the latest version).

One other possibility is to have each widget render to a QPicture in the UI 
thread
and then offload the QPicture-to-QImage rendering (which is probably the 
expensive
part, especially if antialiasing is turned on) to a background thread. The 
PlotWindow
would just recomposite whenever it got a new layer from the background thread;
each rendering request should probably be tagged with the widget's changeset
number so that the rendering thread can throw out already-out-of-date requests.

> A quick hack we could do currently, is for xy widgets to turn off
> antialiasing for themselves when plotting to the screen with over N points.

-- BKS

_______________________________________________
Veusz-discuss mailing list
[email protected]
https://mail.gna.org/listinfo/veusz-discuss

Répondre à