dbe2acc2b1
The create_context() and ensure_context() sections should be more clear on the role of the functions, and their eventual caveats, like being called multiple times.
176 lines
6.5 KiB
Plaintext
176 lines
6.5 KiB
Plaintext
IMPLEMENTING BACKENDS
|
|
=====================
|
|
|
|
Clutter supports multiple backends for handling windowing systems and
|
|
GL/GLES API on different platforms.
|
|
|
|
The GL and GLES API are abstracted by the COGL library. The windowing
|
|
system is handled by the ClutterBackend implementations inside Clutter
|
|
itself.
|
|
|
|
Clutter, at the moment, supports only in-tree backends.
|
|
|
|
In order to write a new backend for a specific platform you should
|
|
create a new sub-directory under clutter/clutter containing:
|
|
|
|
<backend>/clutter-backend-<backend>.h
|
|
<backend>/clutter-backend-<backend>.c
|
|
|
|
-- The subclass of the ClutterBackend abstract class.
|
|
|
|
<backend>/clutter-stage-<backend>.h
|
|
<backend>/clutter-stage-<backend>.c
|
|
|
|
-- The implementation of the stage actor.
|
|
|
|
<backend>/clutter-event-<backend>.c
|
|
|
|
-- The event handling code (optional).
|
|
|
|
<backend>/clutter-<backend>.h
|
|
|
|
-- A header for the backend-specific API that should be installed
|
|
by Clutter inside the include directory along with the rest of
|
|
the public API headers (optional).
|
|
|
|
|
|
Implementing ClutterBackend
|
|
---------------------------
|
|
|
|
Each backend must implement the
|
|
|
|
GType
|
|
_clutter_backend_impl_get_type (void);
|
|
|
|
function declared inside clutter/clutter-private.h. The implementation
|
|
of the function must return the same GType of the backend implementation,
|
|
for instance:
|
|
|
|
GType
|
|
_clutter_backend_impl_get_type (void)
|
|
{
|
|
return CLUTTER_TYPE_BACKEND_GLX;
|
|
}
|
|
|
|
The ClutterBackend implementation is a singleton instance, and the
|
|
backend must ensure that every time g_object_new() is called the same
|
|
pointer is returned (with its reference count increased). The GObject
|
|
API reference describes how to use the ::constructor virtual function
|
|
to implement a singleton, so you should refer to that.
|
|
|
|
The ClutterBackend implementation should hold a single drawing context
|
|
for its entire lifetime; stage implementations should be "made current"
|
|
when needed.
|
|
|
|
When implementing the ClutterBackend subclass these virtual functions
|
|
can be overridden:
|
|
|
|
ClutterBackend::add_options
|
|
-- Use this function to install new, backend-specific GOptionEntry
|
|
definitions to the Clutter GOptionGroup. This function is guaranteed
|
|
to be called just once.
|
|
|
|
ClutterBackend::pre_parse
|
|
-- Use this function to check for environment variables or setting
|
|
up default values before the command line arguments are parsed.
|
|
This function is guaranteed to be called just once.
|
|
|
|
ClutterBackend::post_parse
|
|
-- Use this function to prepare the backend with the values either
|
|
set inside the ::pre_parse virtual function or by the command
|
|
line options parsing code. This function is guaranteed to be
|
|
called just once.
|
|
|
|
ClutterBackend::init_events
|
|
-- Use this function to initialize the event handling. This function
|
|
is guaranteed to be called just once.
|
|
|
|
ClutterBackend::get_features
|
|
-- Use this function to retrieve the features detectable at runtime
|
|
from the GL or GLES implementation, plus the eventual backend-specific
|
|
features.
|
|
|
|
ClutterBackend::create_context
|
|
-- This function is used to create the drawing context to be used
|
|
by Clutter. Clutter will call this function during the initialization
|
|
phase. A GL (or GLES) context must always be available after the
|
|
initialization, so that Cogl and Clutter can query it for capabilities.
|
|
This function might be called multiple times so if a context was
|
|
successfully created in a previous call, this function should
|
|
short-circuit early and return TRUE
|
|
|
|
ClutterBackend::ensure_context
|
|
-- This function is used to ensure that the backend drawing context
|
|
is made current for passed ClutterStage, using the backend-specific
|
|
API. This function is called each time a new stage is going to
|
|
be painted. If the Stage is inside its destruction sequence this
|
|
function should either fall back the drawing context to a default
|
|
drawing surface or should unset the drawing surface from the
|
|
drawing context.
|
|
|
|
ClutterBackend::redraw
|
|
-- This function is used to draw the passed ClutterStage; the backend
|
|
must call clutter_actor_paint() on the ClutterStage that has been
|
|
passed as a parameter and then perform backend-specific tasks, like
|
|
waiting for vertical blanking and swapping the buffers.
|
|
|
|
ClutterBackend::create_stage
|
|
-- This function is used to create the stage implementation. It will
|
|
receive as an argument the ClutterStage instance that is "wrapping"
|
|
the actual implementation being created. The backend must create
|
|
its stage implementation, initialise it and then return it; in case
|
|
of error, the backend must return NULL and set the passed GError.
|
|
|
|
Implementing the stage
|
|
----------------------
|
|
|
|
ClutterStage acts as a wrapper object relaying all the drawing operations
|
|
to the actual implementation. The implementation of the stage can be any
|
|
GObject subclass, as long as it implements the ClutterStageWindow interface.
|
|
|
|
The ClutterStageWindow interface contains a set of virtual functions that
|
|
should be overridden by backends that support a windowing system, like
|
|
::set_title(), ::set_fullscreen(), ::set_cursor_visible(), etc.
|
|
|
|
The stage implementation actor must implement:
|
|
|
|
• ClutterStageWindow::get_wrapper()
|
|
• ClutterStageWindow::realize() and ::unrealize()
|
|
• ClutterStageWindow::show() and ::hide()
|
|
• ClutterStageWindow::resize()
|
|
• ClutterStageWindow::get_geometry()
|
|
|
|
The ::get_wrapper() implementation should return the pointer to the
|
|
ClutterStage actor using the ClutterStageWindow implementation.
|
|
|
|
In the ::realize virtual function the stage implementation should:
|
|
|
|
- create a new native window handle
|
|
- ensure that there is a GL (or GLES) context
|
|
- make sure that the native window handle is compatible with
|
|
the GL (or GLES) context
|
|
|
|
The return value should be TRUE if the stage implementation was successfully
|
|
realized, and FALSE otherwise.
|
|
|
|
Inside the ::unrealize function the stage implementation should destroy
|
|
the native window handle created in ::realize().
|
|
|
|
The ::resize() virtual function implementation should cause an update
|
|
of the COGL viewport.
|
|
|
|
The stage implementation actor can optionally implement:
|
|
|
|
• ClutterStageWindow::get_pending_swaps()
|
|
|
|
The get_pending_swaps() implementation should return the number of swap
|
|
buffer requests pending completion. This is only relevent for backends
|
|
that also support CLUTTER_FEATURE_SWAP_EVENTS.
|
|
|
|
NOTES
|
|
=====
|
|
|
|
If the platform is using X11 you should probably subclass ClutterBackendX11
|
|
and ClutterStageX11, which will provide you with a ready to use code
|
|
implementation for event handling and window management.
|