GSoC Progress: Replacing Slideshow Metafile Rendering with Primitives

Shardul Vikram Singh shardulvikrm at gmail.com
Mon Jun 9 20:12:08 UTC 2025


Hi all,

I wanted to share an update on the progress of my GSoC project - reworking
the Impress slideshow rendering that currently uses GDIMetafiles with a
primitive-based rendering approach.

The existing system takes drawinglayer primitives, converts them into a
metafile, and then renders that using the XCanvas interface. XCanvas itself
is abstract and gets wrapped inside cppcanvas, with cairocanvas (on Linux)
handling the actual rendering. Essentially, we’re converting from
primitives -> metafile -> XCanvas -> screen.

Initially, I planned to write a new primitive renderer that directly
targets the XCanvas interface. But after discussions with my mentor, we
decided to try stripping out the hacks - removing the detour through
metafiles and cppcanvas - and instead aim for rendering primitives directly
to screen. Since drawinglayer already has several pixel processors (like
CairoPixelProcessor2D), this path looks promising.

Summary of Code Understanding -
Internal Structure of Shapes and Primitives

   - I investigated how DrawShape relates to shape metadata.
   - Shapes reference SvxShape, which internally maps to SdrObject.
   - SdrObject connects to ViewContact, which generates
   Primitive2DContainer through createViewIndependentPrimitive2DSequence().

Understanding SlideImpl::loadShapes()

   - I traced through SlideImpl::loadShapes() (called from
   implPrefetchShow) to see how shapes get imported.
   - There are two ShapeImporter functors (master‐page vs. normal page).
   Both push XShapesEntry objects onto maShapesStack.

Figured Out Where Metafiles Are Generated

   - The DrawShape gets its metafile using UnoGraphicExporter.
   - Under the hood, a primitives-to-metafile renderer is used to generate
   metafiles.

Tracing the Rendering Pipeline

   - SlideImpl::show() triggers the rendering.
   - The rendering path calls slideRenderer(), which in turn calls
   SlideImpl::getCurrentSlideBitmap(), and if necessary,
   createCurrentSlideBitmap().
   - During bitmap creation, shapes are rendered to a BitmapCanvas that
   shares its underlying Cairo surface with the SpriteCanvas (verified via GDB
   inspection).
   - LayerManager::renderTo(...) iterates over all DrawShape instances,
   temporarily attaches a DummyLayer for each, and calls
   pShape->addViewLayer(...), which uses the metafile renderer to render onto
   the target bitmap canvas.

Exploring Animation & Sprites

   - I backtraced ActivityImpl::ActivityImpl, used for text-based intrinsic
   animations.
   - I reviewed the animation frame updates via SlideShowImpl::update(),
   which repeatedly calls maActivitiesQueue.process().
   - Activities are implemented as subclasses like SimpleActivity, which
   execute frame updates via animation functors (e.g., PathAnimation) that
   manipulate shape properties over time.
   - The final frame rendering goes through LayerManager::update() and
   ViewShape::update().


Since the current code depends a lot on XCanvas, I’ll proceed iteratively -
removing the extra layers and moving toward rendering primitives directly
to the screen.
That’s it for now. I’ll continue posting updates as the work progresses.
Best,
Shardul
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.freedesktop.org/archives/libreoffice/attachments/20250610/a4cc4cb4/attachment.htm>


More information about the LibreOffice mailing list