Merge branch '1.0-integration'
* 1.0-integration: (138 commits) [x11] Disable XInput by default [xinput] Invert the XI extension version check [cogl-primitives] Fix an unused variable warning when building GLES [clutter-stage-egl] Pass -1,-1 to clutter_stage_x11_fix_window_size Update the GLES backend to have the layer filters in the material [gles/cogl-shader] Add a missing semicolon [cogl] Move the texture filters to be a property of the material layer [text] Fix Pango unit to pixels conversion [actor] Force unrealization on destroy only for non-toplevels [x11] Rework map/unmap and resizing [xinput] Check for the XInput entry points [units] Validate units against the ParamSpec [actor] Add the ::allocation-changed signal [actor] Use flags to control allocations [units] Rework Units into logical distance value Remove a stray g_value_get_int() Remove usage of Units and macros [cogl-material] Allow setting a layer with an invalid texture handle [timeline] Remove the concept of frames from timelines [gles/cogl-shader] Fix parameter spec for cogl_shader_get_info_log ... Conflicts: configure.ac
This commit is contained in:
commit
805fb0620a
49
Makefile.am
49
Makefile.am
@ -1,3 +1,9 @@
|
||||
NULL =
|
||||
|
||||
V = @
|
||||
Q = $(V:1=)
|
||||
QUIET_GEN = $(Q:@=@echo ' GEN '$@;)
|
||||
|
||||
SUBDIRS = common $(CLUTTER_COGL)
|
||||
|
||||
BUILT_SOURCES = cogl.h
|
||||
@ -23,29 +29,42 @@ CLEANFILES = $(pc_files)
|
||||
|
||||
AM_CPPFLAGS = $(CLUTTER_CFLAGS) $(CLUTTER_DEBUG_CFLAGS) $(MAINTAINER_CFLAGS)
|
||||
|
||||
# COGL installed headers
|
||||
cogl_headers = \
|
||||
$(top_srcdir)/clutter/cogl/cogl-bitmap.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-color.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-debug.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-fixed.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-material.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-matrix.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-offscreen.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-path.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-shader.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-texture.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-types.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-vertex-buffer.h
|
||||
$(top_srcdir)/clutter/cogl/cogl-bitmap.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-color.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-debug.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-deprecated.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-fixed.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-material.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-matrix.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-offscreen.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-path.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-shader.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-texture.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-types.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-vertex-buffer.h \
|
||||
$(top_builddir)/clutter/cogl/cogl-defines-@CLUTTER_COGL@.h \
|
||||
$(top_builddir)/clutter/cogl/cogl-enum-types.h \
|
||||
$(top_builddir)/clutter/cogl/cogl.h \
|
||||
$(NULL)
|
||||
|
||||
# this is copied in from common/ to make cogl.h work, but we
|
||||
# need to clean it up ourselves once we're done
|
||||
DISTCLEANFILES = cogl-enum-types.h
|
||||
|
||||
# HACK - gobject-introspection can't scan a library in another directory
|
||||
# so we create a libclutter-cogl.la that's just identical to the one
|
||||
# in the subdir
|
||||
noinst_LTLIBRARIES = libclutter-cogl.la
|
||||
libclutter_cogl_la_LIBADD = $(CLUTTER_COGL)/libclutter-cogl.la
|
||||
libclutter_cogl_la_LIBADD = $(CLUTTER_COGL)/libclutter-cogl-$(CLUTTER_COGL).la
|
||||
libclutter_cogl_la_SOURCES = $(cogl_headers)
|
||||
|
||||
coglincludedir = $(includedir)/clutter-@CLUTTER_API_VERSION@/cogl
|
||||
coglinclude_HEADERS = $(cogl_headers)
|
||||
|
||||
if HAVE_INTROSPECTION
|
||||
Cogl-@CLUTTER_API_VERSION@.gir: $(INTROSPECTION_SCANNER) $(CLUTTER_COGL)/libclutter-cogl.la
|
||||
Cogl-@CLUTTER_API_VERSION@.gir: $(INTROSPECTION_SCANNER) libclutter-cogl.la
|
||||
$(QUIET_GEN)$(INTROSPECTION_SCANNER) -v \
|
||||
--namespace Cogl --nsversion=@CLUTTER_API_VERSION@ \
|
||||
-I$(top_srcdir)/clutter/cogl \
|
||||
@ -59,8 +78,6 @@ Cogl-@CLUTTER_API_VERSION@.gir: $(INTROSPECTION_SCANNER) $(CLUTTER_COGL)/libclut
|
||||
--libtool="$(top_builddir)/doltlibtool" \
|
||||
--pkg gobject-2.0 \
|
||||
--output $@ \
|
||||
$(top_builddir)/clutter/cogl/cogl-defines-@CLUTTER_COGL@.h \
|
||||
$(top_builddir)/clutter/cogl/cogl.h \
|
||||
$(cogl_headers)
|
||||
|
||||
BUILT_GIRSOURCES = Cogl-@CLUTTER_API_VERSION@.gir
|
||||
|
20
cogl-debug.h
20
cogl-debug.h
@ -29,15 +29,16 @@
|
||||
G_BEGIN_DECLS
|
||||
|
||||
typedef enum {
|
||||
COGL_DEBUG_MISC = 1 << 0,
|
||||
COGL_DEBUG_TEXTURE = 1 << 1,
|
||||
COGL_DEBUG_MATERIAL = 1 << 2,
|
||||
COGL_DEBUG_SHADER = 1 << 3,
|
||||
COGL_DEBUG_OFFSCREEN = 1 << 4,
|
||||
COGL_DEBUG_DRAW = 1 << 5,
|
||||
COGL_DEBUG_PANGO = 1 << 6,
|
||||
COGL_DEBUG_RECTANGLES = 1 << 7,
|
||||
COGL_DEBUG_HANDLE = 1 << 8
|
||||
COGL_DEBUG_MISC = 1 << 0,
|
||||
COGL_DEBUG_TEXTURE = 1 << 1,
|
||||
COGL_DEBUG_MATERIAL = 1 << 2,
|
||||
COGL_DEBUG_SHADER = 1 << 3,
|
||||
COGL_DEBUG_OFFSCREEN = 1 << 4,
|
||||
COGL_DEBUG_DRAW = 1 << 5,
|
||||
COGL_DEBUG_PANGO = 1 << 6,
|
||||
COGL_DEBUG_RECTANGLES = 1 << 7,
|
||||
COGL_DEBUG_HANDLE = 1 << 8,
|
||||
COGL_DEBUG_BLEND_STRINGS = 1 << 9
|
||||
} CoglDebugFlags;
|
||||
|
||||
#ifdef COGL_ENABLE_DEBUG
|
||||
@ -69,3 +70,4 @@ extern guint cogl_debug_flags;
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __COGL_DEBUG_H__ */
|
||||
|
||||
|
@ -23,6 +23,14 @@
|
||||
|
||||
#ifndef COGL_DEPRECATED_H
|
||||
|
||||
#define cogl_color cogl_color_REPLACED_BY_cogl_set_source_color
|
||||
#define cogl_color cogl_color_REPLACED_BY_cogl_set_source_color
|
||||
#define cogl_enable_depth_test cogl_enable_depth_test_RENAMED_TO_cogl_set_depth_test_enabled
|
||||
#define cogl_enable_backface_culling cogl_enable_backface_culling_RENAMED_TO_cogl_set_backface_culling_enabled
|
||||
|
||||
#define cogl_texture_rectangle cogl_texture_rectangle_REPLACE_BY_cogl_set_source_texture_AND_cogl_rectangle_with_texture_coords
|
||||
|
||||
#define cogl_texture_multiple_rectangles cogl_texture_multiple_rectangles_REPLACED_BY_cogl_set_source_texture_AND_cogl_rectangles_with_texture_coords
|
||||
|
||||
#define cogl_texture_polygon cogl_texture_polygon_REPLACED_BY_cogl_set_source_texture_AND_cogl_polygon
|
||||
|
||||
#endif
|
||||
|
629
cogl-material.h
629
cogl-material.h
@ -43,6 +43,51 @@ G_BEGIN_DECLS
|
||||
* blended together.
|
||||
*/
|
||||
|
||||
/**
|
||||
* CoglMaterialFilter:
|
||||
* @COGL_MATERIAL_FILTER_NEAREST: Measuring in manhatten distance from the,
|
||||
* current pixel center, use the nearest texture
|
||||
* texel.
|
||||
* @COGL_MATERIAL_FILTER_LINEAR: Use the weighted average of the 4 texels
|
||||
* nearest the current pixel center.
|
||||
* @COGL_MATERIAL_FILTER_NEAREST_MIPMAP_NEAREST: Select the mimap level whose
|
||||
* texel size most closely matches
|
||||
* the current pixel, and use the
|
||||
* COGL_MATERIAL_FILTER_NEAREST
|
||||
* criterion.
|
||||
* @COGL_MATERIAL_FILTER_LINEAR_MIPMAP_NEAREST: Select the mimap level whose
|
||||
* texel size most closely matches
|
||||
* the current pixel, and use the
|
||||
* COGL_MATERIAL_FILTER_LINEAR
|
||||
* criterion.
|
||||
* @COGL_MATERIAL_FILTER_NEAREST_MIPMAP_LINEAR: Select the two mimap levels
|
||||
* whose texel size most closely
|
||||
* matches the current pixel, use
|
||||
* the COGL_MATERIAL_FILTER_NEAREST
|
||||
* criterion on each one and take
|
||||
* their weighted average.
|
||||
* @COGL_MATERIAL_FILTER_LINEAR_MIPMAP_LINEAR: Select the two mimap levels
|
||||
* whose texel size most closely
|
||||
* matches the current pixel, use
|
||||
* the COGL_MATERIAL_FILTER_LINEAR
|
||||
* criterion on each one and take
|
||||
* their weighted average.
|
||||
*
|
||||
* Texture filtering is used whenever the current pixel maps either to more
|
||||
* than one texture element (texel) or less than one. These filter enums
|
||||
* correspond to different strategies used to come up with a pixel color, by
|
||||
* possibly referring to multiple neighbouring texels and taking a weighted
|
||||
* average or simply using the nearest texel.
|
||||
*/
|
||||
typedef enum _CoglMaterialFilter
|
||||
{
|
||||
COGL_MATERIAL_FILTER_NEAREST = GL_NEAREST,
|
||||
COGL_MATERIAL_FILTER_LINEAR = GL_LINEAR,
|
||||
COGL_MATERIAL_FILTER_NEAREST_MIPMAP_NEAREST = GL_NEAREST_MIPMAP_NEAREST,
|
||||
COGL_MATERIAL_FILTER_LINEAR_MIPMAP_NEAREST = GL_LINEAR_MIPMAP_NEAREST,
|
||||
COGL_MATERIAL_FILTER_NEAREST_MIPMAP_LINEAR = GL_NEAREST_MIPMAP_LINEAR,
|
||||
COGL_MATERIAL_FILTER_LINEAR_MIPMAP_LINEAR = GL_LINEAR_MIPMAP_LINEAR
|
||||
} CoglMaterialFilter;
|
||||
|
||||
/**
|
||||
* cogl_material_new:
|
||||
@ -367,80 +412,90 @@ void cogl_material_set_alpha_test_function (CoglHandle material,
|
||||
float alpha_reference);
|
||||
|
||||
/**
|
||||
* CoglMaterialBlendFactor:
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_ZERO: (0, 0, 0, 0)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_ONE: (1, 1, 1, 1)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_SRC_COLOR: (Rs, Gs, Bs, As)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_DST_COLOR: (Rd, Gd, Bd, Ad)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_SRC_COLOR: (1-Rs, 1-Gs, 1-Bs, 1-As)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_DST_COLOR: (1-Rd, 1-Gd, 1-Bd, 1-Ad)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_SRC_ALPHA: (As, As, As, As)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA: (1-As, 1-As, 1-As, 1-As)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_DST_ALPHA: (Ad, Ad, Ad, Ad)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_DST_ALPHA: (1-Ad, 1-Ad, 1-Ad, 1-Ad)
|
||||
* @COGL_MATERIAL_BLEND_FACTOR_SRC_ALPHA_SATURATE: (f,f,f,1) where f=MIN(As,1-Ad)
|
||||
* cogl_material_set_blend:
|
||||
* @material: A CoglMaterial object
|
||||
* @blend_string: A <link linkend="cogl-Blend-Strings">Cogl blend string</link>
|
||||
* describing the desired blend function.
|
||||
* @error: A GError that may report lack of driver support if you give
|
||||
* separate blend string statements for the alpha channel and RGB
|
||||
* channels since some drivers or backends such as GLES 1.1 dont
|
||||
* support this.
|
||||
*
|
||||
* If not already familiar; please refer
|
||||
* <link linkend="cogl-Blend-Strings">here</link> for an overview of what blend
|
||||
* strings are and there syntax.
|
||||
*
|
||||
* Blending occurs after the alpha test function, and combines fragments with
|
||||
* the framebuffer.
|
||||
* <para>
|
||||
* A fixed function is used to determine the blended color, which is based on
|
||||
* the incoming source color of your fragment (Rs, Gs, Bs, As), a source
|
||||
* factor (Sr, Sg, Sb, Sa), a destination color (Rd, Rg, Rb, Ra) and
|
||||
* a destination factor (Dr, Dg, Db, Da), and is given by these equations:
|
||||
* </para>
|
||||
|
||||
* Currently the only blend function Cogl exposes is ADD(). So any valid
|
||||
* blend statements will be of the form:
|
||||
*
|
||||
* <programlisting>
|
||||
* R = Rs*Sr + Rd*Dr
|
||||
* G = Gs*Sg + Gd*Dg
|
||||
* B = Bs*Sb + Bd*Db
|
||||
* A = As*Sa + Ad*Da
|
||||
* <channel-mask>=ADD(SRC_COLOR*(<factor>), DST_COLOR*(<factor>))
|
||||
* </programlisting>
|
||||
*
|
||||
* All factors have a range [0, 1]
|
||||
* <b>NOTE: The brackets around blend factors are currently not optional!</b>
|
||||
*
|
||||
* The factors are selected with the following constants:
|
||||
* This is the list of source-names usable as blend factors:
|
||||
* <itemizedlist>
|
||||
* <listitem>SRC_COLOR: The color of the in comming fragment</listitem>
|
||||
* <listitem>DST_COLOR: The color of the framebuffer</listitem>
|
||||
* <listitem>
|
||||
* CONSTANT: The constant set via cogl_material_set_blend_constant()</listitem>
|
||||
* </itemizedlist>
|
||||
* The source names can be used according to the
|
||||
* <link linkend="cogl-Blend-String-syntax">color-source and factor syntax</link>,
|
||||
* so for example "(1-SRC_COLOR[A])" would be a valid factor, as would
|
||||
* "(CONSTANT[RGB])"
|
||||
*
|
||||
* These can also be used as factors:
|
||||
* <itemizedlist>
|
||||
* <listitem>0: (0, 0, 0, 0)</listitem>
|
||||
* <listitem>1: (1, 1, 1, 1)</listitem>
|
||||
* <listitem>SRC_ALPHA_SATURATE_FACTOR: (f,f,f,1)
|
||||
* where f=MIN(SRC_COLOR[A],1-DST_COLOR[A])</listitem>
|
||||
* </itemizedlist>
|
||||
* <para>
|
||||
* Remember; all color components are normalized to the range [0, 1] before
|
||||
* computing the result of blending.
|
||||
* </para>
|
||||
* <section>
|
||||
* <title>Examples</title>
|
||||
* Blend a non-premultiplied source over a destination with
|
||||
* premultiplied alpha:
|
||||
* <programlisting>
|
||||
* "RGB = ADD(SRC_COLOR*(SRC_COLOR[A]), DST_COLOR*(1-SRC_COLOR[A]))"
|
||||
* "A = ADD(SRC_COLOR, DST_COLOR*(1-SRC_COLOR[A]))"
|
||||
* </programlisting>
|
||||
* Blend a premultiplied source over a destination with premultiplied alpha:
|
||||
* <programlisting>
|
||||
* "RGBA = ADD(SRC_COLOR, DST_COLOR*(1-SRC_COLOR[A]))"
|
||||
* </programlisting>
|
||||
* </section>
|
||||
*
|
||||
* Returns: TRUE if the blend string was successfully parsed, and the described
|
||||
* blending is supported by the underlying driver/hardware. If there
|
||||
* was an error, it returns FALSE.
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglMaterialBlendFactor
|
||||
{
|
||||
COGL_MATERIAL_BLEND_FACTOR_ZERO = GL_ZERO,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ONE = GL_ONE,
|
||||
COGL_MATERIAL_BLEND_FACTOR_SRC_COLOR = GL_SRC_COLOR,
|
||||
COGL_MATERIAL_BLEND_FACTOR_DST_COLOR = GL_DST_COLOR,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_SRC_COLOR = GL_ONE_MINUS_SRC_COLOR,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_DST_COLOR = GL_ONE_MINUS_DST_COLOR,
|
||||
COGL_MATERIAL_BLEND_FACTOR_SRC_ALPHA = GL_SRC_ALPHA,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA = GL_ONE_MINUS_SRC_ALPHA,
|
||||
COGL_MATERIAL_BLEND_FACTOR_DST_ALPHA = GL_DST_ALPHA,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_DST_ALPHA = GL_ONE_MINUS_DST_ALPHA,
|
||||
COGL_MATERIAL_BLEND_FACTOR_SRC_ALPHA_SATURATE = GL_SRC_ALPHA_SATURATE,
|
||||
} CoglMaterialBlendFactor;
|
||||
gboolean cogl_material_set_blend (CoglHandle material,
|
||||
const char *blend_string,
|
||||
GError **error);
|
||||
|
||||
/**
|
||||
* cogl_material_set_blend_factors:
|
||||
* cogl_material_set_blend_constant:
|
||||
* @material: A CoglMaterial object
|
||||
* @src_factor: Chooses the @CoglMaterialBlendFactor you want plugged in to
|
||||
* the blend equation.
|
||||
* @dst_factor: Chooses the @CoglMaterialBlendFactor you want plugged in to
|
||||
* the blend equation.
|
||||
* @constant_color: The constant color you want
|
||||
*
|
||||
* This function lets you control how primitives using this material will get
|
||||
* blended with the contents of your framebuffer. The blended RGBA components
|
||||
* are calculated like this:
|
||||
* When blending is setup to reference a CONSTANT blend factor then
|
||||
* blending will depend on the constant set with this function.
|
||||
*
|
||||
* (RsSr+RdDr, GsSg+GdDg, BsSb+BsSb, AsSa+AdDa)
|
||||
*
|
||||
* Where (Rs,Gs,Bs,As) represents your source - material- color,
|
||||
* (Rd,Gd,Bd,Ad) represents your destination - framebuffer - color,
|
||||
* (Sr,Sg,Sb,Sa) represents your source blend factor and
|
||||
* (Dr,Dg,Db,Da) represents you destination blend factor.
|
||||
*
|
||||
* All factors lie in the range [0,1] and incoming color components are also
|
||||
* normalized to the range [0,1]
|
||||
*
|
||||
* Since 1.0
|
||||
* Since: 1.0
|
||||
*/
|
||||
void cogl_material_set_blend_factors (CoglHandle material,
|
||||
CoglMaterialBlendFactor src_factor,
|
||||
CoglMaterialBlendFactor dst_factor);
|
||||
void cogl_material_set_blend_constant (CoglHandle material,
|
||||
CoglColor *constant_color);
|
||||
|
||||
/**
|
||||
* cogl_material_set_layer:
|
||||
@ -460,7 +515,7 @@ void cogl_material_set_blend_factors (CoglHandle material,
|
||||
* Since 1.0
|
||||
*/
|
||||
void cogl_material_set_layer (CoglHandle material,
|
||||
gint layer_index,
|
||||
int layer_index,
|
||||
CoglHandle texture);
|
||||
|
||||
/**
|
||||
@ -473,233 +528,112 @@ void cogl_material_set_layer (CoglHandle material,
|
||||
void cogl_material_remove_layer (CoglHandle material,
|
||||
gint layer_index);
|
||||
|
||||
|
||||
/**
|
||||
* CoglMaterialLayerCombineFunc:
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_REPLACE: Arg0
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_MODULATE: Arg0 x Arg1
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD: Arg0 + Arg1
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD_SIGNED: Arg0 + Arg1 - 0.5
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_INTERPOLATE: Arg0 x Arg + Arg1 x (1-Arg2)
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_SUBTRACT: Arg0 - Arg1
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_DOT3_RGB: 4 x ((Arg0r - 0.5) x (Arg1r - 0.5)) +
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_FUNC_DOT3_RGBA: ((Arg0b - 0.5) x (Arg1b - 0.5)) +
|
||||
* cogl_material_set_layer_combine:
|
||||
* @material: A CoglMaterial object
|
||||
* @layer_index: Specifies the layer you want define a combine function for
|
||||
* @blend_string: A <link linkend="cogl-Blend-Strings">Cogl blend string</link>
|
||||
* describing the desired texture combine function.
|
||||
* @error: A GError that may report parse errors or lack of GPU/driver support.
|
||||
*
|
||||
* A material may comprise of 1 or more layers that can be combined using a
|
||||
* number of different functions. By default layers are modulated, which is
|
||||
* to say the components of the current source layer S are simply multipled
|
||||
* together with the combined results of the previous layer P like this:
|
||||
* If not already familiar; you can refer
|
||||
* <link linkend="cogl-Blend-Strings">here</link> for an overview of what blend
|
||||
* strings are and there syntax.
|
||||
*
|
||||
* These are all the functions available for texture combining:
|
||||
* <itemizedlist>
|
||||
* <listitem>REPLACE(arg0) = arg0</listitem>
|
||||
* <listitem>MODULATE(arg0, arg1) = arg0 x arg1</listitem>
|
||||
* <listitem>ADD(arg0, arg1) = arg0 + arg1</listitem>
|
||||
* <listitem>ADD_SIGNED(arg0, arg1) = arg0 + arg1 - 0.5</listitem>
|
||||
* <listitem>INTERPOLATE(arg0, arg1, arg2) =
|
||||
* arg0 x arg2 + arg1 x (1 - arg2)</listitem>
|
||||
* <listitem>SUBTRACT(arg0, arg1) = arg0 - arg1</listitem>
|
||||
* <listitem>
|
||||
* DOT3_RGB(arg0, arg1) =
|
||||
* <programlisting>
|
||||
* (Rs*Rp, Gs*Gp, Bs*Bp, As*Ap)
|
||||
* 4 x ((arg0[R] - 0.5)) * (arg1[R] - 0.5) +
|
||||
* (arg0[G] - 0.5)) * (arg1[G] - 0.5) +
|
||||
* (arg0[B] - 0.5)) * (arg1[B] - 0.5))
|
||||
* </programlisting>
|
||||
*
|
||||
* For more advanced techniques, Cogl exposes the fixed function texture
|
||||
* combining capabilities of your GPU to give you greater control.
|
||||
*/
|
||||
typedef enum _CoglMaterialLayerCombineFunc
|
||||
{
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_REPLACE = CGL_REPLACE,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_MODULATE = CGL_MODULATE,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD = CGL_ADD,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD_SIGNED = CGL_ADD_SIGNED,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_INTERPOLATE = CGL_INTERPOLATE,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_SUBTRACT = CGL_SUBTRACT,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_DOT3_RGB = CGL_DOT3_RGB,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_DOT3_RGBA = CGL_DOT3_RGBA
|
||||
} CoglMaterialLayerCombineFunc;
|
||||
|
||||
/**
|
||||
* CoglMaterialLayerCombineChannels:
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB: Modify the function or argument
|
||||
* src/op for the RGB components of a
|
||||
* layer
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_CHANNELS_ALPHA: Modify the function or argument
|
||||
* src/op for the Alpha component of a
|
||||
* layer
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA: Modify the function or argument
|
||||
* src/op for all the components of a
|
||||
* layer
|
||||
*
|
||||
* Cogl optionally lets you describe 2 seperate combine modes for a single
|
||||
* layer; 1 for the RGB components, and 1 for the Alpha component, so in this
|
||||
* case you would repeat the 3 steps documented with the
|
||||
* @cogl_material_set_layer_combine_function function for each channel
|
||||
* selector.
|
||||
*
|
||||
* (Note: you can't have different modes for each channel, so if you need more
|
||||
* control you will need to use a glsl fragment shader)
|
||||
*/
|
||||
typedef enum _CoglMaterialLayerCombineChannels
|
||||
{
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB,
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_ALPHA,
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA
|
||||
} CoglMaterialLayerCombineChannels;
|
||||
|
||||
/**
|
||||
* cogl_material_set_layer_combine_function:
|
||||
* @material: A CoglMaterial object
|
||||
* @layer_index: Specifies the layer whos combine mode you want to modify
|
||||
* @channels: Specifies which channels combine mode you want to modify
|
||||
* (RGB, ALPHA, or RGBA)
|
||||
* @func: Specifies the function you want to use for combining fragments
|
||||
* of the specified layer with the results of previously combined
|
||||
* layers.
|
||||
*
|
||||
* There are three basic steps to describing how a layer should be combined:
|
||||
* <orderedlist>
|
||||
* <listitem>
|
||||
* Choose a function.
|
||||
* </listitem>
|
||||
* <listitem>
|
||||
* Specify the source color for each argument of the chosen function. (Note
|
||||
* the functions don't all take the same number of arguments)
|
||||
* </listitem>
|
||||
* <listitem>
|
||||
* Specify an operator for each argument that can modify the corresponding
|
||||
* source color before the function is applied.
|
||||
* </listitem>
|
||||
* </orderedlist>
|
||||
*
|
||||
* Cogl optionally lets you describe 2 seperate combine modes for a single
|
||||
* layer; 1 for the RGB components, and 1 for the Alpha component, so in this
|
||||
* case you would repeat the 3 steps for each channel selector.
|
||||
*
|
||||
* (Note: you can't have different modes for each channel, so if you need more
|
||||
* control you will need to use a glsl fragment shader)
|
||||
*
|
||||
* For example here is how you could elect to use the ADD function for all
|
||||
* components of layer 1 in your material:
|
||||
* <listitem>DOT3_RGBA(arg0, arg1) =
|
||||
* <programlisting>
|
||||
* //Step 1: Choose a function. Note the ADD function takes 2 arguments...
|
||||
* cogl_material_set_layer_combine_function (material,
|
||||
* 1,
|
||||
* COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA)
|
||||
* COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD);
|
||||
* //Step 2: Specify the source color for the 2 ADD function arguments...
|
||||
* cogl_material_set_layer_combine_arg_src (material,
|
||||
* 1,//layer index
|
||||
* 0,//argument index
|
||||
* COGL_MATERIAL_LAYER_COMBINE_SRC_PREVIOUS);
|
||||
* cogl_material_set_layer_combine_arg_src (material,
|
||||
* 1,//layer index
|
||||
* 1,//argument index
|
||||
* COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA)
|
||||
* COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE);
|
||||
* //Step 3: Specify the operators used to modify the arguments...
|
||||
* cogl_material_set_layer_combine_arg_op (material,
|
||||
* 1,//layer index
|
||||
* 0,//argument index
|
||||
* COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA,
|
||||
* COGL_MATERIAL_LAYER_COMBINE_OP_SRC_COLOR);
|
||||
* cogl_material_set_layer_combine_arg_op (material,
|
||||
* 1,//layer index
|
||||
* 1,//argument index
|
||||
* COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA,
|
||||
* COGL_MATERIAL_LAYER_COMBINE_OP_SRC_COLOR);
|
||||
* 4 x ((arg0[R] - 0.5)) * (arg1[R] - 0.5) +
|
||||
* (arg0[G] - 0.5)) * (arg1[G] - 0.5) +
|
||||
* (arg0[B] - 0.5)) * (arg1[B] - 0.5))
|
||||
* </programlisting>
|
||||
*/
|
||||
void cogl_material_set_layer_combine_function (CoglHandle material,
|
||||
gint layer_index,
|
||||
CoglMaterialLayerCombineChannels channels,
|
||||
CoglMaterialLayerCombineFunc func);
|
||||
|
||||
/**
|
||||
* CoglMaterialLayerCombineSrc:
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE: The fragment color of the current texture layer
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE0: The fragment color of texture unit 0
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE1: The fragment color of texture unit 1
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE2: The fragment color of texture unit 2..7
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_CONSTANT: A fixed constant color (TODO: no API yet to specify the actual color!)
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_PRIMARY_COLOR: The basic color of the primitive ignoring texturing
|
||||
* @COGL_MATERIAL_LAYER_COMBINE_SRC_PREVIOUS: The result of combining all previous layers
|
||||
* </listitem>
|
||||
* </itemizedlist>
|
||||
*
|
||||
* Note for the constants @COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE0..n the
|
||||
* numbers may not correspond to the indices you choose for your layers since
|
||||
* your layer indices don't need to be contiguous. If you need to use these
|
||||
* it would probably be sensible to ensure the layer indices do infact
|
||||
* correspond.
|
||||
* Refer to the
|
||||
* <link linkend="cogl-Blend-String-syntax">color-source syntax</link> for
|
||||
* describing the arguments. The valid source names for texture combining
|
||||
* are:
|
||||
* <itemizedlist>
|
||||
* <listitem>
|
||||
* TEXTURE: Use the color from the current texture layer
|
||||
* </listitem>
|
||||
* <listitem>
|
||||
* TEXTURE_0, TEXTURE_1, etc: Use the color from the specified texture layer
|
||||
* </listitem>
|
||||
* <listitem>
|
||||
* CONSTANT: Use the color from the constant given with
|
||||
* cogl_material_set_layer_constant()
|
||||
* </listitem>
|
||||
* <listitem>
|
||||
* PRIMARY: Use the color of the material as set with cogl_material_set_color()
|
||||
* </listitem>
|
||||
* <listitem>
|
||||
* PREVIOUS: Either use the texture color from the previous layer, or if this
|
||||
* is layer 0, use the color of the material as set with
|
||||
* cogl_material_set_color()
|
||||
* </listitem>
|
||||
* </itemizedlist>
|
||||
* <section>
|
||||
* <title>Example</title>
|
||||
* This is effectively what the default blending is:
|
||||
* <programlisting>
|
||||
* "RGBA = MODULATE (PREVIOUS, TEXTURE)"
|
||||
* </programlisting>
|
||||
* This could be used to cross-fade between two images, using the alpha
|
||||
* component of a constant as the interpolator. The constant color
|
||||
* is given by calling cogl_material_set_layer_constant.
|
||||
* <programlisting>
|
||||
* RGBA = INTERPOLATE (PREVIOUS, TEXTURE, CONSTANT[A])
|
||||
* </programlisting>
|
||||
* </section>
|
||||
* <b>Note: you can't give a multiplication factor for arguments as you can
|
||||
* with blending.</b>
|
||||
*
|
||||
* Returns: TRUE if the blend string was successfully parsed, and the described
|
||||
* texture combining is supported by the underlying driver/hardware.
|
||||
* If there was an error, it returns FALSE.
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglMaterialLayerCombineSrc
|
||||
{
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE = GL_TEXTURE,
|
||||
|
||||
/* Can we find a nicer way... */
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE0 = GL_TEXTURE0,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE1 = GL_TEXTURE1,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE2 = GL_TEXTURE2,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE3 = GL_TEXTURE3,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE4 = GL_TEXTURE4,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE5 = GL_TEXTURE5,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE6 = GL_TEXTURE6,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE7 = GL_TEXTURE7,
|
||||
/* .. who would ever need more than 8 texture layers.. :-) */
|
||||
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_CONSTANT = CGL_CONSTANT,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_PRIMARY_COLOR = CGL_PRIMARY_COLOR,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_PREVIOUS = CGL_PREVIOUS
|
||||
} CoglMaterialLayerCombineSrc;
|
||||
gboolean
|
||||
cogl_material_set_layer_combine (CoglHandle material,
|
||||
gint layer_index,
|
||||
const char *blend_string,
|
||||
GError **error);
|
||||
|
||||
/**
|
||||
* cogl_material_set_layer_combine_arg_src:
|
||||
* cogl_material_set_layer_combine_constant:
|
||||
* @material: A CoglMaterial object
|
||||
* @layer_index:
|
||||
* @argument:
|
||||
* @channels:
|
||||
* @src:
|
||||
* @layer_index: Specifies the layer you want to specify a constant used
|
||||
* for texture combining
|
||||
* @color_constant: The constant color you want
|
||||
*
|
||||
*/
|
||||
void cogl_material_set_layer_combine_arg_src (CoglHandle material,
|
||||
gint layer_index,
|
||||
gint argument,
|
||||
CoglMaterialLayerCombineChannels channels,
|
||||
CoglMaterialLayerCombineSrc src);
|
||||
|
||||
typedef enum _CoglMaterialLayerCombineOp
|
||||
{
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_SRC_COLOR = GL_SRC_COLOR,
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_ONE_MINUS_SRC_COLOR = GL_ONE_MINUS_SRC_COLOR,
|
||||
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_SRC_ALPHA = GL_SRC_ALPHA,
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_ONE_MINUS_SRC_ALPHA = GL_ONE_MINUS_SRC_ALPHA
|
||||
} CoglMaterialLayerCombineOp;
|
||||
|
||||
/**
|
||||
* cogl_material_set_layer_combine_arg_op:
|
||||
* @material: A CoglMaterial object
|
||||
* @layer_index:
|
||||
* @argument:
|
||||
* @channels:
|
||||
* @op:
|
||||
* When you are using the 'CONSTANT' color source in a layer combine
|
||||
* description then you can use this function to define its value.
|
||||
*
|
||||
* Since 1.0
|
||||
*/
|
||||
void cogl_material_set_layer_combine_arg_op (CoglHandle material,
|
||||
gint layer_index,
|
||||
gint argument,
|
||||
CoglMaterialLayerCombineChannels channels,
|
||||
CoglMaterialLayerCombineOp op);
|
||||
|
||||
/* TODO: */
|
||||
#if 0
|
||||
I think it would be be really neat to support a simple string description
|
||||
of the fixed function texture combine modes exposed above. I think we can
|
||||
consider this stuff to be set in stone from the POV that more advanced
|
||||
texture combine functions are catered for with GLSL, so it seems reasonable
|
||||
to find a concise string representation that can represent all the above
|
||||
modes in a *much* more readable/useable fashion. I think somthing like
|
||||
this would be quite nice:
|
||||
|
||||
"MODULATE(TEXTURE[RGB], PREVIOUS[A])"
|
||||
"ADD(TEXTURE[A],PREVIOUS[RGB])"
|
||||
"INTERPOLATE(TEXTURE[1-A], PREVIOUS[RGB])"
|
||||
|
||||
void cogl_material_set_layer_rgb_combine (CoglHandle material
|
||||
gint layer_index,
|
||||
const char *combine_description);
|
||||
void cogl_material_set_layer_alpha_combine (CoglHandle material
|
||||
gint layer_index,
|
||||
const char *combine_description);
|
||||
#endif
|
||||
void cogl_material_set_layer_combine_constant (CoglHandle material,
|
||||
int layer_index,
|
||||
CoglColor *constant);
|
||||
|
||||
/**
|
||||
* cogl_material_set_layer_matrix:
|
||||
@ -709,38 +643,9 @@ void cogl_material_set_layer_alpha_combine (CoglHandle material
|
||||
* and rotate a single layer of a material used to fill your geometry.
|
||||
*/
|
||||
void cogl_material_set_layer_matrix (CoglHandle material,
|
||||
gint layer_index,
|
||||
int layer_index,
|
||||
CoglMatrix *matrix);
|
||||
|
||||
|
||||
/**
|
||||
* SECTION:cogl-material-internals
|
||||
* @short_description: Functions for creating custom primitives that make use
|
||||
* of Cogl materials for filling.
|
||||
*
|
||||
* Normally you shouldn't need to use this API directly, but if you need to
|
||||
* developing a custom/specialised primitive - probably using raw OpenGL - then
|
||||
* this API aims to expose enough of the material internals to support being
|
||||
* able to fill your geometry according to a given Cogl material.
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
* cogl_material_get_cogl_enable_flags:
|
||||
* @material: A CoglMaterial object
|
||||
*
|
||||
* This determines what flags need to be passed to cogl_enable before this
|
||||
* material can be used. Normally you shouldn't need to use this function
|
||||
* directly since Cogl will do this internally, but if you are developing
|
||||
* custom primitives directly with OpenGL you may want to use this.
|
||||
*
|
||||
* Note: This API is hopfully just a stop-gap solution. Ideally cogl_enable
|
||||
* will be replaced.
|
||||
*/
|
||||
/* TODO: find a nicer solution! */
|
||||
gulong
|
||||
cogl_material_get_cogl_enable_flags (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* cogl_material_get_layers:
|
||||
* @material: A CoglMaterial object
|
||||
@ -748,24 +653,20 @@ cogl_material_get_cogl_enable_flags (CoglHandle handle);
|
||||
* This function lets you access a materials internal list of layers
|
||||
* for iteration.
|
||||
*
|
||||
* Note: Normally you shouldn't need to use this function directly since
|
||||
* Cogl will do this internally, but if you are developing custom primitives
|
||||
* directly with OpenGL, you will need to iterate the layers that you want
|
||||
* to texture with.
|
||||
*
|
||||
* Note: This function may return more layers than OpenGL can use at once
|
||||
* so it's your responsability limit yourself to
|
||||
* CGL_MAX_COMBINED_TEXTURE_IMAGE_UNITS.
|
||||
*
|
||||
* Note: It's a bit out of the ordinary to return a const GList *, but it
|
||||
* was considered sensible to try and avoid list manipulation for every
|
||||
* primitive emitted in a scene, every frame.
|
||||
* Returns: A list of #CoglHandle<!-- -->'s that can be passed to the
|
||||
* cogl_material_layer_* functions.
|
||||
*/
|
||||
const GList *cogl_material_get_layers (CoglHandle material_handle);
|
||||
|
||||
/**
|
||||
* CoglMaterialLayerType:
|
||||
* @COGL_MATERIAL_LAYER_TYPE_TEXTURE: The layer represents a CoglTexture
|
||||
* @COGL_MATERIAL_LAYER_TYPE_TEXTURE: The layer represents a
|
||||
* <link linkend="cogl-Textures">Cogl texture</link>
|
||||
*
|
||||
* Available types of layers for a #CoglMaterial. This enumeration
|
||||
* might be expanded in later versions.
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglMaterialLayerType
|
||||
{
|
||||
@ -774,17 +675,12 @@ typedef enum _CoglMaterialLayerType
|
||||
|
||||
/**
|
||||
* cogl_material_layer_get_type:
|
||||
* @layer_handle: A CoglMaterialLayer handle
|
||||
* @layer_handle: A Cogl material layer handle
|
||||
*
|
||||
* Currently there is only one type of layer defined:
|
||||
* COGL_MATERIAL_LAYER_TYPE_TEXTURE, but considering we may add purely GLSL
|
||||
* based layers in the future, you should write code that checks the type
|
||||
* first.
|
||||
*
|
||||
* Note: Normally you shouldn't need to use this function directly since
|
||||
* Cogl will do this internally, but if you are developing custom primitives
|
||||
* directly with OpenGL, you will need to iterate the layers that you want
|
||||
* to texture with, and thus should be checking the layer types.
|
||||
*/
|
||||
CoglMaterialLayerType cogl_material_layer_get_type (CoglHandle layer_handle);
|
||||
|
||||
@ -792,75 +688,58 @@ CoglMaterialLayerType cogl_material_layer_get_type (CoglHandle layer_handle);
|
||||
* cogl_material_layer_get_texture:
|
||||
* @layer_handle: A CoglMaterialLayer handle
|
||||
*
|
||||
* This lets you extract a CoglTexture handle for a specific layer. Normally
|
||||
* you shouldn't need to use this function directly since Cogl will do this
|
||||
* internally, but if you are developing custom primitives directly with
|
||||
* OpenGL you may need this.
|
||||
* This lets you extract a CoglTexture handle for a specific layer.
|
||||
*
|
||||
* Note: In the future, we may support purely GLSL based layers which will
|
||||
* likley return COGL_INVALID_HANDLE if you try to get the texture.
|
||||
* Considering this, you should always call cogl_material_layer_get_type
|
||||
* first, to check it is of type COGL_MATERIAL_LAYER_TYPE_TEXTURE.
|
||||
* likely return COGL_INVALID_HANDLE if you try to get the texture.
|
||||
* Considering this, you can call cogl_material_layer_get_type first,
|
||||
* to check it is of type COGL_MATERIAL_LAYER_TYPE_TEXTURE.
|
||||
*
|
||||
* Note: It is possible for a layer object of type
|
||||
* COGL_MATERIAL_LAYER_TYPE_TEXTURE to be realized before a texture
|
||||
* object has been associated with the layer. For example this happens
|
||||
* if you setup layer combining for a given layer index before calling
|
||||
* cogl_material_set_layer for that index.
|
||||
*
|
||||
* Returns: A CoglHandle to the layers texture object or COGL_INVALID_HANDLE
|
||||
* if a texture has not been set yet.
|
||||
*/
|
||||
CoglHandle cogl_material_layer_get_texture (CoglHandle layer_handle);
|
||||
|
||||
/**
|
||||
* CoglMaterialLayerFlags:
|
||||
* @COGL_MATERIAL_LAYER_FLAG_USER_MATRIX: Means the user has supplied a
|
||||
* custom texture matrix.
|
||||
* cogl_material_layer_get_min_filter:
|
||||
* @layer_handle: a #CoglHandle for a material layer.
|
||||
*
|
||||
* Query the currently set downscaling filter for a cogl material layer.
|
||||
*
|
||||
* Returns: the current downscaling filter for a cogl material layer.
|
||||
*/
|
||||
typedef enum _CoglMaterialLayerFlags
|
||||
{
|
||||
COGL_MATERIAL_LAYER_FLAG_HAS_USER_MATRIX = 1L<<0
|
||||
} CoglMaterialLayerFlags;
|
||||
/* XXX: NB: if you add flags here you will need to update
|
||||
* CoglMaterialLayerPrivFlags!!! */
|
||||
CoglMaterialFilter cogl_material_layer_get_min_filter (CoglHandle layer_handle);
|
||||
|
||||
/**
|
||||
* cogl_material_layer_get_flags:
|
||||
* @layer_handle: A CoglMaterialLayer layer handle
|
||||
* cogl_material_layer_get_mag_filter:
|
||||
* @layer_handle: a #CoglHandle for a material layer.
|
||||
*
|
||||
* This lets you get a number of flag attributes about the layer. Normally
|
||||
* you shouldn't need to use this function directly since Cogl will do this
|
||||
* internally, but if you are developing custom primitives directly with
|
||||
* OpenGL you may need this.
|
||||
* Query the currently set downscaling filter for a cogl material layer.
|
||||
*
|
||||
* Returns: the current downscaling filter for a cogl material layer.
|
||||
*/
|
||||
gulong cogl_material_layer_get_flags (CoglHandle layer_handle);
|
||||
CoglMaterialFilter cogl_material_layer_get_mag_filter (CoglHandle layer_handle);
|
||||
|
||||
/**
|
||||
* CoglMaterialFlushOption:
|
||||
* @COGL_MATERIAL_FLUSH_FALLBACK_MASK: Follow this by a guin32 mask
|
||||
* of the layers that can't be supported with the user supplied texture
|
||||
* and need to be replaced with fallback textures. (1 = fallback, and the
|
||||
* least significant bit = layer 0)
|
||||
* @COGL_MATERIAL_FLUSH_DISABLE_MASK: Follow this by a guint32 mask
|
||||
* of the layers that you want to completly disable texturing for
|
||||
* (1 = fallback, and the least significant bit = layer 0)
|
||||
* @COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE: Follow this by a GLuint OpenGL texture
|
||||
* name to override the texture used for layer 0 of the material. This is
|
||||
* intended for dealing with sliced textures where you will need to point
|
||||
* to each of the texture slices in turn when drawing your geometry.
|
||||
* Passing a value of 0 is the same as not passing the option at all.
|
||||
*/
|
||||
typedef enum _CoglMaterialFlushOption
|
||||
{
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK = 1,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE,
|
||||
} CoglMaterialFlushOption;
|
||||
|
||||
/**
|
||||
* cogl_material_flush_gl_state:
|
||||
* @material: A CoglMaterial object
|
||||
* @...: A NULL terminated list of (CoglMaterialFlushOption, data) pairs
|
||||
* cogl_material_set_layer_filters:
|
||||
* @handle: a #CoglHandle to a material.
|
||||
* @layer_index: the layer number to change.
|
||||
* @min_filter: the filter used when scaling a texture down.
|
||||
* @mag_filter: the filter used when magnifying a texture.
|
||||
*
|
||||
* This function commits the state of the specified CoglMaterial - including
|
||||
* the texture state for all the layers - to the OpenGL[ES] driver.
|
||||
*
|
||||
* Since 1.0
|
||||
* Changes the decimation and interpolation filters used when a texture is
|
||||
* drawn at other scales than 100%.
|
||||
*/
|
||||
void cogl_material_flush_gl_state (CoglHandle material,
|
||||
...) G_GNUC_NULL_TERMINATED;
|
||||
void cogl_material_set_layer_filters (CoglHandle handle,
|
||||
gint layer_index,
|
||||
CoglMaterialFilter min_filter,
|
||||
CoglMaterialFilter mag_filter);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
@ -199,22 +199,50 @@ void cogl_matrix_frustum (CoglMatrix *matrix,
|
||||
float z_far);
|
||||
|
||||
/**
|
||||
* cogl_matrix_transform_point:
|
||||
* cogl_matrix_perspective:
|
||||
* @matrix: A 4x4 transformation matrix
|
||||
* @x: The X component of your points position [in:out]
|
||||
* @y: The Y component of your points position [in:out]
|
||||
* @z: The Z component of your points position [in:out]
|
||||
* @w: The W component of your points position [in:out]
|
||||
* @fov_y: A field of view angle for the Y axis
|
||||
* @aspect: The ratio of width to height determining the field of view angle
|
||||
* for the x axis.
|
||||
* @z_near: The distance to the near clip plane.
|
||||
* Never pass 0 and always pass a positive number.
|
||||
* @z_far: The distance to the far clip plane. (Should always be positive)
|
||||
*
|
||||
* This transforms a point whos position is given and returned
|
||||
* as four float components.
|
||||
* Multiplies the matrix by the described perspective matrix
|
||||
*
|
||||
* Note: you should be careful not to have to great a z_far / z_near ratio
|
||||
* since that will reduce the effectiveness of depth testing since there wont
|
||||
* be enough precision to identify the depth of objects near to each other.
|
||||
*/
|
||||
void
|
||||
cogl_matrix_transform_point (const CoglMatrix *matrix,
|
||||
float *x,
|
||||
float *y,
|
||||
float *z,
|
||||
float *w);
|
||||
cogl_matrix_perspective (CoglMatrix *matrix,
|
||||
float fov_y,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far);
|
||||
|
||||
/**
|
||||
* cogl_matrix_ortho:
|
||||
* @matrix: A 4x4 transformation matrix
|
||||
* @left: The coordinate for the left clipping plane
|
||||
* @right: The coordinate for the right clipping plane
|
||||
* @bottom: The coordinate for the bottom clipping plane
|
||||
* @top: The coordinate for the top clipping plane
|
||||
* @z_near: The coordinate for the near clipping plane (may be negative if
|
||||
* the plane is behind the viewer)
|
||||
* @z_far: The coordinate for the far clipping plane (may be negative if
|
||||
* the plane is behind the viewer)
|
||||
*
|
||||
* Multiples the matrix by a parallel projection matrix.
|
||||
*/
|
||||
void
|
||||
cogl_matrix_ortho (CoglMatrix *matrix,
|
||||
float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far);
|
||||
|
||||
/**
|
||||
* cogl_matrix_init_from_array:
|
||||
@ -234,6 +262,24 @@ void cogl_matrix_init_from_array (CoglMatrix *matrix, const float *array);
|
||||
*/
|
||||
const float *cogl_matrix_get_array (const CoglMatrix *matrix);
|
||||
|
||||
/**
|
||||
* cogl_matrix_transform_point:
|
||||
* @matrix: A 4x4 transformation matrix
|
||||
* @x: The X component of your points position [in:out]
|
||||
* @y: The Y component of your points position [in:out]
|
||||
* @z: The Z component of your points position [in:out]
|
||||
* @w: The W component of your points position [in:out]
|
||||
*
|
||||
* This transforms a point whos position is given and returned
|
||||
* as four float components.
|
||||
*/
|
||||
void
|
||||
cogl_matrix_transform_point (const CoglMatrix *matrix,
|
||||
float *x,
|
||||
float *y,
|
||||
float *z,
|
||||
float *w);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __COGL_MATRIX_H */
|
||||
|
@ -46,9 +46,12 @@ G_BEGIN_DECLS
|
||||
* CoglShaderType:
|
||||
* @COGL_SHADER_TYPE_VERTEX: A program for proccessing vertices
|
||||
* @COGL_SHADER_TYPE_FRAGMENT: A program for processing fragments
|
||||
*
|
||||
* Types of shaders
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglShaderType
|
||||
{
|
||||
typedef enum {
|
||||
COGL_SHADER_TYPE_VERTEX,
|
||||
COGL_SHADER_TYPE_FRAGMENT
|
||||
} CoglShaderType;
|
||||
@ -103,7 +106,7 @@ gboolean cogl_is_shader (CoglHandle handle);
|
||||
* one.
|
||||
*/
|
||||
void cogl_shader_source (CoglHandle shader,
|
||||
const char *source);
|
||||
const gchar *source);
|
||||
/**
|
||||
* cogl_shader_compile:
|
||||
* @handle: #CoglHandle for a shader.
|
||||
@ -111,29 +114,30 @@ void cogl_shader_source (CoglHandle shader,
|
||||
* Compiles the shader, no return value, but the shader is now ready for
|
||||
* linking into a program.
|
||||
*/
|
||||
void cogl_shader_compile (CoglHandle handle);
|
||||
void cogl_shader_compile (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* cogl_shader_get_info_log:
|
||||
* @handle: #CoglHandle for a shader.
|
||||
* @size: maximum number of bytes to retrieve.
|
||||
* @buffer: location for info log.
|
||||
*
|
||||
* Retrieves the information log for a coglobject, can be used in conjunction
|
||||
* with #cogl_shader_get_parameteriv to retrieve the compiler warnings/error
|
||||
* with cogl_shader_get_parameteriv() to retrieve the compiler warnings/error
|
||||
* messages that caused a shader to not compile correctly, mainly useful for
|
||||
* debugging purposes.
|
||||
*
|
||||
* Return value: a newly allocated string containing the info log. Use
|
||||
* g_free() to free it
|
||||
*/
|
||||
void cogl_shader_get_info_log (CoglHandle handle,
|
||||
size_t size,
|
||||
char *buffer);
|
||||
gchar * cogl_shader_get_info_log (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* cogl_shader_get_type:
|
||||
* @handle: #CoglHandle for a shader.
|
||||
*
|
||||
* Returns: COGL_SHADER_TYPE_VERTEX if the shader is a vertex processor
|
||||
* or COGL_SHADER_TYPE_FRAGMENT if the shader is a frament processor
|
||||
* Retrieves the type of a shader #CoglHandle
|
||||
*
|
||||
* Return value: %COGL_SHADER_TYPE_VERTEX if the shader is a vertex processor
|
||||
* or %COGL_SHADER_TYPE_FRAGMENT if the shader is a frament processor
|
||||
*/
|
||||
CoglShaderType cogl_shader_get_type (CoglHandle handle);
|
||||
|
||||
@ -141,7 +145,9 @@ CoglShaderType cogl_shader_get_type (CoglHandle handle);
|
||||
* cogl_shader_is_compiled:
|
||||
* @handle: #CoglHandle for a shader.
|
||||
*
|
||||
* Returns: TRUE if the shader object has sucessfully be compiled else FALSE
|
||||
* Retrieves whether a shader #CoglHandle has been compiled
|
||||
*
|
||||
* Return value: %TRUE if the shader object has sucessfully be compiled
|
||||
*/
|
||||
gboolean cogl_shader_is_compiled (CoglHandle handle);
|
||||
|
||||
|
114
cogl-texture.h
114
cogl-texture.h
@ -41,12 +41,12 @@ G_BEGIN_DECLS
|
||||
* loading and manipulating textures.
|
||||
*/
|
||||
|
||||
#define COGL_TEXTURE_MAX_WASTE 127
|
||||
|
||||
/**
|
||||
* cogl_texture_new_with_size:
|
||||
* @width: width of texture in pixels.
|
||||
* @height: height of texture in pixels.
|
||||
* @max_waste: maximum extra horizontal and|or vertical margin pixels
|
||||
* to make the texture fit GPU limitations
|
||||
* @flags: Optional flags for the texture, or %COGL_TEXTURE_NONE
|
||||
* @internal_format: the #CoglPixelFormat to use for the GPU storage of the
|
||||
* texture.
|
||||
@ -60,15 +60,12 @@ G_BEGIN_DECLS
|
||||
*/
|
||||
CoglHandle cogl_texture_new_with_size (guint width,
|
||||
guint height,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format);
|
||||
|
||||
/**
|
||||
* cogl_texture_new_from_file:
|
||||
* @filename: the file to load
|
||||
* @max_waste: maximum extra horizontal and|or vertical margin pixels
|
||||
* to make the texture fit GPU limitations
|
||||
* @flags: Optional flags for the texture, or %COGL_TEXTURE_NONE
|
||||
* @internal_format: the #CoglPixelFormat to use for the GPU storage of the
|
||||
* texture
|
||||
@ -82,7 +79,6 @@ CoglHandle cogl_texture_new_with_size (guint width,
|
||||
* Since: 0.8
|
||||
*/
|
||||
CoglHandle cogl_texture_new_from_file (const gchar *filename,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format,
|
||||
GError **error);
|
||||
@ -91,8 +87,6 @@ CoglHandle cogl_texture_new_from_file (const gchar *filename,
|
||||
* cogl_texture_new_from_data:
|
||||
* @width: width of texture in pixels
|
||||
* @height: height of texture in pixels
|
||||
* @max_waste: maximum extra horizontal and|or vertical margin pixels
|
||||
* to make the texture fit GPU limitations
|
||||
* @flags: Optional flags for the texture, or %COGL_TEXTURE_NONE
|
||||
* @format: the #CoglPixelFormat the buffer is stored in in RAM
|
||||
* @internal_format: the #CoglPixelFormat that will be used for storing
|
||||
@ -110,7 +104,6 @@ CoglHandle cogl_texture_new_from_file (const gchar *filename,
|
||||
*/
|
||||
CoglHandle cogl_texture_new_from_data (guint width,
|
||||
guint height,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat format,
|
||||
CoglPixelFormat internal_format,
|
||||
@ -136,19 +129,17 @@ CoglHandle cogl_texture_new_from_data (guint width,
|
||||
*
|
||||
* Since: 0.8
|
||||
*/
|
||||
CoglHandle cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
GLenum gl_target,
|
||||
GLuint width,
|
||||
GLuint height,
|
||||
GLuint x_pot_waste,
|
||||
GLuint y_pot_waste,
|
||||
CoglPixelFormat format);
|
||||
CoglHandle cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
GLenum gl_target,
|
||||
GLuint width,
|
||||
GLuint height,
|
||||
GLuint x_pot_waste,
|
||||
GLuint y_pot_waste,
|
||||
CoglPixelFormat format);
|
||||
|
||||
/**
|
||||
* cogl_texture_new_from_bitmap:
|
||||
* @bmp_handle: A CoglBitmap handle
|
||||
* @max_waste: maximum extra horizontal and|or vertical margin pixels
|
||||
* to make the texture fit GPU limitations
|
||||
* @flags: Optional flags for the texture, or %COGL_TEXTURE_NONE
|
||||
* @internal_format: the #CoglPixelFormat to use for the GPU storage of the
|
||||
* texture
|
||||
@ -160,10 +151,9 @@ CoglHandle cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
CoglHandle cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format);
|
||||
CoglHandle cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format);
|
||||
|
||||
/**
|
||||
* cogl_is_texture:
|
||||
@ -228,72 +218,6 @@ guint cogl_texture_get_rowstride (CoglHandle handle);
|
||||
*/
|
||||
gint cogl_texture_get_max_waste (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* CoglTextureFilter:
|
||||
* @COGL_TEXTURE_FILTER_NEAREST: Measuring in manhatten distance from the,
|
||||
* current pixel center, use the nearest texture
|
||||
* texel.
|
||||
* @COGL_TEXTURE_FILTER_LINEAR: Use the weighted average of the 4 texels
|
||||
* nearest the current pixel center.
|
||||
* @COGL_TEXTURE_FILTER_NEAREST_MIPMAP_NEAREST: Select the mimap level whose
|
||||
* texel size most closely matches
|
||||
* the current pixel, and use the
|
||||
* COGL_TEXTURE_FILTER_NEAREST
|
||||
* criterion.
|
||||
* @COGL_TEXTURE_FILTER_LINEAR_MIPMAP_NEAREST: Select the mimap level whose
|
||||
* texel size most closely matches
|
||||
* the current pixel, and use the
|
||||
* COGL_TEXTURE_FILTER_LINEAR
|
||||
* criterion.
|
||||
* @COGL_TEXTURE_FILTER_NEAREST_MIPMAP_LINEAR: Select the two mimap levels
|
||||
* whose texel size most closely
|
||||
* matches the current pixel, use
|
||||
* the COGL_TEXTURE_FILTER_NEAREST
|
||||
* criterion on each one and take
|
||||
* their weighted average.
|
||||
* @COGL_TEXTURE_FILTER_LINEAR_MIPMAP_LINEAR: Select the two mimap levels
|
||||
* whose texel size most closely
|
||||
* matches the current pixel, use
|
||||
* the COGL_TEXTURE_FILTER_LINEAR
|
||||
* criterion on each one and take
|
||||
* their weighted average.
|
||||
*
|
||||
* Texture filtering is used whenever the current pixel maps either to more
|
||||
* than one texture element (texel) or less than one. These filter enums
|
||||
* correspond to different strategies used to come up with a pixel color, by
|
||||
* possibly referring to multiple neighbouring texels and taking a weighted
|
||||
* average or simply using the nearest texel.
|
||||
*/
|
||||
typedef enum _CoglTextureFilter
|
||||
{
|
||||
COGL_TEXTURE_FILTER_NEAREST = GL_NEAREST,
|
||||
COGL_TEXTURE_FILTER_LINEAR = GL_LINEAR,
|
||||
COGL_TEXTURE_FILTER_NEAREST_MIPMAP_NEAREST = GL_NEAREST_MIPMAP_NEAREST,
|
||||
COGL_TEXTURE_FILTER_LINEAR_MIPMAP_NEAREST = GL_LINEAR_MIPMAP_NEAREST,
|
||||
COGL_TEXTURE_FILTER_NEAREST_MIPMAP_LINEAR = GL_NEAREST_MIPMAP_LINEAR,
|
||||
COGL_TEXTURE_FILTER_LINEAR_MIPMAP_LINEAR = GL_LINEAR_MIPMAP_LINEAR
|
||||
} CoglTextureFilter;
|
||||
|
||||
/**
|
||||
* cogl_texture_get_min_filter:
|
||||
* @handle: a #CoglHandle for a texture.
|
||||
*
|
||||
* Query the currently set downscaling filter for a cogl texture.
|
||||
*
|
||||
* Returns: the current downscaling filter for a cogl texture.
|
||||
*/
|
||||
CoglTextureFilter cogl_texture_get_min_filter (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* cogl_texture_get_mag_filter:
|
||||
* @handle: a #CoglHandle for a texture.
|
||||
*
|
||||
* Query the currently set downscaling filter for a cogl texture.
|
||||
*
|
||||
* Returns: the current downscaling filter for a cogl texture.
|
||||
*/
|
||||
CoglTextureFilter cogl_texture_get_mag_filter (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* cogl_texture_is_sliced:
|
||||
* @handle: a #CoglHandle for a texture.
|
||||
@ -343,20 +267,6 @@ gint cogl_texture_get_data (CoglHandle handle,
|
||||
guint rowstride,
|
||||
guchar *data);
|
||||
|
||||
/**
|
||||
* cogl_texture_set_filters:
|
||||
* @handle: a #CoglHandle.
|
||||
* @min_filter: the filter used when scaling the texture down.
|
||||
* @mag_filter: the filter used when magnifying the texture.
|
||||
*
|
||||
* Changes the decimation and interpolation filters used when the texture is
|
||||
* drawn at other scales than 100%.
|
||||
*/
|
||||
void cogl_texture_set_filters (CoglHandle handle,
|
||||
CoglTextureFilter min_filter,
|
||||
CoglTextureFilter mag_filter);
|
||||
|
||||
|
||||
/**
|
||||
* cogl_texture_set_region:
|
||||
* @handle: a #CoglHandle.
|
||||
|
92
cogl-types.h
92
cogl-types.h
@ -123,8 +123,7 @@ typedef struct _CoglTextureVertex CoglTextureVertex;
|
||||
*
|
||||
* Since: 0.8
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
typedef enum { /*< prefix=COGL_PIXEL_FORMAT >*/
|
||||
COGL_PIXEL_FORMAT_ANY = 0,
|
||||
COGL_PIXEL_FORMAT_A_8 = 1 | COGL_A_BIT,
|
||||
|
||||
@ -135,60 +134,21 @@ typedef enum
|
||||
COGL_PIXEL_FORMAT_G_8 = 8,
|
||||
|
||||
COGL_PIXEL_FORMAT_RGB_888 = COGL_PIXEL_FORMAT_24,
|
||||
COGL_PIXEL_FORMAT_BGR_888 = (COGL_PIXEL_FORMAT_24 | COGL_BGR_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_BGR_888 = (COGL_PIXEL_FORMAT_24 |
|
||||
COGL_BGR_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_RGBA_8888 = COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT,
|
||||
|
||||
COGL_PIXEL_FORMAT_BGRA_8888 = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_BGR_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_ARGB_8888 = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_AFIRST_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_ABGR_8888 = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_BGR_BIT |
|
||||
COGL_AFIRST_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_RGBA_8888_PRE = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_PREMULT_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_BGRA_8888_PRE = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_PREMULT_BIT |
|
||||
COGL_BGR_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_ARGB_8888_PRE = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_PREMULT_BIT |
|
||||
COGL_AFIRST_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_ABGR_8888_PRE = (COGL_PIXEL_FORMAT_32 |
|
||||
COGL_A_BIT |
|
||||
COGL_PREMULT_BIT |
|
||||
COGL_BGR_BIT |
|
||||
COGL_AFIRST_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_RGBA_4444_PRE = (COGL_PIXEL_FORMAT_RGBA_4444 |
|
||||
COGL_A_BIT |
|
||||
COGL_PREMULT_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_RGBA_5551_PRE = (COGL_PIXEL_FORMAT_RGBA_5551 |
|
||||
COGL_A_BIT |
|
||||
COGL_PREMULT_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_RGBA_8888 = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT),
|
||||
COGL_PIXEL_FORMAT_BGRA_8888 = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_BGR_BIT),
|
||||
COGL_PIXEL_FORMAT_ARGB_8888 = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_AFIRST_BIT),
|
||||
COGL_PIXEL_FORMAT_ABGR_8888 = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_BGR_BIT | COGL_AFIRST_BIT),
|
||||
|
||||
COGL_PIXEL_FORMAT_RGBA_8888_PRE = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_PREMULT_BIT),
|
||||
COGL_PIXEL_FORMAT_BGRA_8888_PRE = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_PREMULT_BIT | COGL_BGR_BIT),
|
||||
COGL_PIXEL_FORMAT_ARGB_8888_PRE = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_PREMULT_BIT | COGL_AFIRST_BIT),
|
||||
COGL_PIXEL_FORMAT_ABGR_8888_PRE = (COGL_PIXEL_FORMAT_32 | COGL_A_BIT | COGL_PREMULT_BIT | COGL_BGR_BIT | COGL_AFIRST_BIT),
|
||||
COGL_PIXEL_FORMAT_RGBA_4444_PRE = (COGL_PIXEL_FORMAT_RGBA_4444 | COGL_A_BIT | COGL_PREMULT_BIT),
|
||||
COGL_PIXEL_FORMAT_RGBA_5551_PRE = (COGL_PIXEL_FORMAT_RGBA_5551 | COGL_A_BIT | COGL_PREMULT_BIT),
|
||||
} CoglPixelFormat;
|
||||
|
||||
#define COGL_TYPE_PIXEL_FORMAT (cogl_pixel_format_get_type ())
|
||||
GType cogl_pixel_format_get_type (void) G_GNUC_CONST;
|
||||
|
||||
/**
|
||||
* CoglFeatureFlags:
|
||||
* @COGL_FEATURE_TEXTURE_RECTANGLE: ARB_texture_rectangle support
|
||||
@ -222,9 +182,6 @@ typedef enum
|
||||
COGL_FEATURE_VBOS = (1 << 11)
|
||||
} CoglFeatureFlags;
|
||||
|
||||
#define COGL_TYPE_FEATURE_FLAGS (cogl_feature_flags_get_type ())
|
||||
GType cogl_feature_flags_get_type (void) G_GNUC_CONST;
|
||||
|
||||
/**
|
||||
* CoglBufferTarget:
|
||||
* @COGL_WINDOW_BUFFER: FIXME
|
||||
@ -240,9 +197,6 @@ typedef enum
|
||||
COGL_OFFSCREEN_BUFFER = (1 << 2)
|
||||
} CoglBufferTarget;
|
||||
|
||||
#define COGL_TYPE_BUFFER_TARGET (cogl_buffer_target_get_type ())
|
||||
GType cogl_buffer_target_get_type (void) G_GNUC_CONST;
|
||||
|
||||
/**
|
||||
* CoglColor:
|
||||
*
|
||||
@ -290,21 +244,23 @@ struct _CoglTextureVertex
|
||||
/**
|
||||
* CoglTextureFlags:
|
||||
* @COGL_TEXTURE_NONE: No flags specified
|
||||
* @COGL_TEXTURE_AUTO_MIPMAP: Enables the automatic generation of the
|
||||
* mipmap pyramid from the base level image whenever it is updated
|
||||
* @COGL_TEXTURE_NO_AUTO_MIPMAP: Disables the automatic generation of
|
||||
* the mipmap pyramid from the base level image whenever it is
|
||||
* updated. The mipmaps are only generated when the texture is
|
||||
* rendered with a mipmap filter so it should be free to leave out
|
||||
* this flag when using other filtering modes.
|
||||
* @COGL_TEXTURE_NO_SLICING: Disables the slicing of the texture
|
||||
*
|
||||
* Flags to pass to the cogl_texture_new_* family of functions.
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum {
|
||||
COGL_TEXTURE_NONE = 0,
|
||||
COGL_TEXTURE_AUTO_MIPMAP = 1 << 0
|
||||
COGL_TEXTURE_NONE = 0,
|
||||
COGL_TEXTURE_NO_AUTO_MIPMAP = 1 << 0,
|
||||
COGL_TEXTURE_NO_SLICING = 1 << 1
|
||||
} CoglTextureFlags;
|
||||
|
||||
#define COGL_TYPE_TEXTURE_FLAGS (cogl_texture_flags_get_type ())
|
||||
GType cogl_texture_flags_get_type (void) G_GNUC_CONST;
|
||||
|
||||
/**
|
||||
* CoglFogMode:
|
||||
* @COGL_FOG_MODE_LINEAR: Calculates the fog blend factor as:
|
||||
@ -333,16 +289,12 @@ GType cogl_texture_flags_get_type (void) G_GNUC_CONST;
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglFogMode
|
||||
{
|
||||
typedef enum {
|
||||
COGL_FOG_MODE_LINEAR,
|
||||
COGL_FOG_MODE_EXPONENTIAL,
|
||||
COGL_FOG_MODE_EXPONENTIAL_SQUARED
|
||||
} CoglFogMode;
|
||||
|
||||
#define COGL_TYPE_FOG_MODE (cogl_fog_mode_get_type ())
|
||||
GType cogl_fog_mode_get_type (void) G_GNUC_CONST;
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __COGL_TYPES_H__ */
|
||||
|
@ -94,6 +94,29 @@ cogl_vertex_buffer_new (guint n_vertices);
|
||||
guint
|
||||
cogl_vertex_buffer_get_n_vertices (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* CoglAttributeType:
|
||||
* @COGL_ATTRIBUTE_TYPE_BYTE: Data is the same size of a byte
|
||||
* @COGL_ATTRIBUTE_TYPE_UNSIGNED_BYTE: Data is the same size of an
|
||||
* unsigned byte
|
||||
* @COGL_ATTRIBUTE_TYPE_SHORT: Data is the same size of a short integer
|
||||
* @COGL_ATTRIBUTE_TYPE_UNSIGNED_SHORT: Data is the same size of
|
||||
* an unsigned short integer
|
||||
* @COGL_ATTRIBUTE_TYPE_FLOAT: Data is the same size of a float
|
||||
*
|
||||
* Data types for the components of cogl_vertex_buffer_add()
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglAttributeType
|
||||
{
|
||||
COGL_ATTRIBUTE_TYPE_BYTE = GL_BYTE,
|
||||
COGL_ATTRIBUTE_TYPE_UNSIGNED_BYTE = GL_UNSIGNED_BYTE,
|
||||
COGL_ATTRIBUTE_TYPE_SHORT = GL_SHORT,
|
||||
COGL_ATTRIBUTE_TYPE_UNSIGNED_SHORT = GL_UNSIGNED_SHORT,
|
||||
COGL_ATTRIBUTE_TYPE_FLOAT = GL_FLOAT
|
||||
} CoglAttributeType;
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_add:
|
||||
* @handle: A vertex buffer handle
|
||||
@ -111,10 +134,9 @@ cogl_vertex_buffer_get_n_vertices (CoglHandle handle);
|
||||
* the name can have a detail component, E.g.
|
||||
* "gl_Color::active" or "gl_Color::inactive"
|
||||
* @n_components: The number of components per attribute and must be 1,2,3 or 4
|
||||
* @gl_type: Specifies the data type of each component (GL_BYTE, GL_UNSIGNED_BYTE,
|
||||
* GL_SHORT, GL_UNSIGNED_SHORT, GL_INT, GL_UNSIGNED_INT or GL_FLOAT)
|
||||
* @type: a #CoglAttributeType specifying the data type of each component.
|
||||
* @normalized: If GL_TRUE, this specifies that values stored in an integer
|
||||
* format should be mapped into the range [-1.0, 1.0] or [0.1, 1.0]
|
||||
* format should be mapped into the range [-1.0, 1.0] or [0.0, 1.0]
|
||||
* for unsigned values. If GL_FALSE they are converted to floats
|
||||
* directly.
|
||||
* @stride: This specifies the number of bytes from the start of one attribute
|
||||
@ -156,13 +178,13 @@ cogl_vertex_buffer_get_n_vertices (CoglHandle handle);
|
||||
* (Though you can have multiple groups of interleved attributes)
|
||||
*/
|
||||
void
|
||||
cogl_vertex_buffer_add (CoglHandle handle,
|
||||
const char *attribute_name,
|
||||
guint8 n_components,
|
||||
GLenum gl_type,
|
||||
gboolean normalized,
|
||||
guint16 stride,
|
||||
const void *pointer);
|
||||
cogl_vertex_buffer_add (CoglHandle handle,
|
||||
const char *attribute_name,
|
||||
guint8 n_components,
|
||||
CoglAttributeType type,
|
||||
gboolean normalized,
|
||||
guint16 stride,
|
||||
const void *pointer);
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_delete:
|
||||
@ -226,21 +248,37 @@ void
|
||||
cogl_vertex_buffer_enable (CoglHandle handle,
|
||||
const char *attribute_name);
|
||||
|
||||
/**
|
||||
* CoglVerticesMode:
|
||||
* @COGL_VERTICES_MODE_POINTS: FIXME, equivalent to %GL_POINTS
|
||||
* @COGL_VERTICES_MODE_LINE_STRIP: FIXME, equivalent to %GL_LINE_STRIP
|
||||
* @COGL_VERTICES_MODE_LINE_LOOP: FIXME, equivalent to %GL_LINE_LOOP
|
||||
* @COGL_VERTICES_MODE_LINES: FIXME, equivalent to %GL_LINES
|
||||
* @COGL_VERTICES_MODE_TRIANGLE_STRIP: FIXME, equivalent to %GL_TRIANGLE_STRIP
|
||||
* @COGL_VERTICES_MODE_TRIANGLE_FAN: FIXME, equivalent to %GL_TRIANGLE_FAN
|
||||
* @COGL_VERTICES_MODE_TRIANGLES: FIXME, equivalent to %GL_TRIANGLES
|
||||
*
|
||||
* How vertices passed to cogl_vertex_buffer_draw() and
|
||||
* cogl_vertex_buffer_draw_elements() should be interpreted
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglVerticesMode
|
||||
{
|
||||
COGL_VERTICES_MODE_POINTS = GL_POINTS,
|
||||
COGL_VERTICES_MODE_LINE_STRIP = GL_LINE_STRIP,
|
||||
COGL_VERTICES_MODE_LINE_LOOP = GL_LINE_LOOP,
|
||||
COGL_VERTICES_MODE_LINES = GL_LINES,
|
||||
COGL_VERTICES_MODE_TRIANGLE_STRIP = GL_TRIANGLE_STRIP,
|
||||
COGL_VERTICES_MODE_TRIANGLE_FAN = GL_TRIANGLE_FAN,
|
||||
COGL_VERTICES_MODE_TRIANGLES = GL_TRIANGLES
|
||||
} CoglVerticesMode;
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_draw:
|
||||
* @handle: A vertex buffer handle
|
||||
* @mode: Specifies how the vertices should be interpreted, and should be
|
||||
* a valid GL primitive type:
|
||||
* <itemizedlist>
|
||||
* <listitem>GL_POINTS</listitem>
|
||||
* <listitem>GL_LINE_STRIP</listitem>
|
||||
* <listitem>GL_LINE_LOOP</listitem>
|
||||
* <listitem>GL_LINES</listitem>
|
||||
* <listitem>GL_TRIANGLE_STRIP</listitem>
|
||||
* <listitem>GL_TRIANGLE_FAN</listitem>
|
||||
* <listitem>GL_TRIANGLES</listitem>
|
||||
* </itemizedlist>
|
||||
* (Note: only types available in GLES are listed)
|
||||
* @mode: A #CoglVerticesMode specifying how the vertices should be
|
||||
* interpreted.
|
||||
* @first: Specifies the index of the first vertex you want to draw with
|
||||
* @count: Specifies the number of vertices you want to draw.
|
||||
*
|
||||
@ -251,52 +289,90 @@ cogl_vertex_buffer_enable (CoglHandle handle,
|
||||
* drawing.
|
||||
*/
|
||||
void
|
||||
cogl_vertex_buffer_draw (CoglHandle handle,
|
||||
GLenum mode,
|
||||
GLint first,
|
||||
GLsizei count);
|
||||
cogl_vertex_buffer_draw (CoglHandle handle,
|
||||
CoglVerticesMode mode,
|
||||
int first,
|
||||
int count);
|
||||
|
||||
/**
|
||||
* CoglIndicesType:
|
||||
* @COGL_INDICES_TYPE_UNSIGNED_BYTE: Your indices are unsigned bytes
|
||||
* @COGL_INDICES_TYPE_UNSIGNED_SHORT: Your indices are unsigned shorts
|
||||
* @COGL_INDICES_TYPE_UNSIGNED_INT: You indices are unsigned integers
|
||||
*
|
||||
* You should aim to use the smallest data type that gives you enough
|
||||
* range, since it reduces the size of your index array and can help
|
||||
* reduce the demand on memory bandwidth.
|
||||
*/
|
||||
typedef enum _CoglIndicesType
|
||||
{
|
||||
COGL_INDICES_TYPE_UNSIGNED_BYTE,
|
||||
COGL_INDICES_TYPE_UNSIGNED_SHORT,
|
||||
COGL_INDICES_TYPE_UNSIGNED_INT
|
||||
} CoglIndicesType;
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_indices_new:
|
||||
* @indices_type: a #CoglIndicesType specifying the data type used for
|
||||
* the indices.
|
||||
* @indices_array: Specifies the address of your array of indices
|
||||
* @indices_len: The number of indices in indices_array
|
||||
*
|
||||
* Depending on how much geometry you are submitting it can be worthwhile
|
||||
* optimizing the number of redundant vertices you submit. Using an index
|
||||
* array allows you to reference vertices multiple times, for example
|
||||
* during triangle strips.
|
||||
*
|
||||
* Returns: A CoglHandle for the indices which you can pass to
|
||||
* cogl_vertex_buffer_draw_elements().
|
||||
*/
|
||||
CoglHandle
|
||||
cogl_vertex_buffer_indices_new (CoglIndicesType indices_type,
|
||||
const void *indices_array,
|
||||
int indices_len);
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_delete_indices:
|
||||
* @handle: A vertex buffer handle
|
||||
* @indices_id: The identifier for a an array of indices previously added to
|
||||
* the given Cogl vertex buffer using
|
||||
* cogl_vertex_buffer_add_indices().
|
||||
*
|
||||
* Frees the resources associated with a previously added array of vertex
|
||||
* indices.
|
||||
*/
|
||||
void
|
||||
cogl_vertex_buffer_delete_indices (CoglHandle handle,
|
||||
int indices_id);
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_draw_elements:
|
||||
* @handle: A vertex buffer handle
|
||||
* @mode: Specifies how the vertices should be interpreted, and should be
|
||||
* a valid GL primitive type:
|
||||
* <itemizedlist>
|
||||
* <listitem>GL_POINTS</listitem>
|
||||
* <listitem>GL_LINE_STRIP</listitem>
|
||||
* <listitem>GL_LINE_LOOP</listitem>
|
||||
* <listitem>GL_LINES</listitem>
|
||||
* <listitem>GL_TRIANGLE_STRIP</listitem>
|
||||
* <listitem>GL_TRIANGLE_FAN</listitem>
|
||||
* <listitem>GL_TRIANGLES</listitem>
|
||||
* </itemizedlist>
|
||||
* (Note: only types available in GLES are listed)
|
||||
* @mode: A #CoglVerticesMode specifying how the vertices should be
|
||||
* interpreted.
|
||||
* @indices: A CoglHandle for a set of indices allocated via
|
||||
* cogl_vertex_buffer_indices_new ()
|
||||
* @min_index: Specifies the minimum vertex index contained in indices
|
||||
* @max_index: Specifies the maximum vertex index contained in indices
|
||||
* @indices_offset: An offset into named indices. The offset marks the first
|
||||
* index to use for drawing.
|
||||
* @count: Specifies the number of vertices you want to draw.
|
||||
* @indices_type: Specifies the data type used for the indices, and must be
|
||||
* one of:
|
||||
* <itemizedlist>
|
||||
* <listitem>GL_UNSIGNED_BYTE</listitem>
|
||||
* <listitem>GL_UNSIGNED_SHORT</listitem>
|
||||
* <listitem>GL_UNSIGNED_INT</listitem>
|
||||
* </itemizedlist>
|
||||
* @indices: Specifies the address of your array of indices
|
||||
*
|
||||
* This function lets you use an array of indices to specify the vertices
|
||||
* within your vertex buffer that you want to draw.
|
||||
* within your vertex buffer that you want to draw. The indices themselves
|
||||
* are created by calling cogl_vertex_buffer_indices_new ()
|
||||
*
|
||||
* Any un-submitted attribute changes are automatically submitted before
|
||||
* drawing.
|
||||
*/
|
||||
void
|
||||
cogl_vertex_buffer_draw_elements (CoglHandle handle,
|
||||
GLenum mode,
|
||||
GLuint min_index,
|
||||
GLuint max_index,
|
||||
GLsizei count,
|
||||
GLenum indices_type,
|
||||
const GLvoid *indices);
|
||||
cogl_vertex_buffer_draw_elements (CoglHandle handle,
|
||||
CoglVerticesMode mode,
|
||||
CoglHandle indices,
|
||||
int min_index,
|
||||
int max_index,
|
||||
int indices_offset,
|
||||
int count);
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_ref:
|
||||
@ -318,6 +394,46 @@ cogl_vertex_buffer_ref (CoglHandle handle);
|
||||
void
|
||||
cogl_vertex_buffer_unref (CoglHandle handle);
|
||||
|
||||
/**
|
||||
* cogl_vertex_buffer_indices_get_for_quads:
|
||||
* @n_indices: the number of indices in the vertex buffer.
|
||||
*
|
||||
* Creates a vertex buffer containing the indices needed to draw pairs
|
||||
* of triangles from a list of vertices grouped as quads. There will
|
||||
* be at least @n_indices entries in the buffer (but there may be
|
||||
* more).
|
||||
*
|
||||
* The indices will follow this pattern:
|
||||
*
|
||||
* 0, 1, 2, 0, 2, 3, 4, 5, 6, 4, 6, 7 ... etc
|
||||
*
|
||||
* For example, if you submit vertices for a quad like this:
|
||||
*
|
||||
* |[
|
||||
* 0 3
|
||||
* ########
|
||||
* # #
|
||||
* # #
|
||||
* ########
|
||||
* 1 2
|
||||
* ]|
|
||||
*
|
||||
* Then you can request 6 indices to render two triangles like this:
|
||||
*
|
||||
* |[
|
||||
* 0 0 3
|
||||
* ## ########
|
||||
* # ## ## #
|
||||
* # ## ## #
|
||||
* ######## ##
|
||||
* 1 2 2
|
||||
* ]|
|
||||
*
|
||||
* Returns: A %CoglHandle containing the indices. The handled is
|
||||
* owned by Cogl and should not be modified or unref'd.
|
||||
*/
|
||||
CoglHandle
|
||||
cogl_vertex_buffer_indices_get_for_quads (guint n_indices);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
125
cogl.h.in
125
cogl.h.in
@ -45,6 +45,7 @@
|
||||
#include <cogl/cogl-types.h>
|
||||
#include <cogl/cogl-debug.h>
|
||||
#include <cogl/cogl-deprecated.h>
|
||||
#include <cogl/cogl-enum-types.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@ -55,22 +56,6 @@ G_BEGIN_DECLS
|
||||
* General utility functions for COGL.
|
||||
*/
|
||||
|
||||
/* Context manipulation */
|
||||
|
||||
/**
|
||||
* cogl_create_context:
|
||||
*
|
||||
* FIXME
|
||||
*/
|
||||
gboolean cogl_create_context (void);
|
||||
|
||||
/**
|
||||
* cogl_destroy_context:
|
||||
*
|
||||
* FIXME
|
||||
*/
|
||||
void cogl_destroy_context (void);
|
||||
|
||||
/**
|
||||
* cogl_get_option_group:
|
||||
*
|
||||
@ -187,7 +172,30 @@ void cogl_frustum (float left,
|
||||
float z_far);
|
||||
|
||||
/**
|
||||
* cogl_setup_viewport:
|
||||
* cogl_ortho:
|
||||
* @left: The coordinate for the left clipping plane
|
||||
* @right: The coordinate for the right clipping plane
|
||||
* @bottom: The coordinate for the bottom clipping plane
|
||||
* @top: The coordinate for the top clipping plane
|
||||
* @near: The coordinate for the near clipping plane (may be negative if
|
||||
* the plane is behind the viewer)
|
||||
* @far: The coordinate for the far clipping plane (may be negative if
|
||||
* the plane is behind the viewer)
|
||||
*
|
||||
* Replaces the current projection matrix with a parallel projection
|
||||
* matrix.
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
void cogl_ortho (float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float near,
|
||||
float far);
|
||||
|
||||
/*
|
||||
* _cogl_setup_viewport:
|
||||
* @width: Width of the viewport
|
||||
* @height: Height of the viewport
|
||||
* @fovy: Field of view angle in degrees
|
||||
@ -201,9 +209,11 @@ void cogl_frustum (float left,
|
||||
* with one that has a viewing angle of @fovy along the y-axis and a
|
||||
* view scaled according to @aspect along the x-axis. The view is
|
||||
* clipped according to @z_near and @z_far on the z-axis.
|
||||
*
|
||||
* This function is used only by Clutter.
|
||||
*/
|
||||
void cogl_setup_viewport (guint width,
|
||||
guint height,
|
||||
void _cogl_setup_viewport (guint width,
|
||||
guint height,
|
||||
float fovy,
|
||||
float aspect,
|
||||
float z_near,
|
||||
@ -288,6 +298,14 @@ void cogl_rotate (float angle,
|
||||
*/
|
||||
void cogl_get_modelview_matrix (CoglMatrix *matrix);
|
||||
|
||||
/**
|
||||
* cogl_set_modelview_matrix:
|
||||
* @matrix: pointer to a CoglMatrix to set as the new model-view matrix
|
||||
*
|
||||
* Loads matrix as the new model-view matrix.
|
||||
*/
|
||||
void cogl_set_modelview_matrix (CoglMatrix *matrix);
|
||||
|
||||
/**
|
||||
* cogl_get_projection_matrix:
|
||||
* @matrix: pointer to a CoglMatrix to recieve the matrix
|
||||
@ -296,6 +314,14 @@ void cogl_get_modelview_matrix (CoglMatrix *matrix);
|
||||
*/
|
||||
void cogl_get_projection_matrix (CoglMatrix *matrix);
|
||||
|
||||
/**
|
||||
* cogl_set_projection_matrix:
|
||||
* @matrix: pointer to a CoglMatrix to set as the new projection matrix
|
||||
*
|
||||
* Loads matrix as the new projection matrix.
|
||||
*/
|
||||
void cogl_set_projection_matrix (CoglMatrix *matrix);
|
||||
|
||||
/**
|
||||
* cogl_get_viewport:
|
||||
* @v: pointer to a 4 element array of #float<!-- -->s to
|
||||
@ -308,7 +334,7 @@ void cogl_get_projection_matrix (CoglMatrix *matrix);
|
||||
void cogl_get_viewport (float v[4]);
|
||||
|
||||
/**
|
||||
* cogl_enable_depth_test:
|
||||
* cogl_set_depth_test_enable:
|
||||
* @setting: %TRUE to enable depth testing or %FALSE to disable.
|
||||
*
|
||||
* Sets whether depth testing is enabled. If it is disabled then the
|
||||
@ -317,10 +343,19 @@ void cogl_get_viewport (float v[4]);
|
||||
* clutter_actor_lower(), otherwise it will also take into account the
|
||||
* actor's depth. Depth testing is disabled by default.
|
||||
*/
|
||||
void cogl_enable_depth_test (gboolean setting);
|
||||
void cogl_set_depth_test_enable (gboolean setting);
|
||||
|
||||
/**
|
||||
* cogl_enable_backface_culling:
|
||||
* cogl_get_depth_test_enable:
|
||||
*
|
||||
* Queries if depth testing has been enabled via cogl_set_depth_test_enable()
|
||||
*
|
||||
* Returns: TRUE if depth testing is enabled else FALSE
|
||||
*/
|
||||
gboolean cogl_get_depth_test_enable (void);
|
||||
|
||||
/**
|
||||
* cogl_set_backface_culling_enabled:
|
||||
* @setting: %TRUE to enable backface culling or %FALSE to disable.
|
||||
*
|
||||
* Sets whether textures positioned so that their backface is showing
|
||||
@ -329,7 +364,17 @@ void cogl_enable_depth_test (gboolean setting);
|
||||
* only affects calls to the cogl_rectangle* family of functions and
|
||||
* cogl_vertex_buffer_draw*. Backface culling is disabled by default.
|
||||
*/
|
||||
void cogl_enable_backface_culling (gboolean setting);
|
||||
void cogl_set_backface_culling_enabled (gboolean setting);
|
||||
|
||||
/**
|
||||
* cogl_get_backface_culling_enabled:
|
||||
*
|
||||
* Queries if backface culling has been enabled via
|
||||
* cogl_set_backface_culling_enabled()
|
||||
*
|
||||
* Returns: TRUE if backface culling is enabled else FALSE
|
||||
*/
|
||||
gboolean cogl_get_backface_culling_enabled (void);
|
||||
|
||||
/**
|
||||
* cogl_set_fog:
|
||||
@ -368,9 +413,12 @@ void cogl_disable_fog (void);
|
||||
* @COGL_BUFFER_BIT_COLOR: Selects the primary color buffer
|
||||
* @COGL_BUFFER_BIT_DEPTH: Selects the depth buffer
|
||||
* @COGL_BUFFER_BIT_STENCIL: Selects the stencil buffer
|
||||
*
|
||||
* Types of auxiliary buffers
|
||||
*
|
||||
* Since: 1.0
|
||||
*/
|
||||
typedef enum _CoglBufferBit
|
||||
{
|
||||
typedef enum {
|
||||
COGL_BUFFER_BIT_COLOR = 1L<<0,
|
||||
COGL_BUFFER_BIT_DEPTH = 1L<<1,
|
||||
COGL_BUFFER_BIT_STENCIL = 1L<<2
|
||||
@ -379,13 +427,14 @@ typedef enum _CoglBufferBit
|
||||
/**
|
||||
* cogl_clear:
|
||||
* @color: Background color to clear to
|
||||
* @buffers: A mask of @CoglBufferBit<!-- -->'s identifying which auxiliary
|
||||
* buffers to clear
|
||||
* @buffers: A mask of #CoglBufferBit<!-- -->'s identifying which auxiliary
|
||||
* buffers to clear
|
||||
*
|
||||
* Clears all the auxiliary buffers identified in the @buffers mask, and if
|
||||
* that includes the color buffer then the specified @color is used.
|
||||
*/
|
||||
void cogl_clear (const CoglColor *color, gulong buffers);
|
||||
void cogl_clear (const CoglColor *color,
|
||||
gulong buffers);
|
||||
|
||||
/**
|
||||
* cogl_set_source:
|
||||
@ -628,7 +677,24 @@ void cogl_push_draw_buffer (void);
|
||||
*/
|
||||
void cogl_pop_draw_buffer (void);
|
||||
|
||||
/**
|
||||
|
||||
/*
|
||||
* Internal API available only to Clutter.
|
||||
*
|
||||
* These are typically only to deal with the poor seperation of
|
||||
* responsabilities that currently exists between Clutter and Cogl.
|
||||
* Eventually a lot of the backend code currently in Clutter will
|
||||
* move down into Cogl and these functions will be removed.
|
||||
*/
|
||||
|
||||
void _cogl_destroy_context (void);
|
||||
|
||||
/* XXX: Removed before we release Clutter 1.0 since the implementation
|
||||
* wasn't complete, and so we assume no one is using this yet. Util we
|
||||
* have some one with a good usecase, we can't pretend to support breaking
|
||||
* out into raw OpenGL. */
|
||||
#if 0
|
||||
/*
|
||||
* cogl_flush_gl_state:
|
||||
* @flags: flags controlling what is flushed; currently unused, pass in 0
|
||||
*
|
||||
@ -642,6 +708,7 @@ void cogl_pop_draw_buffer (void);
|
||||
* Since: 1.0
|
||||
*/
|
||||
void cogl_flush_gl_state (int flags);
|
||||
#endif
|
||||
|
||||
/* private */
|
||||
void _cogl_set_indirect_context (gboolean indirect);
|
||||
|
@ -1,3 +1,10 @@
|
||||
NULL =
|
||||
|
||||
V = @
|
||||
Q = $(V:1=)
|
||||
QUIET_GEN = $(Q:@=@echo ' GEN '$@;)
|
||||
QUIET_CP = $(Q:@=@echo ' CP '$@;)
|
||||
|
||||
INCLUDES = \
|
||||
-I$(top_srcdir) \
|
||||
-I$(top_srcdir)/clutter \
|
||||
@ -9,12 +16,49 @@ INCLUDES = \
|
||||
-DG_LOG_DOMAIN=\"Cogl-Common\" \
|
||||
-DCLUTTER_COMPILATION
|
||||
|
||||
cogl_public_h = \
|
||||
$(top_srcdir)/clutter/cogl/cogl-bitmap.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-color.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-debug.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-fixed.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-material.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-matrix.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-offscreen.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-path.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-shader.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-texture.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-types.h \
|
||||
$(top_srcdir)/clutter/cogl/cogl-vertex-buffer.h \
|
||||
$(top_builddir)/clutter/cogl/cogl.h \
|
||||
$(NULL)
|
||||
|
||||
noinst_LTLIBRARIES = libclutter-cogl-common.la
|
||||
EXTRA_DIST = stb_image.c
|
||||
|
||||
cogl-enum-types.h: stamp-cogl-enum-types.h
|
||||
@true
|
||||
stamp-cogl-enum-types.h: $(cogl_public_h) Makefile
|
||||
$(QUIET_GEN)( $(GLIB_MKENUMS) \
|
||||
--template $(srcdir)/cogl-enum-types.h.in \
|
||||
$(cogl_public_h) ) > xgen-ceth \
|
||||
&& (cmp -s xgen-ceth cogl-enum-types.h || cp -f xgen-ceth cogl-enum-types.h) \
|
||||
&& cp -f cogl-enum-types.h $(top_builddir)/clutter/cogl/cogl-enum-types.h \
|
||||
&& rm -f xgen-ceth \
|
||||
&& echo timestamp > $(@F)
|
||||
|
||||
cogl-enum-types.c: cogl-enum-types.h
|
||||
$(QUIET_GEN)( $(GLIB_MKENUMS) \
|
||||
--template $(srcdir)/cogl-enum-types.c.in \
|
||||
$(cogl_public_h) ) > xgen-cetc \
|
||||
&& cp -f xgen-cetc cogl-enum-types.c \
|
||||
&& rm -f xgen-cetc
|
||||
|
||||
BUILT_SOURCES = cogl-enum-types.h cogl-enum-types.c
|
||||
|
||||
libclutter_cogl_common_la_CPPFLAGS = $(CLUTTER_CFLAGS) $(COGL_DEBUG_CFLAGS) $(CLUTTER_DEBUG_CFLAGS) $(MAINTAINER_CFLAGS)
|
||||
libclutter_cogl_common_la_LIBADD = -lm $(CLUTTER_LIBS)
|
||||
libclutter_cogl_common_la_SOURCES = \
|
||||
$(top_builddir)/clutter/cogl/common/cogl-enum-types.h \
|
||||
$(top_builddir)/clutter/cogl/common/cogl-enum-types.c \
|
||||
cogl-handle.h \
|
||||
cogl-internal.h \
|
||||
cogl.c \
|
||||
@ -39,4 +83,11 @@ libclutter_cogl_common_la_SOURCES = \
|
||||
cogl-matrix-stack.h \
|
||||
cogl-material.c \
|
||||
cogl-material-private.h \
|
||||
cogl-debug.c
|
||||
cogl-blend-string.c \
|
||||
cogl-blend-string.h \
|
||||
cogl-debug.c \
|
||||
$(NULL)
|
||||
|
||||
EXTRA_DIST = stb_image.c cogl-enum-types.h.in cogl-enum-types.c.in
|
||||
CLEANFILES = stamp-cogl-enum-types.h
|
||||
DISTCLEANFILES = cogl-enum-types.h cogl-enum-types.c
|
||||
|
999
common/cogl-blend-string.c
Normal file
999
common/cogl-blend-string.c
Normal file
@ -0,0 +1,999 @@
|
||||
/*
|
||||
* Cogl
|
||||
*
|
||||
* An object oriented GL/GLES Abstraction/Utility Layer
|
||||
*
|
||||
* Copyright (C) 2009 Intel Corporation.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*
|
||||
* Authors:
|
||||
* Robert Bragg <robert@linux.intel.com>
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <glib.h>
|
||||
|
||||
#include "cogl.h"
|
||||
#include "cogl-internal.h"
|
||||
#include "cogl-context.h"
|
||||
#include "cogl-debug.h"
|
||||
#include "cogl-blend-string.h"
|
||||
|
||||
typedef enum _ParserState
|
||||
{
|
||||
PARSER_STATE_EXPECT_DEST_CHANNELS,
|
||||
PARSER_STATE_SCRAPING_DEST_CHANNELS,
|
||||
PARSER_STATE_EXPECT_FUNCTION_NAME,
|
||||
PARSER_STATE_SCRAPING_FUNCTION_NAME,
|
||||
PARSER_STATE_EXPECT_ARG_START,
|
||||
PARSER_STATE_EXPECT_STATEMENT_END
|
||||
} ParserState;
|
||||
|
||||
typedef enum _ParserArgState
|
||||
{
|
||||
PARSER_ARG_STATE_START,
|
||||
PARSER_ARG_STATE_EXPECT_MINUS,
|
||||
PARSER_ARG_STATE_EXPECT_COLOR_SRC_NAME,
|
||||
PARSER_ARG_STATE_SCRAPING_COLOR_SRC_NAME,
|
||||
PARSER_ARG_STATE_MAYBE_COLOR_MASK,
|
||||
PARSER_ARG_STATE_SCRAPING_MASK,
|
||||
PARSER_ARG_STATE_MAYBE_MULT,
|
||||
PARSER_ARG_STATE_EXPECT_OPEN_PAREN,
|
||||
PARSER_ARG_STATE_EXPECT_FACTOR,
|
||||
PARSER_ARG_STATE_MAYBE_SRC_ALPHA_SATURATE,
|
||||
PARSER_ARG_STATE_MAYBE_MINUS,
|
||||
PARSER_ARG_STATE_EXPECT_CLOSE_PAREN,
|
||||
PARSER_ARG_STATE_EXPECT_END
|
||||
} ParserArgState;
|
||||
|
||||
|
||||
#define DEFINE_COLOR_SOURCE(NAME, NAME_LEN) \
|
||||
{.type = COGL_BLEND_STRING_COLOR_SOURCE_ ## NAME, \
|
||||
.name = #NAME, \
|
||||
.name_len = NAME_LEN}
|
||||
|
||||
static CoglBlendStringColorSourceInfo blending_color_sources[] = {
|
||||
DEFINE_COLOR_SOURCE (SRC_COLOR, 9),
|
||||
DEFINE_COLOR_SOURCE (DST_COLOR, 9),
|
||||
DEFINE_COLOR_SOURCE (CONSTANT, 8)
|
||||
};
|
||||
|
||||
static CoglBlendStringColorSourceInfo tex_combine_color_sources[] = {
|
||||
DEFINE_COLOR_SOURCE (TEXTURE, 7),
|
||||
/* DEFINE_COLOR_SOURCE (TEXTURE_N, *) - handled manually */
|
||||
DEFINE_COLOR_SOURCE (PRIMARY, 7),
|
||||
DEFINE_COLOR_SOURCE (CONSTANT, 8),
|
||||
DEFINE_COLOR_SOURCE (PREVIOUS, 8)
|
||||
};
|
||||
|
||||
static CoglBlendStringColorSourceInfo tex_combine_texture_n_color_source = {
|
||||
.type = COGL_BLEND_STRING_COLOR_SOURCE_TEXTURE_N,
|
||||
.name = "TEXTURE_N",
|
||||
.name_len = 0
|
||||
};
|
||||
|
||||
#undef DEFINE_COLOR_SOURCE
|
||||
|
||||
#define DEFINE_FUNCTION(NAME, NAME_LEN, ARGC) \
|
||||
{ .type = COGL_BLEND_STRING_FUNCTION_ ## NAME, \
|
||||
.name = #NAME, \
|
||||
.name_len = NAME_LEN, \
|
||||
.argc = ARGC }
|
||||
|
||||
/* NB: These must be sorted so any name that's a subset of another
|
||||
* comes later than the longer name. */
|
||||
static CoglBlendStringFunctionInfo tex_combine_functions[] = {
|
||||
DEFINE_FUNCTION (AUTO_COMPOSITE, 14, 0),
|
||||
DEFINE_FUNCTION (REPLACE, 7, 1),
|
||||
DEFINE_FUNCTION (MODULATE, 8, 2),
|
||||
DEFINE_FUNCTION (ADD_SIGNED, 10, 2),
|
||||
DEFINE_FUNCTION (ADD, 3, 2),
|
||||
DEFINE_FUNCTION (INTERPOLATE, 11, 3),
|
||||
DEFINE_FUNCTION (SUBTRACT, 8, 2),
|
||||
DEFINE_FUNCTION (DOT3_RGBA, 9, 2),
|
||||
DEFINE_FUNCTION (DOT3_RGB, 8, 2)
|
||||
};
|
||||
|
||||
static CoglBlendStringFunctionInfo blend_functions[] = {
|
||||
DEFINE_FUNCTION (AUTO_COMPOSITE, 14, 0),
|
||||
DEFINE_FUNCTION (ADD, 3, 2)
|
||||
};
|
||||
|
||||
#undef DEFINE_FUNCTION
|
||||
|
||||
GQuark
|
||||
_cogl_blend_string_error_quark (void)
|
||||
{
|
||||
return g_quark_from_static_string ("cogl-blend-string-error-quark");
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_blend_string_split_rgba_statement (CoglBlendStringStatement *statement,
|
||||
CoglBlendStringStatement *rgb,
|
||||
CoglBlendStringStatement *a)
|
||||
{
|
||||
int i;
|
||||
|
||||
memcpy (rgb, statement, sizeof (CoglBlendStringStatement));
|
||||
memcpy (a, statement, sizeof (CoglBlendStringStatement));
|
||||
|
||||
rgb->mask = COGL_BLEND_STRING_CHANNEL_MASK_RGB;
|
||||
a->mask = COGL_BLEND_STRING_CHANNEL_MASK_ALPHA;
|
||||
|
||||
for (i = 0; i < statement->function->argc; i++)
|
||||
{
|
||||
CoglBlendStringArgument *arg = &statement->args[i];
|
||||
CoglBlendStringArgument *rgb_arg = &rgb->args[i];
|
||||
CoglBlendStringArgument *a_arg = &a->args[i];
|
||||
|
||||
if (arg->source.mask == COGL_BLEND_STRING_CHANNEL_MASK_RGBA)
|
||||
{
|
||||
rgb_arg->source.mask = COGL_BLEND_STRING_CHANNEL_MASK_RGB;
|
||||
a_arg->source.mask = COGL_BLEND_STRING_CHANNEL_MASK_ALPHA;
|
||||
}
|
||||
|
||||
if (arg->factor.is_color &&
|
||||
arg->factor.source.mask == COGL_BLEND_STRING_CHANNEL_MASK_RGBA)
|
||||
{
|
||||
rgb_arg->factor.source.mask = COGL_BLEND_STRING_CHANNEL_MASK_RGB;
|
||||
a_arg->factor.source.mask = COGL_BLEND_STRING_CHANNEL_MASK_ALPHA;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean
|
||||
validate_tex_combine_statements (CoglBlendStringStatement *statements,
|
||||
int n_statements,
|
||||
GError **error)
|
||||
{
|
||||
int i, j;
|
||||
const char *error_string;
|
||||
CoglBlendStringError detail = COGL_BLEND_STRING_ERROR_INVALID_ERROR;
|
||||
|
||||
for (i = 0; i < n_statements; i++)
|
||||
{
|
||||
#ifdef HAVE_COGL_GLES2
|
||||
if (statements[i].function->type != COGL_BLEND_STRING_FUNCTION_MODULATE)
|
||||
{
|
||||
error_string = "Using anything but MODULATE() for texture combining"
|
||||
" under GLES 2 is currently unsupported";
|
||||
detail = COGL_BLEND_STRING_ERROR_GPU_UNSUPPORTED_ERROR;
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
for (j = 0; j < statements[i].function->argc; j++)
|
||||
{
|
||||
CoglBlendStringArgument *arg = &statements[i].args[j];
|
||||
if (arg->source.is_zero)
|
||||
{
|
||||
error_string = "You can't use the constant '0' as a texture "
|
||||
"combine argument";
|
||||
goto error;
|
||||
}
|
||||
if (!arg->factor.is_one)
|
||||
{
|
||||
error_string = "Argument factors are only relevant to blending "
|
||||
"not texture combining";
|
||||
goto error;
|
||||
}
|
||||
#ifdef HAVE_COGL_GLES2
|
||||
if (arg->source.info->type == COGL_BLEND_STRING_COLOR_SOURCE_CONSTANT)
|
||||
{
|
||||
error_string = "Using a constant for texture combining isn't "
|
||||
"currently supported with GLES 2 "
|
||||
"(TODO: glTexEnvf)";
|
||||
detail = COGL_BLEND_STRING_ERROR_GPU_UNSUPPORTED_ERROR;
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
|
||||
error:
|
||||
g_set_error (error,
|
||||
COGL_BLEND_STRING_ERROR,
|
||||
detail,
|
||||
"Invalid texture combine string: %s",
|
||||
error_string);
|
||||
|
||||
if (cogl_debug_flags & COGL_DEBUG_BLEND_STRINGS)
|
||||
{
|
||||
g_debug ("Invalid texture combine string: %s",
|
||||
error_string);
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
validate_blend_statements (CoglBlendStringStatement *statements,
|
||||
int n_statements,
|
||||
GError **error)
|
||||
{
|
||||
int i, j;
|
||||
const char *error_string;
|
||||
CoglBlendStringError detail = COGL_BLEND_STRING_ERROR_INVALID_ERROR;
|
||||
|
||||
#ifdef HAVE_COGL_GL
|
||||
_COGL_GET_CONTEXT (ctx, 0);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_COGL_GL
|
||||
if (n_statements == 2)
|
||||
{
|
||||
/* glBlendEquationSeperate is GL 2.0 only */
|
||||
if (!ctx->pf_glBlendEquationSeparate &&
|
||||
statements[0].function->type != statements[1].function->type)
|
||||
{
|
||||
error_string = "Separate blend functions for the RGB an A "
|
||||
"channels isn't supported by the driver";
|
||||
detail = COGL_BLEND_STRING_ERROR_GPU_UNSUPPORTED_ERROR;
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
#elif defined(HAVE_COGL_GLES)
|
||||
if (n_statements != 1)
|
||||
{
|
||||
error_string = "Separate blend functions for the RGB an A "
|
||||
"channels isn't supported by the GLES 1";
|
||||
detail = COGL_BLEND_STRING_ERROR_GPU_UNSUPPORTED_ERROR;
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
|
||||
for (i = 0; i < n_statements; i++)
|
||||
for (j = 0; j < statements[i].function->argc; j++)
|
||||
{
|
||||
CoglBlendStringArgument *arg = &statements[i].args[j];
|
||||
|
||||
if (arg->source.is_zero)
|
||||
continue;
|
||||
|
||||
if ((j == 0 &&
|
||||
arg->source.info->type !=
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_SRC_COLOR)
|
||||
|| (j == 1 &&
|
||||
arg->source.info->type !=
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_DST_COLOR))
|
||||
{
|
||||
error_string = "For blending you must always use SRC_COLOR "
|
||||
"for arg0 and DST_COLOR for arg1";
|
||||
goto error;
|
||||
}
|
||||
|
||||
#ifdef HAVE_COGL_GLES
|
||||
if (arg->factor.is_color &&
|
||||
arg->factor.source.info->type == COGL_BLEND_STRING_COLOR_SOURCE_CONSTANT)
|
||||
{
|
||||
error_string = "GLES Doesn't support constant blend factors";
|
||||
detail = COGL_BLEND_STRING_ERROR_GPU_UNSUPPORTED_ERROR;
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
|
||||
error:
|
||||
g_set_error (error,
|
||||
COGL_BLEND_STRING_ERROR,
|
||||
detail,
|
||||
"Invalid blend string: %s",
|
||||
error_string);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
validate_statements_for_context (CoglBlendStringStatement *statements,
|
||||
int n_statements,
|
||||
CoglBlendStringContext context,
|
||||
GError **error)
|
||||
{
|
||||
const char *error_string;
|
||||
|
||||
if (n_statements == 1)
|
||||
{
|
||||
if (statements[0].mask == COGL_BLEND_STRING_CHANNEL_MASK_ALPHA)
|
||||
{
|
||||
error_string = "You need to also give a blend statement for the RGB"
|
||||
"channels";
|
||||
goto error;
|
||||
}
|
||||
else if (statements[0].mask == COGL_BLEND_STRING_CHANNEL_MASK_RGB)
|
||||
{
|
||||
error_string = "You need to also give a blend statement for the "
|
||||
"Alpha channel";
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
if (context == COGL_BLEND_STRING_CONTEXT_BLENDING)
|
||||
return validate_blend_statements (statements, n_statements, error);
|
||||
else
|
||||
return validate_tex_combine_statements (statements, n_statements, error);
|
||||
|
||||
error:
|
||||
g_set_error (error,
|
||||
COGL_BLEND_STRING_ERROR,
|
||||
COGL_BLEND_STRING_ERROR_INVALID_ERROR,
|
||||
"Invalid %s string: %s",
|
||||
context == COGL_BLEND_STRING_CONTEXT_BLENDING ?
|
||||
"blend" : "texture combine",
|
||||
error_string);
|
||||
|
||||
if (cogl_debug_flags & COGL_DEBUG_BLEND_STRINGS)
|
||||
{
|
||||
g_debug ("Invalid %s string: %s",
|
||||
context == COGL_BLEND_STRING_CONTEXT_BLENDING ?
|
||||
"blend" : "texture combine",
|
||||
error_string);
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static void
|
||||
print_argument (CoglBlendStringArgument *arg)
|
||||
{
|
||||
const char *mask_names[] = {
|
||||
"RGB",
|
||||
"A",
|
||||
"RGBA"
|
||||
};
|
||||
|
||||
g_print (" Arg:\n");
|
||||
g_print (" is zero = %s\n", arg->source.is_zero ? "yes" : "no");
|
||||
if (!arg->source.is_zero)
|
||||
{
|
||||
g_print (" color source = %s\n", arg->source.info->name);
|
||||
g_print (" one minus = %s\n", arg->source.one_minus ? "yes" : "no");
|
||||
g_print (" mask = %s\n", mask_names[arg->source.mask]);
|
||||
g_print (" texture = %d\n", arg->source.texture);
|
||||
g_print ("\n");
|
||||
g_print (" factor is_one = %s\n", arg->factor.is_one ? "yes" : "no");
|
||||
g_print (" factor is_src_alpha_saturate = %s\n",
|
||||
arg->factor.is_src_alpha_saturate ? "yes" : "no");
|
||||
g_print (" factor is_color = %s\n", arg->factor.is_color ? "yes" : "no");
|
||||
if (arg->factor.is_color)
|
||||
{
|
||||
g_print (" factor color:is zero = %s\n",
|
||||
arg->factor.source.is_zero ? "yes" : "no");
|
||||
g_print (" factor color:color source = %s\n",
|
||||
arg->factor.source.info->name);
|
||||
g_print (" factor color:one minus = %s\n",
|
||||
arg->factor.source.one_minus ? "yes" : "no");
|
||||
g_print (" factor color:mask = %s\n",
|
||||
mask_names[arg->factor.source.mask]);
|
||||
g_print (" factor color:texture = %d\n",
|
||||
arg->factor.source.texture);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
print_statement (int num, CoglBlendStringStatement *statement)
|
||||
{
|
||||
const char *mask_names[] = {
|
||||
"RGB",
|
||||
"A",
|
||||
"RGBA"
|
||||
};
|
||||
int i;
|
||||
g_print ("Statement %d:\n", num);
|
||||
g_print (" Destination channel mask = %s\n",
|
||||
mask_names[statement->mask]);
|
||||
g_print (" Function = %s\n", statement->function->name);
|
||||
for (i = 0; i < statement->function->argc; i++)
|
||||
print_argument (&statement->args[i]);
|
||||
}
|
||||
|
||||
static const CoglBlendStringFunctionInfo *
|
||||
get_function_info (const char *mark,
|
||||
const char *p,
|
||||
CoglBlendStringContext context)
|
||||
{
|
||||
size_t len = p - mark;
|
||||
CoglBlendStringFunctionInfo *functions;
|
||||
size_t array_len;
|
||||
int i;
|
||||
|
||||
if (context == COGL_BLEND_STRING_CONTEXT_BLENDING)
|
||||
{
|
||||
functions = blend_functions;
|
||||
array_len = G_N_ELEMENTS (blend_functions);
|
||||
}
|
||||
else
|
||||
{
|
||||
functions = tex_combine_functions;
|
||||
array_len = G_N_ELEMENTS (tex_combine_functions);
|
||||
}
|
||||
|
||||
for (i = 0; i < array_len; i++)
|
||||
{
|
||||
if (len >= functions[i].name_len
|
||||
&& strncmp (mark, functions[i].name, functions[i].name_len) == 0)
|
||||
return &functions[i];
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static const CoglBlendStringColorSourceInfo *
|
||||
get_color_src_info (const char *mark,
|
||||
const char *p,
|
||||
CoglBlendStringContext context)
|
||||
{
|
||||
size_t len = p - mark;
|
||||
CoglBlendStringColorSourceInfo *sources;
|
||||
size_t array_len;
|
||||
int i;
|
||||
|
||||
if (context == COGL_BLEND_STRING_CONTEXT_BLENDING)
|
||||
{
|
||||
sources = blending_color_sources;
|
||||
array_len = G_N_ELEMENTS (blending_color_sources);
|
||||
}
|
||||
else
|
||||
{
|
||||
sources = tex_combine_color_sources;
|
||||
array_len = G_N_ELEMENTS (tex_combine_color_sources);
|
||||
}
|
||||
|
||||
for (i = 0; i < array_len; i++)
|
||||
{
|
||||
if (len >= sources[i].name_len
|
||||
&& strncmp (mark, sources[i].name, sources[i].name_len) == 0)
|
||||
return &sources[i];
|
||||
}
|
||||
|
||||
if (len >= 9 &&
|
||||
strncmp (mark, "TEXTURE_", 8) == 0 &&
|
||||
g_ascii_isdigit (mark[8]))
|
||||
{
|
||||
return &tex_combine_texture_n_color_source;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
is_symbol_char (const char c)
|
||||
{
|
||||
return (g_ascii_isalpha (c) || c == '_') ? TRUE : FALSE;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
parse_argument (const char *string, /* original user string */
|
||||
const char **ret_p, /* start of argument IN:OUT */
|
||||
const CoglBlendStringStatement *statement,
|
||||
int current_arg,
|
||||
CoglBlendStringArgument *arg, /* OUT */
|
||||
CoglBlendStringContext context,
|
||||
GError **error)
|
||||
{
|
||||
const char *p = *ret_p;
|
||||
const char *mark;
|
||||
const char *error_string;
|
||||
ParserArgState state = PARSER_ARG_STATE_START;
|
||||
gboolean parsing_factor = FALSE;
|
||||
|
||||
arg->source.is_zero = FALSE;
|
||||
arg->source.info = NULL;
|
||||
arg->source.texture = 0;
|
||||
arg->source.one_minus = FALSE;
|
||||
arg->source.mask = statement->mask;
|
||||
|
||||
arg->factor.is_one = FALSE;
|
||||
arg->factor.is_color = FALSE;
|
||||
arg->factor.is_src_alpha_saturate = FALSE;
|
||||
|
||||
arg->factor.source.is_zero = FALSE;
|
||||
arg->factor.source.info = NULL;
|
||||
arg->factor.source.texture = 0;
|
||||
arg->factor.source.one_minus = FALSE;
|
||||
arg->factor.source.mask = statement->mask;
|
||||
|
||||
do
|
||||
{
|
||||
if (g_ascii_isspace (*p))
|
||||
continue;
|
||||
|
||||
if (*p == '\0')
|
||||
{
|
||||
error_string = "Unexpected end of string while parsing argument";
|
||||
goto error;
|
||||
}
|
||||
|
||||
switch (state)
|
||||
{
|
||||
case PARSER_ARG_STATE_START:
|
||||
if (*p == '1')
|
||||
state = PARSER_ARG_STATE_EXPECT_MINUS;
|
||||
else if (*p == '0')
|
||||
{
|
||||
arg->source.is_zero = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_END;
|
||||
}
|
||||
else
|
||||
{
|
||||
p--; /* backtrack */
|
||||
state = PARSER_ARG_STATE_EXPECT_COLOR_SRC_NAME;
|
||||
}
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_EXPECT_MINUS:
|
||||
if (*p != '-')
|
||||
{
|
||||
error_string = "expected a '-' following the 1";
|
||||
goto error;
|
||||
}
|
||||
arg->source.one_minus = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_COLOR_SRC_NAME;
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_EXPECT_COLOR_SRC_NAME:
|
||||
if (!is_symbol_char (*p))
|
||||
{
|
||||
error_string = "expected a color source name";
|
||||
goto error;
|
||||
}
|
||||
state = PARSER_ARG_STATE_SCRAPING_COLOR_SRC_NAME;
|
||||
mark = p;
|
||||
if (parsing_factor)
|
||||
arg->factor.is_color = TRUE;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_ARG_STATE_SCRAPING_COLOR_SRC_NAME:
|
||||
if (!is_symbol_char (*p))
|
||||
{
|
||||
CoglBlendStringColorSource *source =
|
||||
parsing_factor ? &arg->factor.source : &arg->source;
|
||||
source->info = get_color_src_info (mark, p, context);
|
||||
if (!source->info)
|
||||
{
|
||||
error_string = "Unknown color source name";
|
||||
goto error;
|
||||
}
|
||||
if (source->info->type ==
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_TEXTURE_N)
|
||||
{
|
||||
char *endp;
|
||||
source->texture =
|
||||
strtoul (&mark[strlen ("TEXTURE_")], &endp, 10);
|
||||
if (mark == endp)
|
||||
{
|
||||
error_string = "invalid texture number given with "
|
||||
"TEXTURE_N color source";
|
||||
goto error;
|
||||
}
|
||||
p = endp;
|
||||
}
|
||||
state = PARSER_ARG_STATE_MAYBE_COLOR_MASK;
|
||||
}
|
||||
else
|
||||
continue;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_ARG_STATE_MAYBE_COLOR_MASK:
|
||||
if (*p != '[')
|
||||
{
|
||||
p--; /* backtrack */
|
||||
if (!parsing_factor)
|
||||
state = PARSER_ARG_STATE_MAYBE_MULT;
|
||||
else
|
||||
state = PARSER_ARG_STATE_EXPECT_END;
|
||||
continue;
|
||||
}
|
||||
state = PARSER_ARG_STATE_SCRAPING_MASK;
|
||||
mark = p;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_ARG_STATE_SCRAPING_MASK:
|
||||
if (*p == ']')
|
||||
{
|
||||
size_t len = p - mark;
|
||||
CoglBlendStringColorSource *source =
|
||||
parsing_factor ? &arg->factor.source : &arg->source;
|
||||
|
||||
if (len == 5 && strncmp (mark, "[RGBA", len) == 0)
|
||||
{
|
||||
if (statement->mask != COGL_BLEND_STRING_CHANNEL_MASK_RGBA)
|
||||
{
|
||||
error_string = "You can't use an RGBA color mask if the "
|
||||
"statement hasn't also got an RGBA= mask";
|
||||
goto error;
|
||||
}
|
||||
source->mask = COGL_BLEND_STRING_CHANNEL_MASK_RGBA;
|
||||
}
|
||||
else if (len == 4 && strncmp (mark, "[RGB", len) == 0)
|
||||
source->mask = COGL_BLEND_STRING_CHANNEL_MASK_RGB;
|
||||
else if (len == 2 && strncmp (mark, "[A", len) == 0)
|
||||
source->mask = COGL_BLEND_STRING_CHANNEL_MASK_ALPHA;
|
||||
else
|
||||
{
|
||||
error_string = "Expected a channel mask of [RGBA]"
|
||||
"[RGB] or [A]";
|
||||
goto error;
|
||||
}
|
||||
if (parsing_factor)
|
||||
state = PARSER_ARG_STATE_EXPECT_CLOSE_PAREN;
|
||||
else
|
||||
state = PARSER_ARG_STATE_MAYBE_MULT;
|
||||
}
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_EXPECT_OPEN_PAREN:
|
||||
if (*p != '(')
|
||||
{
|
||||
error_string = "Expected '(' before blend factor - the parser "
|
||||
"currently requires that all blend factors "
|
||||
"following a '*' be surrounded in brackets";
|
||||
goto error;
|
||||
}
|
||||
parsing_factor = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_FACTOR;
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_EXPECT_FACTOR:
|
||||
if (*p == '1')
|
||||
state = PARSER_ARG_STATE_MAYBE_MINUS;
|
||||
else if (*p == '0')
|
||||
{
|
||||
arg->source.is_zero = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_CLOSE_PAREN;
|
||||
}
|
||||
else
|
||||
{
|
||||
state = PARSER_ARG_STATE_MAYBE_SRC_ALPHA_SATURATE;
|
||||
mark = p;
|
||||
}
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_MAYBE_SRC_ALPHA_SATURATE:
|
||||
if (!is_symbol_char (*p))
|
||||
{
|
||||
size_t len = p - mark;
|
||||
if (len >= strlen ("SRC_ALPHA_SATURATE") &&
|
||||
strncmp (mark, "SRC_ALPHA_SATURATE", len) == 0)
|
||||
{
|
||||
arg->factor.is_src_alpha_saturate = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_CLOSE_PAREN;
|
||||
}
|
||||
else
|
||||
{
|
||||
state = PARSER_ARG_STATE_EXPECT_COLOR_SRC_NAME;
|
||||
p = mark - 1; /* backtrack */
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_MAYBE_MINUS:
|
||||
if (*p == '-')
|
||||
{
|
||||
arg->factor.source.one_minus = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_COLOR_SRC_NAME;
|
||||
}
|
||||
else
|
||||
{
|
||||
arg->factor.is_one = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_CLOSE_PAREN;
|
||||
}
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_EXPECT_CLOSE_PAREN:
|
||||
if (*p != ')')
|
||||
{
|
||||
error_string = "Expected closing parenthesis after blend factor";
|
||||
goto error;
|
||||
}
|
||||
state = PARSER_ARG_STATE_EXPECT_END;
|
||||
continue;
|
||||
|
||||
case PARSER_ARG_STATE_MAYBE_MULT:
|
||||
if (*p == '*')
|
||||
{
|
||||
state = PARSER_ARG_STATE_EXPECT_OPEN_PAREN;
|
||||
continue;
|
||||
}
|
||||
arg->factor.is_one = TRUE;
|
||||
state = PARSER_ARG_STATE_EXPECT_END;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_ARG_STATE_EXPECT_END:
|
||||
if (*p != ',' && *p != ')')
|
||||
{
|
||||
error_string = "expected , or )";
|
||||
goto error;
|
||||
}
|
||||
|
||||
*ret_p = p - 1;
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
while (p++);
|
||||
|
||||
error:
|
||||
{
|
||||
int offset = p - string;
|
||||
g_set_error (error,
|
||||
COGL_BLEND_STRING_ERROR,
|
||||
COGL_BLEND_STRING_ERROR_ARGUMENT_PARSE_ERROR,
|
||||
"Syntax error for argument %d at offset %d: %s",
|
||||
current_arg,
|
||||
offset,
|
||||
error_string);
|
||||
|
||||
if (cogl_debug_flags & COGL_DEBUG_BLEND_STRINGS)
|
||||
{
|
||||
g_debug ("Syntax error for argument %d at offset %d: %s",
|
||||
current_arg, offset, error_string);
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
_cogl_blend_string_compile (const char *string,
|
||||
CoglBlendStringContext context,
|
||||
CoglBlendStringStatement *statements,
|
||||
GError **error)
|
||||
{
|
||||
const char *p = string;
|
||||
const char *mark;
|
||||
const char *error_string;
|
||||
ParserState state = PARSER_STATE_EXPECT_DEST_CHANNELS;
|
||||
CoglBlendStringStatement *statement = statements;
|
||||
int current_statement = 0;
|
||||
int current_arg = 0;
|
||||
int remaining_argc;
|
||||
|
||||
#if 0
|
||||
cogl_debug_flags |= COGL_DEBUG_BLEND_STRINGS;
|
||||
#endif
|
||||
|
||||
if (cogl_debug_flags & COGL_DEBUG_BLEND_STRINGS)
|
||||
{
|
||||
COGL_NOTE (BLEND_STRINGS, "Compiling %s string:\n%s\n",
|
||||
context == COGL_BLEND_STRING_CONTEXT_BLENDING ?
|
||||
"blend" : "texture combine",
|
||||
string);
|
||||
}
|
||||
|
||||
do
|
||||
{
|
||||
if (g_ascii_isspace (*p))
|
||||
continue;
|
||||
|
||||
if (*p == '\0')
|
||||
{
|
||||
switch (state)
|
||||
{
|
||||
case PARSER_STATE_EXPECT_DEST_CHANNELS:
|
||||
if (current_statement != 0)
|
||||
goto finished;
|
||||
error_string = "Empty statement";
|
||||
goto error;
|
||||
case PARSER_STATE_SCRAPING_DEST_CHANNELS:
|
||||
error_string = "Expected an '=' following the destination "
|
||||
"channel mask";
|
||||
goto error;
|
||||
case PARSER_STATE_EXPECT_FUNCTION_NAME:
|
||||
error_string = "Expected a function name";
|
||||
goto error;
|
||||
case PARSER_STATE_SCRAPING_FUNCTION_NAME:
|
||||
error_string = "Expected parenthesis after the function name";
|
||||
goto error;
|
||||
case PARSER_STATE_EXPECT_ARG_START:
|
||||
error_string = "Expected to find the start of an argument";
|
||||
goto error;
|
||||
case PARSER_STATE_EXPECT_STATEMENT_END:
|
||||
error_string = "Expected closing parenthesis for statement";
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
switch (state)
|
||||
{
|
||||
case PARSER_STATE_EXPECT_DEST_CHANNELS:
|
||||
mark = p;
|
||||
state = PARSER_STATE_SCRAPING_DEST_CHANNELS;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_STATE_SCRAPING_DEST_CHANNELS:
|
||||
if (*p != '=')
|
||||
continue;
|
||||
if (strncmp (mark, "RGBA", 4) == 0)
|
||||
statement->mask = COGL_BLEND_STRING_CHANNEL_MASK_RGBA;
|
||||
else if (strncmp (mark, "RGB", 3) == 0)
|
||||
statement->mask = COGL_BLEND_STRING_CHANNEL_MASK_RGB;
|
||||
else if (strncmp (mark, "A", 1) == 0)
|
||||
statement->mask = COGL_BLEND_STRING_CHANNEL_MASK_ALPHA;
|
||||
else
|
||||
{
|
||||
error_string = "Unknown destination channel mask; "
|
||||
"expected RGBA=, RGB= or A=";
|
||||
goto error;
|
||||
}
|
||||
state = PARSER_STATE_EXPECT_FUNCTION_NAME;
|
||||
continue;
|
||||
|
||||
case PARSER_STATE_EXPECT_FUNCTION_NAME:
|
||||
mark = p;
|
||||
state = PARSER_STATE_SCRAPING_FUNCTION_NAME;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_STATE_SCRAPING_FUNCTION_NAME:
|
||||
if (*p != '(')
|
||||
{
|
||||
if (!is_symbol_char (*p))
|
||||
{
|
||||
error_string = "non alpha numeric character in function"
|
||||
"name";
|
||||
goto error;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
statement->function = get_function_info (mark, p, context);
|
||||
if (!statement->function)
|
||||
{
|
||||
error_string = "Unknown function name";
|
||||
goto error;
|
||||
}
|
||||
remaining_argc = statement->function->argc;
|
||||
current_arg = 0;
|
||||
state = PARSER_STATE_EXPECT_ARG_START;
|
||||
|
||||
/* fall through */
|
||||
case PARSER_STATE_EXPECT_ARG_START:
|
||||
if (*p != '(' && *p != ',')
|
||||
continue;
|
||||
if (remaining_argc)
|
||||
{
|
||||
p++; /* parse_argument expects to see the first char of the arg */
|
||||
if (!parse_argument (string, &p, statement,
|
||||
current_arg, &statement->args[current_arg],
|
||||
context, error))
|
||||
return 0;
|
||||
current_arg++;
|
||||
remaining_argc--;
|
||||
}
|
||||
if (!remaining_argc)
|
||||
state = PARSER_STATE_EXPECT_STATEMENT_END;
|
||||
continue;
|
||||
|
||||
case PARSER_STATE_EXPECT_STATEMENT_END:
|
||||
if (*p != ')')
|
||||
{
|
||||
error_string = "Expected end of statement";
|
||||
goto error;
|
||||
}
|
||||
state = PARSER_STATE_EXPECT_DEST_CHANNELS;
|
||||
if (current_statement++ == 1)
|
||||
goto finished;
|
||||
statement = &statements[current_statement];
|
||||
}
|
||||
}
|
||||
while (p++);
|
||||
|
||||
finished:
|
||||
|
||||
if (cogl_debug_flags & COGL_DEBUG_BLEND_STRINGS)
|
||||
{
|
||||
if (current_statement > 0)
|
||||
print_statement (0, &statements[0]);
|
||||
if (current_statement > 1)
|
||||
print_statement (1, &statements[1]);
|
||||
}
|
||||
|
||||
if (!validate_statements_for_context (statements,
|
||||
current_statement,
|
||||
context,
|
||||
error))
|
||||
return 0;
|
||||
|
||||
return current_statement;
|
||||
|
||||
error:
|
||||
{
|
||||
int offset = p - string;
|
||||
g_set_error (error,
|
||||
COGL_BLEND_STRING_ERROR,
|
||||
COGL_BLEND_STRING_ERROR_PARSE_ERROR,
|
||||
"Syntax error at offset %d: %s",
|
||||
offset,
|
||||
error_string);
|
||||
|
||||
if (cogl_debug_flags & COGL_DEBUG_BLEND_STRINGS)
|
||||
{
|
||||
g_debug ("Syntax error at offset %d: %s",
|
||||
offset, error_string);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* INTERNAL TESTING CODE ...
|
||||
*/
|
||||
|
||||
struct _TestString
|
||||
{
|
||||
const char *string;
|
||||
CoglBlendStringContext context;
|
||||
};
|
||||
|
||||
int
|
||||
_cogl_blend_string_test (void)
|
||||
{
|
||||
struct _TestString strings[] = {
|
||||
{" A = MODULATE ( TEXTURE[RGB], PREVIOUS[A], PREVIOUS[A] ) ",
|
||||
COGL_BLEND_STRING_CONTEXT_TEXTURE_COMBINE },
|
||||
{" RGB = MODULATE ( TEXTURE[RGB], PREVIOUS[A] ) ",
|
||||
COGL_BLEND_STRING_CONTEXT_TEXTURE_COMBINE },
|
||||
{"A=ADD(TEXTURE[A],PREVIOUS[RGB])",
|
||||
COGL_BLEND_STRING_CONTEXT_TEXTURE_COMBINE },
|
||||
{"A=ADD(TEXTURE[A],PREVIOUS[RGB])",
|
||||
COGL_BLEND_STRING_CONTEXT_TEXTURE_COMBINE },
|
||||
|
||||
{"RGBA = ADD(SRC_COLOR*(SRC_COLOR[A]), DST_COLOR*(1-SRC_COLOR[A]))",
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING },
|
||||
{"RGB = ADD(SRC_COLOR, DST_COLOR*(0))",
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING },
|
||||
{"RGB = ADD(SRC_COLOR, 0)",
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING },
|
||||
{"RGB = ADD()",
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING },
|
||||
{"RGB = ADD(SRC_COLOR, 0, DST_COLOR)",
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING },
|
||||
{NULL}
|
||||
};
|
||||
int i;
|
||||
|
||||
GError *error = NULL;
|
||||
for (i = 0; strings[i].string; i++)
|
||||
{
|
||||
CoglBlendStringStatement statements[2];
|
||||
int count = _cogl_blend_string_compile (strings[i].string,
|
||||
strings[i].context,
|
||||
statements,
|
||||
&error);
|
||||
if (!count)
|
||||
{
|
||||
g_print ("Failed to parse string:\n%s\n%s\n",
|
||||
strings[i].string,
|
||||
error->message);
|
||||
g_error_free (error);
|
||||
error = NULL;
|
||||
continue;
|
||||
}
|
||||
g_print ("Original:\n");
|
||||
g_print ("%s\n", strings[i].string);
|
||||
if (count > 0)
|
||||
print_statement (0, &statements[0]);
|
||||
if (count > 1)
|
||||
print_statement (1, &statements[1]);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
151
common/cogl-blend-string.h
Normal file
151
common/cogl-blend-string.h
Normal file
@ -0,0 +1,151 @@
|
||||
/*
|
||||
* Cogl
|
||||
*
|
||||
* An object oriented GL/GLES Abstraction/Utility Layer
|
||||
*
|
||||
* Copyright (C) 2009 Intel Corporation.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*
|
||||
* Authors:
|
||||
* Robert Bragg <robert@linux.intel.com>
|
||||
*/
|
||||
|
||||
#ifndef COGL_BLEND_STRING_H
|
||||
#define COGL_BLEND_STRING_H
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <glib.h>
|
||||
|
||||
typedef enum _CoglBlendStringContext
|
||||
{
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING,
|
||||
COGL_BLEND_STRING_CONTEXT_TEXTURE_COMBINE
|
||||
} CoglBlendStringContext;
|
||||
|
||||
#define COGL_BLEND_STRING_ERROR _cogl_blend_string_error_quark ()
|
||||
|
||||
typedef enum _CoglBlendStringError
|
||||
{
|
||||
COGL_BLEND_STRING_ERROR_PARSE_ERROR,
|
||||
COGL_BLEND_STRING_ERROR_ARGUMENT_PARSE_ERROR,
|
||||
COGL_BLEND_STRING_ERROR_INVALID_ERROR,
|
||||
COGL_BLEND_STRING_ERROR_GPU_UNSUPPORTED_ERROR
|
||||
} CoglBlendStringError;
|
||||
|
||||
/* NB: debug stringify code will get upset if these
|
||||
* are re-ordered */
|
||||
typedef enum _CoglBlendStringChannelMask
|
||||
{
|
||||
COGL_BLEND_STRING_CHANNEL_MASK_RGB,
|
||||
COGL_BLEND_STRING_CHANNEL_MASK_ALPHA,
|
||||
COGL_BLEND_STRING_CHANNEL_MASK_RGBA
|
||||
} CoglBlendStringChannelMask;
|
||||
|
||||
typedef enum _CoglBlendStringColorSourceType
|
||||
{
|
||||
/* blending */
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_SRC_COLOR,
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_DST_COLOR,
|
||||
|
||||
/* shared */
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_CONSTANT,
|
||||
|
||||
/* texture combining */
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_TEXTURE,
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_TEXTURE_N,
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_PRIMARY,
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_PREVIOUS
|
||||
} CoglBlendStringColorSourceType;
|
||||
|
||||
typedef struct _CoglBlendStringColorSourceInfo
|
||||
{
|
||||
CoglBlendStringColorSourceType type;
|
||||
const char *name;
|
||||
size_t name_len;
|
||||
} CoglBlendStringColorSourceInfo;
|
||||
|
||||
typedef struct _CoglBlendStringColorSource
|
||||
{
|
||||
gboolean is_zero;
|
||||
const CoglBlendStringColorSourceInfo *info;
|
||||
int texture; /* for the TEXTURE_N color source */
|
||||
gboolean one_minus;
|
||||
CoglBlendStringChannelMask mask;
|
||||
} CoglBlendStringColorSource;
|
||||
|
||||
typedef struct _CoglBlendStringFactor
|
||||
{
|
||||
gboolean is_one;
|
||||
gboolean is_src_alpha_saturate;
|
||||
gboolean is_color;
|
||||
CoglBlendStringColorSource source;
|
||||
} CoglBlendStringFactor;
|
||||
|
||||
typedef struct _CoglBlendStringArgument
|
||||
{
|
||||
CoglBlendStringColorSource source;
|
||||
CoglBlendStringFactor factor;
|
||||
} CoglBlendStringArgument;
|
||||
|
||||
typedef enum _CoglBlendStringFunctionType
|
||||
{
|
||||
/* shared */
|
||||
COGL_BLEND_STRING_FUNCTION_AUTO_COMPOSITE,
|
||||
COGL_BLEND_STRING_FUNCTION_ADD,
|
||||
|
||||
/* texture combine only */
|
||||
COGL_BLEND_STRING_FUNCTION_REPLACE,
|
||||
COGL_BLEND_STRING_FUNCTION_MODULATE,
|
||||
COGL_BLEND_STRING_FUNCTION_ADD_SIGNED,
|
||||
COGL_BLEND_STRING_FUNCTION_INTERPOLATE,
|
||||
COGL_BLEND_STRING_FUNCTION_SUBTRACT,
|
||||
COGL_BLEND_STRING_FUNCTION_DOT3_RGB,
|
||||
COGL_BLEND_STRING_FUNCTION_DOT3_RGBA
|
||||
} CoglBlendStringFunctionType;
|
||||
|
||||
typedef struct _CoglBlendStringFunctionInfo
|
||||
{
|
||||
enum _CoglBlendStringFunctionType type;
|
||||
const char *name;
|
||||
size_t name_len;
|
||||
int argc;
|
||||
} CoglBlendStringFunctionInfo;
|
||||
|
||||
typedef struct _CoglBlendStringStatement
|
||||
{
|
||||
CoglBlendStringChannelMask mask;
|
||||
const CoglBlendStringFunctionInfo *function;
|
||||
CoglBlendStringArgument args[3];
|
||||
} CoglBlendStringStatement;
|
||||
|
||||
|
||||
gboolean
|
||||
_cogl_blend_string_compile (const char *string,
|
||||
CoglBlendStringContext context,
|
||||
CoglBlendStringStatement *statements,
|
||||
GError **error);
|
||||
|
||||
void
|
||||
_cogl_blend_string_split_rgba_statement (CoglBlendStringStatement *statement,
|
||||
CoglBlendStringStatement *rgb,
|
||||
CoglBlendStringStatement *a);
|
||||
|
||||
GQuark
|
||||
_cogl_blend_string_error_quark (void);
|
||||
|
||||
#endif /* COGL_BLEND_STRING_H */
|
||||
|
@ -45,6 +45,9 @@
|
||||
#define glFrustum(L,R,B,T,N,F) \
|
||||
glFrustumf((GLfloat)L, (GLfloat)R, (GLfloat)B, \
|
||||
(GLfloat)T, (GLfloat)N, (GLfloat)F)
|
||||
|
||||
#define glOrtho glOrthof
|
||||
|
||||
#endif
|
||||
|
||||
#include <string.h>
|
||||
@ -209,30 +212,57 @@ _cogl_current_matrix_frustum (float left,
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_current_matrix_ortho (float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float near_val,
|
||||
float far_val)
|
||||
_cogl_current_matrix_perspective (float fov_y,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
_COGL_GET_CONTEXT_AND_STACK (ctx, current_stack, NO_RETVAL);
|
||||
|
||||
if (current_stack != NULL)
|
||||
_cogl_matrix_stack_perspective (current_stack,
|
||||
fov_y, aspect, z_near, z_far);
|
||||
else
|
||||
{
|
||||
/* NB: There is no glPerspective() (only gluPerspective()) so we use
|
||||
* cogl_matrix_perspective: */
|
||||
CoglMatrix matrix;
|
||||
_cogl_get_matrix (ctx->matrix_mode, &matrix);
|
||||
cogl_matrix_perspective (&matrix,
|
||||
fov_y, aspect, z_near, z_far);
|
||||
_cogl_current_matrix_load (&matrix);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_current_matrix_ortho (float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float near_val,
|
||||
float far_val)
|
||||
{
|
||||
#if 0
|
||||
_COGL_GET_CONTEXT_AND_STACK (ctx, current_stack, NO_RETVAL);
|
||||
|
||||
if (current_stack != NULL)
|
||||
_cogl_matrix_stack_ortho (current_stack,
|
||||
left, right,
|
||||
top, bottom,
|
||||
bottom, top,
|
||||
near_val,
|
||||
far_val);
|
||||
else
|
||||
GE (glOrtho (left, right, bottom, top, near_val, far_val));
|
||||
{
|
||||
#ifdef HAVE_COGL_GLES2
|
||||
/* NB: GLES 2 has no glOrtho(): */
|
||||
CoglMatrix matrix;
|
||||
_cogl_get_matrix (ctx->matrix_mode, &matrix);
|
||||
cogl_matrix_ortho (&matrix,
|
||||
left, right, bottom, top, near_val, far_val);
|
||||
_cogl_current_matrix_load (&matrix);
|
||||
#else
|
||||
/* Nobody is using glOrtho right now anyway, so not bothering */
|
||||
g_warning ("%s not implemented, need to code cogl_matrix_ortho() if you need"
|
||||
" this function",
|
||||
G_STRFUNC);
|
||||
GE (glOrtho (left, right, bottom, top, near_val, far_val));
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
@ -276,6 +306,12 @@ _cogl_get_matrix (CoglMatrixMode mode,
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_set_matrix (const CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_current_matrix_load (matrix);
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_current_matrix_state_init (void)
|
||||
{
|
||||
@ -354,85 +390,19 @@ cogl_rotate (float angle, float x, float y, float z)
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_set_matrix (const CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_current_matrix_load (matrix);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_get_modelview_matrix (CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_get_matrix (COGL_MATRIX_MODELVIEW,
|
||||
matrix);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_get_projection_matrix (CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_get_matrix (COGL_MATRIX_PROJECTION,
|
||||
matrix);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_perspective (float fovy,
|
||||
cogl_perspective (float fov_y,
|
||||
float aspect,
|
||||
float zNear,
|
||||
float zFar)
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
float xmax, ymax;
|
||||
float x, y, c, d;
|
||||
float fovy_rad_half = (fovy * G_PI) / 360;
|
||||
CoglMatrix perspective;
|
||||
GLfloat m[16];
|
||||
float ymax = z_near * tanf (fov_y * G_PI / 360.0);
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
memset (&m[0], 0, sizeof (m));
|
||||
|
||||
_cogl_set_current_matrix (COGL_MATRIX_PROJECTION);
|
||||
_cogl_current_matrix_identity ();
|
||||
|
||||
/*
|
||||
* Based on the original algorithm in perspective():
|
||||
*
|
||||
* 1) xmin = -xmax => xmax + xmin == 0 && xmax - xmin == 2 * xmax
|
||||
* same true for y, hence: a == 0 && b == 0;
|
||||
*
|
||||
* 2) When working with small numbers, we are loosing significant
|
||||
* precision
|
||||
*/
|
||||
ymax = (zNear * (sinf (fovy_rad_half) / cosf (fovy_rad_half)));
|
||||
xmax = (ymax * aspect);
|
||||
|
||||
x = (zNear / xmax);
|
||||
y = (zNear / ymax);
|
||||
c = (-(zFar + zNear) / ( zFar - zNear));
|
||||
d = (-(2 * zFar) * zNear) / (zFar - zNear);
|
||||
|
||||
#define M(row,col) m[col*4+row]
|
||||
M(0,0) = x;
|
||||
M(1,1) = y;
|
||||
M(2,2) = c;
|
||||
M(2,3) = d;
|
||||
M(3,2) = -1.0;
|
||||
|
||||
cogl_matrix_init_from_array (&perspective, m);
|
||||
_cogl_current_matrix_multiply (&perspective);
|
||||
|
||||
_cogl_set_current_matrix (COGL_MATRIX_MODELVIEW);
|
||||
|
||||
/* Calculate and store the inverse of the matrix */
|
||||
memset (ctx->inverse_projection, 0, sizeof (float) * 16);
|
||||
|
||||
#define m ctx->inverse_projection
|
||||
M(0, 0) = (1.0 / x);
|
||||
M(1, 1) = (1.0 / y);
|
||||
M(2, 3) = -1.0;
|
||||
M(3, 2) = (1.0 / d);
|
||||
M(3, 3) = (c / d);
|
||||
#undef m
|
||||
|
||||
#undef M
|
||||
cogl_frustum (-ymax * aspect, /* left */
|
||||
ymax * aspect, /* right */
|
||||
-ymax, /* bottom */
|
||||
ymax, /* top */
|
||||
z_near,
|
||||
z_far);
|
||||
}
|
||||
|
||||
void
|
||||
@ -474,4 +444,65 @@ cogl_frustum (float left,
|
||||
M(3,2) = 1.0 / d;
|
||||
M(3,3) = c / d;
|
||||
#undef M
|
||||
|
||||
_cogl_set_current_matrix (COGL_MATRIX_MODELVIEW);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_ortho (float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
CoglMatrix ortho;
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
cogl_matrix_init_identity (&ortho);
|
||||
cogl_matrix_ortho (&ortho, left, right, bottom, top, z_near, z_far);
|
||||
_cogl_set_current_matrix (COGL_MATRIX_PROJECTION);
|
||||
_cogl_current_matrix_load (&ortho);
|
||||
|
||||
/* Calculate and store the inverse of the matrix */
|
||||
memset (ctx->inverse_projection, 0, sizeof (float) * 16);
|
||||
|
||||
#define M(row,col) ctx->inverse_projection[col*4+row]
|
||||
M(0,0) = 1.0 / ortho.xx;
|
||||
M(0,3) = -ortho.xw;
|
||||
M(1,1) = 1.0 / ortho.yy;
|
||||
M(1,3) = -ortho.yw;
|
||||
M(2,2) = 1.0 / ortho.zz;
|
||||
M(2,3) = -ortho.zw;
|
||||
M(3,3) = 1.0;
|
||||
#undef M
|
||||
}
|
||||
|
||||
void
|
||||
cogl_get_modelview_matrix (CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_get_matrix (COGL_MATRIX_MODELVIEW,
|
||||
matrix);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_set_modelview_matrix (CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_set_current_matrix (COGL_MATRIX_MODELVIEW);
|
||||
_cogl_current_matrix_load (matrix);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_get_projection_matrix (CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_get_matrix (COGL_MATRIX_PROJECTION,
|
||||
matrix);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_set_projection_matrix (CoglMatrix *matrix)
|
||||
{
|
||||
_cogl_set_current_matrix (COGL_MATRIX_PROJECTION);
|
||||
_cogl_current_matrix_load (matrix);
|
||||
}
|
||||
|
||||
|
@ -39,7 +39,8 @@ static const GDebugKey cogl_debug_keys[] = {
|
||||
{ "draw", COGL_DEBUG_DRAW },
|
||||
{ "pango", COGL_DEBUG_PANGO },
|
||||
{ "rectangles", COGL_DEBUG_RECTANGLES },
|
||||
{ "handle", COGL_DEBUG_HANDLE }
|
||||
{ "handle", COGL_DEBUG_HANDLE },
|
||||
{ "blend-strings", COGL_DEBUG_BLEND_STRINGS }
|
||||
};
|
||||
|
||||
static const gint n_cogl_debug_keys = G_N_ELEMENTS (cogl_debug_keys);
|
||||
|
41
common/cogl-enum-types.c.in
Normal file
41
common/cogl-enum-types.c.in
Normal file
@ -0,0 +1,41 @@
|
||||
/*** BEGIN file-header ***/
|
||||
#include "cogl-enum-types.h"
|
||||
#include "cogl.h"
|
||||
/*** END file-header ***/
|
||||
|
||||
/*** BEGIN file-production ***/
|
||||
|
||||
/* enumerations from "@filename@" */
|
||||
#include "@filename@"
|
||||
|
||||
/*** END file-production ***/
|
||||
|
||||
/*** BEGIN value-header ***/
|
||||
GType
|
||||
@enum_name@_get_type (void)
|
||||
{
|
||||
static volatile gsize g_enum_type_id__volatile = 0;
|
||||
|
||||
if (g_once_init_enter (&g_enum_type_id__volatile))
|
||||
{
|
||||
static const G@Type@Value values[] = {
|
||||
/*** END value-header ***/
|
||||
|
||||
/*** BEGIN value-production ***/
|
||||
{ @VALUENAME@, "@VALUENAME@", "@valuenick@" },
|
||||
/*** END value-production ***/
|
||||
|
||||
/*** BEGIN value-tail ***/
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
GType g_enum_type_id;
|
||||
|
||||
g_enum_type_id =
|
||||
g_@type@_register_static (g_intern_static_string ("@EnumName@"), values);
|
||||
|
||||
g_once_init_leave (&g_enum_type_id__volatile, g_enum_type_id);
|
||||
}
|
||||
|
||||
return g_enum_type_id__volatile;
|
||||
}
|
||||
/*** END value-tail ***/
|
25
common/cogl-enum-types.h.in
Normal file
25
common/cogl-enum-types.h.in
Normal file
@ -0,0 +1,25 @@
|
||||
/*** BEGIN file-header ***/
|
||||
#ifndef __COGL_ENUM_TYPES_H__
|
||||
#define __COGL_ENUM_TYPES_H__
|
||||
|
||||
#include <glib-object.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
/*** END file-header ***/
|
||||
|
||||
/*** BEGIN file-production ***/
|
||||
/* enumerations from "@filename@" */
|
||||
/*** END file-production ***/
|
||||
|
||||
/*** BEGIN file-tail ***/
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* !__CLUTTER_ENUM_TYPES_H__ */
|
||||
/*** END file-tail ***/
|
||||
|
||||
/*** BEGIN value-header ***/
|
||||
GType @enum_name@_get_type (void) G_GNUC_CONST;
|
||||
#define COGL_TYPE_@ENUMSHORT@ (@enum_name@_get_type())
|
||||
|
||||
/*** END value-header ***/
|
@ -82,7 +82,7 @@ typedef struct _CoglHandleObject
|
||||
static CoglHandleClass _cogl_##type_name##_class; \
|
||||
\
|
||||
static GQuark \
|
||||
_cogl_##type_name##_get_type (void) \
|
||||
_cogl_handle_##type_name##_get_type (void) \
|
||||
{ \
|
||||
static GQuark type = 0; \
|
||||
if (!type) \
|
||||
@ -99,13 +99,13 @@ _cogl_##type_name##_handle_new (Cogl##TypeName *new_obj) \
|
||||
obj->klass = &_cogl_##type_name##_class; \
|
||||
if (!obj->klass->type) \
|
||||
{ \
|
||||
obj->klass->type = _cogl_##type_name##_get_type (); \
|
||||
obj->klass->virt_free = _cogl_##type_name##_free; \
|
||||
} \
|
||||
obj->klass->type = _cogl_handle_##type_name##_get_type ();\
|
||||
obj->klass->virt_free = _cogl_##type_name##_free; \
|
||||
} \
|
||||
\
|
||||
_COGL_HANDLE_DEBUG_NEW (TypeName, obj); \
|
||||
return (CoglHandle) new_obj; \
|
||||
} \
|
||||
_COGL_HANDLE_DEBUG_NEW (TypeName, obj); \
|
||||
return (CoglHandle) new_obj; \
|
||||
} \
|
||||
\
|
||||
Cogl##TypeName * \
|
||||
_cogl_##type_name##_pointer_from_handle (CoglHandle handle) \
|
||||
@ -121,7 +121,8 @@ cogl_is_##type_name (CoglHandle handle) \
|
||||
if (handle == COGL_INVALID_HANDLE) \
|
||||
return FALSE; \
|
||||
\
|
||||
return (obj->klass->type == _cogl_##type_name##_get_type ()); \
|
||||
return (obj->klass->type == \
|
||||
_cogl_handle_##type_name##_get_type ()); \
|
||||
} \
|
||||
\
|
||||
CoglHandle G_GNUC_DEPRECATED \
|
||||
|
@ -68,15 +68,20 @@ struct _CoglMaterialLayer
|
||||
CoglHandle texture; /*!< The texture for this layer, or COGL_INVALID_HANDLE
|
||||
for an empty layer */
|
||||
|
||||
CoglMaterialFilter mag_filter;
|
||||
CoglMaterialFilter min_filter;
|
||||
|
||||
/* Determines how the color of individual texture fragments
|
||||
* are calculated. */
|
||||
CoglMaterialLayerCombineFunc texture_combine_rgb_func;
|
||||
CoglMaterialLayerCombineSrc texture_combine_rgb_src[3];
|
||||
CoglMaterialLayerCombineOp texture_combine_rgb_op[3];
|
||||
GLint texture_combine_rgb_func;
|
||||
GLint texture_combine_rgb_src[3];
|
||||
GLint texture_combine_rgb_op[3];
|
||||
|
||||
CoglMaterialLayerCombineFunc texture_combine_alpha_func;
|
||||
CoglMaterialLayerCombineSrc texture_combine_alpha_src[3];
|
||||
CoglMaterialLayerCombineOp texture_combine_alpha_op[3];
|
||||
GLint texture_combine_alpha_func;
|
||||
GLint texture_combine_alpha_src[3];
|
||||
GLint texture_combine_alpha_op[3];
|
||||
|
||||
GLfloat texture_combine_constant[4];
|
||||
|
||||
/* TODO: Support purely GLSL based material layers */
|
||||
|
||||
@ -114,11 +119,104 @@ struct _CoglMaterial
|
||||
GLfloat alpha_func_reference;
|
||||
|
||||
/* Determines how this material is blended with other primitives */
|
||||
CoglMaterialBlendFactor blend_src_factor;
|
||||
CoglMaterialBlendFactor blend_dst_factor;
|
||||
#ifndef HAVE_COGL_GLES
|
||||
GLenum blend_equation_rgb;
|
||||
GLenum blend_equation_alpha;
|
||||
GLint blend_src_factor_alpha;
|
||||
GLint blend_dst_factor_alpha;
|
||||
GLfloat blend_constant[4];
|
||||
#endif
|
||||
GLint blend_src_factor_rgb;
|
||||
GLint blend_dst_factor_rgb;
|
||||
|
||||
GList *layers;
|
||||
};
|
||||
|
||||
/*
|
||||
* SECTION:cogl-material-internals
|
||||
* @short_description: Functions for creating custom primitives that make use
|
||||
* of Cogl materials for filling.
|
||||
*
|
||||
* Normally you shouldn't need to use this API directly, but if you need to
|
||||
* developing a custom/specialised primitive - probably using raw OpenGL - then
|
||||
* this API aims to expose enough of the material internals to support being
|
||||
* able to fill your geometry according to a given Cogl material.
|
||||
*/
|
||||
|
||||
|
||||
/*
|
||||
* cogl_material_get_cogl_enable_flags:
|
||||
* @material: A CoglMaterial object
|
||||
*
|
||||
* This determines what flags need to be passed to cogl_enable before this
|
||||
* material can be used. Normally you shouldn't need to use this function
|
||||
* directly since Cogl will do this internally, but if you are developing
|
||||
* custom primitives directly with OpenGL you may want to use this.
|
||||
*
|
||||
* Note: This API is hopfully just a stop-gap solution. Ideally cogl_enable
|
||||
* will be replaced.
|
||||
*/
|
||||
/* TODO: find a nicer solution! */
|
||||
gulong _cogl_material_get_cogl_enable_flags (CoglHandle handle);
|
||||
|
||||
/*
|
||||
* CoglMaterialLayerFlags:
|
||||
* @COGL_MATERIAL_LAYER_FLAG_USER_MATRIX: Means the user has supplied a
|
||||
* custom texture matrix.
|
||||
*/
|
||||
typedef enum _CoglMaterialLayerFlags
|
||||
{
|
||||
COGL_MATERIAL_LAYER_FLAG_HAS_USER_MATRIX = 1L<<0
|
||||
} CoglMaterialLayerFlags;
|
||||
/* XXX: NB: if you add flags here you will need to update
|
||||
* CoglMaterialLayerPrivFlags!!! */
|
||||
|
||||
/*
|
||||
* cogl_material_layer_get_flags:
|
||||
* @layer_handle: A CoglMaterialLayer layer handle
|
||||
*
|
||||
* This lets you get a number of flag attributes about the layer. Normally
|
||||
* you shouldn't need to use this function directly since Cogl will do this
|
||||
* internally, but if you are developing custom primitives directly with
|
||||
* OpenGL you may need this.
|
||||
*/
|
||||
gulong _cogl_material_layer_get_flags (CoglHandle layer_handle);
|
||||
|
||||
/*
|
||||
* CoglMaterialFlushOption:
|
||||
* @COGL_MATERIAL_FLUSH_FALLBACK_MASK: Follow this by a guin32 mask
|
||||
* of the layers that can't be supported with the user supplied texture
|
||||
* and need to be replaced with fallback textures. (1 = fallback, and the
|
||||
* least significant bit = layer 0)
|
||||
* @COGL_MATERIAL_FLUSH_DISABLE_MASK: Follow this by a guint32 mask
|
||||
* of the layers that you want to completly disable texturing for
|
||||
* (1 = fallback, and the least significant bit = layer 0)
|
||||
* @COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE: Follow this by a GLuint OpenGL texture
|
||||
* name to override the texture used for layer 0 of the material. This is
|
||||
* intended for dealing with sliced textures where you will need to point
|
||||
* to each of the texture slices in turn when drawing your geometry.
|
||||
* Passing a value of 0 is the same as not passing the option at all.
|
||||
*/
|
||||
typedef enum _CoglMaterialFlushOption
|
||||
{
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK = 1,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE,
|
||||
} CoglMaterialFlushOption;
|
||||
|
||||
/*
|
||||
* cogl_material_flush_gl_state:
|
||||
* @material: A CoglMaterial object
|
||||
* @...: A NULL terminated list of (CoglMaterialFlushOption, data) pairs
|
||||
*
|
||||
* This function commits the state of the specified CoglMaterial - including
|
||||
* the texture state for all the layers - to the OpenGL[ES] driver.
|
||||
*
|
||||
* Since 1.0
|
||||
*/
|
||||
void _cogl_material_flush_gl_state (CoglHandle material,
|
||||
...) G_GNUC_NULL_TERMINATED;
|
||||
|
||||
|
||||
#endif /* __COGL_MATERIAL_PRIVATE_H */
|
||||
|
||||
|
@ -35,6 +35,7 @@
|
||||
|
||||
#include "cogl-material-private.h"
|
||||
#include "cogl-texture-private.h"
|
||||
#include "cogl-blend-string.h"
|
||||
|
||||
#include <glib.h>
|
||||
#include <string.h>
|
||||
@ -50,6 +51,10 @@
|
||||
#ifdef HAVE_COGL_GL
|
||||
#define glActiveTexture ctx->pf_glActiveTexture
|
||||
#define glClientActiveTexture ctx->pf_glClientActiveTexture
|
||||
#define glBlendFuncSeparate ctx->pf_glBlendFuncSeparate
|
||||
#define glBlendEquation ctx->pf_glBlendEquation
|
||||
#define glBlendColor ctx->pf_glBlendColor
|
||||
#define glBlendEquationSeparate ctx->pf_glBlendEquationSeparate
|
||||
#endif
|
||||
|
||||
static void _cogl_material_free (CoglMaterial *tex);
|
||||
@ -60,6 +65,12 @@ COGL_HANDLE_DEFINE (MaterialLayer, material_layer);
|
||||
|
||||
/* #define DISABLE_MATERIAL_CACHE 1 */
|
||||
|
||||
GQuark
|
||||
_cogl_material_error_quark (void)
|
||||
{
|
||||
return g_quark_from_static_string ("cogl-material-error-quark");
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_material_new (void)
|
||||
{
|
||||
@ -88,8 +99,18 @@ cogl_material_new (void)
|
||||
material->flags |= COGL_MATERIAL_FLAG_DEFAULT_ALPHA_FUNC;
|
||||
|
||||
/* Not the same as the GL default, but seems saner... */
|
||||
material->blend_src_factor = COGL_MATERIAL_BLEND_FACTOR_SRC_ALPHA;
|
||||
material->blend_dst_factor = COGL_MATERIAL_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
|
||||
#ifndef HAVE_COGL_GLES
|
||||
material->blend_equation_rgb = GL_FUNC_ADD;
|
||||
material->blend_equation_alpha = GL_FUNC_ADD;
|
||||
material->blend_src_factor_alpha = GL_SRC_ALPHA;
|
||||
material->blend_dst_factor_alpha = GL_ONE_MINUS_SRC_ALPHA;
|
||||
material->blend_constant[0] = 0;
|
||||
material->blend_constant[1] = 0;
|
||||
material->blend_constant[2] = 0;
|
||||
material->blend_constant[3] = 0;
|
||||
#endif
|
||||
material->blend_src_factor_rgb = GL_SRC_ALPHA;
|
||||
material->blend_dst_factor_rgb = GL_ONE_MINUS_SRC_ALPHA;
|
||||
material->flags |= COGL_MATERIAL_FLAG_DEFAULT_BLEND_FUNC;
|
||||
|
||||
material->layers = NULL;
|
||||
@ -408,20 +429,177 @@ cogl_material_set_alpha_test_function (CoglHandle handle,
|
||||
material->flags &= ~COGL_MATERIAL_FLAG_DEFAULT_ALPHA_FUNC;
|
||||
}
|
||||
|
||||
GLenum
|
||||
arg_to_gl_blend_factor (CoglBlendStringArgument *arg)
|
||||
{
|
||||
if (arg->source.is_zero)
|
||||
return GL_ZERO;
|
||||
if (arg->factor.is_one)
|
||||
return GL_ONE;
|
||||
else if (arg->factor.is_src_alpha_saturate)
|
||||
return GL_SRC_ALPHA_SATURATE;
|
||||
else if (arg->factor.source.info->type ==
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_SRC_COLOR)
|
||||
{
|
||||
if (arg->factor.source.mask == COGL_BLEND_STRING_CHANNEL_MASK_RGB)
|
||||
{
|
||||
if (arg->factor.source.one_minus)
|
||||
return GL_ONE_MINUS_SRC_COLOR;
|
||||
else
|
||||
return GL_SRC_COLOR;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (arg->factor.source.one_minus)
|
||||
return GL_ONE_MINUS_SRC_ALPHA;
|
||||
else
|
||||
return GL_SRC_ALPHA;
|
||||
}
|
||||
}
|
||||
else if (arg->factor.source.info->type ==
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_DST_COLOR)
|
||||
{
|
||||
if (arg->factor.source.mask == COGL_BLEND_STRING_CHANNEL_MASK_RGB)
|
||||
{
|
||||
if (arg->factor.source.one_minus)
|
||||
return GL_ONE_MINUS_DST_COLOR;
|
||||
else
|
||||
return GL_DST_COLOR;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (arg->factor.source.one_minus)
|
||||
return GL_ONE_MINUS_DST_ALPHA;
|
||||
else
|
||||
return GL_DST_ALPHA;
|
||||
}
|
||||
}
|
||||
#ifndef HAVE_COGL_GLES
|
||||
else if (arg->factor.source.info->type ==
|
||||
COGL_BLEND_STRING_COLOR_SOURCE_CONSTANT)
|
||||
{
|
||||
if (arg->factor.source.mask == COGL_BLEND_STRING_CHANNEL_MASK_RGB)
|
||||
{
|
||||
if (arg->factor.source.one_minus)
|
||||
return GL_ONE_MINUS_CONSTANT_COLOR;
|
||||
else
|
||||
return GL_CONSTANT_COLOR;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (arg->factor.source.one_minus)
|
||||
return GL_ONE_MINUS_CONSTANT_ALPHA;
|
||||
else
|
||||
return GL_CONSTANT_ALPHA;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
g_warning ("Unable to determine valid blend factor from blend string\n");
|
||||
return GL_ONE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_blend_factors (CoglHandle handle,
|
||||
CoglMaterialBlendFactor src_factor,
|
||||
CoglMaterialBlendFactor dst_factor)
|
||||
setup_blend_state (CoglBlendStringStatement *statement,
|
||||
GLenum *blend_equation,
|
||||
GLint *blend_src_factor,
|
||||
GLint *blend_dst_factor)
|
||||
{
|
||||
#ifndef HAVE_COGL_GLES
|
||||
switch (statement->function->type)
|
||||
{
|
||||
case COGL_BLEND_STRING_FUNCTION_ADD:
|
||||
*blend_equation = GL_FUNC_ADD;
|
||||
break;
|
||||
/* TODO - add more */
|
||||
default:
|
||||
g_warning ("Unsupported blend function given");
|
||||
*blend_equation = GL_FUNC_ADD;
|
||||
}
|
||||
#endif
|
||||
|
||||
*blend_src_factor = arg_to_gl_blend_factor (&statement->args[0]);
|
||||
*blend_dst_factor = arg_to_gl_blend_factor (&statement->args[1]);
|
||||
}
|
||||
|
||||
gboolean
|
||||
cogl_material_set_blend (CoglHandle handle,
|
||||
const char *blend_description,
|
||||
GError **error)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
CoglBlendStringStatement statements[2];
|
||||
CoglBlendStringStatement split[2];
|
||||
CoglBlendStringStatement *rgb;
|
||||
CoglBlendStringStatement *a;
|
||||
int count;
|
||||
|
||||
g_return_val_if_fail (cogl_is_material (handle), FALSE);
|
||||
|
||||
material = _cogl_material_pointer_from_handle (handle);
|
||||
|
||||
count =
|
||||
_cogl_blend_string_compile (blend_description,
|
||||
COGL_BLEND_STRING_CONTEXT_BLENDING,
|
||||
statements,
|
||||
error);
|
||||
if (!count)
|
||||
return FALSE;
|
||||
|
||||
if (statements[0].mask == COGL_BLEND_STRING_CHANNEL_MASK_RGBA)
|
||||
{
|
||||
_cogl_blend_string_split_rgba_statement (statements,
|
||||
&split[0], &split[1]);
|
||||
rgb = &split[0];
|
||||
a = &split[1];
|
||||
}
|
||||
else
|
||||
{
|
||||
rgb = &statements[0];
|
||||
a = &statements[1];
|
||||
}
|
||||
|
||||
#ifndef HAVE_COGL_GLES
|
||||
setup_blend_state (rgb,
|
||||
&material->blend_equation_rgb,
|
||||
&material->blend_src_factor_rgb,
|
||||
&material->blend_dst_factor_rgb);
|
||||
setup_blend_state (a,
|
||||
&material->blend_equation_alpha,
|
||||
&material->blend_src_factor_alpha,
|
||||
&material->blend_dst_factor_alpha);
|
||||
#else
|
||||
setup_blend_state (rgb,
|
||||
NULL,
|
||||
&material->blend_src_factor_rgb,
|
||||
&material->blend_dst_factor_rgb);
|
||||
#endif
|
||||
|
||||
material->flags &= ~COGL_MATERIAL_FLAG_DEFAULT_BLEND_FUNC;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_blend_constant (CoglHandle handle,
|
||||
CoglColor *constant_color)
|
||||
{
|
||||
#ifndef HAVE_COGL_GLES
|
||||
CoglMaterial *material;
|
||||
GLfloat *constant;
|
||||
|
||||
g_return_if_fail (cogl_is_material (handle));
|
||||
|
||||
material = _cogl_material_pointer_from_handle (handle);
|
||||
material->blend_src_factor = src_factor;
|
||||
material->blend_dst_factor = dst_factor;
|
||||
|
||||
constant = material->blend_constant;
|
||||
constant[0] = cogl_color_get_red_float (constant_color);
|
||||
constant[1] = cogl_color_get_green_float (constant_color);
|
||||
constant[2] = cogl_color_get_blue_float (constant_color);
|
||||
constant[3] = cogl_color_get_alpha_float (constant_color);
|
||||
|
||||
material->flags &= ~COGL_MATERIAL_FLAG_DEFAULT_BLEND_FUNC;
|
||||
#endif
|
||||
}
|
||||
|
||||
/* Asserts that a layer corresponding to the given index exists. If no
|
||||
@ -459,25 +637,22 @@ _cogl_material_get_layer (CoglMaterial *material,
|
||||
layer_handle = _cogl_material_layer_handle_new (layer);
|
||||
layer->index = index_;
|
||||
layer->flags = COGL_MATERIAL_LAYER_FLAG_DEFAULT_COMBINE;
|
||||
layer->mag_filter = COGL_MATERIAL_FILTER_LINEAR;
|
||||
layer->min_filter = COGL_MATERIAL_FILTER_LINEAR;
|
||||
layer->texture = COGL_INVALID_HANDLE;
|
||||
|
||||
/* Choose the same default combine mode as OpenGL:
|
||||
* MODULATE(PREVIOUS[RGBA],TEXTURE[RGBA]) */
|
||||
layer->texture_combine_rgb_func = COGL_MATERIAL_LAYER_COMBINE_FUNC_MODULATE;
|
||||
layer->texture_combine_rgb_src[0] = COGL_MATERIAL_LAYER_COMBINE_SRC_PREVIOUS;
|
||||
layer->texture_combine_rgb_src[1] = COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE;
|
||||
layer->texture_combine_rgb_op[0] = COGL_MATERIAL_LAYER_COMBINE_OP_SRC_COLOR;
|
||||
layer->texture_combine_rgb_op[1] = COGL_MATERIAL_LAYER_COMBINE_OP_SRC_COLOR;
|
||||
layer->texture_combine_alpha_func =
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_MODULATE;
|
||||
layer->texture_combine_alpha_src[0] =
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_PREVIOUS;
|
||||
layer->texture_combine_alpha_src[1] =
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE;
|
||||
layer->texture_combine_alpha_op[0] =
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_SRC_ALPHA;
|
||||
layer->texture_combine_alpha_op[1] =
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_SRC_ALPHA;
|
||||
layer->texture_combine_rgb_func = GL_MODULATE;
|
||||
layer->texture_combine_rgb_src[0] = GL_PREVIOUS;
|
||||
layer->texture_combine_rgb_src[1] = GL_TEXTURE;
|
||||
layer->texture_combine_rgb_op[0] = GL_SRC_COLOR;
|
||||
layer->texture_combine_rgb_op[1] = GL_SRC_COLOR;
|
||||
layer->texture_combine_alpha_func = GL_MODULATE;
|
||||
layer->texture_combine_alpha_src[0] = GL_PREVIOUS;
|
||||
layer->texture_combine_alpha_src[1] = GL_TEXTURE;
|
||||
layer->texture_combine_alpha_op[0] = GL_SRC_ALPHA;
|
||||
layer->texture_combine_alpha_op[1] = GL_SRC_ALPHA;
|
||||
|
||||
cogl_matrix_init_identity (&layer->matrix);
|
||||
|
||||
@ -498,7 +673,8 @@ cogl_material_set_layer (CoglHandle material_handle,
|
||||
int n_layers;
|
||||
|
||||
g_return_if_fail (cogl_is_material (material_handle));
|
||||
g_return_if_fail (cogl_is_texture (texture_handle));
|
||||
g_return_if_fail (texture_handle == COGL_INVALID_HANDLE
|
||||
|| cogl_is_texture (texture_handle));
|
||||
|
||||
material = _cogl_material_pointer_from_handle (material_handle);
|
||||
layer = _cogl_material_get_layer (material_handle, layer_index, TRUE);
|
||||
@ -519,7 +695,8 @@ cogl_material_set_layer (CoglHandle material_handle,
|
||||
* MAX_COMBINED_TEXTURE_IMAGE_UNITS layers. */
|
||||
}
|
||||
|
||||
cogl_handle_ref (texture_handle);
|
||||
if (texture_handle)
|
||||
cogl_handle_ref (texture_handle);
|
||||
|
||||
if (layer->texture)
|
||||
cogl_handle_unref (layer->texture);
|
||||
@ -530,104 +707,164 @@ cogl_material_set_layer (CoglHandle material_handle,
|
||||
layer->flags |= COGL_MATERIAL_LAYER_FLAG_DIRTY;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_layer_combine_function (
|
||||
CoglHandle handle,
|
||||
gint layer_index,
|
||||
CoglMaterialLayerCombineChannels channels,
|
||||
CoglMaterialLayerCombineFunc func)
|
||||
static void
|
||||
setup_texture_combine_state (CoglBlendStringStatement *statement,
|
||||
GLint *texture_combine_func,
|
||||
GLint *texture_combine_src,
|
||||
GLint *texture_combine_op)
|
||||
{
|
||||
int i;
|
||||
|
||||
switch (statement->function->type)
|
||||
{
|
||||
case COGL_BLEND_STRING_FUNCTION_AUTO_COMPOSITE:
|
||||
*texture_combine_func = GL_MODULATE; /* FIXME */
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_REPLACE:
|
||||
*texture_combine_func = GL_REPLACE;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_MODULATE:
|
||||
*texture_combine_func = GL_MODULATE;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_ADD:
|
||||
*texture_combine_func = GL_ADD;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_ADD_SIGNED:
|
||||
*texture_combine_func = GL_ADD_SIGNED;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_INTERPOLATE:
|
||||
*texture_combine_func = GL_INTERPOLATE;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_SUBTRACT:
|
||||
*texture_combine_func = GL_SUBTRACT;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_DOT3_RGB:
|
||||
*texture_combine_func = GL_DOT3_RGB;
|
||||
break;
|
||||
case COGL_BLEND_STRING_FUNCTION_DOT3_RGBA:
|
||||
*texture_combine_func = GL_DOT3_RGBA;
|
||||
break;
|
||||
}
|
||||
|
||||
for (i = 0; i < statement->function->argc; i++)
|
||||
{
|
||||
CoglBlendStringArgument *arg = &statement->args[i];
|
||||
|
||||
switch (arg->source.info->type)
|
||||
{
|
||||
case COGL_BLEND_STRING_COLOR_SOURCE_CONSTANT:
|
||||
texture_combine_src[i] = GL_CONSTANT;
|
||||
break;
|
||||
case COGL_BLEND_STRING_COLOR_SOURCE_TEXTURE:
|
||||
texture_combine_src[i] = GL_TEXTURE;
|
||||
break;
|
||||
case COGL_BLEND_STRING_COLOR_SOURCE_TEXTURE_N:
|
||||
texture_combine_src[i] =
|
||||
GL_TEXTURE0 + arg->source.texture;
|
||||
break;
|
||||
case COGL_BLEND_STRING_COLOR_SOURCE_PRIMARY:
|
||||
texture_combine_src[i] = GL_PRIMARY_COLOR;
|
||||
break;
|
||||
case COGL_BLEND_STRING_COLOR_SOURCE_PREVIOUS:
|
||||
texture_combine_src[i] = GL_PREVIOUS;
|
||||
break;
|
||||
default:
|
||||
g_warning ("Unexpected texture combine source");
|
||||
texture_combine_src[i] = GL_TEXTURE;
|
||||
}
|
||||
|
||||
if (arg->source.mask == COGL_BLEND_STRING_CHANNEL_MASK_RGB)
|
||||
{
|
||||
if (statement->args[i].source.one_minus)
|
||||
texture_combine_op[i] = GL_ONE_MINUS_SRC_COLOR;
|
||||
else
|
||||
texture_combine_op[i] = GL_SRC_COLOR;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (statement->args[i].source.one_minus)
|
||||
texture_combine_op[i] = GL_ONE_MINUS_SRC_ALPHA;
|
||||
else
|
||||
texture_combine_op[i] = GL_SRC_ALPHA;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
gboolean
|
||||
cogl_material_set_layer_combine (CoglHandle handle,
|
||||
gint layer_index,
|
||||
const char *combine_description,
|
||||
GError **error)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
CoglMaterialLayer *layer;
|
||||
gboolean set_alpha_func = FALSE;
|
||||
gboolean set_rgb_func = FALSE;
|
||||
CoglBlendStringStatement statements[2];
|
||||
CoglBlendStringStatement split[2];
|
||||
CoglBlendStringStatement *rgb;
|
||||
CoglBlendStringStatement *a;
|
||||
int count;
|
||||
|
||||
g_return_val_if_fail (cogl_is_material (handle), FALSE);
|
||||
|
||||
material = _cogl_material_pointer_from_handle (handle);
|
||||
layer = _cogl_material_get_layer (material, layer_index, TRUE);
|
||||
|
||||
count =
|
||||
_cogl_blend_string_compile (combine_description,
|
||||
COGL_BLEND_STRING_CONTEXT_TEXTURE_COMBINE,
|
||||
statements,
|
||||
error);
|
||||
if (!count)
|
||||
return FALSE;
|
||||
|
||||
if (statements[0].mask == COGL_BLEND_STRING_CHANNEL_MASK_RGBA)
|
||||
{
|
||||
_cogl_blend_string_split_rgba_statement (statements,
|
||||
&split[0], &split[1]);
|
||||
rgb = &split[0];
|
||||
a = &split[1];
|
||||
}
|
||||
else
|
||||
{
|
||||
rgb = &statements[0];
|
||||
a = &statements[1];
|
||||
}
|
||||
|
||||
setup_texture_combine_state (rgb,
|
||||
&layer->texture_combine_rgb_func,
|
||||
layer->texture_combine_rgb_src,
|
||||
layer->texture_combine_rgb_op);
|
||||
|
||||
setup_texture_combine_state (a,
|
||||
&layer->texture_combine_alpha_func,
|
||||
layer->texture_combine_alpha_src,
|
||||
layer->texture_combine_alpha_op);
|
||||
|
||||
|
||||
layer->flags |= COGL_MATERIAL_LAYER_FLAG_DIRTY;
|
||||
layer->flags &= ~COGL_MATERIAL_LAYER_FLAG_DEFAULT_COMBINE;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_layer_combine_constant (CoglHandle handle,
|
||||
gint layer_index,
|
||||
CoglColor *constant_color)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
CoglMaterialLayer *layer;
|
||||
GLfloat *constant;
|
||||
|
||||
g_return_if_fail (cogl_is_material (handle));
|
||||
|
||||
material = _cogl_material_pointer_from_handle (handle);
|
||||
layer = _cogl_material_get_layer (material, layer_index, TRUE);
|
||||
|
||||
if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA)
|
||||
set_alpha_func = set_rgb_func = TRUE;
|
||||
else if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB)
|
||||
set_rgb_func = TRUE;
|
||||
else if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_ALPHA)
|
||||
set_alpha_func = TRUE;
|
||||
|
||||
if (set_rgb_func)
|
||||
layer->texture_combine_rgb_func = func;
|
||||
if (set_alpha_func)
|
||||
layer->texture_combine_alpha_func = func;
|
||||
|
||||
layer->flags |= COGL_MATERIAL_LAYER_FLAG_DIRTY;
|
||||
layer->flags &= ~COGL_MATERIAL_LAYER_FLAG_DEFAULT_COMBINE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_layer_combine_arg_src (
|
||||
CoglHandle handle,
|
||||
gint layer_index,
|
||||
gint argument,
|
||||
CoglMaterialLayerCombineChannels channels,
|
||||
CoglMaterialLayerCombineSrc src)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
CoglMaterialLayer *layer;
|
||||
gboolean set_arg_alpha_src = FALSE;
|
||||
gboolean set_arg_rgb_src = FALSE;
|
||||
|
||||
g_return_if_fail (cogl_is_material (handle));
|
||||
g_return_if_fail (argument >=0 && argument <= 3);
|
||||
|
||||
material = _cogl_material_pointer_from_handle (handle);
|
||||
layer = _cogl_material_get_layer (material, layer_index, TRUE);
|
||||
|
||||
if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA)
|
||||
set_arg_alpha_src = set_arg_rgb_src = TRUE;
|
||||
else if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB)
|
||||
set_arg_rgb_src = TRUE;
|
||||
else if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_ALPHA)
|
||||
set_arg_alpha_src = TRUE;
|
||||
|
||||
if (set_arg_rgb_src)
|
||||
layer->texture_combine_rgb_src[argument] = src;
|
||||
if (set_arg_alpha_src)
|
||||
layer->texture_combine_alpha_src[argument] = src;
|
||||
|
||||
layer->flags |= COGL_MATERIAL_LAYER_FLAG_DIRTY;
|
||||
layer->flags &= ~COGL_MATERIAL_LAYER_FLAG_DEFAULT_COMBINE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_layer_combine_arg_op (
|
||||
CoglHandle material_handle,
|
||||
gint layer_index,
|
||||
gint argument,
|
||||
CoglMaterialLayerCombineChannels channels,
|
||||
CoglMaterialLayerCombineOp op)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
CoglMaterialLayer *layer;
|
||||
gboolean set_arg_alpha_op = FALSE;
|
||||
gboolean set_arg_rgb_op = FALSE;
|
||||
|
||||
g_return_if_fail (cogl_is_material (material_handle));
|
||||
g_return_if_fail (argument >=0 && argument <= 3);
|
||||
|
||||
material = _cogl_material_pointer_from_handle (material_handle);
|
||||
layer = _cogl_material_get_layer (material, layer_index, TRUE);
|
||||
|
||||
if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGBA)
|
||||
set_arg_alpha_op = set_arg_rgb_op = TRUE;
|
||||
else if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB)
|
||||
set_arg_rgb_op = TRUE;
|
||||
else if (channels == COGL_MATERIAL_LAYER_COMBINE_CHANNELS_ALPHA)
|
||||
set_arg_alpha_op = TRUE;
|
||||
|
||||
if (set_arg_rgb_op)
|
||||
layer->texture_combine_rgb_op[argument] = op;
|
||||
if (set_arg_alpha_op)
|
||||
layer->texture_combine_alpha_op[argument] = op;
|
||||
constant = layer->texture_combine_constant;
|
||||
constant[0] = cogl_color_get_red_float (constant_color);
|
||||
constant[1] = cogl_color_get_green_float (constant_color);
|
||||
constant[2] = cogl_color_get_blue_float (constant_color);
|
||||
constant[3] = cogl_color_get_alpha_float (constant_color);
|
||||
|
||||
layer->flags |= COGL_MATERIAL_LAYER_FLAG_DIRTY;
|
||||
layer->flags &= ~COGL_MATERIAL_LAYER_FLAG_DEFAULT_COMBINE;
|
||||
@ -690,7 +927,7 @@ cogl_material_remove_layer (CoglHandle material_handle,
|
||||
/* XXX: This API is hopfully just a stop-gap solution. Ideally cogl_enable
|
||||
* will be replaced. */
|
||||
gulong
|
||||
cogl_material_get_cogl_enable_flags (CoglHandle material_handle)
|
||||
_cogl_material_get_cogl_enable_flags (CoglHandle material_handle)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
gulong enable_flags = 0;
|
||||
@ -713,7 +950,7 @@ cogl_material_get_cogl_enable_flags (CoglHandle material_handle)
|
||||
* probably sensible to try and avoid list manipulation for every
|
||||
* primitive emitted in a scene, every frame.
|
||||
*
|
||||
* Alternativly; we could either add a _foreach function, or maybe
|
||||
* Alternatively; we could either add a _foreach function, or maybe
|
||||
* a function that gets a passed a buffer (that may be stack allocated)
|
||||
* by the caller.
|
||||
*/
|
||||
@ -748,7 +985,7 @@ cogl_material_layer_get_texture (CoglHandle layer_handle)
|
||||
}
|
||||
|
||||
gulong
|
||||
cogl_material_layer_get_flags (CoglHandle layer_handle)
|
||||
_cogl_material_layer_get_flags (CoglHandle layer_handle)
|
||||
{
|
||||
CoglMaterialLayer *layer;
|
||||
|
||||
@ -760,25 +997,34 @@ cogl_material_layer_get_flags (CoglHandle layer_handle)
|
||||
}
|
||||
|
||||
static guint
|
||||
get_n_args_for_combine_func (CoglMaterialLayerCombineFunc func)
|
||||
get_n_args_for_combine_func (GLint func)
|
||||
{
|
||||
switch (func)
|
||||
{
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_REPLACE:
|
||||
case GL_REPLACE:
|
||||
return 1;
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_MODULATE:
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD:
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_ADD_SIGNED:
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_SUBTRACT:
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_DOT3_RGB:
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_DOT3_RGBA:
|
||||
case GL_MODULATE:
|
||||
case GL_ADD:
|
||||
case GL_ADD_SIGNED:
|
||||
case GL_SUBTRACT:
|
||||
case GL_DOT3_RGB:
|
||||
case GL_DOT3_RGBA:
|
||||
return 2;
|
||||
case COGL_MATERIAL_LAYER_COMBINE_FUNC_INTERPOLATE:
|
||||
case GL_INTERPOLATE:
|
||||
return 3;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
is_mipmap_filter (CoglMaterialFilter filter)
|
||||
{
|
||||
return (filter == COGL_MATERIAL_FILTER_NEAREST_MIPMAP_NEAREST
|
||||
|| filter == COGL_MATERIAL_FILTER_LINEAR_MIPMAP_NEAREST
|
||||
|| filter == COGL_MATERIAL_FILTER_NEAREST_MIPMAP_LINEAR
|
||||
|| filter == COGL_MATERIAL_FILTER_LINEAR_MIPMAP_LINEAR);
|
||||
}
|
||||
|
||||
static void
|
||||
_cogl_material_layer_flush_gl_sampler_state (CoglMaterialLayer *layer,
|
||||
CoglLayerInfo *gl_layer_info)
|
||||
@ -851,6 +1097,9 @@ _cogl_material_layer_flush_gl_sampler_state (CoglMaterialLayer *layer,
|
||||
GE (glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND2_ALPHA,
|
||||
layer->texture_combine_alpha_op[2]));
|
||||
}
|
||||
|
||||
GE (glTexEnvfv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR,
|
||||
layer->texture_combine_constant));
|
||||
}
|
||||
|
||||
#ifndef DISABLE_MATERIAL_CACHE
|
||||
@ -976,6 +1225,13 @@ _cogl_material_flush_layers_gl_state (CoglMaterial *material,
|
||||
|
||||
GE (glActiveTexture (GL_TEXTURE0 + i));
|
||||
|
||||
_cogl_texture_set_filters (layer->texture,
|
||||
layer->min_filter,
|
||||
layer->mag_filter);
|
||||
if (is_mipmap_filter (layer->min_filter)
|
||||
|| is_mipmap_filter (layer->mag_filter))
|
||||
_cogl_texture_ensure_mipmaps (layer->texture);
|
||||
|
||||
/* FIXME: We could be more clever here and only bind the texture
|
||||
if it is different from gl_layer_info->gl_texture to avoid
|
||||
redundant GL calls. However a few other places in Cogl and
|
||||
@ -1122,12 +1378,44 @@ _cogl_material_flush_base_gl_state (CoglMaterial *material)
|
||||
if (!(ctx->current_material_flags & COGL_MATERIAL_FLAG_DEFAULT_BLEND_FUNC
|
||||
&& material->flags & COGL_MATERIAL_FLAG_DEFAULT_BLEND_FUNC))
|
||||
{
|
||||
GE (glBlendFunc (material->blend_src_factor, material->blend_dst_factor));
|
||||
#if defined (HAVE_COGL_GLES2)
|
||||
gboolean have_blend_equation_seperate = TRUE;
|
||||
#elif defined (HAVE_COGL_GL)
|
||||
gboolean have_blend_equation_seperate = FALSE;
|
||||
if (ctx->pf_glBlendEquationSeparate) /* Only GL 2.0 + */
|
||||
have_blend_equation_seperate = TRUE;
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_COGL_GLES /* GLES 1 only has glBlendFunc */
|
||||
if (material->blend_src_factor_rgb != material->blend_src_factor_alpha
|
||||
|| (material->blend_src_factor_rgb !=
|
||||
material->blend_src_factor_alpha))
|
||||
{
|
||||
if (have_blend_equation_seperate &&
|
||||
material->blend_equation_rgb != material->blend_equation_alpha)
|
||||
GE (glBlendEquationSeparate (material->blend_equation_rgb,
|
||||
material->blend_equation_alpha));
|
||||
else
|
||||
GE (glBlendEquation (material->blend_equation_rgb));
|
||||
|
||||
GE (glBlendFuncSeparate (material->blend_src_factor_rgb,
|
||||
material->blend_dst_factor_rgb,
|
||||
material->blend_src_factor_alpha,
|
||||
material->blend_dst_factor_alpha));
|
||||
GE (glBlendColor (material->blend_constant[0],
|
||||
material->blend_constant[1],
|
||||
material->blend_constant[2],
|
||||
material->blend_constant[3]));
|
||||
}
|
||||
else
|
||||
#endif
|
||||
GE (glBlendFunc (material->blend_src_factor_rgb,
|
||||
material->blend_dst_factor_rgb));
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_flush_gl_state (CoglHandle handle, ...)
|
||||
_cogl_material_flush_gl_state (CoglHandle handle, ...)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
va_list ap;
|
||||
@ -1204,3 +1492,44 @@ cogl_set_source_texture (CoglHandle texture_handle)
|
||||
cogl_set_source (ctx->default_material);
|
||||
}
|
||||
|
||||
CoglMaterialFilter
|
||||
cogl_material_layer_get_min_filter (CoglHandle layer_handle)
|
||||
{
|
||||
CoglMaterialLayer *layer;
|
||||
|
||||
g_return_val_if_fail (cogl_is_material_layer (layer_handle), 0);
|
||||
|
||||
layer = _cogl_material_layer_pointer_from_handle (layer_handle);
|
||||
|
||||
return layer->min_filter;
|
||||
}
|
||||
|
||||
CoglMaterialFilter
|
||||
cogl_material_layer_get_mag_filter (CoglHandle layer_handle)
|
||||
{
|
||||
CoglMaterialLayer *layer;
|
||||
|
||||
g_return_val_if_fail (cogl_is_material_layer (layer_handle), 0);
|
||||
|
||||
layer = _cogl_material_layer_pointer_from_handle (layer_handle);
|
||||
|
||||
return layer->mag_filter;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_material_set_layer_filters (CoglHandle handle,
|
||||
gint layer_index,
|
||||
CoglMaterialFilter min_filter,
|
||||
CoglMaterialFilter mag_filter)
|
||||
{
|
||||
CoglMaterial *material;
|
||||
CoglMaterialLayer *layer;
|
||||
|
||||
g_return_if_fail (cogl_is_material (handle));
|
||||
|
||||
material = _cogl_material_pointer_from_handle (handle);
|
||||
layer = _cogl_material_get_layer (material, layer_index, TRUE);
|
||||
|
||||
layer->min_filter = min_filter;
|
||||
layer->mag_filter = mag_filter;
|
||||
}
|
||||
|
@ -257,6 +257,59 @@ _cogl_matrix_stack_multiply (CoglMatrixStack *stack,
|
||||
stack->flushed_state = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_matrix_stack_frustum (CoglMatrixStack *stack,
|
||||
float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
CoglMatrixState *state;
|
||||
|
||||
state = _cogl_matrix_stack_top_mutable (stack);
|
||||
cogl_matrix_frustum (&state->matrix,
|
||||
left, right, bottom, top,
|
||||
z_near, z_far);
|
||||
/* mark dirty */
|
||||
stack->flushed_state = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_matrix_stack_perspective (CoglMatrixStack *stack,
|
||||
float fov_y,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
CoglMatrixState *state;
|
||||
|
||||
state = _cogl_matrix_stack_top_mutable (stack);
|
||||
cogl_matrix_perspective (&state->matrix,
|
||||
fov_y, aspect, z_near, z_far);
|
||||
/* mark dirty */
|
||||
stack->flushed_state = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_matrix_stack_ortho (CoglMatrixStack *stack,
|
||||
float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
CoglMatrixState *state;
|
||||
|
||||
state = _cogl_matrix_stack_top_mutable (stack);
|
||||
cogl_matrix_ortho (&state->matrix,
|
||||
left, right, bottom, top, z_near, z_far);
|
||||
/* mark dirty */
|
||||
stack->flushed_state = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_matrix_stack_get (CoglMatrixStack *stack,
|
||||
CoglMatrix *matrix)
|
||||
@ -280,25 +333,6 @@ _cogl_matrix_stack_set (CoglMatrixStack *stack,
|
||||
stack->flushed_state = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_matrix_stack_frustum (CoglMatrixStack *stack,
|
||||
float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
CoglMatrixState *state;
|
||||
|
||||
state = _cogl_matrix_stack_top_mutable (stack);
|
||||
cogl_matrix_frustum (&state->matrix,
|
||||
left, right, bottom, top,
|
||||
z_near, z_far);
|
||||
/* mark dirty */
|
||||
stack->flushed_state = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_matrix_stack_flush_to_gl (CoglMatrixStack *stack,
|
||||
GLenum gl_mode)
|
||||
|
@ -51,10 +51,6 @@ void _cogl_matrix_stack_rotate (CoglMatrixStack *stack,
|
||||
float z);
|
||||
void _cogl_matrix_stack_multiply (CoglMatrixStack *stack,
|
||||
const CoglMatrix *matrix);
|
||||
void _cogl_matrix_stack_get (CoglMatrixStack *stack,
|
||||
CoglMatrix *matrix);
|
||||
void _cogl_matrix_stack_set (CoglMatrixStack *stack,
|
||||
const CoglMatrix *matrix);
|
||||
void _cogl_matrix_stack_frustum (CoglMatrixStack *stack,
|
||||
float left,
|
||||
float right,
|
||||
@ -62,6 +58,22 @@ void _cogl_matrix_stack_frustum (CoglMatrixStack *stack,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far);
|
||||
void _cogl_matrix_stack_perspective (CoglMatrixStack *stack,
|
||||
float fov_y,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far);
|
||||
void _cogl_matrix_stack_ortho (CoglMatrixStack *stack,
|
||||
float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float z_near,
|
||||
float z_far);
|
||||
void _cogl_matrix_stack_get (CoglMatrixStack *stack,
|
||||
CoglMatrix *matrix);
|
||||
void _cogl_matrix_stack_set (CoglMatrixStack *stack,
|
||||
const CoglMatrix *matrix);
|
||||
void _cogl_matrix_stack_flush_to_gl (CoglMatrixStack *stack,
|
||||
GLenum gl_mode);
|
||||
|
||||
|
@ -151,21 +151,6 @@ cogl_matrix_invert (CoglMatrix *matrix)
|
||||
}
|
||||
#endif
|
||||
|
||||
void
|
||||
cogl_matrix_transform_point (const CoglMatrix *matrix,
|
||||
float *x,
|
||||
float *y,
|
||||
float *z,
|
||||
float *w)
|
||||
{
|
||||
float _x = *x, _y = *y, _z = *z, _w = *w;
|
||||
|
||||
*x = matrix->xx * _x + matrix->xy * _y + matrix->xz * _z + matrix->xw * _w;
|
||||
*y = matrix->yx * _x + matrix->yy * _y + matrix->yz * _z + matrix->yw * _w;
|
||||
*z = matrix->zx * _x + matrix->zy * _y + matrix->zz * _z + matrix->zw * _w;
|
||||
*w = matrix->wx * _x + matrix->wy * _y + matrix->wz * _z + matrix->ww * _w;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_matrix_frustum (CoglMatrix *matrix,
|
||||
float left,
|
||||
@ -208,6 +193,62 @@ cogl_matrix_frustum (CoglMatrix *matrix,
|
||||
cogl_matrix_multiply (matrix, matrix, &frustum);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_matrix_perspective (CoglMatrix *matrix,
|
||||
float fov_y,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
float ymax = z_near * tan (fov_y * G_PI / 360.0);
|
||||
|
||||
cogl_matrix_frustum (matrix,
|
||||
-ymax * aspect, /* left */
|
||||
ymax * aspect, /* right */
|
||||
-ymax, /* bottom */
|
||||
ymax, /* top */
|
||||
z_near,
|
||||
z_far);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_matrix_ortho (CoglMatrix *matrix,
|
||||
float left,
|
||||
float right,
|
||||
float bottom,
|
||||
float top,
|
||||
float near,
|
||||
float far)
|
||||
{
|
||||
CoglMatrix ortho;
|
||||
|
||||
/* column 0 */
|
||||
ortho.xx = 2.0 / (right - left);
|
||||
ortho.yx = 0.0;
|
||||
ortho.zx = 0.0;
|
||||
ortho.wx = 0.0;
|
||||
|
||||
/* column 1 */
|
||||
ortho.xy = 0.0;
|
||||
ortho.yy = 2.0 / (top - bottom);
|
||||
ortho.zy = 0.0;
|
||||
ortho.wy = 0.0;
|
||||
|
||||
/* column 2 */
|
||||
ortho.xz = 0.0;
|
||||
ortho.yz = 0.0;
|
||||
ortho.zz = -2.0 / (far - near);
|
||||
ortho.wz = 0.0;
|
||||
|
||||
/* column 3 */
|
||||
ortho.xw = -(right + left) / (right - left);
|
||||
ortho.yw = -(top + bottom) / (top - bottom);
|
||||
ortho.zw = -(far + near) / (far - near);
|
||||
ortho.ww = 1.0;
|
||||
|
||||
cogl_matrix_multiply (matrix, matrix, &ortho);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_matrix_init_from_array (CoglMatrix *matrix, const float *array)
|
||||
{
|
||||
@ -220,3 +261,19 @@ cogl_matrix_get_array (const CoglMatrix *matrix)
|
||||
return (float *)matrix;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_matrix_transform_point (const CoglMatrix *matrix,
|
||||
float *x,
|
||||
float *y,
|
||||
float *z,
|
||||
float *w)
|
||||
{
|
||||
float _x = *x, _y = *y, _z = *z, _w = *w;
|
||||
|
||||
*x = matrix->xx * _x + matrix->xy * _y + matrix->xz * _z + matrix->xw * _w;
|
||||
*y = matrix->yx * _x + matrix->yy * _y + matrix->yz * _z + matrix->yw * _w;
|
||||
*z = matrix->zx * _x + matrix->zy * _y + matrix->zz * _z + matrix->zw * _w;
|
||||
*w = matrix->wx * _x + matrix->wy * _y + matrix->wz * _z + matrix->ww * _w;
|
||||
}
|
||||
|
||||
|
||||
|
@ -29,7 +29,8 @@
|
||||
#include "cogl-internal.h"
|
||||
#include "cogl-context.h"
|
||||
#include "cogl-texture-private.h"
|
||||
#include "cogl-material.h"
|
||||
#include "cogl-material-private.h"
|
||||
#include "cogl-vertex-buffer-private.h"
|
||||
|
||||
#include <string.h>
|
||||
#include <gmodule.h>
|
||||
@ -39,16 +40,8 @@
|
||||
|
||||
#ifdef HAVE_COGL_GL
|
||||
|
||||
#define glDrawRangeElements ctx->pf_glDrawRangeElements
|
||||
#define glClientActiveTexture ctx->pf_glClientActiveTexture
|
||||
|
||||
#else
|
||||
|
||||
/* GLES doesn't have glDrawRangeElements, so we simply pretend it does
|
||||
* but that it makes no use of the start, end constraints: */
|
||||
#define glDrawRangeElements(mode, start, end, count, type, indices) \
|
||||
glDrawElements (mode, count, type, indices)
|
||||
|
||||
#endif
|
||||
|
||||
/* these are defined in the particular backend */
|
||||
@ -63,7 +56,6 @@ _cogl_journal_flush_quad_batch (CoglJournalEntry *batch_start,
|
||||
gint batch_len,
|
||||
GLfloat *vertex_pointer)
|
||||
{
|
||||
int needed_indices;
|
||||
gsize stride;
|
||||
int i;
|
||||
gulong enable_flags = 0;
|
||||
@ -72,35 +64,6 @@ _cogl_journal_flush_quad_batch (CoglJournalEntry *batch_start,
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
/* The indices are always the same sequence regardless of the vertices so we
|
||||
* only need to change it if there are more vertices than ever before. */
|
||||
needed_indices = batch_len * 6;
|
||||
if (needed_indices > ctx->static_indices->len)
|
||||
{
|
||||
int old_len = ctx->static_indices->len;
|
||||
int vert_num = old_len / 6 * 4;
|
||||
GLushort *q;
|
||||
|
||||
/* Add two triangles for each quad to the list of
|
||||
indices. That makes six new indices but two of the
|
||||
vertices in the triangles are shared. */
|
||||
g_array_set_size (ctx->static_indices, needed_indices);
|
||||
q = &g_array_index (ctx->static_indices, GLushort, old_len);
|
||||
|
||||
for (i = old_len;
|
||||
i < ctx->static_indices->len;
|
||||
i += 6, vert_num += 4)
|
||||
{
|
||||
*(q++) = vert_num + 0;
|
||||
*(q++) = vert_num + 1;
|
||||
*(q++) = vert_num + 3;
|
||||
|
||||
*(q++) = vert_num + 1;
|
||||
*(q++) = vert_num + 2;
|
||||
*(q++) = vert_num + 3;
|
||||
}
|
||||
}
|
||||
|
||||
/* XXX NB:
|
||||
* Our vertex data is arranged as follows:
|
||||
* 4 vertices per quad: 2 GLfloats per position,
|
||||
@ -112,16 +75,16 @@ _cogl_journal_flush_quad_batch (CoglJournalEntry *batch_start,
|
||||
disable_mask = (1 << batch_start->n_layers) - 1;
|
||||
disable_mask = ~disable_mask;
|
||||
|
||||
cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK,
|
||||
batch_start->fallback_mask,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
disable_mask,
|
||||
/* Redundant when dealing with unsliced
|
||||
* textures but does no harm... */
|
||||
COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE,
|
||||
batch_start->layer0_override_texture,
|
||||
NULL);
|
||||
_cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK,
|
||||
batch_start->fallback_mask,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
disable_mask,
|
||||
/* Redundant when dealing with unsliced
|
||||
* textures but does no harm... */
|
||||
COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE,
|
||||
batch_start->layer0_override_texture,
|
||||
NULL);
|
||||
|
||||
for (i = 0; i < batch_start->n_layers; i++)
|
||||
{
|
||||
@ -140,7 +103,7 @@ _cogl_journal_flush_quad_batch (CoglJournalEntry *batch_start,
|
||||
|
||||
/* FIXME: This api is a bit yukky, ideally it will be removed if we
|
||||
* re-work the cogl_enable mechanism */
|
||||
enable_flags |= cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
enable_flags |= _cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
|
||||
if (ctx->enable_backface_culling)
|
||||
enable_flags |= COGL_ENABLE_BACKFACE_CULLING;
|
||||
@ -150,12 +113,32 @@ _cogl_journal_flush_quad_batch (CoglJournalEntry *batch_start,
|
||||
|
||||
GE (glVertexPointer (2, GL_FLOAT, stride, vertex_pointer));
|
||||
_cogl_current_matrix_state_flush ();
|
||||
GE (glDrawRangeElements (GL_TRIANGLES,
|
||||
0, ctx->static_indices->len - 1,
|
||||
6 * batch_len,
|
||||
GL_UNSIGNED_SHORT,
|
||||
ctx->static_indices->data));
|
||||
|
||||
#ifdef HAVE_COGL_GL
|
||||
|
||||
GE( glDrawArrays (GL_QUADS, 0, batch_len * 4) );
|
||||
|
||||
#else /* HAVE_COGL_GL */
|
||||
|
||||
/* GLES doesn't support GL_QUADS so we will use GL_TRIANGLES and
|
||||
indices */
|
||||
{
|
||||
int needed_indices = batch_len * 6;
|
||||
CoglHandle indices_handle
|
||||
= cogl_vertex_buffer_indices_get_for_quads (needed_indices);
|
||||
CoglVertexBufferIndices *indices
|
||||
= _cogl_vertex_buffer_indices_pointer_from_handle (indices_handle);
|
||||
|
||||
GE (glBindBuffer (GL_ELEMENT_ARRAY_BUFFER,
|
||||
GPOINTER_TO_UINT (indices->vbo_name)));
|
||||
GE (glDrawElements (GL_TRIANGLES,
|
||||
6 * batch_len,
|
||||
indices->type,
|
||||
NULL));
|
||||
GE (glBindBuffer (GL_ELEMENT_ARRAY_BUFFER, 0));
|
||||
}
|
||||
|
||||
#endif /* HAVE_COGL_GL */
|
||||
|
||||
/* DEBUGGING CODE XXX:
|
||||
* This path will cause all rectangles to be drawn with a red, green
|
||||
@ -177,7 +160,7 @@ _cogl_journal_flush_quad_batch (CoglJournalEntry *batch_start,
|
||||
color == 1 ? 0xff : 0x00,
|
||||
color == 2 ? 0xff : 0x00,
|
||||
0xff);
|
||||
cogl_material_flush_gl_state (outline, NULL);
|
||||
_cogl_material_flush_gl_state (outline, NULL);
|
||||
_cogl_current_matrix_state_flush ();
|
||||
GE( glDrawArrays (GL_LINE_LOOP, 4 * i, 4) );
|
||||
}
|
||||
@ -791,7 +774,7 @@ _cogl_rectangles_with_multitexture_coords (
|
||||
/* We don't support multi texturing using textures with any waste if the
|
||||
* user has supplied a custom texture matrix, since we don't know if
|
||||
* the result will end up trying to texture from the waste area. */
|
||||
flags = cogl_material_layer_get_flags (layer);
|
||||
flags = _cogl_material_layer_get_flags (layer);
|
||||
if (flags & COGL_MATERIAL_LAYER_FLAG_HAS_USER_MATRIX
|
||||
&& _cogl_texture_span_has_waste (texture, 0, 0))
|
||||
{
|
||||
@ -1041,13 +1024,13 @@ _cogl_texture_sliced_polygon (CoglTextureVertex *vertices,
|
||||
v += stride;
|
||||
}
|
||||
|
||||
cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
(guint32)~1, /* disable all except the
|
||||
_cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
(guint32)~1, /* disable all except the
|
||||
first layer */
|
||||
COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE,
|
||||
gl_handle,
|
||||
NULL);
|
||||
COGL_MATERIAL_FLUSH_LAYER0_OVERRIDE,
|
||||
gl_handle,
|
||||
NULL);
|
||||
_cogl_current_matrix_state_flush ();
|
||||
|
||||
GE( glDrawArrays (GL_TRIANGLE_FAN, 0, n_vertices) );
|
||||
@ -1136,10 +1119,10 @@ _cogl_multitexture_unsliced_polygon (CoglTextureVertex *vertices,
|
||||
c[3] = cogl_color_get_alpha_float (&vertices[i].color);
|
||||
}
|
||||
|
||||
cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK,
|
||||
fallback_mask,
|
||||
NULL);
|
||||
_cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK,
|
||||
fallback_mask,
|
||||
NULL);
|
||||
_cogl_current_matrix_state_flush ();
|
||||
|
||||
GE (glDrawArrays (GL_TRIANGLE_FAN, 0, n_vertices));
|
||||
@ -1175,7 +1158,6 @@ cogl_polygon (CoglTextureVertex *vertices,
|
||||
{
|
||||
CoglHandle layer = (CoglHandle)tmp->data;
|
||||
CoglHandle tex_handle = cogl_material_layer_get_texture (layer);
|
||||
CoglTexture *tex = _cogl_texture_pointer_from_handle (tex_handle);
|
||||
|
||||
if (i == 0 && cogl_texture_is_sliced (tex_handle))
|
||||
{
|
||||
@ -1203,7 +1185,8 @@ cogl_polygon (CoglTextureVertex *vertices,
|
||||
use_sliced_polygon_fallback = TRUE;
|
||||
n_layers = 1;
|
||||
|
||||
if (tex->min_filter != GL_NEAREST || tex->mag_filter != GL_NEAREST)
|
||||
if (cogl_material_layer_get_min_filter (layer) != GL_NEAREST
|
||||
|| cogl_material_layer_get_mag_filter (layer) != GL_NEAREST)
|
||||
{
|
||||
static gboolean warning_seen = FALSE;
|
||||
if (!warning_seen)
|
||||
@ -1217,11 +1200,14 @@ cogl_polygon (CoglTextureVertex *vertices,
|
||||
}
|
||||
|
||||
#ifdef HAVE_COGL_GL
|
||||
/* Temporarily change the wrapping mode on all of the slices to use
|
||||
* a transparent border
|
||||
* XXX: it's doesn't look like we save/restore this, like the comment
|
||||
* implies? */
|
||||
_cogl_texture_set_wrap_mode_parameter (tex, GL_CLAMP_TO_BORDER);
|
||||
{
|
||||
CoglTexture *tex = _cogl_texture_pointer_from_handle (tex_handle);
|
||||
/* Temporarily change the wrapping mode on all of the slices to use
|
||||
* a transparent border
|
||||
* XXX: it's doesn't look like we save/restore this, like
|
||||
* the comment implies? */
|
||||
_cogl_texture_set_wrap_mode_parameter (tex, GL_CLAMP_TO_BORDER);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
@ -1254,7 +1240,7 @@ cogl_polygon (CoglTextureVertex *vertices,
|
||||
|
||||
/* Prepare GL state */
|
||||
enable_flags = COGL_ENABLE_VERTEX_ARRAY;
|
||||
enable_flags |= cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
enable_flags |= _cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
|
||||
if (ctx->enable_backface_culling)
|
||||
enable_flags |= COGL_ENABLE_BACKFACE_CULLING;
|
||||
|
@ -103,159 +103,6 @@ cogl_handle_get_type (void)
|
||||
return our_type;
|
||||
}
|
||||
|
||||
GType
|
||||
cogl_pixel_format_get_type (void)
|
||||
{
|
||||
static GType gtype = 0;
|
||||
|
||||
if (G_UNLIKELY (gtype == 0))
|
||||
{
|
||||
static const GEnumValue values[] = {
|
||||
{ COGL_PIXEL_FORMAT_ANY, "COGL_PIXEL_FORMAT_ANY", "any" },
|
||||
{ COGL_PIXEL_FORMAT_A_8, "COGL_PIXEL_FORMAT_A_8", "a-8" },
|
||||
{ COGL_PIXEL_FORMAT_RGB_565, "COGL_PIXEL_FORMAT_RGB_565", "rgb-565" },
|
||||
{ COGL_PIXEL_FORMAT_RGBA_4444, "COGL_PIXEL_FORMAT_RGBA_4444", "rgba-4444" },
|
||||
{ COGL_PIXEL_FORMAT_RGBA_5551, "COGL_PIXEL_FORMAT_RGBA_5551", "rgba-5551" },
|
||||
{ COGL_PIXEL_FORMAT_YUV, "COGL_PIXEL_FORMAT_YUV", "yuv" },
|
||||
{ COGL_PIXEL_FORMAT_G_8, "COGL_PIXEL_FORMAT_G_8", "g-8" },
|
||||
{ COGL_PIXEL_FORMAT_RGB_888, "COGL_PIXEL_FORMAT_RGB_888", "rgb-888" },
|
||||
{ COGL_PIXEL_FORMAT_BGR_888, "COGL_PIXEL_FORMAT_BGR_888", "bgr-888" },
|
||||
{ COGL_PIXEL_FORMAT_RGBA_8888, "COGL_PIXEL_FORMAT_RGBA_8888", "rgba-8888" },
|
||||
{ COGL_PIXEL_FORMAT_BGRA_8888, "COGL_PIXEL_FORMAT_BGRA_8888", "bgra-8888" },
|
||||
{ COGL_PIXEL_FORMAT_ARGB_8888, "COGL_PIXEL_FORMAT_ARGB_8888", "argb-8888" },
|
||||
{ COGL_PIXEL_FORMAT_ABGR_8888, "COGL_PIXEL_FORMAT_ABGR_8888", "abgr-8888" },
|
||||
{ COGL_PIXEL_FORMAT_RGBA_8888_PRE, "COGL_PIXEL_FORMAT_RGBA_8888_PRE", "rgba-8888-pre" },
|
||||
{ COGL_PIXEL_FORMAT_BGRA_8888_PRE, "COGL_PIXEL_FORMAT_BGRA_8888_PRE", "bgra-8888-pre" },
|
||||
{ COGL_PIXEL_FORMAT_ARGB_8888_PRE, "COGL_PIXEL_FORMAT_ARGB_8888_PRE", "argb-8888-pre" },
|
||||
{ COGL_PIXEL_FORMAT_ABGR_8888_PRE, "COGL_PIXEL_FORMAT_ABGR_8888_PRE", "abgr-8888-pre" },
|
||||
{ COGL_PIXEL_FORMAT_RGBA_4444_PRE, "COGL_PIXEL_FORMAT_RGBA_4444_PRE", "rgba-4444-pre" },
|
||||
{ COGL_PIXEL_FORMAT_RGBA_5551_PRE, "COGL_PIXEL_FORMAT_RGBA_5551_PRE", "rgba-5551-pre" },
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
|
||||
gtype =
|
||||
g_enum_register_static (g_intern_static_string ("CoglPixelFormat"),
|
||||
values);
|
||||
}
|
||||
|
||||
return gtype;
|
||||
}
|
||||
|
||||
GType
|
||||
cogl_feature_flags_get_type (void)
|
||||
{
|
||||
static GType gtype = 0;
|
||||
|
||||
if (G_UNLIKELY (gtype == 0))
|
||||
{
|
||||
static const GFlagsValue values[] = {
|
||||
{ COGL_FEATURE_TEXTURE_RECTANGLE, "COGL_FEATURE_TEXTURE_RECTANGLE", "texture-rectangle" },
|
||||
{ COGL_FEATURE_TEXTURE_NPOT, "COGL_FEATURE_TEXTURE_NPOT", "texture-npot" },
|
||||
{ COGL_FEATURE_TEXTURE_YUV, "COGL_FEATURE_TEXTURE_YUV", "yuv" },
|
||||
{ COGL_FEATURE_TEXTURE_READ_PIXELS, "COGL_FEATURE_TEXTURE_READ_PIXELS", "read-pixels" },
|
||||
{ COGL_FEATURE_SHADERS_GLSL, "COGL_FEATURE_SHADERS_GLSL", "shaders-glsl" },
|
||||
{ COGL_FEATURE_OFFSCREEN, "COGL_FEATURE_OFFSCREEN", "offscreen" },
|
||||
{ COGL_FEATURE_OFFSCREEN_MULTISAMPLE, "COGL_FEATURE_OFFSCREEN_MULTISAMPLE", "offscreen-multisample" },
|
||||
{ COGL_FEATURE_OFFSCREEN_BLIT, "COGL_FEATURE_OFFSCREEN_BLIT", "offscreen-blit" },
|
||||
{ COGL_FEATURE_FOUR_CLIP_PLANES, "COGL_FEATURE_FOUR_CLIP_PLANES", "four-clip-planes" },
|
||||
{ COGL_FEATURE_STENCIL_BUFFER, "COGL_FEATURE_STENCIL_BUFFER", "stencil-buffer" },
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
|
||||
gtype =
|
||||
g_flags_register_static (g_intern_static_string ("CoglFeatureFlags"),
|
||||
values);
|
||||
}
|
||||
|
||||
return gtype;
|
||||
}
|
||||
|
||||
GType
|
||||
cogl_buffer_target_get_type (void)
|
||||
{
|
||||
static GType gtype = 0;
|
||||
|
||||
if (G_UNLIKELY (gtype == 0))
|
||||
{
|
||||
static const GFlagsValue values[] = {
|
||||
{ COGL_WINDOW_BUFFER, "COGL_WINDOW_BUFFER", "window-buffer" },
|
||||
{ COGL_OFFSCREEN_BUFFER, "COGL_OFFSCREEN_BUFFER", "offscreen-buffer" },
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
|
||||
gtype =
|
||||
g_flags_register_static (g_intern_static_string ("CoglBufferTarget"),
|
||||
values);
|
||||
}
|
||||
|
||||
return gtype;
|
||||
}
|
||||
|
||||
GType
|
||||
cogl_matrix_mode_get_type (void)
|
||||
{
|
||||
static GType gtype = 0;
|
||||
|
||||
if (G_UNLIKELY (gtype == 0))
|
||||
{
|
||||
static const GEnumValue values[] = {
|
||||
{ COGL_MATRIX_MODELVIEW, "COGL_MATRIX_MODELVIEW", "modelview" },
|
||||
{ COGL_MATRIX_PROJECTION, "COGL_MATRIX_PROJECTION", "projection" },
|
||||
{ COGL_MATRIX_TEXTURE, "COGL_MATRIX_TEXTURE", "texture" },
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
|
||||
gtype =
|
||||
g_enum_register_static (g_intern_static_string ("CoglMatrixMode"),
|
||||
values);
|
||||
}
|
||||
|
||||
return gtype;
|
||||
}
|
||||
|
||||
GType
|
||||
cogl_texture_flags_get_type (void)
|
||||
{
|
||||
static GType gtype = 0;
|
||||
|
||||
if (G_UNLIKELY (gtype == 0))
|
||||
{
|
||||
static const GFlagsValue values[] = {
|
||||
{ COGL_TEXTURE_NONE, "COGL_TEXTURE_NONE", "none" },
|
||||
{ COGL_TEXTURE_AUTO_MIPMAP, "COGL_TEXTURE_AUTO_MIPMAP", "auto-mipmap" },
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
|
||||
gtype =
|
||||
g_flags_register_static (g_intern_static_string ("CoglTextureFlags"),
|
||||
values);
|
||||
}
|
||||
|
||||
return gtype;
|
||||
}
|
||||
|
||||
GType
|
||||
cogl_fog_mode_get_type (void)
|
||||
{
|
||||
static GType gtype = 0;
|
||||
|
||||
if (G_UNLIKELY (gtype == 0))
|
||||
{
|
||||
static const GEnumValue values[] = {
|
||||
{ COGL_FOG_MODE_LINEAR, "COGL_FOG_MODE_LINEAR", "linear" },
|
||||
{ COGL_FOG_MODE_EXPONENTIAL, "COGL_FOG_MODE_EXPONENTIAL", "exponential" },
|
||||
{ COGL_FOG_MODE_EXPONENTIAL_SQUARED, "COGL_FOG_MODE_EXPONENTIAL_SQUARED", "exponential-squared" },
|
||||
{ 0, NULL, NULL }
|
||||
};
|
||||
|
||||
gtype =
|
||||
g_enum_register_static (g_intern_static_string ("CoglFogMode"),
|
||||
values);
|
||||
}
|
||||
|
||||
return gtype;
|
||||
}
|
||||
|
||||
/*
|
||||
* CoglFixed
|
||||
*/
|
||||
|
@ -99,9 +99,9 @@ typedef struct _CoglVertexBufferAttrib
|
||||
union _u
|
||||
{
|
||||
const void *pointer;
|
||||
gsize vbo_offset;
|
||||
size_t vbo_offset;
|
||||
} u;
|
||||
gsize span_bytes;
|
||||
size_t span_bytes;
|
||||
guint16 stride;
|
||||
guint8 n_components;
|
||||
guint8 texture_unit;
|
||||
@ -129,25 +129,41 @@ typedef struct _CoglVertexBufferVBO
|
||||
{
|
||||
CoglVertexBufferVBOFlags flags;
|
||||
|
||||
/* Note: this is a pointer to handle fallbacks, and normally holds
|
||||
* a GLuint value */
|
||||
gpointer vbo_name; /*!< The name of the corresponding buffer object */
|
||||
gsize vbo_bytes; /*!< The lengh of the allocated buffer object in bytes */
|
||||
/* Note: this is a pointer to handle fallbacks. It normally holds
|
||||
* a GLuint VBO name, but when the driver doesn't support VBOs then
|
||||
* this simply points to an malloc'd buffer. */
|
||||
void *vbo_name; /*!< The name of the corresponding buffer object */
|
||||
size_t vbo_bytes; /*!< The lengh of the allocated buffer object in bytes */
|
||||
GList *attributes;
|
||||
} CoglVertexBufferVBO;
|
||||
|
||||
typedef struct _CoglVertexBufferIndices
|
||||
{
|
||||
CoglHandleObject _parent;
|
||||
|
||||
/* Note: this is a pointer to handle fallbacks. It normally holds
|
||||
* a GLuint VBO name, but when the driver doesn't support VBOs then
|
||||
* this simply points to an malloc'd buffer. */
|
||||
void *vbo_name;
|
||||
GLenum type;
|
||||
} CoglVertexBufferIndices;
|
||||
|
||||
typedef struct _CoglVertexBuffer
|
||||
{
|
||||
CoglHandleObject _parent;
|
||||
|
||||
guint n_vertices; /*!< The number of vertices in the buffer */
|
||||
GList *submitted_vbos; /* The VBOs currently submitted to the GPU */
|
||||
int n_vertices; /*!< The number of vertices in the buffer */
|
||||
GList *submitted_vbos; /* The VBOs currently submitted to the GPU */
|
||||
|
||||
/* Note: new_attributes is normally NULL and only valid while
|
||||
* modifying a buffer. */
|
||||
GList *new_attributes; /*!< attributes pending submission */
|
||||
GList *new_attributes; /*!< attributes pending submission */
|
||||
|
||||
} CoglVertexBuffer;
|
||||
|
||||
CoglVertexBuffer *_cogl_vertex_buffer_pointer_from_handle (CoglHandle handle);
|
||||
CoglVertexBufferIndices *
|
||||
_cogl_vertex_buffer_indices_pointer_from_handle (CoglHandle handle);
|
||||
|
||||
#endif /* __COGL_VERTEX_BUFFER_H */
|
||||
|
||||
|
@ -136,6 +136,7 @@
|
||||
#include "cogl-handle.h"
|
||||
#include "cogl-vertex-buffer-private.h"
|
||||
#include "cogl-texture-private.h"
|
||||
#include "cogl-material-private.h"
|
||||
|
||||
#define PAD_FOR_ALIGNMENT(VAR, TYPE_SIZE) \
|
||||
(VAR = TYPE_SIZE + ((VAR - 1) & ~(TYPE_SIZE - 1)))
|
||||
@ -200,8 +201,10 @@
|
||||
#endif /* HAVE_COGL_GL */
|
||||
|
||||
static void _cogl_vertex_buffer_free (CoglVertexBuffer *buffer);
|
||||
static void _cogl_vertex_buffer_indices_free (CoglVertexBufferIndices *buffer_indices);
|
||||
|
||||
COGL_HANDLE_DEFINE (VertexBuffer, vertex_buffer);
|
||||
COGL_HANDLE_DEFINE (VertexBufferIndices, vertex_buffer_indices);
|
||||
|
||||
CoglHandle
|
||||
cogl_vertex_buffer_new (guint n_vertices)
|
||||
@ -411,13 +414,13 @@ get_gl_type_size (CoglVertexBufferAttribFlags flags)
|
||||
}
|
||||
|
||||
void
|
||||
cogl_vertex_buffer_add (CoglHandle handle,
|
||||
const char *attribute_name,
|
||||
guint8 n_components,
|
||||
GLenum gl_type,
|
||||
gboolean normalized,
|
||||
guint16 stride,
|
||||
const void *pointer)
|
||||
cogl_vertex_buffer_add (CoglHandle handle,
|
||||
const char *attribute_name,
|
||||
guint8 n_components,
|
||||
CoglAttributeType type,
|
||||
gboolean normalized,
|
||||
guint16 stride,
|
||||
const void *pointer)
|
||||
{
|
||||
CoglVertexBuffer *buffer;
|
||||
GQuark name_quark = g_quark_from_string (attribute_name);
|
||||
@ -485,7 +488,7 @@ cogl_vertex_buffer_add (CoglHandle handle,
|
||||
attribute->u.pointer = pointer;
|
||||
attribute->texture_unit = texture_unit;
|
||||
|
||||
flags |= get_attribute_gl_type_flag_from_gl_type (gl_type);
|
||||
flags |= get_attribute_gl_type_flag_from_gl_type (type);
|
||||
flags |= COGL_VERTEX_BUFFER_ATTRIB_FLAG_ENABLED;
|
||||
|
||||
/* Note: We currently just assume, if an attribute is *ever* updated
|
||||
@ -1638,14 +1641,14 @@ enable_state_for_drawing_buffer (CoglVertexBuffer *buffer)
|
||||
}
|
||||
}
|
||||
|
||||
cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK,
|
||||
fallback_mask,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
disable_mask,
|
||||
NULL);
|
||||
_cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_FALLBACK_MASK,
|
||||
fallback_mask,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
disable_mask,
|
||||
NULL);
|
||||
|
||||
enable_flags |= cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
enable_flags |= _cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
|
||||
if (ctx->enable_backface_culling)
|
||||
enable_flags |= COGL_ENABLE_BACKFACE_CULLING;
|
||||
@ -1716,23 +1719,21 @@ disable_state_for_drawing_buffer (CoglVertexBuffer *buffer)
|
||||
}
|
||||
|
||||
void
|
||||
cogl_vertex_buffer_draw (CoglHandle handle,
|
||||
GLenum mode,
|
||||
GLint first,
|
||||
GLsizei count)
|
||||
cogl_vertex_buffer_draw (CoglHandle handle,
|
||||
CoglVerticesMode mode,
|
||||
int first,
|
||||
int count)
|
||||
{
|
||||
CoglVertexBuffer *buffer;
|
||||
|
||||
if (!cogl_is_vertex_buffer (handle))
|
||||
return;
|
||||
|
||||
cogl_clip_ensure ();
|
||||
|
||||
buffer = _cogl_vertex_buffer_pointer_from_handle (handle);
|
||||
|
||||
enable_state_for_drawing_buffer (buffer);
|
||||
|
||||
cogl_clip_ensure ();
|
||||
_cogl_current_matrix_state_flush ();
|
||||
enable_state_for_drawing_buffer (buffer);
|
||||
|
||||
/* FIXME: flush cogl cache */
|
||||
GE (glDrawArrays (mode, first, count));
|
||||
@ -1740,35 +1741,127 @@ cogl_vertex_buffer_draw (CoglHandle handle,
|
||||
disable_state_for_drawing_buffer (buffer);
|
||||
}
|
||||
|
||||
static int
|
||||
get_indices_type_size (GLuint indices_type)
|
||||
{
|
||||
if (indices_type == GL_UNSIGNED_BYTE)
|
||||
return sizeof (GLubyte);
|
||||
if (indices_type == GL_UNSIGNED_SHORT)
|
||||
return sizeof (GLushort);
|
||||
else
|
||||
{
|
||||
g_critical ("Unknown indices type %d\n", indices_type);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_vertex_buffer_indices_new (CoglIndicesType indices_type,
|
||||
const void *indices_array,
|
||||
int indices_len)
|
||||
{
|
||||
gboolean fallback =
|
||||
(cogl_get_features () & COGL_FEATURE_VBOS) ? FALSE : TRUE;
|
||||
size_t indices_bytes;
|
||||
CoglVertexBufferIndices *indices;
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, 0);
|
||||
|
||||
indices = g_slice_alloc (sizeof (CoglVertexBufferIndices));
|
||||
|
||||
if (indices_type == COGL_INDICES_TYPE_UNSIGNED_BYTE)
|
||||
indices->type = GL_UNSIGNED_BYTE;
|
||||
else if (indices_type == COGL_INDICES_TYPE_UNSIGNED_SHORT)
|
||||
indices->type = GL_UNSIGNED_SHORT;
|
||||
else
|
||||
{
|
||||
g_critical ("unknown indices type %d", indices_type);
|
||||
g_slice_free (CoglVertexBufferIndices, indices);
|
||||
return 0;
|
||||
}
|
||||
|
||||
indices_bytes = get_indices_type_size (indices->type) * indices_len;
|
||||
if (fallback)
|
||||
{
|
||||
indices->vbo_name = g_malloc (indices_len);
|
||||
memcpy (indices->vbo_name, indices_array, indices_bytes);
|
||||
}
|
||||
else
|
||||
{
|
||||
GE (glGenBuffers (1, (GLuint *)&indices->vbo_name));
|
||||
GE (glBindBuffer (GL_ELEMENT_ARRAY_BUFFER,
|
||||
GPOINTER_TO_UINT (indices->vbo_name)));
|
||||
GE (glBufferData (GL_ELEMENT_ARRAY_BUFFER,
|
||||
indices_bytes,
|
||||
indices_array,
|
||||
GL_STATIC_DRAW));
|
||||
GE (glBindBuffer (GL_ELEMENT_ARRAY_BUFFER, 0));
|
||||
}
|
||||
|
||||
return _cogl_vertex_buffer_indices_handle_new (indices);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_vertex_buffer_draw_elements (CoglHandle handle,
|
||||
GLenum mode,
|
||||
GLuint min_index,
|
||||
GLuint max_index,
|
||||
GLsizei count,
|
||||
GLenum indices_type,
|
||||
const GLvoid *indices)
|
||||
_cogl_vertex_buffer_indices_free (CoglVertexBufferIndices *indices)
|
||||
{
|
||||
gboolean fallback =
|
||||
(cogl_get_features () & COGL_FEATURE_VBOS) ? FALSE : TRUE;
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
if (fallback)
|
||||
g_free (indices->vbo_name);
|
||||
else
|
||||
GE (glDeleteBuffers (1, (GLuint *)&indices->vbo_name));
|
||||
|
||||
g_slice_free (CoglVertexBufferIndices, indices);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_vertex_buffer_draw_elements (CoglHandle handle,
|
||||
CoglVerticesMode mode,
|
||||
CoglHandle indices_handle,
|
||||
int min_index,
|
||||
int max_index,
|
||||
int indices_offset,
|
||||
int count)
|
||||
{
|
||||
CoglVertexBuffer *buffer;
|
||||
gboolean fallback =
|
||||
(cogl_get_features () & COGL_FEATURE_VBOS) ? FALSE : TRUE;
|
||||
size_t byte_offset;
|
||||
CoglVertexBufferIndices *indices = NULL;
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
if (!cogl_is_vertex_buffer (handle))
|
||||
return;
|
||||
|
||||
cogl_clip_ensure ();
|
||||
|
||||
buffer = _cogl_vertex_buffer_pointer_from_handle (handle);
|
||||
|
||||
if (!cogl_is_vertex_buffer_indices (indices_handle))
|
||||
return;
|
||||
|
||||
indices = _cogl_vertex_buffer_indices_pointer_from_handle (indices_handle);
|
||||
|
||||
cogl_clip_ensure ();
|
||||
_cogl_current_matrix_state_flush ();
|
||||
enable_state_for_drawing_buffer (buffer);
|
||||
|
||||
_cogl_current_matrix_state_flush ();
|
||||
byte_offset = indices_offset * get_indices_type_size (indices->type);
|
||||
if (fallback)
|
||||
byte_offset = (size_t)(((char *)indices->vbo_name) + byte_offset);
|
||||
else
|
||||
GE (glBindBuffer (GL_ELEMENT_ARRAY_BUFFER,
|
||||
GPOINTER_TO_UINT (indices->vbo_name)));
|
||||
|
||||
/* FIXME: flush cogl cache */
|
||||
GE (glDrawRangeElements (mode, min_index, max_index,
|
||||
count, indices_type, indices));
|
||||
count, indices->type, (void *)byte_offset));
|
||||
|
||||
disable_state_for_drawing_buffer (buffer);
|
||||
|
||||
GE (glBindBuffer (GL_ELEMENT_ARRAY_BUFFER, 0));
|
||||
}
|
||||
|
||||
static void
|
||||
@ -1778,8 +1871,92 @@ _cogl_vertex_buffer_free (CoglVertexBuffer *buffer)
|
||||
|
||||
for (tmp = buffer->submitted_vbos; tmp != NULL; tmp = tmp->next)
|
||||
cogl_vertex_buffer_vbo_free (tmp->data, TRUE);
|
||||
g_list_free (buffer->submitted_vbos);
|
||||
|
||||
for (tmp = buffer->new_attributes; tmp != NULL; tmp = tmp->next)
|
||||
cogl_vertex_buffer_attribute_free (tmp->data);
|
||||
g_list_free (buffer->new_attributes);
|
||||
|
||||
g_slice_free (CoglVertexBuffer, buffer);
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_vertex_buffer_indices_get_for_quads (guint n_indices)
|
||||
{
|
||||
_COGL_GET_CONTEXT (ctx, COGL_INVALID_HANDLE);
|
||||
|
||||
/* Check if the indices would fit in a byte array */
|
||||
if (n_indices <= 256 / 4 * 6)
|
||||
{
|
||||
/* Generate the byte array if we haven't already */
|
||||
if (ctx->quad_indices_byte == COGL_INVALID_HANDLE)
|
||||
{
|
||||
guint8 *byte_array = g_malloc (256 / 4 * 6 * sizeof (guint8));
|
||||
guint8 *p = byte_array;
|
||||
int i, vert_num = 0;
|
||||
|
||||
for (i = 0; i < 256 / 4; i++)
|
||||
{
|
||||
*(p++) = vert_num + 0;
|
||||
*(p++) = vert_num + 1;
|
||||
*(p++) = vert_num + 2;
|
||||
*(p++) = vert_num + 0;
|
||||
*(p++) = vert_num + 2;
|
||||
*(p++) = vert_num + 3;
|
||||
vert_num += 4;
|
||||
}
|
||||
|
||||
ctx->quad_indices_byte
|
||||
= cogl_vertex_buffer_indices_new (COGL_INDICES_TYPE_UNSIGNED_BYTE,
|
||||
byte_array,
|
||||
256 / 4 * 6);
|
||||
|
||||
g_free (byte_array);
|
||||
}
|
||||
|
||||
return ctx->quad_indices_byte;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ctx->quad_indices_short_len < n_indices)
|
||||
{
|
||||
guint16 *short_array;
|
||||
guint16 *p;
|
||||
int i, vert_num = 0;
|
||||
|
||||
if (ctx->quad_indices_short != COGL_INVALID_HANDLE)
|
||||
cogl_handle_unref (ctx->quad_indices_short);
|
||||
/* Pick a power of two >= MAX (512, n_indices) */
|
||||
if (ctx->quad_indices_short_len == 0)
|
||||
ctx->quad_indices_short_len = 512;
|
||||
while (ctx->quad_indices_short_len < n_indices)
|
||||
ctx->quad_indices_short_len *= 2;
|
||||
|
||||
/* Over-allocate to generate a whole number of quads */
|
||||
p = short_array = g_malloc ((ctx->quad_indices_short_len
|
||||
+ 5) / 6 * 6
|
||||
* sizeof (guint16));
|
||||
|
||||
/* Fill in the complete quads */
|
||||
for (i = 0; i < ctx->quad_indices_short_len; i += 6)
|
||||
{
|
||||
*(p++) = vert_num + 0;
|
||||
*(p++) = vert_num + 1;
|
||||
*(p++) = vert_num + 2;
|
||||
*(p++) = vert_num + 0;
|
||||
*(p++) = vert_num + 2;
|
||||
*(p++) = vert_num + 3;
|
||||
vert_num += 4;
|
||||
}
|
||||
|
||||
ctx->quad_indices_short
|
||||
= cogl_vertex_buffer_indices_new (COGL_INDICES_TYPE_UNSIGNED_SHORT,
|
||||
short_array,
|
||||
ctx->quad_indices_short_len);
|
||||
|
||||
g_free (short_array);
|
||||
}
|
||||
|
||||
return ctx->quad_indices_short;
|
||||
}
|
||||
}
|
||||
|
@ -42,6 +42,7 @@ typedef CoglFuncPtr (*GLXGetProcAddressProc) (const guint8 *procName);
|
||||
#include "cogl-internal.h"
|
||||
#include "cogl-util.h"
|
||||
#include "cogl-context.h"
|
||||
#include "cogl-material-private.h"
|
||||
|
||||
#if defined (HAVE_COGL_GLES2) || defined (HAVE_COGL_GLES)
|
||||
#include "cogl-gles2-wrapper.h"
|
||||
@ -213,30 +214,39 @@ cogl_get_enable ()
|
||||
}
|
||||
|
||||
void
|
||||
cogl_enable_depth_test (gboolean setting)
|
||||
cogl_set_depth_test_enabled (gboolean setting)
|
||||
{
|
||||
if (setting)
|
||||
{
|
||||
glEnable (GL_DEPTH_TEST);
|
||||
glEnable (GL_ALPHA_TEST);
|
||||
glDepthFunc (GL_LEQUAL);
|
||||
glAlphaFunc (GL_GREATER, 0.1);
|
||||
}
|
||||
else
|
||||
{
|
||||
glDisable (GL_DEPTH_TEST);
|
||||
glDisable (GL_ALPHA_TEST);
|
||||
}
|
||||
glDisable (GL_DEPTH_TEST);
|
||||
}
|
||||
|
||||
gboolean
|
||||
cogl_get_depth_test_enabled (void)
|
||||
{
|
||||
return glIsEnabled (GL_DEPTH_TEST) == GL_TRUE ? TRUE : FALSE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_enable_backface_culling (gboolean setting)
|
||||
cogl_set_backface_culling_enabled (gboolean setting)
|
||||
{
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
ctx->enable_backface_culling = setting;
|
||||
}
|
||||
|
||||
gboolean
|
||||
cogl_get_backface_culling_enabled (void)
|
||||
{
|
||||
_COGL_GET_CONTEXT (ctx, FALSE);
|
||||
|
||||
return ctx->enable_backface_culling;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_set_source_color (const CoglColor *color)
|
||||
{
|
||||
@ -375,7 +385,7 @@ _cogl_add_stencil_clip (float x_offset,
|
||||
{
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
cogl_material_flush_gl_state (ctx->stencil_material, NULL);
|
||||
_cogl_material_flush_gl_state (ctx->stencil_material, NULL);
|
||||
|
||||
if (first)
|
||||
{
|
||||
@ -465,12 +475,12 @@ cogl_viewport (guint width,
|
||||
}
|
||||
|
||||
void
|
||||
cogl_setup_viewport (guint width,
|
||||
guint height,
|
||||
float fovy,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far)
|
||||
_cogl_setup_viewport (guint width,
|
||||
guint height,
|
||||
float fovy,
|
||||
float aspect,
|
||||
float z_near,
|
||||
float z_far)
|
||||
{
|
||||
float z_camera;
|
||||
CoglMatrix projection_matrix;
|
||||
@ -478,7 +488,7 @@ cogl_setup_viewport (guint width,
|
||||
GE( glViewport (0, 0, width, height) );
|
||||
|
||||
/* For Ortho projection.
|
||||
* _cogl_current_matrix_ortho (0, width << 16, 0, height << 16, -1 << 16, 1 << 16);
|
||||
* _cogl_current_matrix_ortho (0, width, 0, height, -1, 1);
|
||||
*/
|
||||
|
||||
cogl_perspective (fovy, aspect, z_near, z_far);
|
||||
@ -532,7 +542,7 @@ cogl_setup_viewport (guint width,
|
||||
}
|
||||
|
||||
CoglFeatureFlags
|
||||
cogl_get_features ()
|
||||
cogl_get_features (void)
|
||||
{
|
||||
_COGL_GET_CONTEXT (ctx, 0);
|
||||
|
||||
@ -653,9 +663,11 @@ cogl_disable_fog (void)
|
||||
glDisable (GL_FOG);
|
||||
}
|
||||
|
||||
#if 0
|
||||
void
|
||||
cogl_flush_gl_state (int flags)
|
||||
{
|
||||
_cogl_current_matrix_state_flush ();
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -70,12 +70,14 @@ HTML_IMAGES=
|
||||
|
||||
# Extra SGML files that are included by $(DOC_MAIN_SGML_FILE).
|
||||
# e.g. content_files=running.sgml building.sgml changes-2.0.sgml
|
||||
content_files= version.xml
|
||||
content_files = \
|
||||
blend-strings.xml
|
||||
|
||||
# SGML files where gtk-doc abbrevations (#GtkWidget) are expanded
|
||||
# These files must be listed here *and* in content_files
|
||||
# e.g. expand_content_files=running.sgml
|
||||
expand_content_files=
|
||||
expand_content_files = \
|
||||
blend-strings.xml
|
||||
|
||||
# CFLAGS and LDFLAGS for compiling gtkdoc-scangobj with your library.
|
||||
# Only needed if you are using gtkdoc-scangobj to dynamically query widget
|
||||
@ -91,4 +93,3 @@ include $(top_srcdir)/gtk-doc.make
|
||||
|
||||
# Other files to distribute
|
||||
# e.g. EXTRA_DIST += version.xml.in
|
||||
EXTRA_DIST += version.xml.in
|
||||
|
130
doc/reference/cogl/blend-strings.xml
Normal file
130
doc/reference/cogl/blend-strings.xml
Normal file
@ -0,0 +1,130 @@
|
||||
<?xml version="1.0"?>
|
||||
<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.1.2//EN"
|
||||
"http://www.oasis-open.org/docbook/xml/4.1.2/docbookx.dtd" [
|
||||
<!ENTITY version SYSTEM "version.xml">
|
||||
]>
|
||||
|
||||
<refentry id="cogl-Blend-Strings">
|
||||
<refmeta>
|
||||
<refentrytitle role="top_of_page" id="cogl-Blend-Strings.top_of_page">Material Blend Strings</refentrytitle>
|
||||
<manvolnum>3</manvolnum>
|
||||
<refmiscinfo>COGL Library</refmiscinfo>
|
||||
</refmeta>
|
||||
|
||||
<refnamediv>
|
||||
<refname>Material Blend Strings</refname>
|
||||
<refpurpose>A simple syntax and grammar for describing blending and texture
|
||||
combining functions.</refpurpose>
|
||||
</refnamediv>
|
||||
|
||||
<refsect1 id="cogl-Blend-Strings.description" role="desc">
|
||||
<title>Cogl Blend Strings</title>
|
||||
<para>
|
||||
Describing GPU blending and texture combining states is rather awkward to do
|
||||
in a consise but also readable fashion. Cogl helps by supporting
|
||||
string based descriptions using a simple syntax.
|
||||
</para>
|
||||
|
||||
<section>
|
||||
<title>Some examples</title>
|
||||
|
||||
<para>Here is an example used for blending:</para>
|
||||
<programlisting>
|
||||
"RGBA = ADD (SRC_COLOR * (SRC_COLOR[A]), DST_COLOR * (1-SRC_COLOR[A]))"
|
||||
</programlisting>
|
||||
<para>In OpenGL terms this replaces glBlendFunc[Separate] and
|
||||
glBlendEquation[Separate]</para>
|
||||
<para>
|
||||
Actually in this case it's more verbose than the GL equivalent:
|
||||
</para>
|
||||
<programlisting>
|
||||
glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||
</programlisting>
|
||||
<para>
|
||||
But unless you are familiar with OpenGL or refer to its API documentation
|
||||
you wouldn't know that the default function used by OpenGL is GL_FUNC_ADD
|
||||
nor would you know that the above arguments determine what the source color
|
||||
and destination color will be multiplied by before being adding.
|
||||
</para>
|
||||
|
||||
<para>Here is an example used for texture combining:</para>
|
||||
<programlisting>
|
||||
"RGB = REPLACE (PREVIOUS)"
|
||||
"A = MODULATE (PREVIOUS, TEXTURE)"
|
||||
</programlisting>
|
||||
<para>
|
||||
In OpenGL terms this replaces glTexEnv, and the above example is equivalent
|
||||
to this OpenGL code:
|
||||
</para>
|
||||
<programlisting>
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_REPLACE);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_SRC0_RGB, GL_PREVIOUS);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_MODULATE);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_SRC0_RGB, GL_PREVIOUS);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_SRC1_RGB, GL_TEXTURE);
|
||||
glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND1_RGB, GL_SRC_COLOR);
|
||||
</programlisting>
|
||||
|
||||
</section>
|
||||
|
||||
<section id="cogl-Blend-String-syntax">
|
||||
<title>Here's the syntax</title>
|
||||
|
||||
<programlisting>
|
||||
<statement>:
|
||||
<channel-mask>=<function-name>(<arg-list>)
|
||||
|
||||
You can either use a single statement with an RGBA channel-mask or you can use
|
||||
two statements; one with an A channel-mask and the other with an RGB
|
||||
channel-mask.
|
||||
|
||||
<channel-mask>:
|
||||
A or RGB or RGBA
|
||||
|
||||
<function-name>:
|
||||
[A-Za-z_]*
|
||||
|
||||
<arg-list>:
|
||||
<arg>,<arg>
|
||||
or <arg>
|
||||
or ""
|
||||
|
||||
I.e. functions may take 0 or more arguments
|
||||
|
||||
<arg>:
|
||||
<color-source>
|
||||
1 - <color-source> : Only intended for texture combining
|
||||
<color-source> * ( <factor> ) : Only intended for blending
|
||||
0 : Only intended for blending
|
||||
|
||||
See the blending or texture combining sections for further notes and examples.
|
||||
|
||||
<color-source>:
|
||||
<source-name>[<channel-mask>]
|
||||
<source-name>
|
||||
|
||||
See the blending or texture combining sections for the list of source-names
|
||||
valid in each context.
|
||||
|
||||
If a channel mask is not given then the channel mask of the statement
|
||||
is assumed instead.
|
||||
|
||||
<factor>:
|
||||
0
|
||||
1
|
||||
<color-source>
|
||||
1-<color-source>
|
||||
SRC_ALPHA_SATURATE
|
||||
</programlisting>
|
||||
|
||||
</section>
|
||||
|
||||
|
||||
</refsect1>
|
||||
|
||||
|
||||
</refentry>
|
@ -1,7 +1,7 @@
|
||||
<?xml version="1.0"?>
|
||||
<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.1.2//EN"
|
||||
"http://www.oasis-open.org/docbook/xml/4.1.2/docbookx.dtd" [
|
||||
<!ENTITY version SYSTEM "version.xml">
|
||||
<!ENTITY version "@VERSION@">
|
||||
]>
|
||||
<book id="index" xmlns:xi="http://www.w3.org/2003/XInclude">
|
||||
|
||||
@ -55,6 +55,7 @@
|
||||
<xi:include href="xml/cogl.xml"/>
|
||||
<xi:include href="xml/cogl-color.xml"/>
|
||||
<xi:include href="xml/cogl-texture.xml"/>
|
||||
<xi:include href="blend-strings.xml"/>
|
||||
<xi:include href="xml/cogl-material.xml"/>
|
||||
<xi:include href="xml/cogl-primitives.xml"/>
|
||||
<xi:include href="xml/cogl-vertex-buffer.xml"/>
|
@ -15,33 +15,35 @@ COGL_UNPREMULT_MASK
|
||||
CoglPixelFormat
|
||||
CoglBufferTarget
|
||||
<SUBSECTION>
|
||||
cogl_create_context
|
||||
cogl_destroy_context
|
||||
<SUBSECTION>
|
||||
CoglFeatureFlags
|
||||
cogl_get_features
|
||||
cogl_features_available
|
||||
cogl_check_extension
|
||||
cogl_get_proc_address
|
||||
<SUBSECTION>
|
||||
cogl_perspective
|
||||
cogl_frustum
|
||||
cogl_setup_viewport
|
||||
cogl_viewport
|
||||
cogl_get_modelview_matrix
|
||||
cogl_get_projection_matrix
|
||||
cogl_get_viewport
|
||||
<SUBSECTION>
|
||||
cogl_push_matrix
|
||||
cogl_pop_matrix
|
||||
cogl_scale
|
||||
cogl_translate
|
||||
cogl_rotate
|
||||
cogl_frustum
|
||||
cogl_perspective
|
||||
cogl_ortho
|
||||
<SUBSECTION>
|
||||
cogl_get_modelview_matrix
|
||||
cogl_set_modelview_matrix
|
||||
cogl_get_projection_matrix
|
||||
cogl_set_projection_matrix
|
||||
cogl_viewport
|
||||
cogl_setup_viewport
|
||||
cogl_get_viewport
|
||||
<SUBSECTION>
|
||||
cogl_clear
|
||||
cogl_get_bitmasks
|
||||
cogl_enable_depth_test
|
||||
cogl_enable_backface_culling
|
||||
cogl_set_depth_test_enabled
|
||||
cogl_get_depth_test_enabled
|
||||
cogl_set_backface_culling_enabled
|
||||
cogl_get_backface_culling_enabled
|
||||
<SUBSECTION>
|
||||
CoglFogMode
|
||||
cogl_set_fog
|
||||
@ -130,12 +132,9 @@ cogl_texture_get_height
|
||||
cogl_texture_get_format
|
||||
cogl_texture_get_rowstride
|
||||
cogl_texture_get_max_waste
|
||||
cogl_texture_get_min_filter
|
||||
cogl_texture_get_mag_filter
|
||||
cogl_texture_is_sliced
|
||||
cogl_texture_get_gl_texture
|
||||
cogl_texture_get_data
|
||||
cogl_texture_set_filters
|
||||
cogl_texture_set_region
|
||||
</SECTION>
|
||||
|
||||
@ -307,7 +306,11 @@ cogl_vertex_buffer_submit
|
||||
cogl_vertex_buffer_disable
|
||||
cogl_vertex_buffer_enable
|
||||
cogl_vertex_buffer_draw
|
||||
CoglIndicesType
|
||||
cogl_vertex_buffer_add_indices
|
||||
cogl_vertex_buffer_delete_indices
|
||||
cogl_vertex_buffer_draw_elements
|
||||
cogl_vertex_buffer_indices_get_for_quads
|
||||
<SUBSECTION Private>
|
||||
CoglVertexBufferAttribFlags
|
||||
COGL_VERTEX_BUFFER_ATTRIB_FLAG_GL_TYPE_MASK
|
||||
@ -349,41 +352,35 @@ cogl_material_set_specular
|
||||
cogl_material_get_specular
|
||||
cogl_material_set_shininess
|
||||
cogl_material_get_shininess
|
||||
<SUBSECTION Advanced Blending>
|
||||
CoglMaterialAlphaFunc
|
||||
cogl_material_set_alpha_test_function
|
||||
CoglMaterialBlendFactor
|
||||
cogl_material_set_blend_factors
|
||||
cogl_material_set_blend
|
||||
cogl_material_set_blend_constant
|
||||
cogl_material_set_layer
|
||||
cogl_material_remove_layer
|
||||
CoglMaterialLayerCombineFunc
|
||||
cogl_material_set_layer_combine_function
|
||||
CoglMaterialLayerCombineChannels
|
||||
CoglMaterialLayerCombineSrc
|
||||
cogl_material_set_layer_combine_arg_src
|
||||
CoglMaterialLayerCombineOp
|
||||
cogl_material_set_layer_combine_arg_op
|
||||
cogl_material_set_layer_combine
|
||||
cogl_material_set_layer_combine_constant
|
||||
cogl_material_set_layer_matrix
|
||||
cogl_material_get_layers
|
||||
CoglMaterialFilter
|
||||
cogl_material_set_layer_filters
|
||||
cogl_material_layer_get_type
|
||||
cogl_material_layer_get_texture
|
||||
cogl_material_layer_get_min_filter
|
||||
cogl_material_layer_get_mag_filter
|
||||
<SUBSECTION Private>
|
||||
CoglMaterial
|
||||
CoglMaterialFlags
|
||||
CoglMaterialLayerPrivFlags
|
||||
cogl_material_set_layer_alpha_combine
|
||||
cogl_material_set_layer_rgb_combine
|
||||
</SECTION>
|
||||
|
||||
<SECTION>
|
||||
<FILE>cogl-material-internals</FILE>
|
||||
<TITLE>Material Internals</TITLE>
|
||||
cogl_material_get_cogl_enable_flags
|
||||
CoglMaterialFlushOption
|
||||
cogl_material_flush_gl_state
|
||||
CoglMaterialLayer
|
||||
cogl_material_get_layers
|
||||
CoglMaterialLayerType
|
||||
cogl_material_layer_get_type
|
||||
CoglMaterialLayerFlags
|
||||
cogl_material_layer_get_flags
|
||||
cogl_material_layer_get_texture
|
||||
cogl_material_layer_flush_gl_sampler_state
|
||||
</SECTION>
|
||||
|
@ -1 +0,0 @@
|
||||
@CLUTTER_VERSION@
|
@ -35,11 +35,6 @@ cogl_sources = \
|
||||
cogl-context.c \
|
||||
$(NULL)
|
||||
|
||||
coglincludedir = $(includedir)/clutter-@CLUTTER_API_VERSION@/cogl
|
||||
coglinclude_HEADERS = \
|
||||
$(cogl_headers) \
|
||||
$(top_builddir)/clutter/cogl/cogl.h
|
||||
|
||||
INCLUDES = \
|
||||
-I$(top_srcdir)/clutter/cogl \
|
||||
-I$(top_srcdir)/clutter/cogl/common \
|
||||
@ -50,12 +45,12 @@ INCLUDES = \
|
||||
-DG_LOG_DOMAIN=\"Cogl-GL\" \
|
||||
-DCLUTTER_COMPILATION
|
||||
|
||||
noinst_LTLIBRARIES = libclutter-cogl.la
|
||||
noinst_LTLIBRARIES = libclutter-cogl-gl.la
|
||||
|
||||
libclutter_cogl_la_CPPFLAGS = $(CLUTTER_CFLAGS) $(COGL_DEBUG_CFLAGS) $(CLUTTER_DEBUG_CFLAGS) $(MAINTAINER_CFLAGS)
|
||||
libclutter_cogl_la_LIBADD = -lm $(CLUTTER_LIBS) $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_la_DEPENDENCIES = $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_la_SOURCES = \
|
||||
libclutter_cogl_gl_la_CPPFLAGS = $(CLUTTER_CFLAGS) $(COGL_DEBUG_CFLAGS) $(CLUTTER_DEBUG_CFLAGS) $(MAINTAINER_CFLAGS)
|
||||
libclutter_cogl_gl_la_LIBADD = -lm $(CLUTTER_LIBS) $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_gl_la_DEPENDENCIES = $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_gl_la_SOURCES = \
|
||||
$(top_builddir)/clutter/cogl/cogl.h \
|
||||
$(cogl_headers) \
|
||||
$(cogl_priv_headers) \
|
||||
|
@ -37,7 +37,7 @@
|
||||
static CoglContext *_context = NULL;
|
||||
static gboolean gl_is_indirect = FALSE;
|
||||
|
||||
gboolean
|
||||
static gboolean
|
||||
cogl_create_context ()
|
||||
{
|
||||
GLubyte default_texture_data[] = { 0xff, 0xff, 0xff, 0x0 };
|
||||
@ -69,7 +69,6 @@ cogl_create_context ()
|
||||
|
||||
_context->journal = g_array_new (FALSE, FALSE, sizeof (CoglJournalEntry));
|
||||
_context->logged_vertices = g_array_new (FALSE, FALSE, sizeof (GLfloat));
|
||||
_context->static_indices = g_array_new (FALSE, FALSE, sizeof (GLushort));
|
||||
_context->polygon_vertices = g_array_new (FALSE, FALSE,
|
||||
sizeof (CoglTextureGLVertex));
|
||||
|
||||
@ -136,6 +135,9 @@ cogl_create_context ()
|
||||
_context->pf_glActiveTexture = NULL;
|
||||
_context->pf_glClientActiveTexture = NULL;
|
||||
|
||||
_context->pf_glBlendFuncSeparate = NULL;
|
||||
_context->pf_glBlendEquationSeparate = NULL;
|
||||
|
||||
/* Initialise the clip stack */
|
||||
_cogl_clip_stack_state_init ();
|
||||
|
||||
@ -146,8 +148,7 @@ cogl_create_context ()
|
||||
_context->default_gl_texture_2d_tex =
|
||||
cogl_texture_new_from_data (1, /* width */
|
||||
1, /* height */
|
||||
-1, /* max waste */
|
||||
COGL_TEXTURE_NONE, /* flags */
|
||||
COGL_TEXTURE_NO_SLICING,
|
||||
COGL_PIXEL_FORMAT_RGBA_8888, /* data format */
|
||||
/* internal format */
|
||||
COGL_PIXEL_FORMAT_RGBA_8888,
|
||||
@ -156,8 +157,7 @@ cogl_create_context ()
|
||||
_context->default_gl_texture_rect_tex =
|
||||
cogl_texture_new_from_data (1, /* width */
|
||||
1, /* height */
|
||||
-1, /* max waste */
|
||||
COGL_TEXTURE_NONE, /* flags */
|
||||
COGL_TEXTURE_NO_SLICING,
|
||||
COGL_PIXEL_FORMAT_RGBA_8888, /* data format */
|
||||
/* internal format */
|
||||
COGL_PIXEL_FORMAT_RGBA_8888,
|
||||
@ -165,16 +165,20 @@ cogl_create_context ()
|
||||
default_texture_data);
|
||||
|
||||
cogl_set_source (_context->default_material);
|
||||
cogl_material_flush_gl_state (_context->source_material, NULL);
|
||||
_cogl_material_flush_gl_state (_context->source_material, NULL);
|
||||
enable_flags =
|
||||
cogl_material_get_cogl_enable_flags (_context->source_material);
|
||||
_cogl_material_get_cogl_enable_flags (_context->source_material);
|
||||
cogl_enable (enable_flags);
|
||||
|
||||
_context->quad_indices_byte = COGL_INVALID_HANDLE;
|
||||
_context->quad_indices_short = COGL_INVALID_HANDLE;
|
||||
_context->quad_indices_short_len = 0;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_destroy_context ()
|
||||
_cogl_destroy_context ()
|
||||
{
|
||||
if (_context == NULL)
|
||||
return;
|
||||
@ -199,13 +203,16 @@ cogl_destroy_context ()
|
||||
if (_context->logged_vertices)
|
||||
g_array_free (_context->logged_vertices, TRUE);
|
||||
|
||||
if (_context->static_indices)
|
||||
g_array_free (_context->static_indices, TRUE);
|
||||
if (_context->polygon_vertices)
|
||||
g_array_free (_context->polygon_vertices, TRUE);
|
||||
if (_context->current_layers)
|
||||
g_array_free (_context->current_layers, TRUE);
|
||||
|
||||
if (_context->quad_indices_byte)
|
||||
cogl_handle_unref (_context->quad_indices_byte);
|
||||
if (_context->quad_indices_short)
|
||||
cogl_handle_unref (_context->quad_indices_short);
|
||||
|
||||
g_free (_context);
|
||||
}
|
||||
|
||||
|
@ -78,7 +78,6 @@ typedef struct
|
||||
* can batch things together. */
|
||||
GArray *journal;
|
||||
GArray *logged_vertices;
|
||||
GArray *static_indices;
|
||||
GArray *polygon_vertices;
|
||||
|
||||
/* Some simple caching, to minimize state changes... */
|
||||
@ -102,6 +101,12 @@ typedef struct
|
||||
floatVec2 path_nodes_max;
|
||||
CoglHandle stencil_material;
|
||||
|
||||
/* Pre-generated VBOs containing indices to generate GL_TRIANGLES
|
||||
out of a vertex array of quads */
|
||||
CoglHandle quad_indices_byte;
|
||||
guint quad_indices_short_len;
|
||||
CoglHandle quad_indices_short;
|
||||
|
||||
/* Relying on glext.h to define these */
|
||||
COGL_PFNGLGENRENDERBUFFERSEXTPROC pf_glGenRenderbuffersEXT;
|
||||
COGL_PFNGLDELETERENDERBUFFERSEXTPROC pf_glDeleteRenderbuffersEXT;
|
||||
@ -115,6 +120,7 @@ typedef struct
|
||||
COGL_PFNGLDELETEFRAMEBUFFERSEXTPROC pf_glDeleteFramebuffersEXT;
|
||||
COGL_PFNGLBLITFRAMEBUFFEREXTPROC pf_glBlitFramebufferEXT;
|
||||
COGL_PFNGLRENDERBUFFERSTORAGEMULTISAMPLEEXTPROC pf_glRenderbufferStorageMultisampleEXT;
|
||||
COGL_PFNGLGENERATEMIPMAPEXTPROC pf_glGenerateMipmapEXT;
|
||||
|
||||
COGL_PFNGLCREATEPROGRAMOBJECTARBPROC pf_glCreateProgramObjectARB;
|
||||
COGL_PFNGLCREATESHADEROBJECTARBPROC pf_glCreateShaderObjectARB;
|
||||
@ -164,6 +170,11 @@ typedef struct
|
||||
|
||||
COGL_PFNGLACTIVETEXTUREPROC pf_glActiveTexture;
|
||||
COGL_PFNGLCLIENTACTIVETEXTUREPROC pf_glClientActiveTexture;
|
||||
|
||||
COGL_PFNGLBLENDEQUATIONPROC pf_glBlendEquation;
|
||||
COGL_PFNGLBLENDCOLORPROC pf_glBlendColor;
|
||||
COGL_PFNGLBLENDFUNCSEPARATEPROC pf_glBlendFuncSeparate;
|
||||
COGL_PFNGLBLENDEQUATIONSEPARATEPROC pf_glBlendEquationSeparate;
|
||||
} CoglContext;
|
||||
|
||||
CoglContext *
|
||||
|
@ -773,6 +773,10 @@ typedef void
|
||||
GLsizei width,
|
||||
GLsizei height);
|
||||
|
||||
typedef void
|
||||
(APIENTRYP COGL_PFNGLGENERATEMIPMAPEXTPROC)
|
||||
(GLenum target);
|
||||
|
||||
typedef GLhandleARB
|
||||
(APIENTRYP COGL_PFNGLCREATEPROGRAMOBJECTARBPROC)
|
||||
(void);
|
||||
@ -1020,6 +1024,29 @@ typedef void
|
||||
(APIENTRYP COGL_PFNGLCLIENTACTIVETEXTUREPROC)
|
||||
(GLenum texture);
|
||||
|
||||
typedef void
|
||||
(APIENTRYP COGL_PFNGLBLENDFUNCSEPARATEPROC)
|
||||
(GLenum srcRGB,
|
||||
GLenum dstRGB,
|
||||
GLenum srcAlpha,
|
||||
GLenum dstAlpha);
|
||||
|
||||
typedef void
|
||||
(APIENTRYP COGL_PFNGLBLENDEQUATIONSEPARATEPROC)
|
||||
(GLenum modeRGB,
|
||||
GLenum modeAlpha);
|
||||
|
||||
typedef void
|
||||
(APIENTRYP COGL_PFNGLBLENDEQUATIONPROC)
|
||||
(GLenum mode);
|
||||
|
||||
typedef void
|
||||
(APIENTRYP COGL_PFNGLBLENDCOLORPROC)
|
||||
(GLclampf red,
|
||||
GLclampf green,
|
||||
GLclampf blue,
|
||||
GLclampf alpha);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif
|
||||
|
@ -29,6 +29,7 @@
|
||||
#include "cogl-internal.h"
|
||||
#include "cogl-context.h"
|
||||
#include "cogl-clip-stack.h"
|
||||
#include "cogl-material-private.h"
|
||||
|
||||
#include <string.h>
|
||||
#include <gmodule.h>
|
||||
@ -78,13 +79,13 @@ _cogl_path_stroke_nodes ()
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
enable_flags |= cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
enable_flags |= _cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
cogl_enable (enable_flags);
|
||||
|
||||
cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
(guint32)~0, /* disable all texture layers */
|
||||
NULL);
|
||||
_cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
(guint32)~0, /* disable all texture layers */
|
||||
NULL);
|
||||
_cogl_current_matrix_state_flush ();
|
||||
|
||||
while (path_start < ctx->path_nodes->len)
|
||||
@ -133,10 +134,10 @@ _cogl_add_path_to_stencil_buffer (floatVec2 nodes_min,
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
/* Just setup a simple material that doesn't use texturing... */
|
||||
cogl_material_flush_gl_state (ctx->stencil_material, NULL);
|
||||
_cogl_material_flush_gl_state (ctx->stencil_material, NULL);
|
||||
|
||||
enable_flags |=
|
||||
cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
_cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
cogl_enable (enable_flags);
|
||||
|
||||
_cogl_path_get_bounds (nodes_min, nodes_max,
|
||||
|
@ -108,22 +108,23 @@ cogl_shader_compile (CoglHandle handle)
|
||||
glCompileShaderARB (shader->gl_handle);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_shader_get_info_log (CoglHandle handle,
|
||||
size_t size,
|
||||
char *buffer)
|
||||
gchar *
|
||||
cogl_shader_get_info_log (CoglHandle handle)
|
||||
{
|
||||
CoglShader *shader;
|
||||
char buffer[512];
|
||||
int len;
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
_COGL_GET_CONTEXT (ctx, NULL);
|
||||
|
||||
if (!cogl_is_shader (handle))
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
shader = _cogl_shader_pointer_from_handle (handle);
|
||||
|
||||
glGetInfoLogARB (shader->gl_handle, size-1, &len, buffer);
|
||||
glGetInfoLogARB (shader->gl_handle, 511, &len, buffer);
|
||||
buffer[len]='\0';
|
||||
|
||||
return g_strdup (buffer);
|
||||
}
|
||||
|
||||
CoglShaderType
|
||||
|
@ -30,6 +30,7 @@
|
||||
typedef struct _CoglTexture CoglTexture;
|
||||
typedef struct _CoglTexSliceSpan CoglTexSliceSpan;
|
||||
typedef struct _CoglSpanIter CoglSpanIter;
|
||||
typedef struct _CoglTexturePixel CoglTexturePixel;
|
||||
|
||||
struct _CoglTexSliceSpan
|
||||
{
|
||||
@ -55,6 +56,18 @@ struct _CoglSpanIter
|
||||
gboolean intersects;
|
||||
};
|
||||
|
||||
/* This is used to store the first pixel of each slice. This is only
|
||||
used when glGenerateMipmap is not available */
|
||||
struct _CoglTexturePixel
|
||||
{
|
||||
/* We need to store the format of the pixel because we store the
|
||||
data in the source format which might end up being different for
|
||||
each slice if a subregion is updated with a different format */
|
||||
GLenum gl_format;
|
||||
GLenum gl_type;
|
||||
guint8 data[4];
|
||||
};
|
||||
|
||||
struct _CoglTexture
|
||||
{
|
||||
CoglHandleObject _parent;
|
||||
@ -68,11 +81,17 @@ struct _CoglTexture
|
||||
GArray *slice_y_spans;
|
||||
GArray *slice_gl_handles;
|
||||
gint max_waste;
|
||||
CoglTextureFilter min_filter;
|
||||
CoglTextureFilter mag_filter;
|
||||
GLenum min_filter;
|
||||
GLenum mag_filter;
|
||||
gboolean is_foreign;
|
||||
GLint wrap_mode;
|
||||
gboolean auto_mipmap;
|
||||
gboolean mipmaps_dirty;
|
||||
|
||||
/* This holds a copy of the first pixel in each slice. It is only
|
||||
used to force an automatic update of the mipmaps when
|
||||
glGenerateMipmap is not available. */
|
||||
CoglTexturePixel *first_pixels;
|
||||
};
|
||||
|
||||
/* To improve batching of geometry when submitting vertices to OpenGL we
|
||||
@ -93,6 +112,14 @@ void
|
||||
_cogl_texture_set_wrap_mode_parameter (CoglTexture *tex,
|
||||
GLenum wrap_mode);
|
||||
|
||||
void
|
||||
_cogl_texture_set_filters (CoglHandle handle,
|
||||
GLenum min_filter,
|
||||
GLenum mag_filter);
|
||||
|
||||
void
|
||||
_cogl_texture_ensure_mipmaps (CoglHandle handle);
|
||||
|
||||
gboolean
|
||||
_cogl_texture_span_has_waste (CoglTexture *tex,
|
||||
gint x_span_index,
|
||||
|
@ -49,6 +49,7 @@
|
||||
#define glDrawRangeElements ctx->pf_glDrawRangeElements
|
||||
#define glActiveTexture ctx->pf_glActiveTexture
|
||||
#define glClientActiveTexture ctx->pf_glClientActiveTexture
|
||||
#define glGenerateMipmap ctx->pf_glGenerateMipmapEXT
|
||||
|
||||
#else
|
||||
|
||||
@ -247,11 +248,12 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
/* Iterate horizontal slices */
|
||||
for (x = 0; x < tex->slice_x_spans->len; ++x)
|
||||
{
|
||||
gint slice_num = y * tex->slice_x_spans->len + x;
|
||||
|
||||
x_span = &g_array_index (tex->slice_x_spans, CoglTexSliceSpan, x);
|
||||
|
||||
/* Pick the gl texture object handle */
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint,
|
||||
y * tex->slice_x_spans->len + x);
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint, slice_num);
|
||||
|
||||
/* Setup gl alignment to match rowstride and top-left corner */
|
||||
prep_for_gl_pixels_upload (tex->bitmap.rowstride,
|
||||
@ -259,6 +261,17 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
y_span->start,
|
||||
bpp);
|
||||
|
||||
/* Keep a copy of the first pixel if needed */
|
||||
if (tex->first_pixels)
|
||||
{
|
||||
memcpy (tex->first_pixels[slice_num].data,
|
||||
tex->bitmap.data + x_span->start * bpp
|
||||
+ y_span->start * tex->bitmap.rowstride,
|
||||
bpp);
|
||||
tex->first_pixels[slice_num].gl_format = tex->gl_format;
|
||||
tex->first_pixels[slice_num].gl_type = tex->gl_type;
|
||||
}
|
||||
|
||||
/* Upload new image data */
|
||||
GE( glBindTexture (tex->gl_target, gl_handle) );
|
||||
|
||||
@ -343,6 +356,8 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
if (waste_buf)
|
||||
g_free (waste_buf);
|
||||
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -494,6 +509,8 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
_cogl_span_iter_next (&x_iter),
|
||||
source_x += inter_w )
|
||||
{
|
||||
gint slice_num;
|
||||
|
||||
/* Discard slices out of the subregion early */
|
||||
if (!x_iter.intersects)
|
||||
{
|
||||
@ -516,10 +533,10 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
local_y = (y_iter.intersect_start -
|
||||
y_iter.pos);
|
||||
|
||||
slice_num = y_iter.index * tex->slice_x_spans->len + x_iter.index;
|
||||
|
||||
/* Pick slice GL handle */
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint,
|
||||
y_iter.index * tex->slice_x_spans->len +
|
||||
x_iter.index);
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint, slice_num);
|
||||
|
||||
/* Setup gl alignment to match rowstride and top-left corner */
|
||||
prep_for_gl_pixels_upload (source_bmp->rowstride,
|
||||
@ -527,6 +544,17 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
source_y,
|
||||
bpp);
|
||||
|
||||
/* Keep a copy of the first pixel if needed */
|
||||
if (tex->first_pixels && local_x == 0 && local_y == 0)
|
||||
{
|
||||
memcpy (tex->first_pixels[slice_num].data,
|
||||
source_bmp->data + source_x * bpp
|
||||
+ source_y * source_bmp->rowstride,
|
||||
bpp);
|
||||
tex->first_pixels[slice_num].gl_format = source_gl_format;
|
||||
tex->first_pixels[slice_num].gl_type = source_gl_type;
|
||||
}
|
||||
|
||||
/* Upload new image data */
|
||||
GE( glBindTexture (tex->gl_target, gl_handle) );
|
||||
|
||||
@ -640,14 +668,16 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
if (waste_buf)
|
||||
g_free (waste_buf);
|
||||
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static gint
|
||||
_cogl_rect_slices_for_size (gint size_to_fill,
|
||||
gint max_span_size,
|
||||
gint max_waste,
|
||||
GArray *out_spans)
|
||||
_cogl_rect_slices_for_size (gint size_to_fill,
|
||||
gint max_span_size,
|
||||
gint max_waste,
|
||||
GArray *out_spans)
|
||||
{
|
||||
gint n_spans = 0;
|
||||
CoglTexSliceSpan span;
|
||||
@ -679,10 +709,10 @@ _cogl_rect_slices_for_size (gint size_to_fill,
|
||||
}
|
||||
|
||||
static gint
|
||||
_cogl_pot_slices_for_size (gint size_to_fill,
|
||||
gint max_span_size,
|
||||
gint max_waste,
|
||||
GArray *out_spans)
|
||||
_cogl_pot_slices_for_size (gint size_to_fill,
|
||||
gint max_span_size,
|
||||
gint max_waste,
|
||||
GArray *out_spans)
|
||||
{
|
||||
gint n_spans = 0;
|
||||
CoglTexSliceSpan span;
|
||||
@ -693,7 +723,8 @@ _cogl_pot_slices_for_size (gint size_to_fill,
|
||||
span.waste = 0;
|
||||
|
||||
/* Fix invalid max_waste */
|
||||
if (max_waste < 0) max_waste = 0;
|
||||
if (max_waste < 0)
|
||||
max_waste = 0;
|
||||
|
||||
while (TRUE)
|
||||
{
|
||||
@ -826,10 +857,10 @@ _cogl_texture_slices_create (CoglTexture *tex)
|
||||
|
||||
/* Check if size supported else bail out */
|
||||
if (!_cogl_texture_size_supported (tex->gl_target,
|
||||
tex->gl_format,
|
||||
tex->gl_type,
|
||||
max_width,
|
||||
max_height))
|
||||
tex->gl_format,
|
||||
tex->gl_type,
|
||||
max_width,
|
||||
max_height))
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
@ -912,6 +943,14 @@ _cogl_texture_slices_create (CoglTexture *tex)
|
||||
|
||||
g_array_set_size (tex->slice_gl_handles, n_slices);
|
||||
|
||||
/* Allocate some space to store a copy of the first pixel of each
|
||||
slice. This is only needed to glGenerateMipmap (which is part of
|
||||
the FBO extension) is not available */
|
||||
if (cogl_features_available (COGL_FEATURE_OFFSCREEN))
|
||||
tex->first_pixels = NULL;
|
||||
else
|
||||
tex->first_pixels = g_new (CoglTexturePixel, n_slices);
|
||||
|
||||
/* Wrap mode not yet set */
|
||||
tex->wrap_mode = GL_FALSE;
|
||||
|
||||
@ -940,14 +979,6 @@ _cogl_texture_slices_create (CoglTexture *tex)
|
||||
/* Setup texture parameters */
|
||||
GE( glBindTexture (tex->gl_target,
|
||||
gl_handles[y * n_x_slices + x]) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_TEXTURE_MAG_FILTER,
|
||||
tex->mag_filter) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_TEXTURE_MIN_FILTER,
|
||||
tex->min_filter) );
|
||||
|
||||
if (tex->auto_mipmap)
|
||||
GE( glTexParameteri (tex->gl_target, GL_GENERATE_MIPMAP,
|
||||
GL_TRUE) );
|
||||
|
||||
/* Use a transparent border color so that we can leave the
|
||||
color buffer alone when using texture co-ordinates
|
||||
@ -984,6 +1015,9 @@ _cogl_texture_slices_free (CoglTexture *tex)
|
||||
|
||||
g_array_free (tex->slice_gl_handles, TRUE);
|
||||
}
|
||||
|
||||
if (tex->first_pixels != NULL)
|
||||
g_free (tex->first_pixels);
|
||||
}
|
||||
|
||||
gboolean
|
||||
@ -1199,11 +1233,10 @@ _cogl_texture_free (CoglTexture *tex)
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_texture_new_with_size (guint width,
|
||||
guint height,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
cogl_texture_new_with_size (guint width,
|
||||
guint height,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
gint bpp;
|
||||
@ -1221,7 +1254,8 @@ cogl_texture_new_with_size (guint width,
|
||||
tex = (CoglTexture*) g_malloc (sizeof (CoglTexture));
|
||||
|
||||
tex->is_foreign = FALSE;
|
||||
tex->auto_mipmap = ((flags & COGL_TEXTURE_AUTO_MIPMAP) != 0);
|
||||
tex->auto_mipmap = (flags & COGL_TEXTURE_NO_AUTO_MIPMAP) == 0;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
tex->bitmap.width = width;
|
||||
tex->bitmap.height = height;
|
||||
@ -1234,9 +1268,14 @@ cogl_texture_new_with_size (guint width,
|
||||
tex->slice_y_spans = NULL;
|
||||
tex->slice_gl_handles = NULL;
|
||||
|
||||
tex->max_waste = max_waste;
|
||||
tex->min_filter = COGL_TEXTURE_FILTER_NEAREST;
|
||||
tex->mag_filter = COGL_TEXTURE_FILTER_NEAREST;
|
||||
if (flags & COGL_TEXTURE_NO_SLICING)
|
||||
tex->max_waste = -1;
|
||||
else
|
||||
tex->max_waste = COGL_TEXTURE_MAX_WASTE;
|
||||
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
|
||||
/* Find closest GL format match */
|
||||
tex->bitmap.format =
|
||||
@ -1258,7 +1297,6 @@ cogl_texture_new_with_size (guint width,
|
||||
CoglHandle
|
||||
cogl_texture_new_from_data (guint width,
|
||||
guint height,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat format,
|
||||
CoglPixelFormat internal_format,
|
||||
@ -1282,7 +1320,8 @@ cogl_texture_new_from_data (guint width,
|
||||
tex = (CoglTexture*) g_malloc (sizeof (CoglTexture));
|
||||
|
||||
tex->is_foreign = FALSE;
|
||||
tex->auto_mipmap = ((flags & COGL_TEXTURE_AUTO_MIPMAP) != 0);
|
||||
tex->auto_mipmap = (flags & COGL_TEXTURE_NO_AUTO_MIPMAP) == 0;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
tex->bitmap.width = width;
|
||||
tex->bitmap.height = height;
|
||||
@ -1295,9 +1334,14 @@ cogl_texture_new_from_data (guint width,
|
||||
tex->slice_y_spans = NULL;
|
||||
tex->slice_gl_handles = NULL;
|
||||
|
||||
tex->max_waste = max_waste;
|
||||
tex->min_filter = COGL_TEXTURE_FILTER_NEAREST;
|
||||
tex->mag_filter = COGL_TEXTURE_FILTER_NEAREST;
|
||||
if (flags & COGL_TEXTURE_NO_SLICING)
|
||||
tex->max_waste = -1;
|
||||
else
|
||||
tex->max_waste = COGL_TEXTURE_MAX_WASTE;
|
||||
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
|
||||
/* FIXME: If upload fails we should set some kind of
|
||||
* error flag but still return texture handle (this
|
||||
@ -1328,10 +1372,9 @@ cogl_texture_new_from_data (guint width,
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
CoglBitmap *bmp = (CoglBitmap *)bmp_handle;
|
||||
@ -1342,7 +1385,8 @@ cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
tex = (CoglTexture*) g_malloc ( sizeof (CoglTexture));
|
||||
|
||||
tex->is_foreign = FALSE;
|
||||
tex->auto_mipmap = ((flags & COGL_TEXTURE_AUTO_MIPMAP) != 0);
|
||||
tex->auto_mipmap = (flags & COGL_TEXTURE_NO_AUTO_MIPMAP) == 0;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
tex->bitmap = *bmp;
|
||||
tex->bitmap_owner = FALSE;
|
||||
@ -1351,9 +1395,14 @@ cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
tex->slice_y_spans = NULL;
|
||||
tex->slice_gl_handles = NULL;
|
||||
|
||||
tex->max_waste = max_waste;
|
||||
tex->min_filter = COGL_TEXTURE_FILTER_NEAREST;
|
||||
tex->mag_filter = COGL_TEXTURE_FILTER_NEAREST;
|
||||
if (flags & COGL_TEXTURE_NO_SLICING)
|
||||
tex->max_waste = -1;
|
||||
else
|
||||
tex->max_waste = COGL_TEXTURE_MAX_WASTE;
|
||||
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
|
||||
/* FIXME: If upload fails we should set some kind of
|
||||
* error flag but still return texture handle if the
|
||||
@ -1388,13 +1437,12 @@ cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
|
||||
CoglHandle
|
||||
cogl_texture_new_from_file (const gchar *filename,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format,
|
||||
GError **error)
|
||||
{
|
||||
CoglHandle bmp;
|
||||
CoglHandle handle;
|
||||
CoglHandle bmp;
|
||||
CoglHandle handle;
|
||||
|
||||
g_return_val_if_fail (error == NULL || *error == NULL, COGL_INVALID_HANDLE);
|
||||
|
||||
@ -1402,10 +1450,7 @@ cogl_texture_new_from_file (const gchar *filename,
|
||||
if (bmp == COGL_INVALID_HANDLE)
|
||||
return COGL_INVALID_HANDLE;
|
||||
|
||||
handle = cogl_texture_new_from_bitmap (bmp,
|
||||
max_waste,
|
||||
flags,
|
||||
internal_format);
|
||||
handle = cogl_texture_new_from_bitmap (bmp, flags, internal_format);
|
||||
cogl_handle_unref (bmp);
|
||||
|
||||
return handle;
|
||||
@ -1433,8 +1478,6 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
GLint gl_int_format = 0;
|
||||
GLint gl_width = 0;
|
||||
GLint gl_height = 0;
|
||||
GLint gl_min_filter;
|
||||
GLint gl_mag_filter;
|
||||
GLint gl_gen_mipmap;
|
||||
guint bpp;
|
||||
CoglTexture *tex;
|
||||
@ -1482,14 +1525,6 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
GL_TEXTURE_HEIGHT,
|
||||
&gl_height) );
|
||||
|
||||
GE( glGetTexParameteriv (gl_target,
|
||||
GL_TEXTURE_MIN_FILTER,
|
||||
&gl_min_filter) );
|
||||
|
||||
GE( glGetTexParameteriv (gl_target,
|
||||
GL_TEXTURE_MAG_FILTER,
|
||||
&gl_mag_filter) );
|
||||
|
||||
GE( glGetTexParameteriv (gl_target,
|
||||
GL_GENERATE_MIPMAP,
|
||||
&gl_gen_mipmap) );
|
||||
@ -1508,18 +1543,16 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
return COGL_INVALID_HANDLE;
|
||||
|
||||
/* Try and match to a cogl format */
|
||||
if (!_cogl_pixel_format_from_gl_internal (gl_int_format,
|
||||
&format))
|
||||
{
|
||||
return COGL_INVALID_HANDLE;
|
||||
}
|
||||
if (!_cogl_pixel_format_from_gl_internal (gl_int_format, &format))
|
||||
return COGL_INVALID_HANDLE;
|
||||
|
||||
/* Create new texture */
|
||||
tex = (CoglTexture*) g_malloc ( sizeof (CoglTexture));
|
||||
tex = (CoglTexture *) g_malloc (sizeof (CoglTexture));
|
||||
|
||||
/* Setup bitmap info */
|
||||
tex->is_foreign = TRUE;
|
||||
tex->auto_mipmap = (gl_gen_mipmap == GL_TRUE) ? TRUE : FALSE;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
bpp = _cogl_get_format_bpp (format);
|
||||
tex->bitmap.format = format;
|
||||
@ -1533,8 +1566,9 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
tex->gl_format = gl_int_format;
|
||||
tex->gl_type = GL_UNSIGNED_BYTE;
|
||||
|
||||
tex->min_filter = gl_min_filter;
|
||||
tex->mag_filter = gl_mag_filter;
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
tex->max_waste = 0;
|
||||
|
||||
/* Wrap mode not yet set */
|
||||
@ -1680,36 +1714,10 @@ cogl_texture_get_gl_texture (CoglHandle handle,
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
CoglTextureFilter
|
||||
cogl_texture_get_min_filter (CoglHandle handle)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
|
||||
if (!cogl_is_texture (handle))
|
||||
return 0;
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
return tex->min_filter;
|
||||
}
|
||||
|
||||
CoglTextureFilter
|
||||
cogl_texture_get_mag_filter (CoglHandle handle)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
|
||||
if (!cogl_is_texture (handle))
|
||||
return 0;
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
return tex->mag_filter;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_texture_set_filters (CoglHandle handle,
|
||||
CoglTextureFilter min_filter,
|
||||
CoglTextureFilter mag_filter)
|
||||
_cogl_texture_set_filters (CoglHandle handle,
|
||||
GLenum min_filter,
|
||||
GLenum mag_filter)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
GLuint gl_handle;
|
||||
@ -1720,14 +1728,18 @@ cogl_texture_set_filters (CoglHandle handle,
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
/* Store new values */
|
||||
tex->min_filter = min_filter;
|
||||
tex->mag_filter = mag_filter;
|
||||
|
||||
/* Make sure slices were created */
|
||||
if (tex->slice_gl_handles == NULL)
|
||||
return;
|
||||
|
||||
if (min_filter == tex->min_filter
|
||||
&& mag_filter == tex->mag_filter)
|
||||
return;
|
||||
|
||||
/* Store new values */
|
||||
tex->min_filter = min_filter;
|
||||
tex->mag_filter = mag_filter;
|
||||
|
||||
/* Apply new filters to every slice */
|
||||
for (i=0; i<tex->slice_gl_handles->len; ++i)
|
||||
{
|
||||
@ -1740,6 +1752,52 @@ cogl_texture_set_filters (CoglHandle handle,
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_texture_ensure_mipmaps (CoglHandle handle)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
int i;
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
if (!cogl_is_texture (handle))
|
||||
return;
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
/* Only update if the mipmaps are dirty */
|
||||
if (!tex->auto_mipmap || !tex->mipmaps_dirty)
|
||||
return;
|
||||
|
||||
/* Make sure slices were created */
|
||||
if (tex->slice_gl_handles == NULL)
|
||||
return;
|
||||
|
||||
/* Regenerate the mipmaps on every slice */
|
||||
for (i = 0; i < tex->slice_gl_handles->len; i++)
|
||||
{
|
||||
GLuint gl_handle = g_array_index (tex->slice_gl_handles, GLuint, i);
|
||||
GE( glBindTexture (tex->gl_target, gl_handle) );
|
||||
|
||||
/* glGenerateMipmap is defined in the FBO extension */
|
||||
if (cogl_features_available (COGL_FEATURE_OFFSCREEN))
|
||||
GE( glGenerateMipmap (tex->gl_target) );
|
||||
else
|
||||
{
|
||||
CoglTexturePixel *pixel = tex->first_pixels + i;
|
||||
/* Temporarily enable automatic mipmap generation and
|
||||
re-upload the first pixel to cause a regeneration */
|
||||
GE( glTexParameteri (tex->gl_target, GL_GENERATE_MIPMAP, GL_TRUE) );
|
||||
GE( glTexSubImage2D (tex->gl_target, 0, 0, 0, 1, 1,
|
||||
pixel->gl_format, pixel->gl_type,
|
||||
pixel->data) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_GENERATE_MIPMAP, GL_FALSE) );
|
||||
}
|
||||
}
|
||||
|
||||
tex->mipmaps_dirty = FALSE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
cogl_texture_set_region (CoglHandle handle,
|
||||
gint src_x,
|
||||
|
24
gl/cogl.c
24
gl/cogl.c
@ -399,6 +399,10 @@ _cogl_features_init (void)
|
||||
(COGL_PFNGLDELETEFRAMEBUFFERSEXTPROC)
|
||||
cogl_get_proc_address ("glDeleteFramebuffersEXT");
|
||||
|
||||
ctx->pf_glGenerateMipmapEXT =
|
||||
(COGL_PFNGLGENERATEMIPMAPEXTPROC)
|
||||
cogl_get_proc_address ("glGenerateMipmapEXT");
|
||||
|
||||
if (ctx->pf_glGenRenderbuffersEXT &&
|
||||
ctx->pf_glBindRenderbufferEXT &&
|
||||
ctx->pf_glRenderbufferStorageEXT &&
|
||||
@ -407,7 +411,8 @@ _cogl_features_init (void)
|
||||
ctx->pf_glFramebufferTexture2DEXT &&
|
||||
ctx->pf_glFramebufferRenderbufferEXT &&
|
||||
ctx->pf_glCheckFramebufferStatusEXT &&
|
||||
ctx->pf_glDeleteFramebuffersEXT)
|
||||
ctx->pf_glDeleteFramebuffersEXT &&
|
||||
ctx->pf_glGenerateMipmapEXT)
|
||||
flags |= COGL_FEATURE_OFFSCREEN;
|
||||
}
|
||||
|
||||
@ -486,6 +491,23 @@ _cogl_features_init (void)
|
||||
(COGL_PFNGLCLIENTACTIVETEXTUREPROC)
|
||||
cogl_get_proc_address ("glClientActiveTexture");
|
||||
|
||||
ctx->pf_glBlendEquation =
|
||||
(COGL_PFNGLBLENDEQUATIONPROC)
|
||||
cogl_get_proc_address ("glBlendEquation");
|
||||
ctx->pf_glBlendColor =
|
||||
(COGL_PFNGLBLENDCOLORPROC)
|
||||
cogl_get_proc_address ("glBlendColor");
|
||||
|
||||
/* Available in 1.4 */
|
||||
ctx->pf_glBlendFuncSeparate =
|
||||
(COGL_PFNGLBLENDFUNCSEPARATEPROC)
|
||||
cogl_get_proc_address ("glBlendFuncSeparate");
|
||||
|
||||
/* Available in 2.0 */
|
||||
ctx->pf_glBlendEquationSeparate =
|
||||
(COGL_PFNGLBLENDEQUATIONSEPARATEPROC)
|
||||
cogl_get_proc_address ("glBlendEquationSeparate");
|
||||
|
||||
/* Cache features */
|
||||
ctx->feature_flags = flags;
|
||||
ctx->features_cached = TRUE;
|
||||
|
@ -27,12 +27,12 @@ INCLUDES = \
|
||||
-DG_LOG_DOMAIN=\"Cogl-GLES\" \
|
||||
-DCLUTTER_COMPILATION
|
||||
|
||||
noinst_LTLIBRARIES = libclutter-cogl.la
|
||||
noinst_LTLIBRARIES = libclutter-cogl-gles.la
|
||||
|
||||
libclutter_cogl_la_CPPFLAGS = $(CLUTTER_CFLAGS) $(COGL_DEBUG_CFLAGS) $(CLUTTER_DEBUG_CFLAGS) $(MAINTAINER_CFLAGS)
|
||||
libclutter_cogl_la_LIBADD = -lm $(CLUTTER_LIBS) $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_la_DEPENDENCIES = $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_la_SOURCES = \
|
||||
libclutter_cogl_gles_la_CPPFLAGS = $(CLUTTER_CFLAGS) $(COGL_DEBUG_CFLAGS) $(CLUTTER_DEBUG_CFLAGS) $(MAINTAINER_CFLAGS)
|
||||
libclutter_cogl_gles_la_LIBADD = -lm $(CLUTTER_LIBS) $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_gles_la_DEPENDENCIES = $(top_builddir)/clutter/cogl/common/libclutter-cogl-common.la
|
||||
libclutter_cogl_gles_la_SOURCES = \
|
||||
$(top_builddir)/clutter/cogl/cogl.h \
|
||||
$(top_builddir)/clutter/cogl/cogl-defines-gles.h \
|
||||
$(top_builddir)/clutter/cogl/cogl-color.h \
|
||||
@ -60,7 +60,7 @@ libclutter_cogl_la_SOURCES = \
|
||||
cogl-shader.c
|
||||
|
||||
if USE_GLES2_WRAPPER
|
||||
libclutter_cogl_la_SOURCES += \
|
||||
libclutter_cogl_gles_la_SOURCES += \
|
||||
cogl-gles2-wrapper.c \
|
||||
cogl-fixed-vertex-shader.h \
|
||||
cogl-fixed-vertex-shader.c \
|
||||
|
@ -39,7 +39,7 @@
|
||||
static CoglContext *_context = NULL;
|
||||
static gboolean gl_is_indirect = FALSE;
|
||||
|
||||
gboolean
|
||||
static gboolean
|
||||
cogl_create_context ()
|
||||
{
|
||||
GLubyte default_texture_data[] = { 0xff, 0xff, 0xff, 0x0 };
|
||||
@ -72,7 +72,6 @@ cogl_create_context ()
|
||||
|
||||
_context->journal = g_array_new (FALSE, FALSE, sizeof (CoglJournalEntry));
|
||||
_context->logged_vertices = g_array_new (FALSE, FALSE, sizeof (GLfloat));
|
||||
_context->static_indices = g_array_new (FALSE, FALSE, sizeof (GLushort));
|
||||
_context->polygon_vertices = g_array_new (FALSE, FALSE,
|
||||
sizeof (CoglTextureGLVertex));
|
||||
|
||||
@ -107,8 +106,7 @@ cogl_create_context ()
|
||||
_context->default_gl_texture_2d_tex =
|
||||
cogl_texture_new_from_data (1, /* width */
|
||||
1, /* height */
|
||||
-1, /* max waste */
|
||||
COGL_TEXTURE_NONE, /* flags */
|
||||
COGL_TEXTURE_NO_SLICING, /* flags */
|
||||
COGL_PIXEL_FORMAT_RGBA_8888, /* data format */
|
||||
/* internal format */
|
||||
COGL_PIXEL_FORMAT_RGBA_8888,
|
||||
@ -117,8 +115,7 @@ cogl_create_context ()
|
||||
_context->default_gl_texture_rect_tex =
|
||||
cogl_texture_new_from_data (1, /* width */
|
||||
1, /* height */
|
||||
-1, /* max waste */
|
||||
COGL_TEXTURE_NONE, /* flags */
|
||||
COGL_TEXTURE_NO_SLICING, /* flags */
|
||||
COGL_PIXEL_FORMAT_RGBA_8888, /* data format */
|
||||
/* internal format */
|
||||
COGL_PIXEL_FORMAT_RGBA_8888,
|
||||
@ -126,16 +123,20 @@ cogl_create_context ()
|
||||
default_texture_data);
|
||||
|
||||
cogl_set_source (_context->default_material);
|
||||
cogl_material_flush_gl_state (_context->source_material, NULL);
|
||||
_cogl_material_flush_gl_state (_context->source_material, NULL);
|
||||
enable_flags =
|
||||
cogl_material_get_cogl_enable_flags (_context->source_material);
|
||||
_cogl_material_get_cogl_enable_flags (_context->source_material);
|
||||
cogl_enable (enable_flags);
|
||||
|
||||
_context->quad_indices_byte = COGL_INVALID_HANDLE;
|
||||
_context->quad_indices_short = COGL_INVALID_HANDLE;
|
||||
_context->quad_indices_short_len = 0;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_destroy_context ()
|
||||
_cogl_destroy_context ()
|
||||
{
|
||||
if (_context == NULL)
|
||||
return;
|
||||
@ -160,13 +161,16 @@ cogl_destroy_context ()
|
||||
if (_context->logged_vertices)
|
||||
g_array_free (_context->logged_vertices, TRUE);
|
||||
|
||||
if (_context->static_indices)
|
||||
g_array_free (_context->static_indices, TRUE);
|
||||
if (_context->polygon_vertices)
|
||||
g_array_free (_context->polygon_vertices, TRUE);
|
||||
if (_context->current_layers)
|
||||
g_array_free (_context->current_layers, TRUE);
|
||||
|
||||
if (_context->quad_indices_byte)
|
||||
cogl_handle_unref (_context->quad_indices_byte);
|
||||
if (_context->quad_indices_short)
|
||||
cogl_handle_unref (_context->quad_indices_short);
|
||||
|
||||
g_free (_context);
|
||||
}
|
||||
|
||||
|
@ -80,7 +80,6 @@ typedef struct
|
||||
* can batch things together. */
|
||||
GArray *journal;
|
||||
GArray *logged_vertices;
|
||||
GArray *static_indices;
|
||||
GArray *polygon_vertices;
|
||||
|
||||
/* Some simple caching, to minimize state changes... */
|
||||
@ -104,6 +103,12 @@ typedef struct
|
||||
floatVec2 path_nodes_max;
|
||||
CoglHandle stencil_material;
|
||||
|
||||
/* Pre-generated VBOs containing indices to generate GL_TRIANGLES
|
||||
out of a vertex array of quads */
|
||||
CoglHandle quad_indices_byte;
|
||||
guint quad_indices_short_len;
|
||||
CoglHandle quad_indices_short;
|
||||
|
||||
#ifdef HAVE_COGL_GLES2
|
||||
CoglGles2Wrapper gles2;
|
||||
|
||||
@ -111,7 +116,6 @@ typedef struct
|
||||
supported */
|
||||
GLint viewport_store[4];
|
||||
#endif
|
||||
|
||||
} CoglContext;
|
||||
|
||||
CoglContext *
|
||||
|
@ -89,13 +89,13 @@ cogl_gles2_wrapper_create_shader (GLenum type, const char *source)
|
||||
|
||||
if (!status)
|
||||
{
|
||||
char log[1024];
|
||||
char shader_log[1024];
|
||||
GLint len;
|
||||
|
||||
glGetShaderInfoLog (shader, sizeof (log) - 1, &len, log);
|
||||
log[len] = '\0';
|
||||
glGetShaderInfoLog (shader, sizeof (shader_log) - 1, &len, shader_log);
|
||||
shader_log[len] = '\0';
|
||||
|
||||
g_critical ("%s", log);
|
||||
g_critical ("%s", shader_log);
|
||||
|
||||
glDeleteShader (shader);
|
||||
|
||||
@ -538,9 +538,9 @@ cogl_gles2_wrapper_get_program (const CoglGles2WrapperSettings *settings)
|
||||
CoglShader *shader
|
||||
= _cogl_shader_pointer_from_handle ((CoglHandle) node->data);
|
||||
|
||||
if (shader->type == CGL_VERTEX_SHADER)
|
||||
if (shader->type == COGL_SHADER_TYPE_VERTEX)
|
||||
custom_vertex_shader = TRUE;
|
||||
else if (shader->type == CGL_FRAGMENT_SHADER)
|
||||
else if (shader->type == COGL_SHADER_TYPE_FRAGMENT)
|
||||
custom_fragment_shader = TRUE;
|
||||
}
|
||||
}
|
||||
@ -581,13 +581,13 @@ cogl_gles2_wrapper_get_program (const CoglGles2WrapperSettings *settings)
|
||||
|
||||
if (!status)
|
||||
{
|
||||
char log[1024];
|
||||
char shader_log[1024];
|
||||
GLint len;
|
||||
|
||||
glGetProgramInfoLog (program->program, sizeof (log) - 1, &len, log);
|
||||
log[len] = '\0';
|
||||
glGetProgramInfoLog (program->program, sizeof (shader_log) - 1, &len, shader_log);
|
||||
shader_log[len] = '\0';
|
||||
|
||||
g_critical ("%s", log);
|
||||
g_critical ("%s", shader_log);
|
||||
|
||||
glDeleteProgram (program->program);
|
||||
g_slice_free (CoglGles2WrapperProgram, program);
|
||||
@ -1300,13 +1300,20 @@ cogl_gles2_wrapper_bind_texture (GLenum target, GLuint texture,
|
||||
}
|
||||
|
||||
void
|
||||
cogl_wrap_glTexEnvi (GLenum target, GLenum pname, GLfloat param)
|
||||
cogl_wrap_glTexEnvi (GLenum target, GLenum pname, GLint param)
|
||||
{
|
||||
/* This function is only used to set the texture mode once to
|
||||
GL_MODULATE. The shader is hard-coded to modulate the texture so
|
||||
nothing needs to be done here. */
|
||||
}
|
||||
|
||||
void
|
||||
cogl_wrap_glTexEnvfv (GLenum target, GLenum pname, const GLfloat *params)
|
||||
{
|
||||
/* FIXME: Currently needed to support texture combining using
|
||||
* COGL_BLEND_STRING_COLOR_SOURCE_CONSTANT */
|
||||
}
|
||||
|
||||
void
|
||||
cogl_wrap_glClientActiveTexture (GLenum texture)
|
||||
{
|
||||
|
@ -259,6 +259,7 @@ struct _CoglGles2WrapperShader
|
||||
|
||||
#define GL_TEXTURE_ENV 0x2300
|
||||
#define GL_TEXTURE_ENV_MODE 0x2200
|
||||
#define GL_TEXTURE_ENV_COLOR 0x2201
|
||||
#define GL_MODULATE 0x2100
|
||||
|
||||
#define GL_EXP 0x8000
|
||||
@ -327,7 +328,8 @@ void cogl_wrap_glColorPointer (GLint size, GLenum type, GLsizei stride,
|
||||
void cogl_wrap_glNormalPointer (GLenum type, GLsizei stride,
|
||||
const GLvoid *pointer);
|
||||
|
||||
void cogl_wrap_glTexEnvi (GLenum target, GLenum pname, GLfloat param);
|
||||
void cogl_wrap_glTexEnvi (GLenum target, GLenum pname, GLint param);
|
||||
void cogl_wrap_glTexEnvfv (GLenum target, GLenum pname, const GLfloat *params);
|
||||
|
||||
void cogl_wrap_glClientActiveTexture (GLenum texture);
|
||||
void cogl_wrap_glActiveTexture (GLenum texture);
|
||||
@ -384,6 +386,7 @@ void _cogl_gles2_clear_cache_for_program (CoglHandle program);
|
||||
#define glColorPointer cogl_wrap_glColorPointer
|
||||
#define glNormalPointer cogl_wrap_glNormalPointer
|
||||
#define glTexEnvi cogl_wrap_glTexEnvi
|
||||
#define glTexEnvfv cogl_wrap_glTexEnvfv
|
||||
#define glActiveTexture cogl_wrap_glActiveTexture
|
||||
#define glClientActiveTexture cogl_wrap_glClientActiveTexture
|
||||
#define glEnableClientState cogl_wrap_glEnableClientState
|
||||
|
@ -29,6 +29,7 @@
|
||||
#include "cogl-internal.h"
|
||||
#include "cogl-context.h"
|
||||
#include "cogl-clip-stack.h"
|
||||
#include "cogl-material-private.h"
|
||||
|
||||
#include <string.h>
|
||||
#include <gmodule.h>
|
||||
@ -78,13 +79,13 @@ _cogl_path_stroke_nodes ()
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
enable_flags |= cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
enable_flags |= _cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
cogl_enable (enable_flags);
|
||||
|
||||
cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
(guint32)~0, /* disable all texture layers */
|
||||
NULL);
|
||||
_cogl_material_flush_gl_state (ctx->source_material,
|
||||
COGL_MATERIAL_FLUSH_DISABLE_MASK,
|
||||
(guint32)~0, /* disable all texture layers */
|
||||
NULL);
|
||||
_cogl_current_matrix_state_flush ();
|
||||
|
||||
while (path_start < ctx->path_nodes->len)
|
||||
@ -139,10 +140,10 @@ _cogl_add_path_to_stencil_buffer (floatVec2 nodes_min,
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
/* Just setup a simple material that doesn't use texturing... */
|
||||
cogl_material_flush_gl_state (ctx->stencil_material, NULL);
|
||||
_cogl_material_flush_gl_state (ctx->stencil_material, NULL);
|
||||
|
||||
enable_flags |=
|
||||
cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
_cogl_material_get_cogl_enable_flags (ctx->source_material);
|
||||
cogl_enable (enable_flags);
|
||||
|
||||
_cogl_path_get_bounds (nodes_min, nodes_max,
|
||||
@ -361,30 +362,30 @@ _cogl_path_fill_nodes_scanlines (CoglPathNode *path,
|
||||
while (iter)
|
||||
{
|
||||
GSList *next = iter->next;
|
||||
GLfloat x0, x1;
|
||||
GLfloat y0, y1;
|
||||
GLfloat x_0, x_1;
|
||||
GLfloat y_0, y_1;
|
||||
if (!next)
|
||||
break;
|
||||
|
||||
x0 = GPOINTER_TO_INT (iter->data);
|
||||
x1 = GPOINTER_TO_INT (next->data);
|
||||
y0 = bounds_y + i;
|
||||
y1 = bounds_y + i + 1.0625f;
|
||||
x_0 = GPOINTER_TO_INT (iter->data);
|
||||
x_1 = GPOINTER_TO_INT (next->data);
|
||||
y_0 = bounds_y + i;
|
||||
y_1 = bounds_y + i + 1.0625f;
|
||||
/* render scanlines 1.0625 high to avoid gaps when
|
||||
transformed */
|
||||
|
||||
coords[span_no * 12 + 0] = x0;
|
||||
coords[span_no * 12 + 1] = y0;
|
||||
coords[span_no * 12 + 2] = x1;
|
||||
coords[span_no * 12 + 3] = y0;
|
||||
coords[span_no * 12 + 4] = x1;
|
||||
coords[span_no * 12 + 5] = y1;
|
||||
coords[span_no * 12 + 6] = x0;
|
||||
coords[span_no * 12 + 7] = y0;
|
||||
coords[span_no * 12 + 8] = x0;
|
||||
coords[span_no * 12 + 9] = y1;
|
||||
coords[span_no * 12 + 10] = x1;
|
||||
coords[span_no * 12 + 11] = y1;
|
||||
coords[span_no * 12 + 0] = x_0;
|
||||
coords[span_no * 12 + 1] = y_0;
|
||||
coords[span_no * 12 + 2] = x_1;
|
||||
coords[span_no * 12 + 3] = y_0;
|
||||
coords[span_no * 12 + 4] = x_1;
|
||||
coords[span_no * 12 + 5] = y_1;
|
||||
coords[span_no * 12 + 6] = x_0;
|
||||
coords[span_no * 12 + 7] = y_0;
|
||||
coords[span_no * 12 + 8] = x_0;
|
||||
coords[span_no * 12 + 9] = y_1;
|
||||
coords[span_no * 12 + 10] = x_1;
|
||||
coords[span_no * 12 + 11] = y_1;
|
||||
span_no ++;
|
||||
iter = next->next;
|
||||
}
|
||||
|
@ -99,22 +99,23 @@ cogl_shader_compile (CoglHandle handle)
|
||||
glCompileShader (shader->gl_handle);
|
||||
}
|
||||
|
||||
void
|
||||
cogl_shader_get_info_log (CoglHandle handle,
|
||||
size_t size,
|
||||
char *buffer)
|
||||
gchar *
|
||||
cogl_shader_get_info_log (CoglHandle handle)
|
||||
{
|
||||
CoglShader *shader;
|
||||
char buffer[512];
|
||||
int len = 0;
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
_COGL_GET_CONTEXT (ctx, NULL);
|
||||
|
||||
if (!cogl_is_shader (handle))
|
||||
return;
|
||||
return NULL;
|
||||
|
||||
shader = _cogl_shader_pointer_from_handle (handle);
|
||||
|
||||
glGetShaderInfoLog (shader->gl_handle, size - 1, &len, buffer);
|
||||
glGetShaderInfoLog (shader->gl_handle, 511, &len, buffer);
|
||||
buffer[len] = '\0';
|
||||
|
||||
return g_strdup (buffer);
|
||||
}
|
||||
|
||||
CoglShaderType
|
||||
@ -199,11 +200,10 @@ cogl_shader_compile (CoglHandle shader_handle)
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
cogl_shader_get_info_log (CoglHandle handle,
|
||||
size_t size,
|
||||
char *buffer)
|
||||
gchar *
|
||||
cogl_shader_get_info_log (CoglHandle handle)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
CoglShaderType
|
||||
|
@ -30,6 +30,7 @@
|
||||
typedef struct _CoglTexture CoglTexture;
|
||||
typedef struct _CoglTexSliceSpan CoglTexSliceSpan;
|
||||
typedef struct _CoglSpanIter CoglSpanIter;
|
||||
typedef struct _CoglTexturePixel CoglTexturePixel;
|
||||
|
||||
struct _CoglTexSliceSpan
|
||||
{
|
||||
@ -55,6 +56,18 @@ struct _CoglSpanIter
|
||||
gboolean intersects;
|
||||
};
|
||||
|
||||
/* This is used to store the first pixel of each slice. This is only
|
||||
used when glGenerateMipmap is not available */
|
||||
struct _CoglTexturePixel
|
||||
{
|
||||
/* We need to store the format of the pixel because we store the
|
||||
data in the source format which might end up being different for
|
||||
each slice if a subregion is updated with a different format */
|
||||
GLenum gl_format;
|
||||
GLenum gl_type;
|
||||
guint8 data[4];
|
||||
};
|
||||
|
||||
struct _CoglTexture
|
||||
{
|
||||
CoglHandleObject _parent;
|
||||
@ -68,11 +81,17 @@ struct _CoglTexture
|
||||
GArray *slice_y_spans;
|
||||
GArray *slice_gl_handles;
|
||||
gint max_waste;
|
||||
CoglTextureFilter min_filter;
|
||||
CoglTextureFilter mag_filter;
|
||||
GLenum min_filter;
|
||||
GLenum mag_filter;
|
||||
gboolean is_foreign;
|
||||
GLint wrap_mode;
|
||||
gboolean auto_mipmap;
|
||||
gboolean mipmaps_dirty;
|
||||
|
||||
/* This holds a copy of the first pixel in each slice. It is only
|
||||
used to force an automatic update of the mipmaps when
|
||||
glGenerateMipmap is not available. */
|
||||
CoglTexturePixel *first_pixels;
|
||||
};
|
||||
|
||||
/* To improve batching of geometry when submitting vertices to OpenGL we
|
||||
@ -93,6 +112,14 @@ void
|
||||
_cogl_texture_set_wrap_mode_parameter (CoglTexture *tex,
|
||||
GLenum wrap_mode);
|
||||
|
||||
void
|
||||
_cogl_texture_set_filters (CoglHandle handle,
|
||||
GLenum min_filter,
|
||||
GLenum mag_filter);
|
||||
|
||||
void
|
||||
_cogl_texture_ensure_mipmaps (CoglHandle handle);
|
||||
|
||||
gboolean
|
||||
_cogl_texture_span_has_waste (CoglTexture *tex,
|
||||
gint x_span_index,
|
||||
|
@ -225,11 +225,12 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
/* Iterate horizontal slices */
|
||||
for (x = 0; x < tex->slice_x_spans->len; ++x)
|
||||
{
|
||||
gint slice_num = y * tex->slice_x_spans->len + x;
|
||||
|
||||
x_span = &g_array_index (tex->slice_x_spans, CoglTexSliceSpan, x);
|
||||
|
||||
/* Pick the gl texture object handle */
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint,
|
||||
y * tex->slice_x_spans->len + x);
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint, slice_num);
|
||||
|
||||
/* FIXME: might optimize by not copying to intermediate slice
|
||||
bitmap when source rowstride = bpp * width and the texture
|
||||
@ -258,6 +259,16 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
slice_bmp.width,
|
||||
slice_bmp.height);
|
||||
|
||||
/* Keep a copy of the first pixel if needed */
|
||||
if (tex->first_pixels)
|
||||
{
|
||||
memcpy (tex->first_pixels[slice_num].data,
|
||||
slice_bmp.data,
|
||||
bpp);
|
||||
tex->first_pixels[slice_num].gl_format = tex->gl_format;
|
||||
tex->first_pixels[slice_num].gl_type = tex->gl_type;
|
||||
}
|
||||
|
||||
/* Upload new image data */
|
||||
GE( cogl_gles2_wrapper_bind_texture (tex->gl_target, gl_handle,
|
||||
tex->gl_intformat) );
|
||||
@ -338,9 +349,6 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
waste_buf) );
|
||||
}
|
||||
|
||||
if (tex->auto_mipmap)
|
||||
cogl_wrap_glGenerateMipmap (tex->gl_target);
|
||||
|
||||
/* Free temp bitmap */
|
||||
g_free (slice_bmp.data);
|
||||
}
|
||||
@ -349,6 +357,8 @@ _cogl_texture_upload_to_gl (CoglTexture *tex)
|
||||
if (waste_buf)
|
||||
g_free (waste_buf);
|
||||
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -442,6 +452,7 @@ _cogl_texture_download_from_gl (CoglTexture *tex,
|
||||
gint bpp;
|
||||
GLint viewport[4];
|
||||
CoglBitmap alpha_bmp;
|
||||
CoglHandle prev_source;
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, FALSE);
|
||||
|
||||
@ -477,31 +488,21 @@ _cogl_texture_download_from_gl (CoglTexture *tex,
|
||||
if (ctx->texture_download_material == COGL_INVALID_HANDLE)
|
||||
{
|
||||
ctx->texture_download_material = cogl_material_new ();
|
||||
cogl_material_set_layer_combine_function (
|
||||
ctx->texture_download_material,
|
||||
0, /* layer */
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB,
|
||||
COGL_MATERIAL_LAYER_COMBINE_FUNC_REPLACE);
|
||||
cogl_material_set_layer_combine_arg_src (
|
||||
ctx->texture_download_material,
|
||||
0, /* layer */
|
||||
0, /* arg */
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB,
|
||||
COGL_MATERIAL_LAYER_COMBINE_SRC_TEXTURE);
|
||||
cogl_material_set_blend_factors (ctx->texture_download_material,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ONE,
|
||||
COGL_MATERIAL_BLEND_FACTOR_ZERO);
|
||||
cogl_material_set_blend (ctx->texture_download_material,
|
||||
"RGBA = ADD (SRC_COLOR, 0)",
|
||||
NULL);
|
||||
}
|
||||
|
||||
prev_source = cogl_handle_ref (ctx->source_material);
|
||||
cogl_set_source (ctx->texture_download_material);
|
||||
|
||||
cogl_material_set_layer (ctx->texture_download_material, 0, tex);
|
||||
|
||||
cogl_material_set_layer_combine_arg_op (
|
||||
ctx->texture_download_material,
|
||||
0, /* layer */
|
||||
0, /* arg */
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB,
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_SRC_COLOR);
|
||||
cogl_material_flush_gl_state (ctx->texture_download_material, NULL);
|
||||
cogl_material_set_layer_combine (ctx->texture_download_material,
|
||||
0, /* layer */
|
||||
"RGBA = REPLACE (TEXTURE)",
|
||||
NULL);
|
||||
|
||||
_cogl_texture_draw_and_read (tex, target_bmp, viewport);
|
||||
|
||||
/* Check whether texture has alpha and framebuffer not */
|
||||
@ -534,13 +535,11 @@ _cogl_texture_download_from_gl (CoglTexture *tex,
|
||||
alpha_bmp.height);
|
||||
|
||||
/* Draw alpha values into RGB channels */
|
||||
cogl_material_set_layer_combine_arg_op (
|
||||
ctx->texture_download_material,
|
||||
0, /* layer */
|
||||
0, /* arg */
|
||||
COGL_MATERIAL_LAYER_COMBINE_CHANNELS_RGB,
|
||||
COGL_MATERIAL_LAYER_COMBINE_OP_SRC_ALPHA);
|
||||
cogl_material_flush_gl_state (ctx->texture_download_material, NULL);
|
||||
cogl_material_set_layer_combine (ctx->texture_download_material,
|
||||
0, /* layer */
|
||||
"RGBA = REPLACE (TEXTURE[A])",
|
||||
NULL);
|
||||
|
||||
_cogl_texture_draw_and_read (tex, &alpha_bmp, viewport);
|
||||
|
||||
/* Copy temp R to target A */
|
||||
@ -568,6 +567,10 @@ _cogl_texture_download_from_gl (CoglTexture *tex,
|
||||
_cogl_set_current_matrix (COGL_MATRIX_MODELVIEW);
|
||||
_cogl_current_matrix_pop ();
|
||||
|
||||
/* restore the original material */
|
||||
cogl_set_source (prev_source);
|
||||
cogl_handle_unref (prev_source);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -631,6 +634,8 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
_cogl_span_iter_next (&x_iter),
|
||||
source_x += inter_w )
|
||||
{
|
||||
gint slice_num;
|
||||
|
||||
/* Discard slices out of the subregion early */
|
||||
if (!x_iter.intersects)
|
||||
{
|
||||
@ -653,10 +658,10 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
local_y = (y_iter.intersect_start -
|
||||
y_iter.pos);
|
||||
|
||||
slice_num = y_iter.index * tex->slice_x_spans->len + x_iter.index;
|
||||
|
||||
/* Pick slice GL handle */
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint,
|
||||
y_iter.index * tex->slice_x_spans->len +
|
||||
x_iter.index);
|
||||
gl_handle = g_array_index (tex->slice_gl_handles, GLuint, slice_num);
|
||||
|
||||
/* FIXME: might optimize by not copying to intermediate slice
|
||||
bitmap when source rowstride = bpp * width and the texture
|
||||
@ -685,6 +690,15 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
slice_bmp.width,
|
||||
slice_bmp.height);
|
||||
|
||||
/* Keep a copy of the first pixel if needed */
|
||||
if (tex->first_pixels && local_x == 0 && local_y == 0)
|
||||
{
|
||||
memcpy (tex->first_pixels[slice_num].data,
|
||||
slice_bmp.data, bpp);
|
||||
tex->first_pixels[slice_num].gl_format = source_gl_format;
|
||||
tex->first_pixels[slice_num].gl_type = source_gl_type;
|
||||
}
|
||||
|
||||
/* Upload new image data */
|
||||
GE( cogl_gles2_wrapper_bind_texture (tex->gl_target, gl_handle,
|
||||
tex->gl_intformat) );
|
||||
@ -794,9 +808,6 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
waste_buf) );
|
||||
}
|
||||
|
||||
if (tex->auto_mipmap)
|
||||
cogl_wrap_glGenerateMipmap (tex->gl_target);
|
||||
|
||||
/* Free temp bitmap */
|
||||
g_free (slice_bmp.data);
|
||||
}
|
||||
@ -805,6 +816,8 @@ _cogl_texture_upload_subregion_to_gl (CoglTexture *tex,
|
||||
if (waste_buf)
|
||||
g_free (waste_buf);
|
||||
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -858,7 +871,8 @@ _cogl_pot_slices_for_size (gint size_to_fill,
|
||||
span.waste = 0;
|
||||
|
||||
/* Fix invalid max_waste */
|
||||
if (max_waste < 0) max_waste = 0;
|
||||
if (max_waste < 0)
|
||||
max_waste = 0;
|
||||
|
||||
while (TRUE)
|
||||
{
|
||||
@ -866,7 +880,9 @@ _cogl_pot_slices_for_size (gint size_to_fill,
|
||||
if (size_to_fill > span.size)
|
||||
{
|
||||
/* Not yet - add a span of this size */
|
||||
if (out_spans) g_array_append_val (out_spans, span);
|
||||
if (out_spans)
|
||||
g_array_append_val (out_spans, span);
|
||||
|
||||
span.start += span.size;
|
||||
size_to_fill -= span.size;
|
||||
n_spans++;
|
||||
@ -875,7 +891,9 @@ _cogl_pot_slices_for_size (gint size_to_fill,
|
||||
{
|
||||
/* Yes and waste is small enough */
|
||||
span.waste = span.size - size_to_fill;
|
||||
if (out_spans) g_array_append_val (out_spans, span);
|
||||
if (out_spans)
|
||||
g_array_append_val (out_spans, span);
|
||||
|
||||
return ++n_spans;
|
||||
}
|
||||
else
|
||||
@ -971,10 +989,10 @@ _cogl_texture_slices_create (CoglTexture *tex)
|
||||
|
||||
/* Check if size supported else bail out */
|
||||
if (!_cogl_texture_size_supported (tex->gl_target,
|
||||
tex->gl_format,
|
||||
tex->gl_type,
|
||||
max_width,
|
||||
max_height))
|
||||
tex->gl_format,
|
||||
tex->gl_type,
|
||||
max_width,
|
||||
max_height))
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
@ -1057,6 +1075,14 @@ _cogl_texture_slices_create (CoglTexture *tex)
|
||||
|
||||
g_array_set_size (tex->slice_gl_handles, n_slices);
|
||||
|
||||
/* Allocate some space to store a copy of the first pixel of each
|
||||
slice. This is only needed to glGenerateMipmap (which is part of
|
||||
the FBO extension) is not available */
|
||||
if (cogl_features_available (COGL_FEATURE_OFFSCREEN))
|
||||
tex->first_pixels = NULL;
|
||||
else
|
||||
tex->first_pixels = g_new (CoglTexturePixel, n_slices);
|
||||
|
||||
/* Wrap mode not yet set */
|
||||
tex->wrap_mode = GL_FALSE;
|
||||
|
||||
@ -1087,20 +1113,11 @@ _cogl_texture_slices_create (CoglTexture *tex)
|
||||
GE( cogl_gles2_wrapper_bind_texture (tex->gl_target,
|
||||
gl_handles[y * n_x_slices + x],
|
||||
tex->gl_intformat) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_TEXTURE_MAG_FILTER,
|
||||
tex->mag_filter) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_TEXTURE_MIN_FILTER,
|
||||
tex->min_filter) );
|
||||
|
||||
GE( glTexParameteri (tex->gl_target, GL_TEXTURE_WRAP_S,
|
||||
tex->wrap_mode) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_TEXTURE_WRAP_T,
|
||||
tex->wrap_mode) );
|
||||
|
||||
if (tex->auto_mipmap)
|
||||
GE( glTexParameteri (tex->gl_target, GL_GENERATE_MIPMAP,
|
||||
GL_TRUE) );
|
||||
|
||||
/* Pass NULL data to init size and internal format */
|
||||
GE( glTexImage2D (tex->gl_target, 0, tex->gl_intformat,
|
||||
x_span->size, y_span->size, 0,
|
||||
@ -1130,6 +1147,9 @@ _cogl_texture_slices_free (CoglTexture *tex)
|
||||
|
||||
g_array_free (tex->slice_gl_handles, TRUE);
|
||||
}
|
||||
|
||||
if (tex->first_pixels != NULL)
|
||||
g_free (tex->first_pixels);
|
||||
}
|
||||
|
||||
gboolean
|
||||
@ -1288,11 +1308,10 @@ _cogl_texture_free (CoglTexture *tex)
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_texture_new_with_size (guint width,
|
||||
guint height,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
cogl_texture_new_with_size (guint width,
|
||||
guint height,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
gint bpp;
|
||||
@ -1310,7 +1329,8 @@ cogl_texture_new_with_size (guint width,
|
||||
tex = (CoglTexture*) g_malloc (sizeof (CoglTexture));
|
||||
|
||||
tex->is_foreign = FALSE;
|
||||
tex->auto_mipmap = ((flags & COGL_TEXTURE_AUTO_MIPMAP) != 0);
|
||||
tex->auto_mipmap = (flags & COGL_TEXTURE_NO_AUTO_MIPMAP) == 0;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
tex->bitmap.width = width;
|
||||
tex->bitmap.height = height;
|
||||
@ -1323,9 +1343,14 @@ cogl_texture_new_with_size (guint width,
|
||||
tex->slice_y_spans = NULL;
|
||||
tex->slice_gl_handles = NULL;
|
||||
|
||||
tex->max_waste = max_waste;
|
||||
tex->min_filter = CGL_NEAREST;
|
||||
tex->mag_filter = CGL_NEAREST;
|
||||
if (flags & COGL_TEXTURE_NO_SLICING)
|
||||
tex->max_waste = -1;
|
||||
else
|
||||
tex->max_waste = COGL_TEXTURE_MAX_WASTE;
|
||||
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
|
||||
/* Find closest GL format match */
|
||||
tex->bitmap.format =
|
||||
@ -1347,7 +1372,6 @@ cogl_texture_new_with_size (guint width,
|
||||
CoglHandle
|
||||
cogl_texture_new_from_data (guint width,
|
||||
guint height,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat format,
|
||||
CoglPixelFormat internal_format,
|
||||
@ -1371,7 +1395,8 @@ cogl_texture_new_from_data (guint width,
|
||||
tex = (CoglTexture*) g_malloc (sizeof (CoglTexture));
|
||||
|
||||
tex->is_foreign = FALSE;
|
||||
tex->auto_mipmap = ((flags & COGL_TEXTURE_AUTO_MIPMAP) != 0);
|
||||
tex->auto_mipmap = (flags & COGL_TEXTURE_NO_AUTO_MIPMAP) == 0;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
tex->bitmap.width = width;
|
||||
tex->bitmap.height = height;
|
||||
@ -1384,9 +1409,14 @@ cogl_texture_new_from_data (guint width,
|
||||
tex->slice_y_spans = NULL;
|
||||
tex->slice_gl_handles = NULL;
|
||||
|
||||
tex->max_waste = max_waste;
|
||||
tex->min_filter = CGL_NEAREST;
|
||||
tex->mag_filter = CGL_NEAREST;
|
||||
if (flags & COGL_TEXTURE_NO_SLICING)
|
||||
tex->max_waste = -1;
|
||||
else
|
||||
tex->max_waste = COGL_TEXTURE_MAX_WASTE;
|
||||
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
|
||||
/* FIXME: If upload fails we should set some kind of
|
||||
* error flag but still return texture handle (this
|
||||
@ -1417,10 +1447,9 @@ cogl_texture_new_from_data (guint width,
|
||||
}
|
||||
|
||||
CoglHandle
|
||||
cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
CoglBitmap *bmp = (CoglBitmap *)bmp_handle;
|
||||
@ -1429,7 +1458,8 @@ cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
tex = (CoglTexture*) g_malloc ( sizeof (CoglTexture));
|
||||
|
||||
tex->is_foreign = FALSE;
|
||||
tex->auto_mipmap = ((flags & COGL_TEXTURE_AUTO_MIPMAP) != 0);
|
||||
tex->auto_mipmap = (flags & COGL_TEXTURE_NO_AUTO_MIPMAP) == 0;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
tex->bitmap = *bmp;
|
||||
tex->bitmap_owner = TRUE;
|
||||
@ -1439,9 +1469,14 @@ cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
tex->slice_y_spans = NULL;
|
||||
tex->slice_gl_handles = NULL;
|
||||
|
||||
tex->max_waste = max_waste;
|
||||
tex->min_filter = CGL_NEAREST;
|
||||
tex->mag_filter = CGL_NEAREST;
|
||||
if (flags & COGL_TEXTURE_NO_SLICING)
|
||||
tex->max_waste = -1;
|
||||
else
|
||||
tex->max_waste = COGL_TEXTURE_MAX_WASTE;
|
||||
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
|
||||
/* FIXME: If upload fails we should set some kind of
|
||||
* error flag but still return texture handle if the
|
||||
@ -1476,7 +1511,6 @@ cogl_texture_new_from_bitmap (CoglHandle bmp_handle,
|
||||
|
||||
CoglHandle
|
||||
cogl_texture_new_from_file (const gchar *filename,
|
||||
gint max_waste,
|
||||
CoglTextureFlags flags,
|
||||
CoglPixelFormat internal_format,
|
||||
GError **error)
|
||||
@ -1490,10 +1524,7 @@ cogl_texture_new_from_file (const gchar *filename,
|
||||
if (bmp == COGL_INVALID_HANDLE)
|
||||
return COGL_INVALID_HANDLE;
|
||||
|
||||
handle = cogl_texture_new_from_bitmap (bmp,
|
||||
max_waste,
|
||||
flags,
|
||||
internal_format);
|
||||
handle = cogl_texture_new_from_bitmap (bmp, flags, internal_format);
|
||||
cogl_handle_unref (bmp);
|
||||
|
||||
return handle;
|
||||
@ -1521,8 +1552,6 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
GLint gl_int_format = 0;
|
||||
GLint gl_width = 0;
|
||||
GLint gl_height = 0;
|
||||
GLint gl_min_filter;
|
||||
GLint gl_mag_filter;
|
||||
GLint gl_gen_mipmap;
|
||||
guint bpp;
|
||||
CoglTexture *tex;
|
||||
@ -1569,14 +1598,6 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
gl_height = height + y_pot_waste;
|
||||
#endif
|
||||
|
||||
GE( glGetTexParameteriv (gl_target,
|
||||
GL_TEXTURE_MIN_FILTER,
|
||||
&gl_min_filter) );
|
||||
|
||||
GE( glGetTexParameteriv (gl_target,
|
||||
GL_TEXTURE_MAG_FILTER,
|
||||
&gl_mag_filter) );
|
||||
|
||||
GE( glGetTexParameteriv (gl_target,
|
||||
GL_GENERATE_MIPMAP,
|
||||
&gl_gen_mipmap) );
|
||||
@ -1607,6 +1628,7 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
/* Setup bitmap info */
|
||||
tex->is_foreign = TRUE;
|
||||
tex->auto_mipmap = (gl_gen_mipmap == GL_TRUE) ? TRUE : FALSE;
|
||||
tex->mipmaps_dirty = TRUE;
|
||||
|
||||
bpp = _cogl_get_format_bpp (format);
|
||||
tex->bitmap.format = format;
|
||||
@ -1620,8 +1642,9 @@ cogl_texture_new_from_foreign (GLuint gl_handle,
|
||||
tex->gl_format = gl_int_format;
|
||||
tex->gl_type = GL_UNSIGNED_BYTE;
|
||||
|
||||
tex->min_filter = gl_min_filter;
|
||||
tex->mag_filter = gl_mag_filter;
|
||||
/* Unknown filter */
|
||||
tex->min_filter = GL_FALSE;
|
||||
tex->mag_filter = GL_FALSE;
|
||||
tex->max_waste = 0;
|
||||
|
||||
/* Wrap mode not yet set */
|
||||
@ -1767,36 +1790,10 @@ cogl_texture_get_gl_texture (CoglHandle handle,
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
CoglTextureFilter
|
||||
cogl_texture_get_min_filter (CoglHandle handle)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
|
||||
if (!cogl_is_texture (handle))
|
||||
return 0;
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
return tex->min_filter;
|
||||
}
|
||||
|
||||
CoglTextureFilter
|
||||
cogl_texture_get_mag_filter (CoglHandle handle)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
|
||||
if (!cogl_is_texture (handle))
|
||||
return 0;
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
return tex->mag_filter;
|
||||
}
|
||||
|
||||
void
|
||||
cogl_texture_set_filters (CoglHandle handle,
|
||||
CoglTextureFilter min_filter,
|
||||
CoglTextureFilter mag_filter)
|
||||
_cogl_texture_set_filters (CoglHandle handle,
|
||||
GLenum min_filter,
|
||||
GLenum mag_filter)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
GLuint gl_handle;
|
||||
@ -1807,14 +1804,18 @@ cogl_texture_set_filters (CoglHandle handle,
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
/* Store new values */
|
||||
tex->min_filter = min_filter;
|
||||
tex->mag_filter = mag_filter;
|
||||
|
||||
/* Make sure slices were created */
|
||||
if (tex->slice_gl_handles == NULL)
|
||||
return;
|
||||
|
||||
if (min_filter == tex->min_filter
|
||||
&& mag_filter == tex->mag_filter)
|
||||
return;
|
||||
|
||||
/* Store new values */
|
||||
tex->min_filter = min_filter;
|
||||
tex->mag_filter = mag_filter;
|
||||
|
||||
/* Apply new filters to every slice */
|
||||
for (i=0; i<tex->slice_gl_handles->len; ++i)
|
||||
{
|
||||
@ -1827,6 +1828,52 @@ cogl_texture_set_filters (CoglHandle handle,
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
_cogl_texture_ensure_mipmaps (CoglHandle handle)
|
||||
{
|
||||
CoglTexture *tex;
|
||||
int i;
|
||||
|
||||
_COGL_GET_CONTEXT (ctx, NO_RETVAL);
|
||||
|
||||
if (!cogl_is_texture (handle))
|
||||
return;
|
||||
|
||||
tex = _cogl_texture_pointer_from_handle (handle);
|
||||
|
||||
/* Only update if the mipmaps are dirty */
|
||||
if (!tex->auto_mipmap || !tex->mipmaps_dirty)
|
||||
return;
|
||||
|
||||
/* Make sure slices were created */
|
||||
if (tex->slice_gl_handles == NULL)
|
||||
return;
|
||||
|
||||
/* Regenerate the mipmaps on every slice */
|
||||
for (i = 0; i < tex->slice_gl_handles->len; i++)
|
||||
{
|
||||
GLuint gl_handle = g_array_index (tex->slice_gl_handles, GLuint, i);
|
||||
GE( glBindTexture (tex->gl_target, gl_handle) );
|
||||
|
||||
/* glGenerateMipmap is defined in the FBO extension */
|
||||
if (cogl_features_available (COGL_FEATURE_OFFSCREEN))
|
||||
GE( cogl_wrap_glGenerateMipmap (tex->gl_target) );
|
||||
else
|
||||
{
|
||||
CoglTexturePixel *pixel = tex->first_pixels + i;
|
||||
/* Temporarily enable automatic mipmap generation and
|
||||
re-upload the first pixel to cause a regeneration */
|
||||
GE( glTexParameteri (tex->gl_target, GL_GENERATE_MIPMAP, GL_TRUE) );
|
||||
GE( glTexSubImage2D (tex->gl_target, 0, 0, 0, 1, 1,
|
||||
pixel->gl_format, pixel->gl_type,
|
||||
pixel->data) );
|
||||
GE( glTexParameteri (tex->gl_target, GL_GENERATE_MIPMAP, GL_FALSE) );
|
||||
}
|
||||
}
|
||||
|
||||
tex->mipmaps_dirty = FALSE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
cogl_texture_set_region (CoglHandle handle,
|
||||
gint src_x,
|
||||
|
Loading…
Reference in New Issue
Block a user