summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CMakeLists.txt1
-rw-r--r--cmake/CMakeLists.txt2
-rw-r--r--cmake/CompizCommon.cmake12
-rw-r--r--cmake/CompizPlugin.cmake24
-rw-r--r--cmake/FindOpenGLES2.cmake51
-rw-r--r--cmake/base.cmake4
-rw-r--r--cmake/plugin_extensions/CompizOpenGLFixups.cmake22
-rw-r--r--include/core/rect.h2
-rw-r--r--plugins/annotate/src/annotate.cpp208
-rw-r--r--plugins/blur/CMakeLists.txt20
-rw-r--r--plugins/clone/src/clone.cpp5
-rw-r--r--plugins/compiztoolbox/src/compiztoolbox.cpp36
-rw-r--r--plugins/copytex/src/copytex.cpp9
-rw-r--r--plugins/cube/CMakeLists.txt2
-rw-r--r--plugins/cube/src/cube.cpp4
-rw-r--r--plugins/decor/src/decor.cpp32
-rw-r--r--plugins/decor/src/decor.h2
-rw-r--r--plugins/imgsvg/src/imgsvg.cpp21
-rw-r--r--plugins/imgsvg/src/imgsvg.h3
-rw-r--r--plugins/obs/src/obs.cpp17
-rw-r--r--plugins/obs/src/obs.h2
-rw-r--r--plugins/opengl/CMakeLists.txt13
-rw-r--r--plugins/opengl/compiz-opengl.pc.in4
-rw-r--r--plugins/opengl/include/opengl/fragment.h124
-rw-r--r--plugins/opengl/include/opengl/matrix.h2
-rw-r--r--plugins/opengl/include/opengl/opengl.h189
-rw-r--r--plugins/opengl/include/opengl/program.h68
-rw-r--r--plugins/opengl/include/opengl/programcache.h51
-rw-r--r--plugins/opengl/include/opengl/texture.h4
-rw-r--r--plugins/opengl/include/opengl/vertexbuffer.h83
-rw-r--r--plugins/opengl/opengl.xml.in2
-rw-r--r--plugins/opengl/src/fragment.cpp1145
-rw-r--r--plugins/opengl/src/matrix.cpp54
-rw-r--r--plugins/opengl/src/paint.cpp697
-rw-r--r--plugins/opengl/src/privatefragment.h54
-rw-r--r--plugins/opengl/src/privates.h32
-rw-r--r--plugins/opengl/src/privatetexture.h32
-rw-r--r--plugins/opengl/src/privatevertexbuffer.h71
-rw-r--r--plugins/opengl/src/program.cpp225
-rw-r--r--plugins/opengl/src/programcache.cpp175
-rw-r--r--plugins/opengl/src/screen.cpp341
-rw-r--r--plugins/opengl/src/shaders.h130
-rw-r--r--plugins/opengl/src/texture.cpp129
-rw-r--r--plugins/opengl/src/vertexbuffer.cpp414
-rw-r--r--plugins/opengl/src/window.cpp111
-rw-r--r--plugins/resize/src/resize.cpp93
-rw-r--r--plugins/rotate/CMakeLists.txt2
-rw-r--r--plugins/scale/src/scale.cpp30
-rw-r--r--plugins/screenshot/src/screenshot.cpp75
-rw-r--r--plugins/switcher/src/switcher.cpp89
-rw-r--r--plugins/water/CMakeLists.txt2
-rw-r--r--plugins/wobbly/CMakeLists.txt2
-rw-r--r--plugins/zoom/src/zoom.cpp60
-rw-r--r--src/event.cpp11
-rw-r--r--src/plugin.cpp4
55 files changed, 2745 insertions, 2252 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 3544717..3fdbd4f 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -131,4 +131,3 @@ _print_configure_results ()
_check_compiz_cmake_macro (${CMAKE_MODULE_PATH_ORIG})
-
diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt
index 5c7b1f8..be99603 100644
--- a/cmake/CMakeLists.txt
+++ b/cmake/CMakeLists.txt
@@ -15,6 +15,8 @@ list (APPEND _PluginExtensionFiles
plugin_extensions/CompizGenInstallData.cmake)
list (APPEND _PluginExtensionFiles
plugin_extensions/CompizGenInstallImages.cmake)
+list (APPEND _PluginExtensionFiles
+ plugin_extensions/CompizOpenGLFixups.cmake)
if (USE_GCONF)
list (APPEND _files CompizGconf.cmake)
diff --git a/cmake/CompizCommon.cmake b/cmake/CompizCommon.cmake
index ba84d8d..efaabb8 100644
--- a/cmake/CompizCommon.cmake
+++ b/cmake/CompizCommon.cmake
@@ -18,6 +18,7 @@ cmake_policy (SET CMP0011 OLD)
set (CMAKE_SKIP_RPATH FALSE)
+option (BUILD_GLES "Build against GLESv2 instead of GL" OFF)
option (COMPIZ_BUILD_WITH_RPATH "Leave as ON unless building packages" ON)
option (COMPIZ_RUN_LDCONFIG "Leave OFF unless you need to run ldconfig after install")
option (COMPIZ_PACKAGING_ENABLED "Enable to manually set prefix, exec_prefix, libdir, includedir, datadir" OFF)
@@ -70,6 +71,17 @@ elseif (IS_DIRECTORY ${CMAKE_SOURCE_DIR}/.bzr)
set(IS_BZR_REPO 0)
endif (IS_DIRECTORY ${CMAKE_SOURCE_DIR}/.bzr)
+set (USE_GLES ${BUILD_GLES})
+
+if (USE_GLES)
+ find_package(OpenGLES2)
+
+ if (NOT OPENGLES2_FOUND)
+ set (USE_GLES 0)
+ message (SEND_ERROR "OpenGLESv2 not found")
+ endif (NOT OPENGLES2_FOUND)
+endif (USE_GLES)
+
function (compiz_ensure_linkage)
find_program (LDCONFIG_EXECUTABLE ldconfig)
mark_as_advanced (FORCE LDCONFIG_EXECUTABLE)
diff --git a/cmake/CompizPlugin.cmake b/cmake/CompizPlugin.cmake
index 55fb73f..2579599 100644
--- a/cmake/CompizPlugin.cmake
+++ b/cmake/CompizPlugin.cmake
@@ -304,6 +304,16 @@ function (_build_compiz_plugin plugin)
NO_DEFAULT_PATH
)
+ set (COMPIZ_CURRENT_PLUGIN ${plugin})
+ set (COMPIZ_CURRENT_XML_FILE ${_translated_xml})
+
+ # find extension files
+ file (GLOB _extension_files "${COMPIZ_CMAKE_MODULE_PATH}/plugin_extensions/*.cmake")
+
+ foreach (_file ${_extension_files})
+ include (${_file})
+ endforeach ()
+
# generate pkgconfig file and install it and the plugin header file
if (_${plugin}_pkg AND EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/include/${plugin})
if ("${PLUGIN_BUILDTYPE}" STREQUAL "local")
@@ -316,11 +326,15 @@ function (_build_compiz_plugin plugin)
set (VERSION 0.0.1-git)
endif (NOT VERSION)
+ #add CFLAGSADD so pkg-config file has correct flags
+ set (COMPIZ_CFLAGS ${COMPIZ_CFLAGS} ${${_PLUGIN}_CFLAGSADD})
+
compiz_configure_file (
${_${plugin}_pkg}
${CMAKE_BINARY_DIR}/generated/compiz-${plugin}.pc
COMPIZ_REQUIRES
COMPIZ_CFLAGS
+ PKGCONFIG_LIBS
)
install (
@@ -334,16 +348,6 @@ function (_build_compiz_plugin plugin)
endif ()
endif ()
- set (COMPIZ_CURRENT_PLUGIN ${plugin})
- set (COMPIZ_CURRENT_XML_FILE ${_translated_xml})
-
- # find extension files
- file (GLOB _extension_files "${COMPIZ_CMAKE_MODULE_PATH}/plugin_extensions/*.cmake")
-
- foreach (_file ${_extension_files})
- include (${_file})
- endforeach ()
-
# find files for build
file (GLOB _h_files "${CMAKE_CURRENT_SOURCE_DIR}/src/*.h")
file (GLOB _h_ins_files "${CMAKE_CURRENT_SOURCE_DIR}/include/${plugin}/*.h")
diff --git a/cmake/FindOpenGLES2.cmake b/cmake/FindOpenGLES2.cmake
new file mode 100644
index 0000000..e8f7904
--- /dev/null
+++ b/cmake/FindOpenGLES2.cmake
@@ -0,0 +1,51 @@
+# - Try to find OpenGLES
+# Once done this will define
+#
+# OPENGLES2_FOUND - system has OpenGLES
+# OPENGLES2_INCLUDE_DIR - the GLES include directory
+# OPENGLES2_LIBRARY - the GLES library
+# OPENGLES2_LIBRARIES - Link this to use OpenGLES
+#
+
+FIND_PATH(OPENGLES2_INCLUDE_DIR GLES2/gl2.h
+ /usr/openwin/share/include
+ /opt/graphics/OpenGL/include /usr/X11R6/include
+ /usr/include
+)
+
+FIND_LIBRARY(OPENGLES2_LIBRARY
+ NAMES GLESv2
+ PATHS /opt/graphics/OpenGL/lib
+ /usr/openwin/lib
+ /usr/shlib /usr/X11R6/lib
+ /usr/lib
+)
+
+FIND_LIBRARY(OPENGLES2_EGL_LIBRARY
+ NAMES EGL
+ PATHS /usr/shlib /usr/X11R6/lib
+ /usr/lib
+)
+
+# On Unix OpenGL most certainly always requires X11.
+# Feel free to tighten up these conditions if you don't
+# think this is always true.
+# It's not true on OSX.
+
+IF (OPENGLES2_LIBRARY)
+ IF(NOT X11_FOUND)
+ INCLUDE(FindX11)
+ ENDIF(NOT X11_FOUND)
+ IF (X11_FOUND)
+ IF (NOT APPLE)
+ SET (OPENGLES2_LIBRARIES ${X11_LIBRARIES})
+ ENDIF (NOT APPLE)
+ ENDIF (X11_FOUND)
+ENDIF(OPENGLES2_LIBRARY)
+
+SET( OPENGLES2_FOUND "NO" )
+IF(OPENGLES2_LIBRARY AND OPENGLES2_EGL_LIBRARY)
+ SET( OPENGLES2_LIBRARIES ${OPENGLES2_LIBRARY} ${OPENGLES2_EGL_LIBRARY} ${OPENGLES2_LIBRARIES})
+ SET( OPENGLES2_FOUND "YES" )
+ENDIF(OPENGLES2_LIBRARY AND OPENGLES2_EGL_LIBRARY)
+
diff --git a/cmake/base.cmake b/cmake/base.cmake
index cdb34d8..9783ac4 100644
--- a/cmake/base.cmake
+++ b/cmake/base.cmake
@@ -24,6 +24,7 @@ function (_print_configure_results)
compiz_print_configure_header ("Compiz")
compiz_color_message ("\n${_escape}[4mOptional features:${_escape}[0m\n")
+ compiz_print_result_message ("GLESv2" USE_GLES)
compiz_print_result_message ("gtk window decorator" USE_GTK)
compiz_print_result_message ("metacity theme support" USE_METACITY)
compiz_print_result_message ("gconf schemas" USE_GCONF)
@@ -46,7 +47,8 @@ function (_check_compiz_cmake_macro)
endif ()
add_custom_target (findcompiz_install
${CMAKE_COMMAND} -E make_directory ${COMPIZ_DESTDIR}${CMAKE_ROOT}/Modules &&
- ${CMAKE_COMMAND} -E copy ${CMAKE_SOURCE_DIR}/cmake/FindCompiz.cmake ${COMPIZ_DESTDIR}${CMAKE_ROOT}/Modules
+ ${CMAKE_COMMAND} -E copy ${CMAKE_SOURCE_DIR}/cmake/FindCompiz.cmake ${COMPIZ_DESTDIR}${CMAKE_ROOT}/Modules &&
+ ${CMAKE_COMMAND} -E copy ${CMAKE_SOURCE_DIR}/cmake/FindOpenGLES2.cmake ${COMPIZ_DESTDIR}${CMAKE_ROOT}/Modules
)
endfunction ()
diff --git a/cmake/plugin_extensions/CompizOpenGLFixups.cmake b/cmake/plugin_extensions/CompizOpenGLFixups.cmake
new file mode 100644
index 0000000..053ff15
--- /dev/null
+++ b/cmake/plugin_extensions/CompizOpenGLFixups.cmake
@@ -0,0 +1,22 @@
+
+# modify pkg-config libs for opengl based on if we found GLES or not
+if (${COMPIZ_CURRENT_PLUGIN} STREQUAL "opengl")
+ if (USE_GLES)
+ set (PKGCONFIG_LIBS "-lGLESv2 -lEGL")
+ else (USE_GLES)
+ set (PKGCONFIG_LIBS "-lGL")
+ endif (USE_GLES)
+endif (${COMPIZ_CURRENT_PLUGIN} STREQUAL "opengl")
+
+# if plugin is using opengl plugin check for GLES library and set correct define
+if (NOT "${${_PLUGIN}_PLUGINDEPS}" STREQUAL "")
+ string (REGEX MATCH "opengl" opengl_found ${${_PLUGIN}_PLUGINDEPS})
+
+ if (opengl_found STREQUAL "opengl")
+ if (USE_GLES)
+ set (${_PLUGIN}_CFLAGSADD ${${_PLUGIN}_CFLAGSADD} " -DUSE_GLES")
+ string (REPLACE ";" " " ${_PLUGIN}_CFLAGSADD ${${_PLUGIN}_CFLAGSADD})
+ endif (USE_GLES)
+ endif (opengl_found STREQUAL "opengl")
+endif (NOT "${${_PLUGIN}_PLUGINDEPS}" STREQUAL "")
+
diff --git a/include/core/rect.h b/include/core/rect.h
index f58107d..590a48e 100644
--- a/include/core/rect.h
+++ b/include/core/rect.h
@@ -26,6 +26,8 @@
#ifndef _COMPRECT_H
#define _COMPRECT_H
+#include <core/point.h>
+
/**
* A 2D rectangle, which is likely in screen space. It's data is
* isolated and can only be mutated with set() methods.
diff --git a/plugins/annotate/src/annotate.cpp b/plugins/annotate/src/annotate.cpp
index 16949b0..9e9bde5 100644
--- a/plugins/annotate/src/annotate.cpp
+++ b/plugins/annotate/src/annotate.cpp
@@ -627,11 +627,14 @@ AnnoScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
if (status)
{
+ GLVertexBuffer *streamingBuffer = GLVertexBuffer::streamingBuffer ();
+ GLfloat vertexData[18];
+ GLfloat textureData[8];
CompRect rect;
GLMatrix sTransform = transform;
int numRect;
int pos = 0;
- float vectorX, vectorY, offset;
+ float offset;
int angle;
offset = optionGetStrokeWidth () / 2;
@@ -639,12 +642,6 @@ AnnoScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
/* This replaced prepareXCoords (s, output, -DEFAULT_Z_CAMERA) */
sTransform.toScreenSpace (output, -DEFAULT_Z_CAMERA);
- glPushMatrix ();
- glLoadMatrixf (sTransform.getMatrix ());
-
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
- glEnable (GL_BLEND);
-
if (content && !region.isEmpty ())
{
foreach (GLTexture *tex, texture)
@@ -654,34 +651,48 @@ AnnoScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
tex->enable (GLTexture::Fast);
- glBegin (GL_QUADS);
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
while (numRect--)
{
- glTexCoord2f (
- COMP_TEX_COORD_X (tex->matrix (), rect.at (pos).x1 ()),
- COMP_TEX_COORD_Y (tex->matrix (), rect.at (pos).y2 ()));
- glVertex2i (rect.at (pos).x1 (), rect.at (pos).y2 ());
-
- glTexCoord2f (
- COMP_TEX_COORD_X (tex->matrix (), rect.at (pos).x2 ()),
- COMP_TEX_COORD_Y (tex->matrix (), rect.at (pos).y2 ()));
- glVertex2i (rect.at (pos).x2 (), rect.at (pos).y2 ());
-
- glTexCoord2f (
- COMP_TEX_COORD_X (tex->matrix (), rect.at (pos).x2 ()),
- COMP_TEX_COORD_Y (tex->matrix (), rect.at (pos).y1 ()));
- glVertex2i (rect.at (pos).x2 (), rect.at (pos).y1 ());
-
- glTexCoord2f (
- COMP_TEX_COORD_X (tex->matrix (), rect.at (pos).x1 ()),
- COMP_TEX_COORD_Y (tex->matrix (), rect.at (pos).y1 ()));
- glVertex2i (rect.at (pos).x1 (), rect.at (pos).y1 ());
-
+ vertexData[0] = rect.at (pos).x1 ();
+ vertexData[1] = rect.at (pos).y1 ();
+ vertexData[2] = 0.0f;
+ vertexData[3] = rect.at (pos).x1 ();
+ vertexData[4] = rect.at (pos).y2 ();
+ vertexData[5] = 0.0f;
+ vertexData[6] = rect.at (pos).x2 ();
+ vertexData[7] = rect.at (pos).y1 ();
+ vertexData[8] = 0.0f;
+ vertexData[9] = rect.at (pos).x2 ();
+ vertexData[10] = rect.at (pos).y2 ();
+ vertexData[11] = 0.0f;
+
+ textureData[0] = COMP_TEX_COORD_X (tex->matrix (),
+ rect.at (pos).x1 ());
+ textureData[1] = COMP_TEX_COORD_Y (tex->matrix (),
+ rect.at (pos).y1 ());
+ textureData[2] = COMP_TEX_COORD_X (tex->matrix (),
+ rect.at (pos).x1 ());
+ textureData[3] = COMP_TEX_COORD_Y (tex->matrix (),
+ rect.at (pos).y2 ());
+ textureData[4] = COMP_TEX_COORD_X (tex->matrix (),
+ rect.at (pos).x2 ());
+ textureData[5] = COMP_TEX_COORD_Y (tex->matrix (),
+ rect.at (pos).y1 ());
+ textureData[6] = COMP_TEX_COORD_X (tex->matrix (),
+ rect.at (pos).x2 ());
+ textureData[7] = COMP_TEX_COORD_Y (tex->matrix (),
+ rect.at (pos).y2 ());
+
+ streamingBuffer->addVertices (4, vertexData);
+ streamingBuffer->addTexCoords (0, 4, textureData);
pos++;
}
- glEnd ();
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
+
tex->disable ();
}
}
@@ -689,85 +700,130 @@ AnnoScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
switch (drawMode)
{
case LineMode:
- glColor4usv (optionGetStrokeColor ());
glLineWidth (optionGetStrokeWidth ());
- glBegin (GL_LINES);
- glVertex2i (initialPointerX, initialPointerY);
- glVertex2i (lineVector.x (), lineVector.y ());
- glEnd ();
+
+ streamingBuffer->begin (GL_LINES);
+
+ streamingBuffer->addColors (1, optionGetStrokeColor ());
+
+ vertexData[0] = initialPointerX;
+ vertexData[1] = initialPointerY;
+ vertexData[2] = 0.0f;
+ vertexData[3] = lineVector.x ();
+ vertexData[4] = lineVector.y ();
+ vertexData[5] = 0.0f;
+ streamingBuffer->addVertices (2, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
break;
case RectangleMode:
+ vertexData[0] = rectangle.x1 ();
+ vertexData[1] = rectangle.y1 ();
+ vertexData[2] = 0.0f;
+ vertexData[3] = rectangle.x1 ();
+ vertexData[4] = rectangle.y2 ();
+ vertexData[5] = 0.0f;
+ vertexData[6] = rectangle.x2 ();
+ vertexData[7] = rectangle.y1 ();
+ vertexData[8] = 0.0f;
+ vertexData[9] = rectangle.x2 ();
+ vertexData[10] = rectangle.y2 ();
+ vertexData[11] = 0.0f;
+
/* fill rectangle */
- glColor4usv (optionGetFillColor ());
- glRecti (rectangle.x1 (), rectangle.y2 (),
- rectangle.x2 (), rectangle.y1 ());
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
+ streamingBuffer->addColors (1, optionGetFillColor ());
+ streamingBuffer->addVertices (4, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
/* draw rectangle outline */
- glColor4usv (optionGetStrokeColor ());
- glRecti (rectangle.x1 () - offset, rectangle.y2 (),
- rectangle.x1 () + offset, rectangle.y1 ());
+/* streamingBuffer->begin ();
+
+ streamingBuffer->addColors (1, optionGetStrokeColor ());
+
+ vertexData[0] = rectangle.x1 () - offset;
+ vertexData[3] = rectangle.x1 () - offset;
+ streamingBuffer->addVertices (4, vertexData);
+
glRecti (rectangle.x2 () - offset, rectangle.y2 (),
rectangle.x2 () + offset, rectangle.y1 ());
glRecti (rectangle.x1 () - offset, rectangle.y1 () + offset,
rectangle.x2 () + offset, rectangle.y1 () - offset);
glRecti (rectangle.x1 () - offset, rectangle.y2 () + offset,
- rectangle.x2 () + offset, rectangle.y2 () - offset);
+ rectangle.x2 () + offset, rectangle.y2 () - offset);*/
break;
case EllipseMode:
/* fill ellipse */
- glColor4usv (optionGetFillColor ());
+ streamingBuffer->begin (GL_TRIANGLE_FAN);
+
+ streamingBuffer->addColors (1, optionGetFillColor ());
+
+ vertexData[0] = ellipse.center.x ();
+ vertexData[1] = ellipse.center.y ();
+ vertexData[2] = 0.0f;
+ streamingBuffer->addVertices (1, vertexData);
- glBegin (GL_TRIANGLE_FAN);
- glVertex2d (ellipse.center.x (), ellipse.center.y ());
for (angle = 0; angle <= 360; angle += 1)
{
- vectorX = ellipse.center.x () +
- (ellipse.radiusX * sinf (angle * DEG2RAD));
- vectorY = ellipse.center.y () +
- (ellipse.radiusY * cosf (angle * DEG2RAD));
- glVertex2d (vectorX, vectorY);
+ vertexData[0] = ellipse.center.x () +
+ (ellipse.radiusX * sinf (angle * DEG2RAD));
+ vertexData[1] = ellipse.center.y () +
+ (ellipse.radiusY * cosf (angle * DEG2RAD));
+ streamingBuffer->addVertices (1, vertexData);
}
- glVertex2d (ellipse.center.x (), ellipse.center.y () +
- ellipse.radiusY);
- glEnd();
+
+ vertexData[0] = ellipse.center.x ();
+ vertexData[1] = ellipse.center.y () + ellipse.radiusY;
+ streamingBuffer->addVertices (1, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
/* draw ellipse outline */
- glColor4usv (optionGetStrokeColor ());
glLineWidth (optionGetStrokeWidth ());
- glBegin (GL_TRIANGLE_STRIP);
- glVertex2d (ellipse.center.x (), ellipse.center.y () +
- ellipse.radiusY - offset);
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
+ streamingBuffer->addColors (1, optionGetStrokeColor ());
+
+
+ vertexData[0] = ellipse.center.x ();
+ vertexData[1] = ellipse.center.y () + ellipse.radiusY - offset;
+ vertexData[2] = 0.0f;
+ streamingBuffer->addVertices (1, vertexData);
+
for (angle = 360; angle >= 0; angle -= 1)
{
- vectorX = ellipse.center.x () + ((ellipse.radiusX -
- offset) * sinf (angle * DEG2RAD));
- vectorY = ellipse.center.y () + ((ellipse.radiusY -
- offset) * cosf (angle * DEG2RAD));
- glVertex2d (vectorX, vectorY);
- vectorX = ellipse.center.x () + ((ellipse.radiusX +
- offset) * sinf (angle * DEG2RAD));
- vectorY = ellipse.center.y () + ((ellipse.radiusY +
- offset) * cosf (angle * DEG2RAD));
- glVertex2d (vectorX, vectorY);
+ vertexData[0] = ellipse.center.x () + ((ellipse.radiusX -
+ offset) * sinf (angle * DEG2RAD));
+ vertexData[1] = ellipse.center.y () + ((ellipse.radiusY -
+ offset) * cosf (angle * DEG2RAD));
+ vertexData[2] = 0.0f;
+ vertexData[3] = ellipse.center.x () + ((ellipse.radiusX +
+ offset) * sinf (angle * DEG2RAD));
+ vertexData[4] = ellipse.center.y () + ((ellipse.radiusY +
+ offset) * cosf (angle * DEG2RAD));
+ vertexData[5] = 0.0f;
+ streamingBuffer->addVertices (2, vertexData);
}
- glVertex2d (ellipse.center.x (), ellipse.center.y () +
- ellipse.radiusY + offset);
- glEnd();
+
+ vertexData[0] = ellipse.center.x ();
+ vertexData[1] = ellipse.center.y () + ellipse.radiusY + offset;
+ streamingBuffer->addVertices (1, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
break;
default:
break;
}
-
- /* clean up */
- glColor4usv (defaultColor);
- glDisable (GL_BLEND);
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
-
- glPopMatrix ();
}
return status;
diff --git a/plugins/blur/CMakeLists.txt b/plugins/blur/CMakeLists.txt
index 55bb230..5529441 100644
--- a/plugins/blur/CMakeLists.txt
+++ b/plugins/blur/CMakeLists.txt
@@ -2,15 +2,15 @@ find_package (Compiz REQUIRED)
include (CompizPlugin)
-find_package (OpenGL)
+#find_package (OpenGL)
-if (OPENGL_GLU_FOUND)
- compiz_plugin(blur PLUGINDEPS composite opengl LIBRARIES decoration ${OPENGL_glu_LIBRARY} INCDIRS ${OPENGL_INCLUDE_DIR})
+#if (OPENGL_GLU_FOUND)
+# compiz_plugin(blur PLUGINDEPS composite opengl LIBRARIES decoration ${OPENGL_glu_LIBRARY} INCDIRS ${OPENGL_INCLUDE_DIR})
- if (COMPIZ_BUILD_WITH_RPATH AND NOT COMPIZ_DISABLE_PLUGIN_BLUR)
- set_target_properties (
- blur PROPERTIES
- INSTALL_RPATH "${COMPIZ_LIBDIR}"
- )
- endif (COMPIZ_BUILD_WITH_RPATH AND NOT COMPIZ_DISABLE_PLUGIN_BLUR)
-endif ()
+# if (COMPIZ_BUILD_WITH_RPATH AND NOT COMPIZ_DISABLE_PLUGIN_BLUR)
+# set_target_properties (
+# blur PROPERTIES
+# INSTALL_RPATH "${COMPIZ_LIBDIR}"
+# )
+# endif (COMPIZ_BUILD_WITH_RPATH AND NOT COMPIZ_DISABLE_PLUGIN_BLUR)
+#endif ()
diff --git a/plugins/clone/src/clone.cpp b/plugins/clone/src/clone.cpp
index ac3413d..6ea2fb7 100644
--- a/plugins/clone/src/clone.cpp
+++ b/plugins/clone/src/clone.cpp
@@ -295,9 +295,6 @@ CloneScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
0.0f);
sTransform.scale (zoomX, zoomY, 1.0f);
- glPushMatrix ();
- glLoadMatrixf (sTransform.getMatrix ());
-
filter = gScreen->textureFilter ();
if (offset == 0.0f)
@@ -325,8 +322,6 @@ CloneScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
}
gScreen->setTextureFilter (filter);
-
- glPopMatrix ();
}
return status;
diff --git a/plugins/compiztoolbox/src/compiztoolbox.cpp b/plugins/compiztoolbox/src/compiztoolbox.cpp
index 69fa3b5..17b581e 100644
--- a/plugins/compiztoolbox/src/compiztoolbox.cpp
+++ b/plugins/compiztoolbox/src/compiztoolbox.cpp
@@ -459,9 +459,7 @@ BaseSwitchWindow::paintThumb (const GLWindowPaintAttrib &attrib,
sAttrib.yTranslate = wy - g.y () +
window->border ().top * sAttrib.yScale;
- GLFragment::Attrib fragment (sAttrib);
-
- if (window->alpha () || fragment.getOpacity () != OPAQUE)
+ if (window->alpha () || sAttrib.opacity != OPAQUE)
mask |= PAINT_WINDOW_TRANSLUCENT_MASK;
wTransform.translate (g.x (), g.y (), 0.0f);
@@ -470,9 +468,6 @@ BaseSwitchWindow::paintThumb (const GLWindowPaintAttrib &attrib,
sAttrib.yTranslate / sAttrib.yScale - g.y (),
0.0f);
- glPushMatrix ();
- glLoadMatrixf (wTransform.getMatrix ());
-
filter = gScreen->textureFilter ();
if (baseScreen->getMipmap ())
@@ -482,13 +477,11 @@ BaseSwitchWindow::paintThumb (const GLWindowPaintAttrib &attrib,
very ugly but necessary until the vertex stage has been made
fully pluggable. */
gWindow->glAddGeometrySetCurrentIndex (MAXSHORT);
- gWindow->glDraw (wTransform, fragment, infiniteRegion, mask);
+ gWindow->glDraw (wTransform, sAttrib, infiniteRegion, mask);
gWindow->glAddGeometrySetCurrentIndex (addWindowGeometryIndex);
gScreen->setTextureFilter (filter);
- glPopMatrix ();
-
if (iconMode != HideIcon)
{
icon = gWindow->getIcon (MAX_ICON_SIZE, MAX_ICON_SIZE);
@@ -529,30 +522,23 @@ BaseSwitchWindow::paintThumb (const GLWindowPaintAttrib &attrib,
sAttrib.xTranslate = wx - g.x ();
sAttrib.yTranslate = wy - g.y ();
- gWindow->geometry ().reset ();
+ gWindow->vertexBuffer ()->begin ();
gWindow->glAddGeometrySetCurrentIndex (MAXSHORT);
gWindow->glAddGeometry (matrix, iconReg, infiniteRegion);
gWindow->glAddGeometrySetCurrentIndex (addWindowGeometryIndex);
- if (gWindow->geometry ().vCount)
- {
- GLFragment::Attrib fragment (sAttrib);
- GLMatrix wTransform (transform);
-
- wTransform.translate (g.x (), g.y (), 0.0f);
- wTransform.scale (sAttrib.xScale, sAttrib.yScale, 1.0f);
- wTransform.translate (sAttrib.xTranslate / sAttrib.xScale - g.x (),
- sAttrib.yTranslate / sAttrib.yScale - g.y (),
- 0.0f);
+ gWindow->vertexBuffer ()->end ();
- glPushMatrix ();
- glLoadMatrixf (wTransform.getMatrix ());
+ GLMatrix wTransform (transform);
- gWindow->glDrawTexture (icon, fragment, mask);
+ wTransform.translate (g.x (), g.y (), 0.0f);
+ wTransform.scale (sAttrib.xScale, sAttrib.yScale, 1.0f);
+ wTransform.translate (sAttrib.xTranslate / sAttrib.xScale - g.x (),
+ sAttrib.yTranslate / sAttrib.yScale - g.y (),
+ 0.0f);
- glPopMatrix ();
- }
+ gWindow->glDrawTexture (icon, wTransform, sAttrib, mask);
}
}
diff --git a/plugins/copytex/src/copytex.cpp b/plugins/copytex/src/copytex.cpp
index 2cad1dc..97a5d69 100644
--- a/plugins/copytex/src/copytex.cpp
+++ b/plugins/copytex/src/copytex.cpp
@@ -112,6 +112,14 @@ CopyTexture::CopyTexture (CopyPixmap::Ptr cp, CompRect dim) :
GLenum target;
GLTexture::Matrix matrix = _identity_matrix;
+#ifdef USE_GLES
+ target = GL_TEXTURE_2D;
+ matrix.xx = 1.0f / dim.width ();
+ matrix.yy = 1.0f / dim.height ();
+ matrix.x0 = -dim.x () * matrix.xx;
+ matrix.y0 = -dim.y () * matrix.yy;
+#else
+
if (GL::textureNonPowerOfTwo ||
(POWER_OF_TWO (dim.width ()) && POWER_OF_TWO (dim.height ())))
{
@@ -129,6 +137,7 @@ CopyTexture::CopyTexture (CopyPixmap::Ptr cp, CompRect dim) :
matrix.x0 = -dim.x ();
matrix.y0 = -dim.y ();
}
+#endif
setData (target, matrix, false);
setGeometry (dim.x1 (), dim.y1 (), dim.x2 () - dim.x1 (), dim.y2 () - dim.y1 ());
diff --git a/plugins/cube/CMakeLists.txt b/plugins/cube/CMakeLists.txt
index 4d09af3..a3994c0 100644
--- a/plugins/cube/CMakeLists.txt
+++ b/plugins/cube/CMakeLists.txt
@@ -2,4 +2,4 @@ find_package (Compiz REQUIRED)
include (CompizPlugin)
-compiz_plugin(cube PLUGINDEPS composite opengl) \ No newline at end of file
+#compiz_plugin(cube PLUGINDEPS composite opengl)
diff --git a/plugins/cube/src/cube.cpp b/plugins/cube/src/cube.cpp
index 0751388..66e6d81 100644
--- a/plugins/cube/src/cube.cpp
+++ b/plugins/cube/src/cube.cpp
@@ -1123,7 +1123,6 @@ CubeScreen::cubePaintTop (const GLScreenPaintAttrib &sAttrib,
if ((priv->mDesktopOpacity != OPAQUE) || (color[3] != OPAQUE))
{
priv->gScreen->setTexEnvMode (GL_MODULATE);
- glEnable (GL_BLEND);
glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
}
@@ -1149,7 +1148,6 @@ CubeScreen::cubePaintTop (const GLScreenPaintAttrib &sAttrib,
glEnableClientState (GL_TEXTURE_COORD_ARRAY);
priv->gScreen->setTexEnvMode (GL_REPLACE);
- glDisable (GL_BLEND);
glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
}
@@ -1190,7 +1188,6 @@ CubeScreen::cubePaintBottom (const GLScreenPaintAttrib &sAttrib,
if ((priv->mDesktopOpacity != OPAQUE) || (color[3] != OPAQUE))
{
priv->gScreen->setTexEnvMode (GL_MODULATE);
- glEnable (GL_BLEND);
glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
}
@@ -1206,7 +1203,6 @@ CubeScreen::cubePaintBottom (const GLScreenPaintAttrib &sAttrib,
glEnableClientState (GL_TEXTURE_COORD_ARRAY);
priv->gScreen->setTexEnvMode (GL_REPLACE);
- glDisable (GL_BLEND);
glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
}
diff --git a/plugins/decor/src/decor.cpp b/plugins/decor/src/decor.cpp
index ae9a858..1f96c9d 100644
--- a/plugins/decor/src/decor.cpp
+++ b/plugins/decor/src/decor.cpp
@@ -236,10 +236,10 @@ DecorWindow::computeShadowRegion ()
*/
bool
-DecorWindow::glDraw (const GLMatrix &transform,
- GLFragment::Attrib &attrib,
- const CompRegion &region,
- unsigned int mask)
+DecorWindow::glDraw (const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ const CompRegion &region,
+ unsigned int mask)
{
bool status;
@@ -255,7 +255,7 @@ DecorWindow::glDraw (const GLMatrix &transform,
GLTexture::MatrixList ml (1);
mask |= PAINT_WINDOW_BLEND_MASK;
- gWindow->geometry ().reset ();
+ gWindow->vertexBuffer ()->begin ();
for (int i = 0; i < wd->nQuad; i++)
{
@@ -271,9 +271,10 @@ DecorWindow::glDraw (const GLMatrix &transform,
}
}
- if (gWindow->geometry ().vCount)
- gWindow->glDrawTexture (wd->decor->texture->textures[0],
- attrib, mask);
+ gWindow->vertexBuffer ()->end ();
+
+ gWindow->glDrawTexture (wd->decor->texture->textures[0], transform,
+ attrib, mask);
}
else if (wd && !reg.isEmpty () &&
wd->decor->type == WINDOW_DECORATION_TYPE_WINDOW)
@@ -288,11 +289,12 @@ DecorWindow::glDraw (const GLMatrix &transform,
if (gWindow->textures ().size () == 1)
{
ml[0] = gWindow->matrices ()[0];
- gWindow->geometry ().reset ();
+ gWindow->vertexBuffer ()->begin ();
gWindow->glAddGeometry (ml, window->frameRegion (), reg);
+ gWindow->vertexBuffer ()->end ();
- if (gWindow->geometry ().vCount)
- gWindow->glDrawTexture (gWindow->textures ()[0], attrib, mask);
+ gWindow->glDrawTexture (gWindow->textures ()[0], transform,
+ attrib, mask);
}
else
{
@@ -301,12 +303,12 @@ DecorWindow::glDraw (const GLMatrix &transform,
for (unsigned int i = 0; i < gWindow->textures ().size (); i++)
{
ml[0] = gWindow->matrices ()[i];
- gWindow->geometry ().reset ();
+ gWindow->vertexBuffer ()->begin ();
gWindow->glAddGeometry (ml, regions[i], reg);
+ gWindow->vertexBuffer ()->end ();
- if (gWindow->geometry ().vCount)
- gWindow->glDrawTexture (gWindow->textures ()[i], attrib,
- mask);
+ gWindow->glDrawTexture (gWindow->textures ()[i], transform,
+ attrib, mask);
}
}
}
diff --git a/plugins/decor/src/decor.h b/plugins/decor/src/decor.h
index c15c198..353dc58 100644
--- a/plugins/decor/src/decor.h
+++ b/plugins/decor/src/decor.h
@@ -203,7 +203,7 @@ class DecorWindow :
void computeShadowRegion ();
- bool glDraw (const GLMatrix &, GLFragment::Attrib &,
+ bool glDraw (const GLMatrix &, const GLWindowPaintAttrib &,
const CompRegion &, unsigned int);
void windowNotify (CompWindowNotify n);
diff --git a/plugins/imgsvg/src/imgsvg.cpp b/plugins/imgsvg/src/imgsvg.cpp
index 626d9e2..055e63b 100644
--- a/plugins/imgsvg/src/imgsvg.cpp
+++ b/plugins/imgsvg/src/imgsvg.cpp
@@ -218,12 +218,12 @@ SvgWindow::~SvgWindow ()
}
bool
-SvgWindow::glDraw (const GLMatrix &transform,
- GLFragment::Attrib &fragment,
- const CompRegion &region,
- unsigned int mask)
+SvgWindow::glDraw (const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ const CompRegion &region,
+ unsigned int mask)
{
- bool status = gWindow->glDraw (transform, fragment, region, mask);
+ bool status = gWindow->glDraw (transform, attrib, region, mask);
if (!status)
return status;
@@ -249,13 +249,15 @@ SvgWindow::glDraw (const GLMatrix &transform,
{
matrix[0] = context->texture[0].matrices[i];
- gWindow->geometry ().reset ();
+ gWindow->vertexBuffer ()->begin ();
gWindow->glAddGeometry (matrix, context->box, reg);
+ gWindow->vertexBuffer ()->end ();
if (mask & PAINT_WINDOW_TRANSLUCENT_MASK)
mask |= PAINT_WINDOW_BLEND_MASK;
- gWindow->glDrawTexture (context->texture[0].textures[i], fragment, mask);
+ gWindow->glDrawTexture (context->texture[0].textures[i], transform,
+ attrib, mask);
if (rect.width () > 0 && rect.height () > 0)
{
@@ -319,11 +321,12 @@ SvgWindow::glDraw (const GLMatrix &transform,
saveFilter = gScreen->filter (SCREEN_TRANS_FILTER);
gScreen->setFilter (SCREEN_TRANS_FILTER, GLTexture::Good);
- gWindow->geometry ().reset ();
+ gWindow->vertexBuffer ()->begin ();
gWindow->glAddGeometry (matrix, r, reg);
+ gWindow->vertexBuffer ()->end ();
gWindow->glDrawTexture (context->texture[1].textures[j],
- fragment, mask);
+ transform, attrib, mask);
gScreen->setFilter (SCREEN_TRANS_FILTER, saveFilter);
}
diff --git a/plugins/imgsvg/src/imgsvg.h b/plugins/imgsvg/src/imgsvg.h
index 6986cf0..21f0535 100644
--- a/plugins/imgsvg/src/imgsvg.h
+++ b/plugins/imgsvg/src/imgsvg.h
@@ -76,7 +76,8 @@ class SvgWindow :
SvgWindow (CompWindow *window);
~SvgWindow ();
- bool glDraw (const GLMatrix &transform, GLFragment::Attrib &fragment,
+ bool glDraw (const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
const CompRegion &region, unsigned int mask);
void moveNotify (int dx, int dy, bool immediate);
void resizeNotify (int dx, int dy, int dwidth, int dheight);
diff --git a/plugins/obs/src/obs.cpp b/plugins/obs/src/obs.cpp
index e7f0af5..82d8565 100644
--- a/plugins/obs/src/obs.cpp
+++ b/plugins/obs/src/obs.cpp
@@ -151,29 +151,30 @@ ObsWindow::glPaint (const GLWindowPaintAttrib& attrib,
we wrap into glDrawWindow here */
bool
-ObsWindow::glDraw (const GLMatrix& transform,
- GLFragment::Attrib& attrib,
- const CompRegion& region,
- unsigned int mask)
+ObsWindow::glDraw (const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ const CompRegion &region,
+ unsigned int mask)
{
+ GLWindowPaintAttrib wAttrib (attrib);
int factor;
factor = customFactor[MODIFIER_OPACITY];
if (factor != 100)
{
- attrib.setOpacity (factor * attrib.getOpacity () / 100);
+ wAttrib.opacity = factor * wAttrib.opacity / 100;
mask |= PAINT_WINDOW_TRANSLUCENT_MASK;
}
factor = customFactor[MODIFIER_BRIGHTNESS];
if (factor != 100)
- attrib.setBrightness (factor * attrib.getBrightness () / 100);
+ wAttrib.brightness = factor * wAttrib.brightness / 100;
factor = customFactor[MODIFIER_SATURATION];
if (factor != 100)
- attrib.setSaturation (factor * attrib.getSaturation () / 100);
+ wAttrib.saturation = factor * wAttrib.saturation / 100;
- return gWindow->glDraw (transform, attrib, region, mask);
+ return gWindow->glDraw (transform, wAttrib, region, mask);
}
void
diff --git a/plugins/obs/src/obs.h b/plugins/obs/src/obs.h
index d288ddf..a82ab5d 100644
--- a/plugins/obs/src/obs.h
+++ b/plugins/obs/src/obs.h
@@ -66,7 +66,7 @@ class ObsWindow :
bool glPaint (const GLWindowPaintAttrib &, const GLMatrix &,
const CompRegion &, unsigned int);
- bool glDraw (const GLMatrix &, GLFragment::Attrib &,
+ bool glDraw (const GLMatrix &, const GLWindowPaintAttrib &,
const CompRegion &, unsigned int);
void changePaintModifier (unsigned int, int);
diff --git a/plugins/opengl/CMakeLists.txt b/plugins/opengl/CMakeLists.txt
index 5cb799c..e1f7495 100644
--- a/plugins/opengl/CMakeLists.txt
+++ b/plugins/opengl/CMakeLists.txt
@@ -2,7 +2,12 @@ find_package (Compiz REQUIRED)
include (CompizPlugin)
-find_package (OpenGL)
-if (OPENGL_FOUND)
- compiz_plugin(opengl PLUGINDEPS composite LIBRARIES ${OPENGL_gl_LIBRARY} INCDIRS ${OPENGL_INCLUDE_DIR})
-endif () \ No newline at end of file
+if (USE_GLES)
+ compiz_plugin(opengl PLUGINDEPS composite CFLAGSADD -DUSE_GLES LIBRARIES ${OPENGLES2_LIBRARIES} INCDIRS ${OPENGLES2_INCLUDE_DIR})
+else (USE_GLES)
+ find_package (OpenGL)
+ if (OPENGL_FOUND)
+ compiz_plugin(opengl PLUGINDEPS composite LIBRARIES ${OPENGL_gl_LIBRARY} INCDIRS ${OPENGL_INCLUDE_DIR})
+ endif (OPENGL_FOUND)
+endif (USE_GLES)
+
diff --git a/plugins/opengl/compiz-opengl.pc.in b/plugins/opengl/compiz-opengl.pc.in
index 12c55c7..a4912a0 100644
--- a/plugins/opengl/compiz-opengl.pc.in
+++ b/plugins/opengl/compiz-opengl.pc.in
@@ -8,5 +8,5 @@ Description: Opengl compositing plugin for compiz
Version: @VERSION@
Requires: compiz compiz-composite
-Libs: -lGL -L${libdir} -lopengl
-Cflags: @COMPIZ_CFLAGS@ -I${includedir}/compiz \ No newline at end of file
+Libs: @PKGCONFIG_LIBS@ -L${libdir} -lopengl
+Cflags: @COMPIZ_CFLAGS@ -I${includedir}/compiz
diff --git a/plugins/opengl/include/opengl/fragment.h b/plugins/opengl/include/opengl/fragment.h
deleted file mode 100644
index 253bd07..0000000
--- a/plugins/opengl/include/opengl/fragment.h
+++ /dev/null
@@ -1,124 +0,0 @@
-/*
- * Copyright © 2008 Dennis Kasprzyk
- * Copyright © 2007 Novell, Inc.
- *
- * Permission to use, copy, modify, distribute, and sell this software
- * and its documentation for any purpose is hereby granted without
- * fee, provided that the above copyright notice appear in all copies
- * and that both that copyright notice and this permission notice
- * appear in supporting documentation, and that the name of
- * Dennis Kasprzyk not be used in advertising or publicity pertaining to
- * distribution of the software without specific, written prior permission.
- * Dennis Kasprzyk makes no representations about the suitability of this
- * software for any purpose. It is provided "as is" without express or
- * implied warranty.
- *
- * DENNIS KASPRZYK DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
- * NO EVENT SHALL DENNIS KASPRZYK BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
- * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
- * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
- * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
- *
- * Authors: Dennis Kasprzyk <onestone@compiz-fusion.org>
- * David Reveman <davidr@novell.com>
- */
-
-#ifndef _GLFRAGMENT_H
-#define _GLFRAGMENT_H
-
-#define MAX_FRAGMENT_FUNCTIONS 16
-
-#define COMP_FETCH_TARGET_2D 0
-#define COMP_FETCH_TARGET_RECT 1
-#define COMP_FETCH_TARGET_NUM 2
-
-struct GLWindowPaintAttrib;
-class GLScreen;
-
-/**
- * Describes a texture modification fragment program
- * for a texture
- */
-namespace GLFragment {
-
- class Storage;
-
- typedef unsigned int FunctionId;
-
- class PrivateFunctionData;
- class PrivateAttrib;
-
- class FunctionData {
- public:
- FunctionData ();
- ~FunctionData ();
-
- /**
- * Returns the status of this fragment program
- * (valid or invalid)
- */
- bool status ();
-
- void addTempHeaderOp (const char *name);
-
- void addParamHeaderOp (const char *name);
-
- void addAttribHeaderOp (const char *name);
-
-
- void addFetchOp (const char *dst, const char *offset, int target);
-
- void addColorOp (const char *dst, const char *src);
-
- void addDataOp (const char *str, ...);
-
- void addBlendOp (const char *str, ...);
-
- FunctionId createFragmentFunction (const char *name);
-
- private:
- PrivateFunctionData *priv;
- };
-
- class Attrib {
- public:
- Attrib (const GLWindowPaintAttrib &paint);
- Attrib (const Attrib&);
- ~Attrib ();
-
- Attrib &operator= (const Attrib &rhs);
-
- unsigned int allocTextureUnits (unsigned int nTexture);
-
- unsigned int allocParameters (unsigned int nParam);
-
- void addFunction (FunctionId function);
-
- bool enable (bool *blending);
- void disable ();
-
- unsigned short getSaturation ();
- unsigned short getBrightness ();
- unsigned short getOpacity ();
-
- void setSaturation (unsigned short);
- void setBrightness (unsigned short);
- void setOpacity (unsigned short);
-
- bool hasFunctions ();
-
- private:
- PrivateAttrib *priv;
- };
-
- void destroyFragmentFunction (FunctionId id);
-
- FunctionId getSaturateFragmentFunction (GLTexture *texture,
- int param);
-};
-
-
-
-#endif
diff --git a/plugins/opengl/include/opengl/matrix.h b/plugins/opengl/include/opengl/matrix.h
index fabb60c..fa13b7f 100644
--- a/plugins/opengl/include/opengl/matrix.h
+++ b/plugins/opengl/include/opengl/matrix.h
@@ -44,6 +44,8 @@ class GLMatrix {
void reset ();
void toScreenSpace (const CompOutput *output, float z);
+ bool invert ();
+
void rotate (const float angle, const float x,
const float y, const float z);
void rotate (const float angle, const GLVector& vector);
diff --git a/plugins/opengl/include/opengl/opengl.h b/plugins/opengl/include/opengl/opengl.h
index a9c74ef..0bc6f94 100644
--- a/plugins/opengl/include/opengl/opengl.h
+++ b/plugins/opengl/include/opengl/opengl.h
@@ -28,17 +28,35 @@
#ifndef _COMPIZ_OPENGL_H
#define _COMPIZ_OPENGL_H
+#ifdef USE_GLES
+#define SUPPORT_X11
+#include <GLES2/gl2.h>
+#include <GLES2/gl2ext.h>
+#include <EGL/egl.h>
+#include <EGL/eglext.h>
+#else
#include <GL/gl.h>
#include <GL/glx.h>
+#endif
#include <opengl/matrix.h>
#include <opengl/texture.h>
-#include <opengl/fragment.h>
+#include <opengl/vertexbuffer.h>
+#include <opengl/program.h>
+#include <opengl/programcache.h>
#define COMPIZ_OPENGL_ABI 3
#include <core/pluginclasshandler.h>
+#if !defined(GL_BGRA)
+ #if !defined(GL_BGRA_EXT)
+ #error GL_BGRA support is required
+ #else
+ #define GL_BGRA GL_BGRA_EXT
+ #endif
+#endif
+
/**
* camera distance from screen, 0.5 * tan (FOV)
*/
@@ -75,8 +93,21 @@ extern GLushort defaultColor[4];
#endif
namespace GL {
-
+ #ifdef USE_GLES
+ typedef EGLImageKHR (*EGLCreateImageKHRProc) (EGLDisplay dpy,
+ EGLContext ctx,
+ EGLenum target,
+ EGLClientBuffer buffer,
+ const EGLint *attrib_list);
+ typedef EGLBoolean (*EGLDestroyImageKHRProc) (EGLDisplay dpy,
+ EGLImageKHR image);
+
+ typedef void (*GLEGLImageTargetTexture2DOESProc) (GLenum target,
+ GLeglImageOES image);
+
+ #else
typedef void (*FuncPtr) (void);
+
typedef FuncPtr (*GLXGetProcAddressProc) (const GLubyte *procName);
typedef void (*GLXBindTexImageProc) (Display *display,
@@ -121,10 +152,6 @@ namespace GL {
typedef void (*GLXDestroyPixmapProc) (Display *display,
GLXPixmap pixmap);
- typedef void (*GLActiveTextureProc) (GLenum texture);
- typedef void (*GLClientActiveTextureProc) (GLenum texture);
- typedef void (*GLMultiTexCoord2fProc) (GLenum, GLfloat, GLfloat);
-
typedef void (*GLGenProgramsProc) (GLsizei n,
GLuint *programs);
typedef void (*GLDeleteProgramsProc) (GLsizei n,
@@ -144,11 +171,16 @@ namespace GL {
typedef void (*GLGetProgramivProc) (GLenum target,
GLenum pname,
int *params);
+ #endif
+
+ typedef void (*GLActiveTextureProc) (GLenum texture);
+ typedef void (*GLClientActiveTextureProc) (GLenum texture);
+ typedef void (*GLMultiTexCoord2fProc) (GLenum, GLfloat, GLfloat);
typedef void (*GLGenFramebuffersProc) (GLsizei n,
GLuint *framebuffers);
typedef void (*GLDeleteFramebuffersProc) (GLsizei n,
- GLuint *framebuffers);
+ const GLuint *framebuffers);
typedef void (*GLBindFramebufferProc) (GLenum target,
GLuint framebuffer);
typedef GLenum (*GLCheckFramebufferStatusProc) (GLenum target);
@@ -159,6 +191,28 @@ namespace GL {
GLint level);
typedef void (*GLGenerateMipmapProc) (GLenum target);
+ typedef void (*GLBindBufferProc) (GLenum target,
+ GLuint buffer);
+ typedef void (*GLDeleteBuffersProc) (GLsizei n,
+ const GLuint *buffers);
+ typedef void (*GLGenBuffersProc) (GLsizei n,
+ GLuint *buffers);
+ typedef void (*GLBufferDataProc) (GLenum target,
+ GLsizeiptr size,
+ const GLvoid *data,
+ GLenum usage);
+ typedef void (*GLBufferSubDataProc) (GLenum target,
+ GLintptr offset,
+ GLsizeiptr size,
+ const GLvoid *data);
+
+ #ifdef USE_GLES
+ extern EGLCreateImageKHRProc createImage;
+ extern EGLDestroyImageKHRProc destroyImage;
+
+ extern GLEGLImageTargetTexture2DOESProc eglImageTargetTexture;
+
+ #else
extern GLXBindTexImageProc bindTexImage;
extern GLXReleaseTexImageProc releaseTexImage;
extern GLXQueryDrawableProc queryDrawable;
@@ -170,10 +224,6 @@ namespace GL {
extern GLXCreatePixmapProc createPixmap;
extern GLXDestroyPixmapProc destroyPixmap;
- extern GLActiveTextureProc activeTexture;
- extern GLClientActiveTextureProc clientActiveTexture;
- extern GLMultiTexCoord2fProc multiTexCoord2f;
-
extern GLGenProgramsProc genPrograms;
extern GLDeleteProgramsProc deletePrograms;
extern GLBindProgramProc bindProgram;
@@ -181,6 +231,11 @@ namespace GL {
extern GLProgramParameter4fProc programEnvParameter4f;
extern GLProgramParameter4fProc programLocalParameter4f;
extern GLGetProgramivProc getProgramiv;
+ #endif
+
+ extern GLActiveTextureProc activeTexture;
+ extern GLClientActiveTextureProc clientActiveTexture;
+ extern GLMultiTexCoord2fProc multiTexCoord2f;
extern GLGenFramebuffersProc genFramebuffers;
extern GLDeleteFramebuffersProc deleteFramebuffers;
@@ -189,6 +244,12 @@ namespace GL {
extern GLFramebufferTexture2DProc framebufferTexture2D;
extern GLGenerateMipmapProc generateMipmap;
+ extern GLBindBufferProc bindBuffer;
+ extern GLDeleteBuffersProc deleteBuffers;
+ extern GLGenBuffersProc genBuffers;
+ extern GLBufferDataProc bufferData;
+ extern GLBufferSubDataProc bufferSubData;
+
extern bool textureFromPixmap;
extern bool textureRectangle;
extern bool textureNonPowerOfTwo;
@@ -198,6 +259,7 @@ namespace GL {
extern bool textureCompression;
extern GLint maxTextureSize;
extern bool fbo;
+ extern bool vbo;
extern bool fragmentProgram;
extern GLint maxTextureUnits;
@@ -217,6 +279,7 @@ struct GLScreenPaintAttrib {
#define MAX_DEPTH 32
+#ifndef USE_GLES
struct GLFBConfig {
GLXFBConfig fbConfig;
int yInverted;
@@ -224,6 +287,14 @@ struct GLFBConfig {
int textureFormat;
int textureTargets;
};
+#endif
+
+struct GLShaderData
+{
+ std::string name;
+ std::string vertex_shader;
+ std::string fragment_shader;
+};
#define NOTHING_TRANS_FILTER 0
#define SCREEN_TRANS_FILTER 1
@@ -299,6 +370,8 @@ class GLScreenInterface :
CompOutput *);
virtual void glDisableOutputClipping ();
+ virtual GLMatrix *projectionMatrix ();
+
};
@@ -329,7 +402,9 @@ class GLScreen :
/**
* Gets the libGL address of a particular openGL functor
*/
+ #ifndef USE_GLES
GL::FuncPtr getProcAddress (const char *name);
+ #endif
void updateBackground ();
@@ -343,8 +418,6 @@ class GLScreen :
*/
void setFilter (int, GLTexture::Filter);
- GLFragment::Storage * fragmentStorage ();
-
/**
* Sets a new compiz-wid openGL texture environment mode
*/
@@ -368,7 +441,19 @@ class GLScreen :
GLTexture::BindPixmapHandle registerBindPixmap (GLTexture::BindPixmapProc);
void unregisterBindPixmap (GLTexture::BindPixmapHandle);
+ #ifndef USE_GLES
GLFBConfig * glxPixmapFBConfig (unsigned int depth);
+ #endif
+
+
+ #ifdef USE_GLES
+ EGLContext getEGLContext ();
+ #endif
+
+ /**
+ * Returns a GLProgram from the cache or creates one and caches it
+ */
+ GLProgram *getProgram (std::list<GLShaderData*>);
/**
* Returns a default icon texture
@@ -377,12 +462,6 @@ class GLScreen :
void resetRasterPos ();
- /**
- * Returns a 4x4 const float array which
- * represents the current projection matrix
- */
- const float * projectionMatrix ();
-
WRAPABLE_HND (0, GLScreenInterface, bool, glPaintOutput,
const GLScreenPaintAttrib &, const GLMatrix &,
const CompRegion &, CompOutput *, unsigned int);
@@ -397,6 +476,8 @@ class GLScreen :
const GLMatrix &, const CompRegion &, CompOutput *);
WRAPABLE_HND (4, GLScreenInterface, void, glDisableOutputClipping);
+ WRAPABLE_HND (5, GLScreenInterface, GLMatrix *, projectionMatrix);
+
friend class GLTexture;
private:
@@ -448,10 +529,10 @@ class GLWindowInterface :
* @param region Describes which region will be drawn
* @param mask Bitmask which describes how this window is drawn
*/
- virtual bool glDraw (const GLMatrix &matrix,
- GLFragment::Attrib &attrib,
- const CompRegion &region,
- unsigned int mask);
+ virtual bool glDraw (const GLMatrix &matrix,
+ const GLWindowPaintAttrib &attrib,
+ const CompRegion &region,
+ unsigned int mask);
/**
* Hookable function to add points to a window
@@ -474,9 +555,8 @@ class GLWindowInterface :
const CompRegion &clipRegion,
unsigned int min = MAXSHORT,
unsigned int max = MAXSHORT);
- virtual void glDrawTexture (GLTexture *texture, GLFragment::Attrib &,
- unsigned int);
- virtual void glDrawGeometry ();
+ virtual void glDrawTexture (GLTexture *texture, const GLMatrix &,
+ const GLWindowPaintAttrib &, unsigned int);
};
class GLWindow :
@@ -485,40 +565,8 @@ class GLWindow :
{
public:
- /**
- * Class which describes the texture geometry and transformation points
- * of a window
- */
- class Geometry {
- public:
- Geometry ();
- ~Geometry ();
-
- void reset ();
-
- /**
- * Set the number of vertices in the texture geometry
- */
- bool moreVertices (int newSize);
-
- /**
- * Set the number of indices in the texture geometry
- */
- bool moreIndices (int newSize);
-
- public:
- GLfloat *vertices;
- int vertexSize;
- int vertexStride;
- GLushort *indices;
- int indexSize;
- int vCount;
- int texUnits;
- int texCoordSize;
- int indexCount;
- };
-
static GLWindowPaintAttrib defaultPaintAttrib;
+
public:
GLWindow (CompWindow *w);
@@ -561,9 +609,20 @@ class GLWindow :
void updatePaintAttribs ();
/**
- * Returns the window texture geometry
+ * Returns the window vertex buffer object
+ */
+ GLVertexBuffer * vertexBuffer ();
+
+ /**
+ * Add a vertex and/or fragment shader function to the pipeline.
+ *
+ * @param name Name of the plugin adding the functions
+ * @param vertex_shader Function to add to the vertex shader
+ * @param fragment_shader Function to add to the fragment shader
*/
- Geometry & geometry ();
+ void addShaders (std::string name,
+ std::string vertex_shader,
+ std::string fragment_shader);
GLTexture *getIcon (int width, int height);
@@ -571,14 +630,15 @@ class GLWindow :
const GLWindowPaintAttrib &, const GLMatrix &,
const CompRegion &, unsigned int);
WRAPABLE_HND (1, GLWindowInterface, bool, glDraw, const GLMatrix &,
- GLFragment::Attrib &, const CompRegion &, unsigned int);
+ const GLWindowPaintAttrib &, const CompRegion &,
+ unsigned int);
WRAPABLE_HND (2, GLWindowInterface, void, glAddGeometry,
const GLTexture::MatrixList &, const CompRegion &,
const CompRegion &,
unsigned int = MAXSHORT, unsigned int = MAXSHORT);
WRAPABLE_HND (3, GLWindowInterface, void, glDrawTexture,
- GLTexture *texture, GLFragment::Attrib &, unsigned int);
- WRAPABLE_HND (4, GLWindowInterface, void, glDrawGeometry);
+ GLTexture *texture, const GLMatrix &,
+ const GLWindowPaintAttrib &, unsigned int);
friend class GLScreen;
friend class PrivateGLScreen;
@@ -588,3 +648,4 @@ class GLWindow :
};
#endif
+
diff --git a/plugins/opengl/include/opengl/program.h b/plugins/opengl/include/opengl/program.h
new file mode 100644
index 0000000..f7ac571
--- /dev/null
+++ b/plugins/opengl/include/opengl/program.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#ifndef _COMPIZ_GLPROGRAM_H
+#define _COMPIZ_GLPROGRAM_H
+
+#ifdef USE_GLES
+#include <GLES2/gl2.h>
+#else
+#include <GL/gl.h>
+#endif
+
+#include <core/core.h>
+#include <opengl/matrix.h>
+
+class PrivateProgram;
+
+class GLProgram
+{
+ public:
+ GLProgram (CompString &vertexShader, CompString &fragmentShader);
+ ~GLProgram ();
+
+ bool valid ();
+ void bind ();
+ void unbind ();
+
+ bool setUniform (const char *name, GLfloat value);
+ bool setUniform (const char *name, GLint value);
+ bool setUniform (const char *name, const GLMatrix &value);
+ bool setUniform2f (const char *name, GLfloat x, GLfloat y);
+ bool setUniform3f (const char *name, GLfloat x, GLfloat y, GLfloat z);
+ bool setUniform4f (const char *name,
+ GLfloat x,
+ GLfloat y,
+ GLfloat z,
+ GLfloat w);
+
+ GLuint attributeLocation (const char *name);
+
+ private:
+ PrivateProgram *priv;
+};
+
+#endif // _COMPIZ_GLPROGRAM_H
+
diff --git a/plugins/opengl/include/opengl/programcache.h b/plugins/opengl/include/opengl/programcache.h
new file mode 100644
index 0000000..c2784f1
--- /dev/null
+++ b/plugins/opengl/include/opengl/programcache.h
@@ -0,0 +1,51 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#ifndef _COMPIZ_GLPROGRAMCACHE_H
+#define _COMPIZ_GLPROGRAMCACHE_H
+
+#include <string>
+#include <list>
+#include <map>
+#include <boost/bind.hpp>
+#include <opengl/program.h>
+
+class PrivateProgramCache;
+struct GLShaderData;
+
+class GLProgramCache
+{
+ private:
+ PrivateProgramCache *priv;
+
+ public:
+ GLProgramCache (size_t);
+ ~GLProgramCache ();
+
+ GLProgram* operator () (std::list<GLShaderData*>);
+};
+
+#endif // _COMPIZ_GLPROGRAMCACHE_H
+
diff --git a/plugins/opengl/include/opengl/texture.h b/plugins/opengl/include/opengl/texture.h
index 2023402..33ea8b8 100644
--- a/plugins/opengl/include/opengl/texture.h
+++ b/plugins/opengl/include/opengl/texture.h
@@ -30,7 +30,11 @@
#include <X11/Xlib-xcb.h>
+#ifdef USE_GLES
+#include <GLES2/gl2.h>
+#else
#include <GL/gl.h>
+#endif
#include <vector>
diff --git a/plugins/opengl/include/opengl/vertexbuffer.h b/plugins/opengl/include/opengl/vertexbuffer.h
new file mode 100644
index 0000000..f819685
--- /dev/null
+++ b/plugins/opengl/include/opengl/vertexbuffer.h
@@ -0,0 +1,83 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#ifndef _COMPIZ_GLVERTEXBUFFER_H
+#define _COMPIZ_GLVERTEXBUFFER_H
+
+#ifdef USE_GLES
+#include <GLES2/gl2.h>
+#else
+#include <GL/gl.h>
+#endif
+
+#include <core/core.h>
+#include <opengl/program.h>
+
+class PrivateVertexBuffer;
+struct GLWindowPaintAttrib;
+
+class GLVertexBuffer
+{
+ public:
+ GLVertexBuffer ();
+ GLVertexBuffer (GLenum usage);
+ ~GLVertexBuffer ();
+
+ static GLVertexBuffer *streamingBuffer ();
+
+ void begin (GLenum primitiveType);
+ // default primitiveType is GL_TRIANGLE_STRIP
+ void begin ();
+ int end ();
+
+ // vertices and normals are 3 parts, count is number of xyz groups
+ void addVertices (GLuint nVertices, GLfloat *vertices);
+ void addNormals (GLuint nNormals, GLfloat *normals);
+
+ // color is always RGBA (4 parts), count is number of rgba groups
+ void addColors (GLuint nColors, GLushort *colors);
+
+ // texture is index, texcoords are 2 parts, count is number of pairs
+ void addTexCoords (GLuint texture,
+ GLuint nTexcoords,
+ GLfloat *texcoords);
+
+ void setProgram (GLProgram *program);
+
+ int render (const GLMatrix &modelview);
+
+ int render (const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib);
+
+ int render (const GLMatrix &projection,
+ const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib);
+
+ private:
+ PrivateVertexBuffer *priv;
+};
+
+#endif // _COMPIZ_GLVERTEXBUFFER_H
+
diff --git a/plugins/opengl/opengl.xml.in b/plugins/opengl/opengl.xml.in
index 143297f..9b82453 100644
--- a/plugins/opengl/opengl.xml.in
+++ b/plugins/opengl/opengl.xml.in
@@ -36,7 +36,7 @@
<option name="sync_to_vblank" type="bool">
<_short>Sync To VBlank</_short>
<_long>Only perform screen updates during vertical blanking period</_long>
- <default>true</default>
+ <default>false</default>
</option>
<option name="texture_compression" type="bool">
<_short>Texture Compression</_short>
diff --git a/plugins/opengl/src/fragment.cpp b/plugins/opengl/src/fragment.cpp
deleted file mode 100644
index fb6c506..0000000
--- a/plugins/opengl/src/fragment.cpp
+++ /dev/null
@@ -1,1145 +0,0 @@
-/*
- * Copyright © 2007 Novell, Inc.
- *
- * Permission to use, copy, modify, distribute, and sell this software
- * and its documentation for any purpose is hereby granted without
- * fee, provided that the above copyright notice appear in all copies
- * and that both that copyright notice and this permission notice
- * appear in supporting documentation, and that the name of
- * Novell, Inc. not be used in advertising or publicity pertaining to
- * distribution of the software without specific, written prior permission.
- * Novell, Inc. makes no representations about the suitability of this
- * software for any purpose. It is provided "as is" without express or
- * implied warranty.
- *
- * NOVELL, INC. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
- * NO EVENT SHALL NOVELL, INC. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
- * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
- * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
- * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
- *
- * Author: David Reveman <davidr@novell.com>
- */
-
-#include <boost/function.hpp>
-#include <boost/bind.hpp>
-#include <boost/foreach.hpp>
-#define foreach BOOST_FOREACH
-
-#include <core/core.h>
-#include <opengl/texture.h>
-#include <opengl/fragment.h>
-#include "privatefragment.h"
-#include "privates.h"
-
-#include <string.h>
-#include <stdlib.h>
-#include <stdarg.h>
-
-#define COMP_FUNCTION_TYPE_ARB 0
-#define COMP_FUNCTION_TYPE_NUM 1
-
-#define COMP_FUNCTION_ARB_MASK (1 << 0)
-#define COMP_FUNCTION_MASK (COMP_FUNCTION_ARB_MASK)
-
-namespace GLFragment {
-
- class Program {
- public:
- Program () :
- signature (0),
- blending (false),
- name (0),
- type (GL_FRAGMENT_PROGRAM_ARB)
- {};
- ~Program ()
- {
- if (name)
- (*GL::deletePrograms) (1, &name);
- };
-
- public:
- std::vector<FunctionId> signature;
-
- bool blending;
-
- GLuint name;
- GLenum type;
- };
-
- typedef enum {
- OpTypeData,
- OpTypeDataStore,
- OpTypeDataOffset,
- OpTypeDataBlend,
- OpTypeHeaderTemp,
- OpTypeHeaderParam,
- OpTypeHeaderAttrib,
- OpTypeColor,
- OpTypeFetch,
- OpTypeLoad
- } OpType;
-
- class HeaderOp {
- public:
- HeaderOp () : type (OpTypeHeaderTemp), name ("") {};
- public:
- OpType type;
- CompString name;
- };
-
- class BodyOp {
- public:
- BodyOp () :
- type (OpTypeData),
- data (""),
- dst (""),
- src (""),
- target (0)
- {
- foreach (CompString &str, noOffset)
- str = "";
- foreach (CompString &str, offset)
- str = "";
- };
-
- public:
- OpType type;
- CompString data;
- CompString dst;
- CompString src;
- unsigned int target;
- CompString noOffset[COMP_FETCH_TARGET_NUM];
- CompString offset[COMP_FETCH_TARGET_NUM];
-
- };
-
- class PrivateFunctionData {
- public:
- PrivateFunctionData () : header (0), body (0), status (true) {};
- PrivateFunctionData (const PrivateFunctionData&, CompString);
-
- public:
- std::vector<HeaderOp> header;
- std::vector<BodyOp> body;
- bool status;
- };
-
- class Function {
- public:
- Function ():
- id (0),
- name (""),
- mask (0)
- {};
-
- public:
- FunctionId id;
- CompString name;
- PrivateFunctionData data[COMP_FUNCTION_TYPE_NUM];
- unsigned int mask;
- };
-
- class PrivateAttrib {
- public:
- PrivateAttrib () :
- opacity (0xffff),
- brightness (0xffff),
- saturation (0xffff),
- nTexture (0),
- nFunction (0),
- nParam (0)
- {}
-
- PrivateAttrib (const PrivateAttrib &pa) :
- opacity (pa.opacity),
- brightness (pa.brightness),
- saturation (pa.saturation),
- nTexture (pa.nTexture),
- nFunction (pa.nFunction),
- nParam (pa.nParam)
- {
- for (int i = 0; i < MAX_FRAGMENT_FUNCTIONS; i++)
- function[i] = pa.function[i];
- }
-
- public:
- GLushort opacity;
- GLushort brightness;
- GLushort saturation;
- int nTexture;
- FunctionId function[MAX_FRAGMENT_FUNCTIONS];
- int nFunction;
- int nParam;
- };
-
- typedef boost::function<void (BodyOp *, int)> DataOpCallBack;
-
- class InitialLoadFunction : public Function {
- public:
- InitialLoadFunction ()
- {
- id = 0;
- name = "__core_load";
- mask = COMP_FUNCTION_MASK;
-
- BodyOp b;
- b.type = OpTypeLoad;
- b.noOffset[0] = "TEX output, fragment.texcoord[0], texture[0], 2D;";
- b.noOffset[1] = "TEX output, fragment.texcoord[0], texture[0], RECT;";
- b.offset[0] = "TEX output, __tmp_texcoord0, texture[0], 2D;";
- b.offset[1] = "TEX output, __tmp_texcoord0, texture[0], RECT;";
- data[0].body.push_back (b);
- };
- };
-
- static InitialLoadFunction initialLoadFunction;
-
- static Function *
- findFragmentFunction (GLScreen *s,
- FunctionId id)
- {
- foreach (Function *f, s->fragmentStorage ()->functions)
- if (f->id == id)
- return f;
- return NULL;
- }
-
- static Function *
- findFragmentFunctionWithName (GLScreen *s,
- CompString name)
- {
- foreach (Function *f, s->fragmentStorage ()->functions)
- if (f->name.compare (name) == 0)
- return f;
- return NULL;
- }
-
- static Program *
- findFragmentProgram (GLScreen *s,
- FunctionId *signature,
- unsigned int nSignature)
- {
- unsigned int i;
-
- foreach (Program *p, s->fragmentStorage ()->programs)
- {
- if (p->signature.size () != nSignature)
- continue;
-
- for (i = 0; i < nSignature; i++)
- if (signature[i] != p->signature[i])
- break;
-
- if (i == nSignature)
- return p;
- }
- return NULL;
- }
-
- static unsigned int
- functionMaskToType (int mask)
- {
- static struct {
- unsigned int type;
- unsigned int mask;
- } maskToType[] = {
- { COMP_FUNCTION_TYPE_ARB, COMP_FUNCTION_ARB_MASK }
- };
-
- unsigned int i;
-
- for (i = 0; i < sizeof (maskToType) / sizeof (maskToType[0]); i++)
- if (mask & maskToType[i].mask)
- return maskToType[i].type;
-
- return 0;
- }
-
- static void
- forEachDataOpInFunction (std::vector<Function *> list,
- int index,
- int type,
- int loadTarget,
- CompString loadOffset,
- bool *color,
- bool *blend,
- DataOpCallBack callBack)
- {
- Function *f = list[index];
- BodyOp dataOp;
- bool colorDone = false;
- bool blendDone = false;
-
- *color = false;
- *blend = false;
-
- foreach (BodyOp &bodyOp, f->data[type].body)
- {
- switch (bodyOp.type) {
- case OpTypeFetch: {
- CompString offset = loadOffset;
-
- /* add offset */
- if (bodyOp.data.size ())
- {
- if (loadOffset.size ())
- {
- dataOp.type = OpTypeDataOffset;
- dataOp.data =
- compPrintf ("ADD __tmp_texcoord%d, %s, %s;",
- index, loadOffset.c_str (),
- bodyOp.data.c_str ());
-
- callBack (&dataOp, index);
-
- offset = compPrintf ("__tmp_texcoord%d", index);
- }
- else
- {
- offset = bodyOp.data;
- }
- }
-
- forEachDataOpInFunction (list, index - 1, type,
- bodyOp.target,
- offset, &colorDone, &blendDone,
- callBack);
-
- if (bodyOp.dst.compare ("output"))
- {
- dataOp.type = OpTypeDataStore;
- dataOp.data =
- compPrintf ("MOV %s, output;", bodyOp.dst.c_str ());
-
- /* move to destination */
- callBack (&dataOp, index);
- }
- } break;
- case OpTypeLoad:
- if (loadOffset.size ())
- {
- dataOp.type = OpTypeDataOffset;
- dataOp.data =
- compPrintf ("ADD __tmp_texcoord0, fragment.texcoord[0], %s;",
- loadOffset.c_str ());
-
- callBack (&dataOp, index);
-
- dataOp.data = bodyOp.offset[loadTarget];
- }
- else
- {
- dataOp.data = bodyOp.noOffset[loadTarget];
- }
-
- dataOp.type = OpTypeData;
-
- callBack (&dataOp, index);
-
- break;
- case OpTypeColor:
- if (!colorDone)
- {
- dataOp.type = OpTypeData;
- dataOp.data =
- compPrintf ("MUL %s, fragment.color, %s;",
- bodyOp.dst.c_str (),
- bodyOp.src.c_str ());
-
- callBack (&dataOp, index);
- }
- else if (bodyOp.dst.compare (bodyOp.src))
- {
- dataOp.type = OpTypeData;
- dataOp.data =
- compPrintf ("MOV %s, %s;",
- bodyOp.dst.c_str (),
- bodyOp.src.c_str ());
-
- callBack (&dataOp, index);
- }
- *color = true;
- break;
- case OpTypeDataBlend:
- *blend = true;
- /* fall-through */
- case OpTypeData:
- callBack (&bodyOp, index);
- break;
- case OpTypeDataStore:
- case OpTypeDataOffset:
- case OpTypeHeaderTemp:
- case OpTypeHeaderParam:
- case OpTypeHeaderAttrib:
- break;
- }
- }
-
- if (colorDone)
- *color = true;
-
- if (blendDone)
- *blend = true;
- }
-
- static int
- forEachHeaderOpWithType (std::vector<HeaderOp> list,
- int index,
- OpType type,
- CompString prefix,
- CompString functionPrefix,
- int count,
- DataOpCallBack callBack)
- {
- BodyOp dataOp;
-
- dataOp.type = OpTypeData;
-
- foreach (HeaderOp &header, list)
- {
- if (header.type == type)
- {
- if (count)
- {
- dataOp.data = ", ";
- }
- else
- {
- dataOp.data = prefix;
- }
-
- dataOp.data += functionPrefix;
- dataOp.data += "_";
- dataOp.data += header.name;
-
- callBack (&dataOp, index);
-
- count++;
- }
- }
-
- return count;
- }
-
- static bool
- forEachDataOp (std::vector<Function *> list,
- int type,
- DataOpCallBack callBack)
- {
- BodyOp dataOp;
- bool colorDone;
- bool blendDone;
- int count, nList = list.size ();
-
- dataOp.type = OpTypeData;
-
- count = 1;
-
- dataOp.data = "TEMP output";
-
- callBack (&dataOp, nList);
-
- foreach (Function *f, list)
- count = forEachHeaderOpWithType (f->data[type].header,
- nList, OpTypeHeaderTemp,
- "", f->name, count, callBack);
-
- dataOp.data = ";";
-
- callBack (&dataOp, nList);
-
- count = 0;
-
- foreach (Function *f, list)
- count = forEachHeaderOpWithType (f->data[type].header,
- nList, OpTypeHeaderParam,
- "PARAM ", f->name, count,
- callBack);
-
- if (count)
- {
- dataOp.data = ";";
-
- callBack (&dataOp, nList);
- }
-
- count = 0;
-
- foreach (Function *f, list)
- count = forEachHeaderOpWithType (f->data[type].header,
- nList, OpTypeHeaderAttrib,
- "ATTRIB ", f->name, count,
- callBack);
-
- if (count)
- {
- dataOp.data = ";";
-
- callBack (&dataOp, nList);
- }
-
- forEachDataOpInFunction (list, nList - 1, type, 0, "",
- &colorDone, &blendDone,
- callBack);
-
- if (colorDone)
- dataOp.data = "MOV result.color, output;END";
- else
- dataOp.data = "MUL result.color, fragment.color, output;END";
-
- callBack (&dataOp, nList);
-
- return blendDone;
- }
-
- static void
- addFetchOffsetVariables (BodyOp *op,
- int index,
- bool *indices,
- CompString *data)
- {
- if (op->type == OpTypeDataOffset)
- {
- if (!indices[index])
- {
- data->append (compPrintf ("TEMP __tmp_texcoord%d;", index));
- indices[index] = true;
- }
- }
- }
-
- static void
- addData (BodyOp *op,
- CompString *data)
- {
- data->append (op->data);
- }
-
- static Program *
- buildFragmentProgram (GLScreen *s,
- PrivateAttrib *attrib)
- {
- Program *program;
- std::vector<Function *> functionList (1);
- int mask = COMP_FUNCTION_MASK;
- int type;
- GLint errorPos;
- GLenum errorType;
- CompString fetchData;
- bool indices[MAX_FRAGMENT_FUNCTIONS];
- int i;
-
- program = new Program ();
- if (!program)
- return NULL;
-
- functionList[0] = &initialLoadFunction;
-
- for (i = 0; i < attrib->nFunction; i++)
- {
- Function *f = findFragmentFunction (s, attrib->function[i]);
-
- if (f)
- functionList.push_back (f);
- }
-
- foreach (Function *f, functionList)
- mask &= f->mask;
-
- if (!mask)
- {
- compLogMessage ("opengl", CompLogLevelWarn,
- "fragment functions can't be linked together "
- "because a common type doesn't exist");
- }
-
- if (!mask || functionList.size () == 1)
- {
- delete program;
- return NULL;
- }
-
- for (i = 0; i < attrib->nFunction; i++)
- program->signature.push_back (attrib->function[i]);
-
- type = functionMaskToType (mask);
-
- fetchData = "!!ARBfp1.0";
-
- foreach (bool &val, indices)
- val = false;
-
- forEachDataOp (functionList, type,
- boost::bind (addFetchOffsetVariables, _1, _2, indices, &fetchData));
-
- program->blending = forEachDataOp (functionList, type,
- boost::bind (addData, _1, &fetchData));
-
- program->type = GL_FRAGMENT_PROGRAM_ARB;
-
- glGetError ();
-
- (*GL::genPrograms) (1, &program->name);
- (*GL::bindProgram) (GL_FRAGMENT_PROGRAM_ARB, program->name);
- (*GL::programString) (GL_FRAGMENT_PROGRAM_ARB,
- GL_PROGRAM_FORMAT_ASCII_ARB,
- fetchData.size (), fetchData.c_str ());
-
- glGetIntegerv (GL_PROGRAM_ERROR_POSITION_ARB, &errorPos);
- errorType = glGetError ();
- if (errorType != GL_NO_ERROR || errorPos != -1)
- {
- compLogMessage ("opengl", CompLogLevelError,
- "failed to load fragment program");
-
- (*GL::deletePrograms) (1, &program->name);
-
- program->name = 0;
- program->type = 0;
- }
-
- return program;
- }
-
- static GLuint
- getFragmentProgram (GLScreen *s,
- PrivateAttrib *attrib,
- GLenum *type,
- bool *blending)
- {
- Program *program;
-
- if (!attrib->nFunction)
- return 0;
-
- program = findFragmentProgram (s, attrib->function, attrib->nFunction);
- if (!program)
- {
- program = buildFragmentProgram (s, attrib);
- if (program)
- {
- s->fragmentStorage ()->programs.push_back (program);
- }
- }
-
- if (program)
- {
- *type = program->type;
- *blending = program->blending;
-
- return program->name;
- }
-
- return 0;
- }
-
-
- /* performs simple variable substitution */
- static CompString
- copyData (std::vector<HeaderOp> header,
- const CompString prefix,
- CompString data)
- {
- CompString inPrefix (prefix);
- inPrefix += "_";
-
- foreach (HeaderOp &h, header)
- {
- size_t pos = data.find (h.name);
- while (pos != std::string::npos)
- {
- bool prependPrefix = false;
- /* It is possible to match parts of words here, so
- * make sure that we have found the next chunk in the
- * string and not just a header which matches
- * part of another word */
- if (data.size () > pos + h.name.size ())
- {
- const CompString &token = data.substr (pos + h.name.size (), 1);
- if (token == "," ||
- token == "." ||
- token == ";")
- {
- prependPrefix = true;
- }
- else
- {
- /* We matched part of another word as our
- * token so search for the next whole
- * header op */
- pos = data.find (h.name, pos + 1);
- }
- }
- else
- {
- /* If this is the last word in the string, then it must
- * have matched exactly our header op, so it is ok
- * to prepend a prefix here and go straight to
- * std::string::npos */
- prependPrefix = true;
- }
-
- if (prependPrefix)
- {
- /* prepend the header op prefix to the header op
- * and seek past this word to the next instance
- * of the unprepended header op */
- data.insert (pos, inPrefix);
- pos += inPrefix.size () + h.name.size ();
- pos = data.find (h.name, pos);
- }
- }
- }
-
- return data;
- }
-
- PrivateFunctionData::PrivateFunctionData (const PrivateFunctionData& src,
- CompString dstPrefix) :
- header (src.header),
- body (0),
- status (src.status)
- {
-
- foreach (BodyOp b, src.body)
- {
- BodyOp dst;
- dst.type = b.type;
-
- switch (b.type) {
- case OpTypeFetch:
- dst.dst = copyData (header, dstPrefix, b.dst);
- if (b.data.size ())
- dst.data = copyData (header, dstPrefix, b.data);
- else
- dst.data = "";
-
- dst.target = b.target;
- break;
- case OpTypeLoad:
- case OpTypeHeaderTemp:
- case OpTypeHeaderParam:
- case OpTypeHeaderAttrib:
- break;
- case OpTypeData:
- case OpTypeDataBlend:
- case OpTypeDataStore:
- case OpTypeDataOffset:
- dst.data = copyData (header, dstPrefix, b.data);
- break;
- case OpTypeColor:
- dst.dst = copyData (header, dstPrefix, b.dst);
- dst.src = copyData (header, dstPrefix, b.src);
- break;
- }
- body.push_back (dst);
- }
- }
-
- static bool
- addHeaderOpToFunctionData (PrivateFunctionData *data,
- const char *name,
- OpType type)
- {
- static const char *reserved[] = {
- "output",
- "__tmp_texcoord",
- "fragment",
- "program",
- "result",
- "state",
- "texture"
- };
- HeaderOp header;
- CompString n (name);
-
- foreach (const char *word, reserved)
- {
- if (n.find (word) != std::string::npos)
- {
- compLogMessage ("opengl", CompLogLevelWarn,
- "%s is a reserved word", word);
- return false;
- }
- }
-
-
- header.type = type;
- header.name = n;
- data->header.push_back (header);
-
- return true;
- }
-
- FunctionData::FunctionData () :
- priv (new PrivateFunctionData ())
- {
- }
-
- FunctionData::~FunctionData ()
- {
- delete priv;
- }
-
- bool
- FunctionData::status ()
- {
- return priv->status;
- }
-
- void
- FunctionData::addTempHeaderOp (const char *name)
- {
- priv->status &=
- addHeaderOpToFunctionData (priv, name, OpTypeHeaderTemp);
- }
-
- void
- FunctionData::addParamHeaderOp (const char *name)
- {
- priv->status &=
- addHeaderOpToFunctionData (priv, name, OpTypeHeaderParam);
- }
-
- void
- FunctionData::addAttribHeaderOp (const char *name)
- {
- priv->status &=
- addHeaderOpToFunctionData (priv, name, OpTypeHeaderAttrib);
- }
-
-
- void
- FunctionData::addFetchOp (const char *dst, const char *offset, int target)
- {
- BodyOp b;
-
- b.type = OpTypeFetch;
- b.dst = CompString (dst);
- b.target = target;
-
- if (offset)
- b.data = CompString (offset);
- else
- b.data = CompString ("");
-
- priv->body.push_back (b);
- }
-
- void
- FunctionData::addColorOp (const char *dst, const char *src)
- {
- BodyOp b;
-
- b.type = OpTypeColor;
- b.dst = CompString (dst);
- b.src = CompString (src);
-
- priv->body.push_back (b);
- }
-
- void
- FunctionData::addDataOp (const char *str, ...)
- {
- BodyOp b;
- va_list ap;
-
- b.type = OpTypeData;
- va_start (ap, str);
- b.data = compPrintf (str, ap);
- va_end (ap);
-
- priv->body.push_back (b);
- }
-
- void
- FunctionData::addBlendOp (const char *str, ...)
- {
- BodyOp b;
- va_list ap;
-
- b.type = OpTypeDataBlend;
- va_start (ap, str);
- b.data = compPrintf (str, ap);
- va_end (ap);
-
- priv->body.push_back (b);
- }
-
- FunctionId
- FunctionData::createFragmentFunction (const char *name)
- {
- GLScreen *s = GLScreen::get (screen);
- Function *function = new Function ();
- CompString validName = name;
- unsigned int i = 0;
-
- while (findFragmentFunctionWithName (s, validName))
- {
- validName = compPrintf ("%s%d", name, i++);
- }
-
- function->data[COMP_FUNCTION_TYPE_ARB] =
- PrivateFunctionData (*priv, validName);
-
- function->name = validName;
- function->mask = COMP_FUNCTION_ARB_MASK;
- function->id = s->fragmentStorage ()->lastFunctionId++;
-
- s->fragmentStorage ()->functions.push_back (function);
-
- return function->id;
- }
-
- Attrib::Attrib (const GLWindowPaintAttrib &paint) :
- priv (new PrivateAttrib ())
- {
- priv->opacity = paint.opacity;
- priv->brightness = paint.brightness;
- priv->saturation = paint.saturation;
- priv->nTexture = 0;
- priv->nFunction = 0;
- priv->nParam = 0;
-
- foreach (FunctionId &f, priv->function)
- f = 0;
- }
-
- Attrib::Attrib (const Attrib &fa) :
- priv (new PrivateAttrib (*fa.priv))
- {
- }
-
- Attrib::~Attrib ()
- {
- delete priv;
- }
-
- Attrib &
- Attrib::operator= (const Attrib &rhs)
- {
- if (this == &rhs) // Check for self-assignment
- return *this;
-
- delete priv;
- priv = new PrivateAttrib (*rhs.priv);
-
- return *this;
- }
-
- unsigned int
- Attrib::allocTextureUnits (unsigned int nTexture)
- {
- unsigned int first = priv->nTexture;
-
- priv->nTexture += nTexture;
-
- /* 0 is reserved for source texture */
- return 1 + first;
- }
-
- unsigned int
- Attrib::allocParameters (unsigned int nParam)
- {
- unsigned int first = priv->nParam;
-
- priv->nParam += nParam;
-
- return first;
- }
-
- void
- Attrib::addFunction (FunctionId function)
- {
- if (priv->nFunction < MAX_FRAGMENT_FUNCTIONS)
- priv->function[priv->nFunction++] = function;
- }
-
- bool
- Attrib::enable (bool *blending)
- {
- GLuint name;
- GLenum type;
- bool programBlending;
-
- if (!GL::fragmentProgram)
- return false;
-
- name = getFragmentProgram (GLScreen::get (screen), priv, &type,
- &programBlending);
- if (!name)
- return false;
-
- *blending = !programBlending;
-
- glEnable (GL_FRAGMENT_PROGRAM_ARB);
-
- (*GL::bindProgram) (type, name);
-
- return true;
- }
-
- void
- Attrib::disable ()
- {
- glDisable (GL_FRAGMENT_PROGRAM_ARB);
- }
-
- unsigned short
- Attrib::getSaturation ()
- {
- return priv->saturation;
- }
-
- unsigned short
- Attrib::getBrightness ()
- {
- return priv->brightness;
- }
-
- unsigned short
- Attrib::getOpacity ()
- {
- return priv->opacity;
- }
-
- void
- Attrib::setSaturation (unsigned short value)
- {
- priv->saturation = value;
- }
-
- void
- Attrib::setBrightness (unsigned short value)
- {
- priv->brightness = value;
- }
-
-
- void
- Attrib::setOpacity (unsigned short value)
- {
- priv->opacity = value;
- }
-
- bool
- Attrib::hasFunctions ()
- {
- return priv->nFunction > 0;
- }
-
- void destroyFragmentFunction (FunctionId id)
- {
- GLScreen *s = GLScreen::get (screen);
- Function *function;
- Program *program;
-
- function = findFragmentFunction (s, id);
-
- if (!function)
- return;
-
- std::vector<Program *>::iterator it;
-
- do {
- program = NULL;
-
- it = s->fragmentStorage ()->programs.begin ();
-
- for (; it != s->fragmentStorage ()->programs.end (); it++)
- {
- foreach (FunctionId i, (*it)->signature)
- if (i == id)
- {
- program = (*it);
- break;
- }
-
- if (program)
- break;
- }
-
- if (program)
- {
- delete program;
- s->fragmentStorage ()->programs.erase (it);
- }
-
- } while (program);
-
- std::vector<Function *>::iterator fi =
- std::find (s->fragmentStorage ()->functions.begin (),
- s->fragmentStorage ()->functions.end (),
- function);
- if (fi != s->fragmentStorage ()->functions.end ())
- s->fragmentStorage ()->functions.erase (fi);
-
- delete (function);
- }
-
- FunctionId
- getSaturateFragmentFunction (GLTexture *texture,
- int param)
- {
- int target;
- GLScreen *s = GLScreen::get (screen);
-
- if (param >= 64)
- return 0;
-
- if (texture->target () == GL_TEXTURE_2D)
- target = COMP_FETCH_TARGET_2D;
- else
- target = COMP_FETCH_TARGET_RECT;
-
- if (!s->fragmentStorage ()->saturateFunction [target][param])
- {
- static const char *saturateData =
- "MUL temp, output, { 1.0, 1.0, 1.0, 0.0 };"
- "DP3 temp, temp, program.env[%d];"
- "LRP output.xyz, program.env[%d].w, output, temp;";
- FunctionData data;
-
- data.addTempHeaderOp ("temp");
- data.addFetchOp ("output", NULL, target);
- data.addColorOp ("output", "output");
-
- data.addDataOp (saturateData, param, param);
-
- if (!data.status ())
- return 0;
-
- s->fragmentStorage ()->saturateFunction [target][param] =
- data.createFragmentFunction ("__core_saturate");
-
- }
-
- return s->fragmentStorage ()->saturateFunction [target][param];
- }
-
- Storage::Storage () :
- lastFunctionId (1),
- functions (0),
- programs (0)
- {
- for (int i = 0; i < 64; i++)
- {
- saturateFunction[0][i] = 0;
- saturateFunction[1][i] = 0;
- }
- }
-
- Storage::~Storage ()
- {
- foreach (Program *p, programs)
- delete p;
- programs.clear ();
- foreach (Function *f, functions)
- delete f;
- functions.clear ();
- }
-
-};
diff --git a/plugins/opengl/src/matrix.cpp b/plugins/opengl/src/matrix.cpp
index 28d4e96..bc3d9d4 100644
--- a/plugins/opengl/src/matrix.cpp
+++ b/plugins/opengl/src/matrix.cpp
@@ -159,6 +159,60 @@ operator* (const GLMatrix& lhs,
#undef B
#undef P
+/*
+** Invert 4x4 matrix.
+** Contributed by David Moore (See Mesa bug #6748)
+*/
+bool GLMatrix::invert ()
+{
+ float inv[16], det;
+ int i;
+
+ inv[0] = m[5]*m[10]*m[15] - m[5]*m[11]*m[14] - m[9]*m[6]*m[15]
+ + m[9]*m[7]*m[14] + m[13]*m[6]*m[11] - m[13]*m[7]*m[10];
+ inv[4] = -m[4]*m[10]*m[15] + m[4]*m[11]*m[14] + m[8]*m[6]*m[15]
+ - m[8]*m[7]*m[14] - m[12]*m[6]*m[11] + m[12]*m[7]*m[10];
+ inv[8] = m[4]*m[9]*m[15] - m[4]*m[11]*m[13] - m[8]*m[5]*m[15]
+ + m[8]*m[7]*m[13] + m[12]*m[5]*m[11] - m[12]*m[7]*m[9];
+ inv[12] = -m[4]*m[9]*m[14] + m[4]*m[10]*m[13] + m[8]*m[5]*m[14]
+ - m[8]*m[6]*m[13] - m[12]*m[5]*m[10] + m[12]*m[6]*m[9];
+ inv[1] = -m[1]*m[10]*m[15] + m[1]*m[11]*m[14] + m[9]*m[2]*m[15]
+ - m[9]*m[3]*m[14] - m[13]*m[2]*m[11] + m[13]*m[3]*m[10];
+ inv[5] = m[0]*m[10]*m[15] - m[0]*m[11]*m[14] - m[8]*m[2]*m[15]
+ + m[8]*m[3]*m[14] + m[12]*m[2]*m[11] - m[12]*m[3]*m[10];
+ inv[9] = -m[0]*m[9]*m[15] + m[0]*m[11]*m[13] + m[8]*m[1]*m[15]
+ - m[8]*m[3]*m[13] - m[12]*m[1]*m[11] + m[12]*m[3]*m[9];
+ inv[13] = m[0]*m[9]*m[14] - m[0]*m[10]*m[13] - m[8]*m[1]*m[14]
+ + m[8]*m[2]*m[13] + m[12]*m[1]*m[10] - m[12]*m[2]*m[9];
+ inv[2] = m[1]*m[6]*m[15] - m[1]*m[7]*m[14] - m[5]*m[2]*m[15]
+ + m[5]*m[3]*m[14] + m[13]*m[2]*m[7] - m[13]*m[3]*m[6];
+ inv[6] = -m[0]*m[6]*m[15] + m[0]*m[7]*m[14] + m[4]*m[2]*m[15]
+ - m[4]*m[3]*m[14] - m[12]*m[2]*m[7] + m[12]*m[3]*m[6];
+ inv[10] = m[0]*m[5]*m[15] - m[0]*m[7]*m[13] - m[4]*m[1]*m[15]
+ + m[4]*m[3]*m[13] + m[12]*m[1]*m[7] - m[12]*m[3]*m[5];
+ inv[14] = -m[0]*m[5]*m[14] + m[0]*m[6]*m[13] + m[4]*m[1]*m[14]
+ - m[4]*m[2]*m[13] - m[12]*m[1]*m[6] + m[12]*m[2]*m[5];
+ inv[3] = -m[1]*m[6]*m[11] + m[1]*m[7]*m[10] + m[5]*m[2]*m[11]
+ - m[5]*m[3]*m[10] - m[9]*m[2]*m[7] + m[9]*m[3]*m[6];
+ inv[7] = m[0]*m[6]*m[11] - m[0]*m[7]*m[10] - m[4]*m[2]*m[11]
+ + m[4]*m[3]*m[10] + m[8]*m[2]*m[7] - m[8]*m[3]*m[6];
+ inv[11] = -m[0]*m[5]*m[11] + m[0]*m[7]*m[9] + m[4]*m[1]*m[11]
+ - m[4]*m[3]*m[9] - m[8]*m[1]*m[7] + m[8]*m[3]*m[5];
+ inv[15] = m[0]*m[5]*m[10] - m[0]*m[6]*m[9] - m[4]*m[1]*m[10]
+ + m[4]*m[2]*m[9] + m[8]*m[1]*m[6] - m[8]*m[2]*m[5];
+
+ det = m[0]*inv[0] + m[1]*inv[4] + m[2]*inv[8] + m[3]*inv[12];
+ if (det == 0)
+ return false;
+
+ det = 1.0f / det;
+
+ for (i = 0; i < 16; i++)
+ m[i] = inv[i] * det;
+
+ return true;
+}
+
/**
* Generate a 4x4 transformation matrix from glRotate parameters, and
* post-multiply the input matrix by it.
diff --git a/plugins/opengl/src/paint.cpp b/plugins/opengl/src/paint.cpp
index cf83c86..c7e8b1c 100644
--- a/plugins/opengl/src/paint.cpp
+++ b/plugins/opengl/src/paint.cpp
@@ -1,5 +1,6 @@
/*
* Copyright © 2005 Novell, Inc.
+ * Copyright © 2011 Linaro, Ltd.
*
* Permission to use, copy, modify, distribute, and sell this software
* and its documentation for any purpose is hereby granted without
@@ -20,7 +21,8 @@
* NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
* WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
- * Author: David Reveman <davidr@novell.com>
+ * Authors: David Reveman <davidr@novell.com>
+ * Travis Watkins <travis.watkins@linaro.org>
*/
#include <stdlib.h>
@@ -34,6 +36,7 @@
#include <opengl/opengl.h>
#include "privates.h"
+#include "shaders.h"
GLScreenPaintAttrib defaultScreenPaintAttrib = {
@@ -63,12 +66,16 @@ GLScreen::glApplyTransform (const GLScreenPaintAttrib &sAttrib,
}
void
-PrivateGLScreen::paintBackground (const CompRegion &region,
- bool transformed)
+PrivateGLScreen::paintBackground (const GLMatrix &transform,
+ const CompRegion &region,
+ bool transformed)
{
+ GLVertexBuffer *streamingBuffer = GLVertexBuffer::streamingBuffer ();
+ GLfloat vertexData[16];
+ GLushort colorData[4];
+
BoxPtr pBox = const_cast <Region> (region.handle ())->rects;
int n, nBox = const_cast <Region> (region.handle ())->numRects;
- GLfloat *d, *data;
if (!nBox)
return;
@@ -92,81 +99,83 @@ PrivateGLScreen::paintBackground (const CompRegion &region,
backgroundLoaded = true;
}
- data = new GLfloat [nBox * 16];
- if (!data)
- return;
-
- d = data;
n = nBox;
if (backgroundTextures.empty ())
{
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
while (n--)
{
- *d++ = pBox->x1;
- *d++ = pBox->y2;
-
- *d++ = pBox->x2;
- *d++ = pBox->y2;
-
- *d++ = pBox->x2;
- *d++ = pBox->y1;
-
- *d++ = pBox->x1;
- *d++ = pBox->y1;
+ vertexData[0] = pBox->x1;
+ vertexData[1] = pBox->y1;
+ vertexData[2] = 0.0f;
+ vertexData[3] = pBox->x1;
+ vertexData[4] = pBox->y2;
+ vertexData[5] = 0.0f;
+ vertexData[6] = pBox->x2;
+ vertexData[7] = pBox->y1;
+ vertexData[8] = 0.0f;
+ vertexData[9] = pBox->x2;
+ vertexData[10] = pBox->y2;
+ vertexData[11] = 0.0f;
+
+ streamingBuffer->addVertices (4, vertexData);
pBox++;
}
- glVertexPointer (2, GL_FLOAT, sizeof (GLfloat) * 2, data + 2);
+ colorData[0] = colorData[1] = colorData[2] = colorData[3] = 0;
+ streamingBuffer->addColors (1, colorData);
- glColor4us (0, 0, 0, 0);
- glDrawArrays (GL_QUADS, 0, nBox * 4);
- glColor4usv (defaultColor);
+ streamingBuffer->end ();
+ streamingBuffer->render (transform);
}
else
{
for (unsigned int i = 0; i < backgroundTextures.size (); i++)
{
+ GLfloat textureData[8];
GLTexture *bg = backgroundTextures[i];
CompRegion r = region & *bg;
pBox = const_cast <Region> (r.handle ())->rects;
nBox = const_cast <Region> (r.handle ())->numRects;
- d = data;
n = nBox;
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
while (n--)
{
- *d++ = COMP_TEX_COORD_X (bg->matrix (), pBox->x1);
- *d++ = COMP_TEX_COORD_Y (bg->matrix (), pBox->y2);
-
- *d++ = pBox->x1;
- *d++ = pBox->y2;
-
- *d++ = COMP_TEX_COORD_X (bg->matrix (), pBox->x2);
- *d++ = COMP_TEX_COORD_Y (bg->matrix (), pBox->y2);
-
- *d++ = pBox->x2;
- *d++ = pBox->y2;
-
- *d++ = COMP_TEX_COORD_X (bg->matrix (), pBox->x2);
- *d++ = COMP_TEX_COORD_Y (bg->matrix (), pBox->y1);
-
- *d++ = pBox->x2;
- *d++ = pBox->y1;
-
- *d++ = COMP_TEX_COORD_X (bg->matrix (), pBox->x1);
- *d++ = COMP_TEX_COORD_Y (bg->matrix (), pBox->y1);
-
- *d++ = pBox->x1;
- *d++ = pBox->y1;
+ vertexData[0] = pBox->x1;
+ vertexData[1] = pBox->y1;
+ vertexData[2] = 0.0f;
+ vertexData[3] = pBox->x1;
+ vertexData[4] = pBox->y2;
+ vertexData[5] = 0.0f;
+ vertexData[6] = pBox->x2;
+ vertexData[7] = pBox->y1;
+ vertexData[8] = 0.0f;
+ vertexData[9] = pBox->x2;
+ vertexData[10] = pBox->y2;
+ vertexData[11] = 0.0f;
+
+ textureData[0] = COMP_TEX_COORD_X (bg->matrix (), pBox->x1);
+ textureData[1] = COMP_TEX_COORD_X (bg->matrix (), pBox->y1);
+ textureData[2] = COMP_TEX_COORD_X (bg->matrix (), pBox->x1);
+ textureData[3] = COMP_TEX_COORD_X (bg->matrix (), pBox->y2);
+ textureData[4] = COMP_TEX_COORD_X (bg->matrix (), pBox->x2);
+ textureData[5] = COMP_TEX_COORD_X (bg->matrix (), pBox->y1);
+ textureData[6] = COMP_TEX_COORD_X (bg->matrix (), pBox->x2);
+ textureData[7] = COMP_TEX_COORD_X (bg->matrix (), pBox->y2);
+
+ streamingBuffer->addVertices (4, vertexData);
+ streamingBuffer->addTexCoords (0, 4, textureData);
pBox++;
}
- glTexCoordPointer (2, GL_FLOAT, sizeof (GLfloat) * 4, data);
- glVertexPointer (2, GL_FLOAT, sizeof (GLfloat) * 4, data + 2);
+ streamingBuffer->end ();
if (bg->name ())
{
@@ -175,14 +184,12 @@ PrivateGLScreen::paintBackground (const CompRegion &region,
else
bg->enable (GLTexture::Fast);
- glDrawArrays (GL_QUADS, 0, nBox * 4);
+ streamingBuffer->render (transform);
bg->disable ();
}
}
}
-
- delete [] data;
}
@@ -309,7 +316,9 @@ PrivateGLScreen::paintOutputRegion (const GLMatrix &transform,
CompositeWindow::get (fullscreenWindow)->unredirect ();
if (!(mask & PAINT_SCREEN_NO_BACKGROUND_MASK))
- paintBackground (tmpRegion, (mask & PAINT_SCREEN_TRANSFORMED_MASK));
+ paintBackground (transform,
+ tmpRegion,
+ (mask & PAINT_SCREEN_TRANSFORMED_MASK));
/* paint all windows from bottom to top */
foreach (w, pl)
@@ -358,6 +367,7 @@ GLScreen::glEnableOutputClipping (const GLMatrix &transform,
{
WRAPABLE_HND_FUNC (3, glEnableOutputClipping, transform, region, output)
+ #ifndef USE_GLES
GLdouble h = screen->height ();
GLdouble p1[2] = { static_cast<GLdouble> (region.handle ()->extents.x1),
@@ -390,6 +400,7 @@ GLScreen::glEnableOutputClipping (const GLMatrix &transform,
glEnable (GL_CLIP_PLANE3);
glPopMatrix ();
+ #endif
}
void
@@ -397,10 +408,12 @@ GLScreen::glDisableOutputClipping ()
{
WRAPABLE_HND_FUNC (4, glDisableOutputClipping)
+ #ifndef USE_GLES
glDisable (GL_CLIP_PLANE0);
glDisable (GL_CLIP_PLANE1);
glDisable (GL_CLIP_PLANE2);
glDisable (GL_CLIP_PLANE3);
+ #endif
}
#define CLIP_PLANE_MASK (PAINT_SCREEN_TRANSFORMED_MASK | \
@@ -430,26 +443,14 @@ GLScreen::glPaintTransformedOutput (const GLScreenPaintAttrib &sAttrib,
glEnableOutputClipping (sTransform, region, output);
sTransform.toScreenSpace (output, -sAttrib.zTranslate);
-
- glPushMatrix ();
- glLoadMatrixf (sTransform.getMatrix ());
-
priv->paintOutputRegion (sTransform, region, output, mask);
- glPopMatrix ();
-
glDisableOutputClipping ();
}
else
{
sTransform.toScreenSpace (output, -sAttrib.zTranslate);
-
- glPushMatrix ();
- glLoadMatrixf (sTransform.getMatrix ());
-
priv->paintOutputRegion (sTransform, region, output, mask);
-
- glPopMatrix ();
}
}
@@ -484,13 +485,8 @@ GLScreen::glPaintOutput (const GLScreenPaintAttrib &sAttrib,
sTransform.toScreenSpace (output, -DEFAULT_Z_CAMERA);
- glPushMatrix ();
- glLoadMatrixf (sTransform.getMatrix ());
-
priv->paintOutputRegion (sTransform, region, output, mask);
- glPopMatrix ();
-
return true;
}
else if (mask & PAINT_SCREEN_FULL_MASK)
@@ -506,182 +502,172 @@ GLScreen::glPaintOutput (const GLScreenPaintAttrib &sAttrib,
}
}
-#define ADD_RECT(data, m, n, x1, y1, x2, y2) \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_X (mat, x1); \
- *(data)++ = COMP_TEX_COORD_Y (mat, y1); \
- } \
- *(data)++ = (x1); \
- *(data)++ = (y1); \
- *(data)++ = 0.0; \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_X (mat, x1); \
- *(data)++ = COMP_TEX_COORD_Y (mat, y2); \
- } \
- *(data)++ = (x1); \
- *(data)++ = (y2); \
- *(data)++ = 0.0; \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_X (mat, x2); \
- *(data)++ = COMP_TEX_COORD_Y (mat, y2); \
- } \
- *(data)++ = (x2); \
- *(data)++ = (y2); \
- *(data)++ = 0.0; \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_X (mat, x2); \
- *(data)++ = COMP_TEX_COORD_Y (mat, y1); \
- } \
- *(data)++ = (x2); \
- *(data)++ = (y1); \
- *(data)++ = 0.0
-
-#define ADD_QUAD(data, m, n, x1, y1, x2, y2) \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_XY (mat, x1, y1); \
- *(data)++ = COMP_TEX_COORD_YX (mat, x1, y1); \
- } \
- *(data)++ = (x1); \
- *(data)++ = (y1); \
- *(data)++ = 0.0; \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_XY (mat, x1, y2); \
- *(data)++ = COMP_TEX_COORD_YX (mat, x1, y2); \
- } \
- *(data)++ = (x1); \
- *(data)++ = (y2); \
- *(data)++ = 0.0; \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_XY (mat, x2, y2); \
- *(data)++ = COMP_TEX_COORD_YX (mat, x2, y2); \
- } \
- *(data)++ = (x2); \
- *(data)++ = (y2); \
- *(data)++ = 0.0; \
- for (it = 0; it < n; it++) \
- { \
- const GLTexture::Matrix &mat = m[it]; \
- *(data)++ = COMP_TEX_COORD_XY (mat, x2, y1); \
- *(data)++ = COMP_TEX_COORD_YX (mat, x2, y1); \
- } \
- *(data)++ = (x2); \
- *(data)++ = (y1); \
- *(data)++ = 0.0;
-
-void
-GLWindow::glDrawGeometry ()
-{
- WRAPABLE_HND_FUNC (4, glDrawGeometry)
-
- int texUnit = priv->geometry.texUnits;
- int currentTexUnit = 0;
- int stride = priv->geometry.vertexStride;
- GLfloat *vertices = priv->geometry.vertices + (stride - 3);
-
- stride *= sizeof (GLfloat);
-
- glVertexPointer (3, GL_FLOAT, stride, vertices);
-
- while (texUnit--)
- {
- if (texUnit != currentTexUnit)
- {
- (*GL::clientActiveTexture) (GL_TEXTURE0_ARB + texUnit);
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
- currentTexUnit = texUnit;
- }
- vertices -= priv->geometry.texCoordSize;
- glTexCoordPointer (priv->geometry.texCoordSize,
- GL_FLOAT, stride, vertices);
+#define ADD_RECT(vertexBuffer, m, n, x1, y1, x2, y2) \
+ GLfloat vertexData[18] = { \
+ x1, y1, 0.0, \
+ x1, y2, 0.0, \
+ x2, y1, 0.0, \
+ x2, y1, 0.0, \
+ x1, y2, 0.0, \
+ x2, y2, 0.0 \
+ }; \
+ vertexBuffer->addVertices (6, vertexData); \
+ \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_X (mat, x1); \
+ data[1] = COMP_TEX_COORD_Y (mat, y1); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_X (mat, x1); \
+ data[1] = COMP_TEX_COORD_Y (mat, y2); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_X (mat, x2); \
+ data[1] = COMP_TEX_COORD_Y (mat, y1); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_X (mat, x2); \
+ data[1] = COMP_TEX_COORD_Y (mat, y1); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_X (mat, x1); \
+ data[1] = COMP_TEX_COORD_Y (mat, y2); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_X (mat, x2); \
+ data[1] = COMP_TEX_COORD_Y (mat, y2); \
+ vertexBuffer->addTexCoords (it, 1, data); \
}
- glDrawArrays (GL_QUADS, 0, priv->geometry.vCount);
-
- /* disable all texture coordinate arrays except 0 */
- texUnit = priv->geometry.texUnits;
- if (texUnit > 1)
- {
- while (--texUnit)
- {
- (*GL::clientActiveTexture) (GL_TEXTURE0_ARB + texUnit);
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
- }
-
- (*GL::clientActiveTexture) (GL_TEXTURE0_ARB);
+#define ADD_QUAD(vertexBuffer, m, n, x1, y1, x2, y2) \
+ GLfloat vertexData[18] = { \
+ x1, y1, 0.0, \
+ x1, y2, 0.0, \
+ x2, y1, 0.0, \
+ x2, y1, 0.0, \
+ x1, y2, 0.0, \
+ x2, y2, 0.0 \
+ }; \
+ vertexBuffer->addVertices (6, vertexData); \
+ \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_XY (mat, x1, y1); \
+ data[1] = COMP_TEX_COORD_YX (mat, x1, y1); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_XY (mat, x1, y2); \
+ data[1] = COMP_TEX_COORD_YX (mat, x1, y2); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_XY (mat, x2, y1); \
+ data[1] = COMP_TEX_COORD_YX (mat, x2, y1); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_XY (mat, x2, y1); \
+ data[1] = COMP_TEX_COORD_YX (mat, x2, y1); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_XY (mat, x1, y2); \
+ data[1] = COMP_TEX_COORD_YX (mat, x1, y2); \
+ vertexBuffer->addTexCoords (it, 1, data); \
+ } \
+ for (it = 0; it < n; it++) \
+ { \
+ GLfloat data[2]; \
+ const GLTexture::Matrix &mat = m[it]; \
+ data[0] = COMP_TEX_COORD_XY (mat, x2, y2); \
+ data[1] = COMP_TEX_COORD_YX (mat, x2, y2); \
+ vertexBuffer->addTexCoords (it, 1, data); \
}
-}
+
static inline void
-addSingleQuad (GLfloat *&d,
- const GLTexture::MatrixList &matrix,
- unsigned int nMatrix,
- int x1,
- int y1,
- int x2,
- int y2,
- int &n,
- bool rect)
+addSingleQuad (GLVertexBuffer *vertexBuffer,
+ const GLTexture::MatrixList &matrix,
+ unsigned int nMatrix,
+ int x1,
+ int y1,
+ int x2,
+ int y2,
+ int &n,
+ bool rect)
{
unsigned int it;
if (rect)
{
- ADD_RECT (d, matrix, nMatrix, x1, y1, x2, y2);
+ ADD_RECT (vertexBuffer, matrix, nMatrix, x1, y1, x2, y2);
}
else
{
- ADD_QUAD (d, matrix, nMatrix, x1, y1, x2, y2);
+ ADD_QUAD (vertexBuffer, matrix, nMatrix, x1, y1, x2, y2);
}
n++;
}
static inline void
-addQuads (GLfloat *&d,
- const GLTexture::MatrixList &matrix,
- unsigned int nMatrix,
- int x1,
- int y1,
- int x2,
- int y2,
- int &n,
- int vSize,
- bool rect,
- GLWindow::Geometry &geometry,
- unsigned int maxGridWidth,
- unsigned int maxGridHeight)
+addQuads (GLVertexBuffer *vertexBuffer,
+ const GLTexture::MatrixList &matrix,
+ unsigned int nMatrix,
+ int x1,
+ int y1,
+ int x2,
+ int y2,
+ int &n,
+ bool rect,
+ unsigned int maxGridWidth,
+ unsigned int maxGridHeight)
{
int nQuadsX = (maxGridWidth == MAXSHORT) ? 1 :
1 + (x2 - x1 - 1) / (int) maxGridWidth; // ceil. division
int nQuadsY = (maxGridHeight == MAXSHORT) ? 1 :
1 + (y2 - y1 - 1) / (int) maxGridHeight;
- int newVertexSize = (n + nQuadsX * nQuadsY) * vSize * 4;
-
- // Make sure enough vertices are allocated for nQuadsX * nQuadsY more quads
- if (newVertexSize > geometry.vertexSize)
- {
- if (!geometry.moreVertices (newVertexSize))
- return;
-
- d = geometry.vertices + (n * vSize * 4);
- }
if (nQuadsX == 1 && nQuadsY == 1)
{
- addSingleQuad (d, matrix, nMatrix, x1, y1, x2, y2, n, rect);
+ addSingleQuad (vertexBuffer, matrix, nMatrix, x1, y1, x2, y2, n, rect);
}
else
{
@@ -697,7 +683,8 @@ addQuads (GLfloat *&d,
{
nx2 = MIN (nx1 + (int) quadWidth, x2);
- addSingleQuad (d, matrix, nMatrix, nx1, ny1, nx2, ny2, n, rect);
+ addSingleQuad (vertexBuffer, matrix, nMatrix,
+ nx1, ny1, nx2, ny2, n, rect);
}
}
}
@@ -715,8 +702,6 @@ GLWindow::glAddGeometry (const GLTexture::MatrixList &matrix,
BoxRec full;
int nMatrix = matrix.size ();
- priv->geometry.texUnits = nMatrix;
-
full = clip.handle ()->extents;
if (region.handle ()->extents.x1 > full.x1)
full.x1 = region.handle ()->extents.x1;
@@ -734,9 +719,7 @@ GLWindow::glAddGeometry (const GLTexture::MatrixList &matrix,
BoxPtr pClip;
int nClip;
BoxRec cbox;
- int vSize;
int n, it, x1, y1, x2, y2;
- GLfloat *d;
bool rect = true;
for (it = 0; it < nMatrix; it++)
@@ -751,18 +734,6 @@ GLWindow::glAddGeometry (const GLTexture::MatrixList &matrix,
pBox = const_cast <Region> (region.handle ())->rects;
nBox = const_cast <Region> (region.handle ())->numRects;
- vSize = 3 + nMatrix * 2;
-
- n = priv->geometry.vCount / 4;
-
- if ((n + nBox) * vSize * 4 > priv->geometry.vertexSize)
- {
- if (!priv->geometry.moreVertices ((n + nBox) * vSize * 4))
- return;
- }
-
- d = priv->geometry.vertices + (priv->geometry.vCount * vSize);
-
while (nBox--)
{
x1 = pBox->x1;
@@ -787,24 +758,15 @@ GLWindow::glAddGeometry (const GLTexture::MatrixList &matrix,
if (nClip == 1)
{
- addQuads (d, matrix, nMatrix,
+ addQuads (priv->vertexBuffer, matrix, nMatrix,
x1, y1, x2, y2,
- n, vSize, rect, priv->geometry,
+ n, rect,
maxGridWidth, maxGridHeight);
}
else
{
pClip = const_cast <Region> (clip.handle ())->rects;
- if (((n + nClip) * vSize * 4) > priv->geometry.vertexSize)
- {
- if (!priv->geometry.moreVertices ((n + nClip) *
- vSize * 4))
- return;
-
- d = priv->geometry.vertices + (n * vSize * 4);
- }
-
while (nClip--)
{
cbox = *pClip;
@@ -822,120 +784,32 @@ GLWindow::glAddGeometry (const GLTexture::MatrixList &matrix,
if (cbox.x1 < cbox.x2 && cbox.y1 < cbox.y2)
{
- addQuads (d, matrix, nMatrix,
+ addQuads (priv->vertexBuffer, matrix, nMatrix,
cbox.x1, cbox.y1, cbox.x2, cbox.y2,
- n, vSize, rect, priv->geometry,
+ n, rect,
maxGridWidth, maxGridHeight);
}
}
}
}
}
-
- priv->geometry.vCount = n * 4;
- priv->geometry.vertexStride = vSize;
- priv->geometry.texCoordSize = 2;
}
}
-static bool
-enableFragmentProgramAndDrawGeometry (GLScreen *gs,
- GLWindow *w,
- GLTexture *texture,
- GLFragment::Attrib &attrib,
- GLTexture::Filter filter,
- unsigned int mask)
-{
- GLFragment::Attrib fa (attrib);
- bool blending;
-
- if (GL::canDoSaturated && attrib.getSaturation () != COLOR)
- {
- int param, function;
-
- param = fa.allocParameters (1);
- function =
- GLFragment::getSaturateFragmentFunction (texture, param);
-
- fa.addFunction (function);
-
- (*GL::programEnvParameter4f) (GL_FRAGMENT_PROGRAM_ARB, param,
- RED_SATURATION_WEIGHT,
- GREEN_SATURATION_WEIGHT,
- BLUE_SATURATION_WEIGHT,
- attrib.getSaturation () / 65535.0f);
- }
-
- if (!fa.enable (&blending))
- return false;
-
- texture->enable (filter);
-
- if (mask & PAINT_WINDOW_BLEND_MASK)
- {
- if (blending)
- glEnable (GL_BLEND);
-
- if (attrib.getOpacity () != OPAQUE || attrib.getBrightness () != BRIGHT)
- {
- GLushort color;
-
- color = (attrib.getOpacity () * attrib.getBrightness ()) >> 16;
-
- gs->setTexEnvMode (GL_MODULATE);
- glColor4us (color, color, color, attrib.getOpacity ());
-
- w->glDrawGeometry ();
-
- glColor4usv (defaultColor);
- gs->setTexEnvMode (GL_REPLACE);
- }
- else
- {
- w->glDrawGeometry ();
- }
-
- if (blending)
- glDisable (GL_BLEND);
- }
- else if (attrib.getBrightness () != BRIGHT)
- {
- gs->setTexEnvMode (GL_MODULATE);
- glColor4us (attrib.getBrightness (), attrib.getBrightness (),
- attrib.getBrightness (), BRIGHT);
-
- w->glDrawGeometry ();
-
- glColor4usv (defaultColor);
- gs->setTexEnvMode (GL_REPLACE);
- }
- else
- {
- w->glDrawGeometry ();
- }
-
- texture->disable ();
-
- fa.disable ();
-
- return true;
-}
-
+#ifndef USE_GLES
static void
-enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
- GLWindow *w,
- GLTexture *texture,
- GLFragment::Attrib &attrib,
- GLTexture::Filter filter,
- unsigned int mask)
+enableLegacyOBSAndRender (GLScreen *gs,
+ GLWindow *w,
+ GLTexture *texture,
+ const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ GLTexture::Filter filter,
+ unsigned int mask)
{
- if (GL::canDoSaturated && attrib.getSaturation () != COLOR)
+ if (GL::canDoSaturated && attrib.saturation != COLOR)
{
GLfloat constant[4];
- if (mask & PAINT_WINDOW_BLEND_MASK)
- glEnable (GL_BLEND);
-
texture->enable (filter);
glTexEnvf (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
@@ -966,7 +840,7 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND1_RGB, GL_SRC_COLOR);
- if (GL::canDoSlightlySaturated && attrib.getSaturation () > 0)
+ if (GL::canDoSlightlySaturated && attrib.saturation > 0)
{
glTexEnvf (GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
glTexEnvf (GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_PREVIOUS);
@@ -997,20 +871,20 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
glTexEnvf (GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_PREVIOUS);
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
- constant[3] = attrib.getSaturation () / 65535.0f;
+ constant[3] = attrib.saturation / 65535.0f;
glTexEnvfv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constant);
- if (attrib.getOpacity () < OPAQUE ||
- attrib.getBrightness () != BRIGHT)
+ if (attrib.opacity < OPAQUE ||
+ attrib.brightness != BRIGHT)
{
GL::activeTexture (GL_TEXTURE3_ARB);
texture->enable (filter);
- constant[3] = attrib.getOpacity () / 65535.0f;
+ constant[3] = attrib.opacity / 65535.0f;
constant[0] = constant[1] = constant[2] = constant[3] *
- attrib.getBrightness () / 65535.0f;
+ attrib.brightness / 65535.0f;
glTexEnvfv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constant);
@@ -1028,7 +902,7 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND1_ALPHA, GL_SRC_ALPHA);
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
texture->disable ();
@@ -1038,7 +912,7 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
}
else
{
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
}
texture->disable ();
@@ -1055,9 +929,9 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
glTexEnvf (GL_TEXTURE_ENV, GL_OPERAND1_ALPHA, GL_SRC_ALPHA);
- constant[3] = attrib.getOpacity () / 65535.0f;
+ constant[3] = attrib.opacity / 65535.0f;
constant[0] = constant[1] = constant[2] = constant[3] *
- attrib.getBrightness ()/ 65535.0f;
+ attrib.brightness / 65535.0f;
constant[0] = 0.5f + 0.5f * RED_SATURATION_WEIGHT * constant[0];
constant[1] = 0.5f + 0.5f * GREEN_SATURATION_WEIGHT * constant[1];
@@ -1065,7 +939,7 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
glTexEnvfv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constant);
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
}
texture->disable ();
@@ -1078,9 +952,6 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
glColor4usv (defaultColor);
gs->setTexEnvMode (GL_REPLACE);
-
- if (mask & PAINT_WINDOW_BLEND_MASK)
- glDisable (GL_BLEND);
}
else
{
@@ -1088,57 +959,57 @@ enableFragmentOperationsAndDrawGeometry (GLScreen *gs,
if (mask & PAINT_WINDOW_BLEND_MASK)
{
- glEnable (GL_BLEND);
- if (attrib.getOpacity ()!= OPAQUE ||
- attrib.getBrightness () != BRIGHT)
+ if (attrib.opacity != OPAQUE ||
+ attrib.brightness != BRIGHT)
{
GLushort color;
- color = (attrib.getOpacity () * attrib.getBrightness ()) >> 16;
+ color = (attrib.opacity * attrib.brightness) >> 16;
gs->setTexEnvMode (GL_MODULATE);
- glColor4us (color, color, color, attrib.getOpacity ());
+ glColor4us (color, color, color, attrib.opacity);
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
glColor4usv (defaultColor);
gs->setTexEnvMode (GL_REPLACE);
}
else
{
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
}
-
- glDisable (GL_BLEND);
}
- else if (attrib.getBrightness () != BRIGHT)
+ else if (attrib.brightness != BRIGHT)
{
gs->setTexEnvMode (GL_MODULATE);
- glColor4us (attrib.getBrightness (), attrib.getBrightness (),
- attrib.getBrightness (), BRIGHT);
+ glColor4us (attrib.brightness, attrib.brightness,
+ attrib.brightness, BRIGHT);
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
glColor4usv (defaultColor);
gs->setTexEnvMode (GL_REPLACE);
}
else
{
- w->glDrawGeometry ();
+ w->vertexBuffer ()->render (transform, attrib);
}
texture->disable ();
}
}
+#endif
void
-GLWindow::glDrawTexture (GLTexture *texture,
- GLFragment::Attrib &attrib,
- unsigned int mask)
+GLWindow::glDrawTexture (GLTexture *texture,
+ const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ unsigned int mask)
{
- WRAPABLE_HND_FUNC (3, glDrawTexture, texture, attrib, mask)
+ WRAPABLE_HND_FUNC (3, glDrawTexture, texture, transform, attrib, mask)
GLTexture::Filter filter;
+ GLProgram *program = NULL;
if (mask & (PAINT_WINDOW_TRANSFORMED_MASK |
PAINT_WINDOW_ON_TRANSFORMED_SCREEN_MASK))
@@ -1146,24 +1017,36 @@ GLWindow::glDrawTexture (GLTexture *texture,
else
filter = priv->gScreen->filter (NOTHING_TRANS_FILTER);
- if ((!attrib.hasFunctions () && (!priv->gScreen->lighting () ||
- attrib.getSaturation () == COLOR || attrib.getSaturation () == 0)) ||
- !enableFragmentProgramAndDrawGeometry (priv->gScreen, this, texture,
- attrib, filter, mask))
- {
- enableFragmentOperationsAndDrawGeometry (priv->gScreen, this, texture,
- attrib, filter, mask);
- }
+ // add the opengl functions (main) to the shader list, use it, then clear it
+ addShaders ("opengl", vertex_shader, fragment_shader);
+ program = priv->gScreen->getProgram (priv->shaders);
+ priv->vertexBuffer->setProgram (program);
+ priv->shaders.clear ();
+
+ texture->enable (filter);
+
+ #ifdef USE_GLES
+ priv->vertexBuffer->render (transform, attrib);
+ #else
+
+ if (!GL::vbo)
+ enableLegacyOBSAndRender (priv->gScreen, this, texture, transform,
+ attrib, filter, mask);
+ else
+ priv->vertexBuffer->render (transform, attrib);
+ #endif
+
+ texture->disable ();
}
bool
-GLWindow::glDraw (const GLMatrix &transform,
- GLFragment::Attrib &fragment,
- const CompRegion &region,
- unsigned int mask)
+GLWindow::glDraw (const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ const CompRegion &region,
+ unsigned int mask)
{
WRAPABLE_HND_FUNC_RETURN (1, bool, glDraw, transform,
- fragment, region, mask)
+ attrib, region, mask)
const CompRegion reg = (mask & PAINT_WINDOW_TRANSFORMED_MASK) ?
infiniteRegion : region;
@@ -1185,10 +1068,11 @@ GLWindow::glDraw (const GLMatrix &transform,
if (priv->textures.size () == 1)
{
ml[0] = priv->matrices[0];
- priv->geometry.reset ();
+ priv->vertexBuffer->begin ();
glAddGeometry (ml, priv->window->region (), reg);
- if (priv->geometry.vCount)
- glDrawTexture (priv->textures[0], fragment, mask);
+ priv->vertexBuffer->end ();
+
+ glDrawTexture (priv->textures[0], transform, attrib, mask);
}
else
{
@@ -1197,10 +1081,11 @@ GLWindow::glDraw (const GLMatrix &transform,
for (unsigned int i = 0; i < priv->textures.size (); i++)
{
ml[0] = priv->matrices[i];
- priv->geometry.reset ();
+ priv->vertexBuffer->begin ();
glAddGeometry (ml, priv->regions[i], reg);
- if (priv->geometry.vCount)
- glDrawTexture (priv->textures[i], fragment, mask);
+ priv->vertexBuffer->end ();
+
+ glDrawTexture (priv->textures[i], transform, attrib, mask);
}
}
@@ -1215,7 +1100,6 @@ GLWindow::glPaint (const GLWindowPaintAttrib &attrib,
{
WRAPABLE_HND_FUNC_RETURN (0, bool, glPaint, attrib, transform, region, mask)
- GLFragment::Attrib fragment (attrib);
bool status;
priv->lastPaint = attrib;
@@ -1245,18 +1129,7 @@ GLWindow::glPaint (const GLWindowPaintAttrib &attrib,
if (mask & PAINT_WINDOW_NO_CORE_INSTANCE_MASK)
return true;
- if (mask & PAINT_WINDOW_TRANSFORMED_MASK ||
- mask & PAINT_WINDOW_WITH_OFFSET_MASK)
- {
- glPushMatrix ();
- glLoadMatrixf (transform.getMatrix ());
- }
-
- status = glDraw (transform, fragment, region, mask);
-
- if (mask & PAINT_WINDOW_TRANSFORMED_MASK ||
- mask & PAINT_WINDOW_WITH_OFFSET_MASK)
- glPopMatrix ();
+ status = glDraw (transform, attrib, region, mask);
return status;
}
diff --git a/plugins/opengl/src/privatefragment.h b/plugins/opengl/src/privatefragment.h
deleted file mode 100644
index 8a94d04..0000000
--- a/plugins/opengl/src/privatefragment.h
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright © 2008 Dennis Kasprzyk
- * Copyright © 2007 Novell, Inc.
- *
- * Permission to use, copy, modify, distribute, and sell this software
- * and its documentation for any purpose is hereby granted without
- * fee, provided that the above copyright notice appear in all copies
- * and that both that copyright notice and this permission notice
- * appear in supporting documentation, and that the name of
- * Dennis Kasprzyk not be used in advertising or publicity pertaining to
- * distribution of the software without specific, written prior permission.
- * Dennis Kasprzyk makes no representations about the suitability of this
- * software for any purpose. It is provided "as is" without express or
- * implied warranty.
- *
- * DENNIS KASPRZYK DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
- * NO EVENT SHALL DENNIS KASPRZYK BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
- * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
- * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
- * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
- *
- * Authors: Dennis Kasprzyk <onestone@compiz-fusion.org>
- * David Reveman <davidr@novell.com>
- */
-
-#ifndef _PRIVATEFRAGMENT_H
-#define _PRIVATEFRAGMENT_H
-
-#include <vector>
-
-#include <opengl/fragment.h>
-
-namespace GLFragment {
-
- class Function;
- class Program;
-
- class Storage {
- public:
- Storage ();
- ~Storage ();
-
- public:
- int lastFunctionId;
- std::vector<Function *> functions;
- std::vector<Program *> programs;
-
- FunctionId saturateFunction[2][64];
- };
-};
-
-#endif
diff --git a/plugins/opengl/src/privates.h b/plugins/opengl/src/privates.h
index 3aebaf0..a25a27d 100644
--- a/plugins/opengl/src/privates.h
+++ b/plugins/opengl/src/privates.h
@@ -32,8 +32,8 @@
#include <opengl/opengl.h>
#include <core/atoms.h>
-#include "privatefragment.h"
#include "privatetexture.h"
+#include "privatevertexbuffer.h"
#include "opengl_options.h"
extern CompOutput *targetOutput;
@@ -72,8 +72,9 @@ class PrivateGLScreen :
void waitForVideoSync ();
- void paintBackground (const CompRegion &region,
- bool transformed);
+ void paintBackground (const GLMatrix &transform,
+ const CompRegion &region,
+ bool transformed);
void paintOutputRegion (const GLMatrix &transform,
const CompRegion &region,
@@ -91,7 +92,9 @@ class PrivateGLScreen :
GLenum textureFilter;
+ #ifndef USE_GLES
GLFBConfig glxPixmapFBConfigs[MAX_DEPTH + 1];
+ #endif
GLTexture::List backgroundTextures;
bool backgroundLoaded;
@@ -100,17 +103,20 @@ class PrivateGLScreen :
CompPoint rasterPos;
- GLFragment::Storage fragmentStorage;
-
- GLfloat projection[16];
+ GLMatrix *projection;
bool clearBuffers;
bool lighting;
- GL::GLXGetProcAddressProc getProcAddress;
-
+ #ifdef USE_GLES
+ EGLContext ctx;
+ EGLSurface surface;
+ #else
GLXContext ctx;
+ GL::GLXGetProcAddressProc getProcAddress;
+ #endif
+
CompRegion outputRegion;
bool pendingCommands;
@@ -121,6 +127,8 @@ class PrivateGLScreen :
bool hasCompositing;
GLIcon defaultIcon;
+
+ GLProgramCache *programCache;
};
class PrivateGLWindow :
@@ -163,10 +171,14 @@ class PrivateGLWindow :
unsigned int lastMask;
- GLWindow::Geometry geometry;
+ GLVertexBuffer *vertexBuffer;
+
+ // map of shaders, plugin name is key, pair of vertex and fragment
+ // shader source code is value
+ std::list<GLShaderData*> shaders;
std::list<GLIcon> icons;
};
-
#endif
+
diff --git a/plugins/opengl/src/privatetexture.h b/plugins/opengl/src/privatetexture.h
index e647876..8997321 100644
--- a/plugins/opengl/src/privatetexture.h
+++ b/plugins/opengl/src/privatetexture.h
@@ -1,6 +1,7 @@
/*
* Copyright © 2008 Dennis Kasprzyk
* Copyright © 2007 Novell, Inc.
+ * Copyright © 2011 Linaro Ltd.
*
* Permission to use, copy, modify, distribute, and sell this software
* and its documentation for any purpose is hereby granted without
@@ -23,6 +24,7 @@
*
* Authors: Dennis Kasprzyk <onestone@compiz-fusion.org>
* David Reveman <davidr@novell.com>
+ * Travis Watkins <travis.watkins@linaro.org>
*/
#ifndef _PRIVATETEXTURE_H
@@ -30,8 +32,15 @@
#include <map>
+#ifdef USE_GLES
+#define SUPPORT_X11
+#include <GLES2/gl2.h>
+#include <EGL/egl.h>
+#include <EGL/eglext.h>
+#else
#include <GL/gl.h>
#include <GL/glx.h>
+#endif
#include <opengl/texture.h>
class GLScreen;
@@ -61,6 +70,28 @@ class PrivateTexture {
int refCount;
};
+#ifdef USE_GLES
+class EglTexture : public GLTexture {
+ public:
+ EglTexture ();
+ ~EglTexture ();
+
+ void enable (Filter filter);
+
+ static List bindPixmapToTexture (Pixmap pixmap,
+ int width,
+ int height,
+ int depth);
+
+ public:
+ bool damaged;
+ Damage damage;
+ bool updateMipMap;
+};
+
+extern std::map<Damage, EglTexture*> boundPixmapTex;
+#else
+
class TfpTexture : public GLTexture {
public:
TfpTexture ();
@@ -81,5 +112,6 @@ class TfpTexture : public GLTexture {
};
extern std::map<Damage, TfpTexture*> boundPixmapTex;
+#endif
#endif
diff --git a/plugins/opengl/src/privatevertexbuffer.h b/plugins/opengl/src/privatevertexbuffer.h
new file mode 100644
index 0000000..71a2bcb
--- /dev/null
+++ b/plugins/opengl/src/privatevertexbuffer.h
@@ -0,0 +1,71 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#ifndef _VERTEXBUFFER_PRIVATE_H
+#define _VERTEXBUFFER_PRIVATE_H
+
+#ifdef USE_GLES
+#include <GLES2/gl2.h>
+#else
+#include <GL/gl.h>
+#endif
+
+#include <opengl/program.h>
+
+class GLVertexBuffer;
+
+class PrivateVertexBuffer
+{
+ public:
+ PrivateVertexBuffer ();
+ ~PrivateVertexBuffer ();
+
+ int render (const GLMatrix &projection,
+ const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib);
+ int legacyRender (const GLMatrix &projection,
+ const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib);
+
+ public:
+ static GLVertexBuffer *streamingBuffer;
+
+ std::vector<GLfloat> vertexData;
+ std::vector<GLfloat> normalData;
+ std::vector<GLfloat> colorData;
+ std::vector<std::vector<GLfloat> > textureData;
+
+ GLProgram *program;
+ GLenum primitiveType;
+ GLenum usage;
+
+ GLuint vertexBuffer;
+ GLuint normalBuffer;
+ GLuint colorBuffer;
+ std::vector<GLuint> textureBuffers;
+};
+
+#endif //_VERTEXBUFFER_PRIVATE_H
+
diff --git a/plugins/opengl/src/program.cpp b/plugins/opengl/src/program.cpp
new file mode 100644
index 0000000..9d16880
--- /dev/null
+++ b/plugins/opengl/src/program.cpp
@@ -0,0 +1,225 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#define GL_GLEXT_PROTOTYPES
+
+#include <iostream>
+#include <fstream>
+#include <opengl/program.h>
+
+class PrivateProgram
+{
+ public:
+ GLuint program;
+ bool valid;
+};
+
+
+void printShaderInfoLog (GLuint shader)
+{
+ GLint length = 0;
+ GLint chars = 0;
+ GLchar *infoLog;
+
+ glGetShaderiv (shader, GL_INFO_LOG_LENGTH, &length);
+
+ if (length > 0)
+ {
+ infoLog = new GLchar[length];
+ glGetShaderInfoLog (shader, length, &chars, infoLog);
+ std::cout << infoLog << std::endl;
+ delete[] infoLog;
+ }
+}
+
+void printProgramInfoLog(GLuint program)
+{
+ GLint length = 0;
+ GLint chars = 0;
+ GLchar *infoLog;
+
+ glGetProgramiv (program, GL_INFO_LOG_LENGTH, &length);
+
+ if (length > 0)
+ {
+ infoLog = new GLchar[length];
+ glGetProgramInfoLog (program, length, &chars, infoLog);
+ std::cout << infoLog << std::endl;
+ delete[] infoLog;
+ }
+}
+
+static bool compileShader (GLuint *shader, GLenum type, CompString &source)
+{
+ const GLchar *data;
+ GLint status;
+
+ data = (GLchar *)source.c_str ();
+
+ *shader = glCreateShader (type);
+ glShaderSource (*shader, 1, &data, NULL);
+ glCompileShader (*shader);
+
+ glGetShaderiv (*shader, GL_COMPILE_STATUS, &status);
+ return (status == GL_TRUE);
+}
+
+GLProgram::GLProgram (CompString &vertexShader, CompString &fragmentShader) :
+ priv (new PrivateProgram ())
+{
+ GLuint vertex, fragment;
+ GLint status;
+
+ priv->valid = false;
+ priv->program = glCreateProgram ();
+
+ if (!compileShader (&vertex, GL_VERTEX_SHADER, vertexShader))
+ {
+ printShaderInfoLog (vertex);
+ std::cout << vertexShader << std::endl << std::endl;
+ return;
+ }
+
+ if (!compileShader (&fragment, GL_FRAGMENT_SHADER, fragmentShader))
+ {
+ printShaderInfoLog (fragment);
+ std::cout << fragmentShader << std::endl << std::endl;
+ return;
+ }
+
+ glAttachShader (priv->program, vertex);
+ glAttachShader (priv->program, fragment);
+
+ glLinkProgram (priv->program);
+ glValidateProgram (priv->program);
+
+ glGetProgramiv (priv->program, GL_LINK_STATUS, &status);
+ if (status == GL_FALSE)
+ {
+ printProgramInfoLog (priv->program);
+ return;
+ }
+
+ glDeleteShader (vertex);
+ glDeleteShader (fragment);
+
+ priv->valid = true;
+}
+
+GLProgram::~GLProgram ()
+{
+ glDeleteProgram (priv->program);
+ delete priv;
+}
+
+bool GLProgram::valid ()
+{
+ return priv->valid;
+}
+
+void GLProgram::bind ()
+{
+ glUseProgram (priv->program);
+}
+
+void GLProgram::unbind ()
+{
+ glUseProgram (0);
+}
+
+bool GLProgram::setUniform (const char *name, GLfloat value)
+{
+ GLint location = glGetUniformLocation (priv->program, name);
+ if (location == -1)
+ return false;
+
+ glUniform1f (location, value);
+ return true;
+}
+
+bool GLProgram::setUniform (const char *name, GLint value)
+{
+ GLint location = glGetUniformLocation (priv->program, name);
+ if (location == -1)
+ return false;
+
+ glUniform1i (location, value);
+ return true;
+}
+
+bool GLProgram::setUniform (const char *name, const GLMatrix &value)
+{
+ GLint location = glGetUniformLocation (priv->program, name);
+ if (location == -1)
+ return false;
+
+ glUniformMatrix4fv (location, 1, GL_FALSE, value.getMatrix ());
+ return true;
+}
+
+bool GLProgram::setUniform2f (const char *name,
+ GLfloat x,
+ GLfloat y)
+{
+ GLint location = glGetUniformLocation (priv->program, name);
+ if (location == -1)
+ return false;
+
+ glUniform2f (location, x, y);
+ return true;
+}
+
+bool GLProgram::setUniform3f (const char *name,
+ GLfloat x,
+ GLfloat y,
+ GLfloat z)
+{
+ GLint location = glGetUniformLocation (priv->program, name);
+ if (location == -1)
+ return false;
+
+ glUniform3f (location, x, y, z);
+ return true;
+}
+
+bool GLProgram::setUniform4f (const char *name,
+ GLfloat x,
+ GLfloat y,
+ GLfloat z,
+ GLfloat w)
+{
+ GLint location = glGetUniformLocation (priv->program, name);
+ if (location == -1)
+ return false;
+
+ glUniform4f (location, x, y, z, w);
+ return true;
+}
+
+GLuint GLProgram::attributeLocation (const char *name)
+{
+ return glGetAttribLocation (priv->program, name);
+}
+
diff --git a/plugins/opengl/src/programcache.cpp b/plugins/opengl/src/programcache.cpp
new file mode 100644
index 0000000..0635874
--- /dev/null
+++ b/plugins/opengl/src/programcache.cpp
@@ -0,0 +1,175 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#include <opengl/programcache.h>
+#include "privates.h"
+
+typedef std::list<std::string> access_history_t;
+typedef std::pair<GLProgram*, access_history_t::iterator> value;
+
+static GLProgram *
+compileProgram (std::string name, std::list<GLShaderData*> shaders)
+{
+ std::list<GLShaderData*>::iterator it;
+ std::string vertex_shader;
+ std::string fragment_shader;
+ std::string vertex_functions = "";
+ std::string vertex_function_calls = "";
+ std::string fragment_functions = "";
+ std::string fragment_function_calls = "";
+ int vpos, vcallpos, fpos, fcallpos;
+
+ for (it = shaders.begin (); it != shaders.end (); it++)
+ {
+ //find the special shaders to put the rest in
+ if ((*it)->vertex_shader.find ("@VERTEX_FUNCTIONS@") != std::string::npos)
+ {
+ vertex_shader = (*it)->vertex_shader;
+ }
+ else
+ {
+ if ((*it)->vertex_shader.length ())
+ {
+ vertex_functions += (*it)->vertex_shader;
+ vertex_function_calls += (*it)->name + "_vertex();\n";
+ }
+ }
+
+ if ((*it)->fragment_shader.find ("@FRAGMENT_FUNCTIONS@") != std::string::npos)
+ {
+ fragment_shader = (*it)->fragment_shader;
+ }
+ else
+ {
+ if ((*it)->fragment_shader.length ())
+ {
+ fragment_functions += (*it)->fragment_shader;
+ fragment_function_calls += (*it)->name + "_fragment();\n";
+ }
+ }
+ }
+
+ // put shader functions and function calls into the main shader
+ vpos = vertex_shader.find ("@VERTEX_FUNCTIONS@");
+ vertex_shader.replace (vpos, 18, vertex_functions);
+
+ vcallpos = vertex_shader.find ("@VERTEX_FUNCTION_CALLS@");
+ vertex_shader.replace (vcallpos, 23, vertex_function_calls);
+
+ fpos = fragment_shader.find ("@FRAGMENT_FUNCTIONS@");
+ fragment_shader.replace (fpos, 20, fragment_functions);
+
+ fcallpos = fragment_shader.find ("@FRAGMENT_FUNCTION_CALLS@");
+ fragment_shader.replace (fcallpos, 25, fragment_function_calls);
+
+ return new GLProgram (vertex_shader, fragment_shader);
+}
+
+class PrivateProgramCache
+{
+ public:
+ PrivateProgramCache (size_t);
+
+ const size_t capacity;
+ access_history_t access_history;
+ std::map<std::string, value> cache;
+
+ void insert (std::string, GLProgram *);
+ void evict ();
+};
+
+GLProgramCache::GLProgramCache (size_t capacity) :
+ priv (new PrivateProgramCache (capacity))
+{
+ assert (priv->capacity != 0);
+}
+
+GLProgramCache::~GLProgramCache ()
+{
+ delete priv;
+}
+
+GLProgram* GLProgramCache::operator () (std::list<GLShaderData*> shaders)
+{
+ std::list<GLShaderData*>::iterator name_it;
+ std::string name;
+
+ for (name_it = shaders.begin(); name_it != shaders.end(); name_it++)
+ {
+ if (name.length () == 0)
+ name += (*name_it)->name;
+ else
+ name += ":" + (*name_it)->name;
+ }
+
+ std::map<std::string, value>::iterator it = priv->cache.find (name);
+
+ if (it == priv->cache.end ())
+ {
+ GLProgram *program = compileProgram (name, shaders);
+ priv->insert (name, program);
+ return program;
+ }
+ else
+ {
+ priv->access_history.splice (priv->access_history.end (),
+ priv->access_history,
+ (*it).second.second);
+ (*it).second.second = priv->access_history.rbegin ().base ();
+
+ return (*it).second.first;
+ }
+}
+
+PrivateProgramCache::PrivateProgramCache (size_t c) :
+ capacity (c)
+{
+}
+
+void PrivateProgramCache::insert (std::string name, GLProgram *program)
+{
+ assert (cache.find (name) == cache.end ());
+
+ if (cache.size () == capacity)
+ evict ();
+
+ // update most recently used GLProgram
+ access_history_t::iterator it = access_history.insert (access_history.end (), name);
+
+ cache.insert (std::make_pair (name, std::make_pair (program, it)));
+}
+
+void PrivateProgramCache::evict ()
+{
+ assert (!access_history.empty ());
+
+ // find least recently used GLProgram
+ std::map<std::string, value>::iterator it = cache.find (access_history.front ());
+ assert (it != cache.end ());
+
+ cache.erase (it);
+ access_history.pop_front ();
+}
+
diff --git a/plugins/opengl/src/screen.cpp b/plugins/opengl/src/screen.cpp
index 253f03b..a589d48 100644
--- a/plugins/opengl/src/screen.cpp
+++ b/plugins/opengl/src/screen.cpp
@@ -1,4 +1,5 @@
/*
+ * Copyright © 2011 Linaro Ltd.
* Copyright © 2008 Dennis Kasprzyk
* Copyright © 2007 Novell, Inc.
*
@@ -23,6 +24,7 @@
*
* Authors: Dennis Kasprzyk <onestone@compiz-fusion.org>
* David Reveman <davidr@novell.com>
+ * Travis Watkins <travis.watkins@linaro.org>
*/
#include "privates.h"
@@ -31,6 +33,13 @@
#include <math.h>
namespace GL {
+ #ifdef USE_GLES
+ EGLCreateImageKHRProc createImage;
+ EGLDestroyImageKHRProc destroyImage;
+
+ GLEGLImageTargetTexture2DOESProc eglImageTargetTexture;
+ #else
+
GLXBindTexImageProc bindTexImage = NULL;
GLXReleaseTexImageProc releaseTexImage = NULL;
GLXQueryDrawableProc queryDrawable = NULL;
@@ -42,10 +51,6 @@ namespace GL {
GLXCreatePixmapProc createPixmap = NULL;
GLXDestroyPixmapProc destroyPixmap = NULL;
- GLActiveTextureProc activeTexture = NULL;
- GLClientActiveTextureProc clientActiveTexture = NULL;
- GLMultiTexCoord2fProc multiTexCoord2f = NULL;
-
GLGenProgramsProc genPrograms = NULL;
GLDeleteProgramsProc deletePrograms = NULL;
GLBindProgramProc bindProgram = NULL;
@@ -53,6 +58,11 @@ namespace GL {
GLProgramParameter4fProc programEnvParameter4f = NULL;
GLProgramParameter4fProc programLocalParameter4f = NULL;
GLGetProgramivProc getProgramiv = NULL;
+ #endif
+
+ GLActiveTextureProc activeTexture = NULL;
+ GLClientActiveTextureProc clientActiveTexture = NULL;
+ GLMultiTexCoord2fProc multiTexCoord2f = NULL;
GLGenFramebuffersProc genFramebuffers = NULL;
GLDeleteFramebuffersProc deleteFramebuffers = NULL;
@@ -61,6 +71,12 @@ namespace GL {
GLFramebufferTexture2DProc framebufferTexture2D = NULL;
GLGenerateMipmapProc generateMipmap = NULL;
+ GLBindBufferProc bindBuffer = NULL;
+ GLDeleteBuffersProc deleteBuffers = NULL;
+ GLGenBuffersProc genBuffers = NULL;
+ GLBufferDataProc bufferData = NULL;
+ GLBufferSubDataProc bufferSubData = NULL;
+
bool textureFromPixmap = true;
bool textureRectangle = false;
bool textureNonPowerOfTwo = false;
@@ -70,6 +86,7 @@ namespace GL {
bool textureCompression = false;
GLint maxTextureSize = 0;
bool fbo = false;
+ bool vbo = false;
bool fragmentProgram = false;
GLint maxTextureUnits = 1;
@@ -83,6 +100,179 @@ GLScreen::GLScreen (CompScreen *s) :
PluginClassHandler<GLScreen, CompScreen, COMPIZ_OPENGL_ABI> (s),
priv (new PrivateGLScreen (this))
{
+ #ifdef USE_GLES
+ Display *xdpy;
+ Window overlay;
+ EGLDisplay dpy;
+ EGLConfig config;
+ EGLint major, minor;
+ const char *eglExtensions, *glExtensions;
+ XWindowAttributes attr;
+ EGLint count, visualid;
+ EGLConfig configs[1024];
+ CompOption::Vector o (0);
+
+ const EGLint config_attribs[] = {
+ EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
+ EGL_RED_SIZE, 1,
+ EGL_GREEN_SIZE, 1,
+ EGL_BLUE_SIZE, 1,
+ EGL_ALPHA_SIZE, 0,
+ EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
+ EGL_CONFIG_CAVEAT, EGL_NONE,
+ EGL_NONE,
+ };
+
+ const EGLint context_attribs[] = {
+ EGL_CONTEXT_CLIENT_VERSION, 2,
+ EGL_NONE
+ };
+
+ xdpy = s->dpy ();
+ dpy = eglGetDisplay ((EGLNativeDisplayType)xdpy);
+ if (!eglInitialize (dpy, &major, &minor))
+ {
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ eglBindAPI (EGL_OPENGL_ES_API);
+
+ if (!eglChooseConfig (dpy, config_attribs, configs, 1024, &count))
+ {
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ if (!XGetWindowAttributes (xdpy, s->root (), &attr))
+ {
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ visualid = XVisualIDFromVisual (attr.visual);
+ config = configs[0];
+ for (int i = 0; i < count; i++) {
+ EGLint val;
+ eglGetConfigAttrib (dpy, configs[i], EGL_NATIVE_VISUAL_ID, &val);
+ if (visualid == val) {
+ config = configs[i];
+ break;
+ }
+ }
+
+ overlay = CompositeScreen::get (s)->overlay ();
+ priv->surface = eglCreateWindowSurface (dpy, config, overlay, 0);
+ if (priv->surface == EGL_NO_SURFACE)
+ {
+ compLogMessage ("opengl", CompLogLevelFatal,
+ "eglCreateWindowSurface failed");
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ priv->ctx = eglCreateContext (dpy, config, EGL_NO_CONTEXT, context_attribs);
+ if (priv->ctx == EGL_NO_CONTEXT)
+ {
+ compLogMessage ("opengl", CompLogLevelFatal, "eglCreateContext failed");
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ if (!eglMakeCurrent (dpy, priv->surface, priv->surface, priv->ctx))
+ {
+ compLogMessage ("opengl", CompLogLevelFatal,
+ "eglMakeCurrent failed");
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ eglExtensions = (const char *) eglQueryString (dpy, EGL_EXTENSIONS);
+ glExtensions = (const char *) glGetString (GL_EXTENSIONS);
+
+ if (!glExtensions || !eglExtensions)
+ {
+ compLogMessage ("opengl", CompLogLevelFatal,
+ "No valid GL extensions string found.");
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+ GL::textureFromPixmap = true;
+ GL::textureNonPowerOfTwo = true;
+ GL::fbo = true;
+ GL::vbo = true;
+ GL::maxTextureUnits = 4;
+ glGetIntegerv (GL_MAX_TEXTURE_SIZE, &GL::maxTextureSize);
+
+ GL::createImage = (GL::EGLCreateImageKHRProc)
+ eglGetProcAddress ("eglCreateImageKHR");
+ GL::destroyImage = (GL::EGLDestroyImageKHRProc)
+ eglGetProcAddress ("eglDestroyImageKHR");
+ GL::eglImageTargetTexture = (GL::GLEGLImageTargetTexture2DOESProc)
+ eglGetProcAddress ("glEGLImageTargetTexture2DOES");
+
+ if (!strstr (eglExtensions, "EGL_KHR_image_pixmap") ||
+ !strstr (glExtensions, "GL_OES_EGL_image") ||
+ !GL::createImage || !GL::destroyImage || !GL::eglImageTargetTexture)
+ {
+ compLogMessage ("opengl", CompLogLevelFatal,
+ "GL_OES_EGL_image is missing");
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+
+// work around efika supporting GL_BGRA directly instead of via this extension
+#ifndef GL_BGRA
+ if (!strstr (glExtensions, "GL_EXT_texture_format_BGRA8888"))
+ {
+ compLogMessage ("opengl", CompLogLevelFatal,
+ "GL_EXT_texture_format_BGRA8888 is missing");
+ screen->handleCompizEvent ("opengl", "fatal_fallback", o);
+ setFailed ();
+ return;
+ }
+#endif
+
+ GL::activeTexture = glActiveTexture;
+ GL::genFramebuffers = glGenFramebuffers;
+ GL::deleteFramebuffers = glDeleteFramebuffers;
+ GL::bindFramebuffer = glBindFramebuffer;
+ GL::checkFramebufferStatus = glCheckFramebufferStatus;
+ GL::framebufferTexture2D = glFramebufferTexture2D;
+ GL::generateMipmap = glGenerateMipmap;
+
+ GL::bindBuffer = glBindBuffer;
+ GL::deleteBuffers = glDeleteBuffers;
+ GL::genBuffers = glGenBuffers;
+ GL::bufferData = glBufferData;
+ GL::bufferSubData = glBufferSubData;
+
+ glClearColor (0.0, 0.0, 0.0, 1.0);
+ glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
+ glEnable (GL_CULL_FACE);
+
+ priv->updateView ();
+
+ priv->lighting = false;
+
+ priv->filter[NOTHING_TRANS_FILTER] = GLTexture::Fast;
+ priv->filter[SCREEN_TRANS_FILTER] = GLTexture::Good;
+ priv->filter[WINDOW_TRANS_FILTER] = GLTexture::Good;
+
+ if (GL::textureFromPixmap)
+ registerBindPixmap (EglTexture::bindPixmapToTexture);
+
+ #else
+
Display *dpy = s->dpy ();
XVisualInfo templ;
XVisualInfo *visinfo;
@@ -359,6 +549,27 @@ GLScreen::GLScreen (CompScreen *s) :
GL::fbo = true;
}
+ if (strstr (glExtensions, "GL_ARB_vertex_buffer_object"))
+ {
+ GL::bindBuffer = (GL::GLBindBufferProc)
+ getProcAddress ("glBindBufferARB");
+ GL::deleteBuffers = (GL::GLDeleteBuffersProc)
+ getProcAddress ("glDeleteBuffersARB");
+ GL::genBuffers = (GL::GLGenBuffersProc)
+ getProcAddress ("glGenBuffersARB");
+ GL::bufferData = (GL::GLBufferDataProc)
+ getProcAddress ("glBufferDataARB");
+ GL::bufferSubData = (GL::GLBufferSubDataProc)
+ getProcAddress ("glBufferSubDataARB");
+
+ if (GL::bindBuffer &&
+ GL::deleteBuffers &&
+ GL::genBuffers &&
+ GL::bufferData &&
+ GL::bufferSubData)
+ GL::vbo = true;
+ }
+
if (strstr (glExtensions, "GL_ARB_texture_compression"))
GL::textureCompression = true;
@@ -495,7 +706,6 @@ GLScreen::GLScreen (CompScreen *s) :
glClearColor (0.0, 0.0, 0.0, 1.0);
glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
glEnable (GL_CULL_FACE);
- glDisable (GL_BLEND);
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glColor4usv (defaultColor);
glEnableClientState (GL_VERTEX_ARRAY);
@@ -530,14 +740,27 @@ GLScreen::GLScreen (CompScreen *s) :
if (GL::textureFromPixmap)
registerBindPixmap (TfpTexture::bindPixmapToTexture);
-
+ #endif
}
GLScreen::~GLScreen ()
{
if (priv->hasCompositing)
CompositeScreen::get (screen)->unregisterPaintHandler ();
+
+ #ifdef USE_GLES
+ Display *xdpy = screen->dpy ();
+ EGLDisplay dpy = eglGetDisplay (xdpy);
+
+ eglMakeCurrent (dpy, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
+ eglDestroyContext (dpy, priv->ctx);
+ eglDestroySurface (dpy, priv->surface);
+ eglTerminate (dpy);
+ eglReleaseThread ();
+ #else
+
glXDestroyContext (screen->dpy (), priv->ctx);
+ #endif
delete priv;
}
@@ -548,20 +771,24 @@ PrivateGLScreen::PrivateGLScreen (GLScreen *gs) :
backgroundTextures (),
backgroundLoaded (false),
rasterPos (0, 0),
- fragmentStorage (),
+ projection (NULL),
clearBuffers (true),
lighting (false),
+ #ifndef USE_GLES
getProcAddress (0),
+ #endif
outputRegion (),
pendingCommands (false),
bindPixmap (),
- hasCompositing (false)
+ hasCompositing (false),
+ programCache (new GLProgramCache (30))
{
ScreenInterface::setHandler (screen);
}
PrivateGLScreen::~PrivateGLScreen ()
{
+ delete programCache;
}
GLushort defaultColor[4] = { 0xffff, 0xffff, 0xffff, 0xffff };
@@ -616,8 +843,13 @@ PrivateGLScreen::handleEvent (XEvent *event)
{
XDamageNotifyEvent *de = (XDamageNotifyEvent *) event;
+ #ifdef USE_GLES
+ std::map<Damage, EglTexture*>::iterator it =
+ boundPixmapTex.find (de->damage);
+ #else
std::map<Damage, TfpTexture*>::iterator it =
boundPixmapTex.find (de->damage);
+ #endif
if (it != boundPixmapTex.end ())
{
it->second->damaged = true;
@@ -681,22 +913,32 @@ perspective (GLfloat *m,
void
PrivateGLScreen::updateView ()
{
+ GLfloat projection_array[16];
+
+ #ifndef USE_GLES
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
glMatrixMode (GL_MODELVIEW);
glLoadIdentity ();
glDepthRange (0, 1);
- glViewport (-1, -1, 2, 2);
glRasterPos2f (0, 0);
+ #endif
+ glViewport (-1, -1, 2, 2);
rasterPos = CompPoint (0, 0);
- perspective (projection, 60.0f, 1.0f, 0.1f, 100.0f);
+ perspective (projection_array, 60.0f, 1.0f, 0.1f, 100.0f);
+
+ if (projection != NULL)
+ delete projection;
+ projection = new GLMatrix (projection_array);
+ #ifndef USE_GLES
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
- glMultMatrixf (projection);
+ glMultMatrixf (projection_array);
glMatrixMode (GL_MODELVIEW);
+ #endif
CompRegion region (screen->region ());
/* remove all output regions from visible screen region */
@@ -718,6 +960,7 @@ PrivateGLScreen::outputChangeNotify ()
updateView ();
}
+#ifndef USE_GLES
GL::FuncPtr
GLScreen::getProcAddress (const char *name)
{
@@ -743,6 +986,7 @@ GLScreen::getProcAddress (const char *name)
return funcPtr;
}
+#endif
void
PrivateGLScreen::updateScreenBackground ()
@@ -836,15 +1080,18 @@ PrivateGLScreen::updateScreenBackground ()
void
GLScreen::setTexEnvMode (GLenum mode)
{
+ #ifndef USE_GLES
if (priv->lighting)
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
else
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, mode);
+ #endif
}
void
GLScreen::setLighting (bool lighting)
{
+ #ifndef USE_GLES
if (priv->lighting != lighting)
{
if (!priv->optionGetLighting ())
@@ -865,6 +1112,7 @@ GLScreen::setLighting (bool lighting)
setTexEnvMode (GL_REPLACE);
}
+ #endif
}
bool
@@ -900,6 +1148,19 @@ void
GLScreenInterface::glDisableOutputClipping ()
WRAPABLE_DEF (glDisableOutputClipping)
+GLMatrix *
+GLScreenInterface::projectionMatrix ()
+ WRAPABLE_DEF (projectionMatrix)
+
+
+GLMatrix *
+GLScreen::projectionMatrix ()
+{
+ WRAPABLE_HND_FUNC_RETURN (5, GLMatrix *, projectionMatrix)
+
+ return priv->projection;
+}
+
void
GLScreen::updateBackground ()
{
@@ -930,17 +1191,13 @@ GLScreen::setFilter (int num, GLTexture::Filter filter)
priv->filter[num] = filter;
}
-GLFragment::Storage *
-GLScreen::fragmentStorage ()
-{
- return &priv->fragmentStorage;
-}
-
+#ifndef USE_GLES
GLFBConfig*
GLScreen::glxPixmapFBConfig (unsigned int depth)
{
return &priv->glxPixmapFBConfigs[depth];
}
+#endif
void
GLScreen::clearOutput (CompOutput *output,
@@ -953,16 +1210,13 @@ GLScreen::clearOutput (CompOutput *output,
pBox->x2 != (int) screen->width () ||
pBox->y2 != (int) screen->height ())
{
- glPushAttrib (GL_SCISSOR_BIT);
-
glEnable (GL_SCISSOR_TEST);
glScissor (pBox->x1,
screen->height () - pBox->y2,
pBox->x2 - pBox->x1,
pBox->y2 - pBox->y1);
glClear (mask);
-
- glPopAttrib ();
+ glDisable (GL_SCISSOR_TEST);
}
else
{
@@ -985,9 +1239,24 @@ GLScreen::setDefaultViewport ()
priv->lastViewport.height);
}
+#ifdef USE_GLES
+EGLContext
+GLScreen::getEGLContext ()
+{
+ return priv->ctx;
+}
+#endif
+
+GLProgram *
+GLScreen::getProgram (std::list<GLShaderData*> shaders)
+{
+ return (*priv->programCache)(shaders);
+}
+
void
PrivateGLScreen::waitForVideoSync ()
{
+#ifndef USE_GLES
unsigned int sync;
if (!optionGetSyncToVblank ())
@@ -1000,6 +1269,7 @@ PrivateGLScreen::waitForVideoSync ()
(*GL::getVideoSync) (&sync);
(*GL::waitVideoSync) (2, (sync + 1) % 2, &sync);
}
+#endif
}
void
@@ -1073,6 +1343,23 @@ PrivateGLScreen::paintOutputs (CompOutput::ptrList &outputs,
waitForVideoSync ();
+ #ifdef USE_GLES
+ Display *xdpy = screen->dpy ();
+
+ glFlush ();
+ if (mask & COMPOSITE_SCREEN_DAMAGE_ALL_MASK)
+ {
+ eglSwapBuffers (eglGetDisplay (xdpy), surface);
+ }
+ else
+ {
+ #warning use proper extension for this
+ eglSwapBuffers (eglGetDisplay (xdpy), surface);
+ }
+ eglWaitGL ();
+ XFlush (xdpy);
+
+ #else
if (mask & COMPOSITE_SCREEN_DAMAGE_ALL_MASK)
{
glXSwapBuffers (screen->dpy (), cScreen->output ());
@@ -1132,12 +1419,17 @@ PrivateGLScreen::paintOutputs (CompOutput::ptrList &outputs,
glFlush ();
}
}
+ #endif
}
bool
PrivateGLScreen::hasVSync ()
{
+ #ifdef USE_GLES
+ return false;
+ #else
return (GL::getVideoSync && optionGetSyncToVblank ());
+ #endif
}
void
@@ -1207,13 +1499,10 @@ GLScreen::defaultIcon ()
void
GLScreen::resetRasterPos ()
{
+ #ifndef USE_GLES
glRasterPos2f (0, 0);
+ #endif
priv->rasterPos.setX (0);
priv->rasterPos.setY (0);
}
-const float *
-GLScreen::projectionMatrix ()
-{
- return priv->projection;
-}
diff --git a/plugins/opengl/src/shaders.h b/plugins/opengl/src/shaders.h
new file mode 100644
index 0000000..9ed4032
--- /dev/null
+++ b/plugins/opengl/src/shaders.h
@@ -0,0 +1,130 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#ifndef _COMPIZ_GLSHADERS_H
+#define _COMPIZ_GLSHADERS_H
+
+static std::string vertex_shader = " \n\
+#ifdef GL_ES \n\
+precision mediump float; \n\
+#endif \n\
+ \n\
+uniform vec3 singleNormal; \n\
+uniform mat4 modelview; \n\
+uniform mat4 projection; \n\
+ \n\
+attribute vec3 normal; \n\
+attribute vec4 color; \n\
+attribute vec2 texCoord0; \n\
+attribute vec2 texCoord1; \n\
+attribute vec2 texCoord2; \n\
+attribute vec2 texCoord3; \n\
+attribute vec3 position; \n\
+ \n\
+@VERTEX_FUNCTIONS@ \n\
+ \n\
+varying vec4 vColor; \n\
+varying vec2 vTexCoord0; \n\
+varying vec2 vTexCoord1; \n\
+varying vec2 vTexCoord2; \n\
+varying vec2 vTexCoord3; \n\
+ \n\
+void main () { \n\
+ vTexCoord0 = texCoord0; \n\
+ vTexCoord1 = texCoord1; \n\
+ vTexCoord2 = texCoord2; \n\
+ vTexCoord3 = texCoord3; \n\
+ vColor = color; \n\
+ \n\
+ gl_Position = projection * modelview * vec4(position, 1.0); \n\
+ \n\
+ @VERTEX_FUNCTION_CALLS@ \n\
+ \n\
+}";
+
+
+//params is a 4-part system for determining how to draw the scene
+// - x is whether or not to use a single color for drawing
+// - y is whether or not to use the varying color for drawing
+// - z is the number of texture units to use
+// - w is the blend mode to use
+
+//paintAttrib is a list of opacity, brightness, and saturation values
+// - x is opacity
+// - y is brightness
+// - z is saturation
+
+static std::string fragment_shader = " \n\
+#ifdef GL_ES \n\
+precision mediump float; \n\
+#endif \n\
+ \n\
+uniform vec4 params; \n\
+uniform vec3 paintAttrib; \n\
+ \n\
+uniform sampler2D texture0; \n\
+uniform sampler2D texture1; \n\
+uniform sampler2D texture2; \n\
+uniform sampler2D texture3; \n\
+ \n\
+uniform vec4 singleColor; \n\
+ \n\
+varying vec4 vColor; \n\
+varying vec2 vTexCoord0; \n\
+varying vec2 vTexCoord1; \n\
+varying vec2 vTexCoord2; \n\
+varying vec2 vTexCoord3; \n\
+ \n\
+@FRAGMENT_FUNCTIONS@ \n\
+ \n\
+void main () { \n\
+ vec4 color = vec4 (1, 1, 1, 1); \n\
+ \n\
+ if (params.x == 1.0) \n\
+ color *= singleColor; \n\
+ if (params.y == 1.0) \n\
+ color *= vColor; \n\
+ \n\
+ if (params.z == 0.25) \n\
+ color *= texture2D (texture0, vTexCoord0); \n\
+ \n\
+ if (paintAttrib.z != 1.0) \n\
+ { \n\
+ vec3 desaturated = color.rgb * vec3 (0.30, 0.59, 0.11); \n\
+ desaturated = vec3 (dot (desaturated, color.rgb)); \n\
+ color.rgb = color.rgb * vec3 (paintAttrib.z) + desaturated * \n\
+ vec3 (1.0 - paintAttrib.z); \n\
+ } \n\
+ \n\
+ color.rgb = color.rgb * paintAttrib.x * paintAttrib.y; \n\
+ color.a = color.a * paintAttrib.x; \n\
+ \n\
+ gl_FragColor = color; \n\
+ \n\
+ @FRAGMENT_FUNCTION_CALLS@ \n\
+}";
+
+#endif // _COMPIZ_GLSHADERS_H
+
diff --git a/plugins/opengl/src/texture.cpp b/plugins/opengl/src/texture.cpp
index 3c4ddcf..a1e4fe3 100644
--- a/plugins/opengl/src/texture.cpp
+++ b/plugins/opengl/src/texture.cpp
@@ -38,7 +38,11 @@
#include <privatetexture.h>
#include "privates.h"
+#ifdef USE_GLES
+std::map<Damage, EglTexture*> boundPixmapTex;
+#else
std::map<Damage, TfpTexture*> boundPixmapTex;
+#endif
static GLTexture::Matrix _identity_matrix = {
1.0f, 0.0f,
@@ -166,7 +170,9 @@ void
GLTexture::enable (GLTexture::Filter filter)
{
GLScreen *gs = GLScreen::get (screen);
+#ifndef USE_GLES
glEnable (priv->target);
+#endif
glBindTexture (priv->target, priv->name);
if (filter == Fast)
@@ -229,7 +235,7 @@ GLTexture::enable (GLTexture::Filter filter)
{
if (priv->initial)
{
- (*GL::generateMipmap) (priv->target);
+ GL::generateMipmap (priv->target);
priv->initial = false;
}
}
@@ -239,7 +245,9 @@ void
GLTexture::disable ()
{
glBindTexture (priv->target, 0);
+#ifndef USE_GLES
glDisable (priv->target);
+#endif
}
void
@@ -303,6 +311,13 @@ PrivateTexture::loadImageData (const char *image,
GLenum target;
bool mipmap;
+ #ifdef USE_GLES
+ target = GL_TEXTURE_2D;
+ matrix.xx = 1.0f / width;
+ matrix.yy = 1.0f / height;
+ matrix.y0 = 0.0f;
+ mipmap = true;
+ #else
if (GL::textureNonPowerOfTwo ||
(POWER_OF_TWO (width) && POWER_OF_TWO (height)))
@@ -321,17 +336,25 @@ PrivateTexture::loadImageData (const char *image,
matrix.y0 = 0.0f;
mipmap = false;
}
+ #endif
t->setData (target, matrix, mipmap);
t->setGeometry (0, 0, width, height);
glBindTexture (target, t->name ());
+ #ifdef USE_GLES
+// internalFormat = GL_BGRA;
+ internalFormat = GL_BGRA;
+ #else
+ internalFormat = GL_RGBA;
+ #endif
+
+ #ifndef USE_GLES
opt = GLScreen::get (screen)->getOption ("texture_compression");
if (opt->value ().b () && GL::textureCompression)
internalFormat = GL_COMPRESSED_RGBA_ARB;
- else
- internalFormat = GL_RGBA;
+ #endif
glTexImage2D (target, 0, internalFormat, width, height, 0,
format, type, image);
@@ -416,6 +439,104 @@ GLTexture::bindPixmapToTexture (Pixmap pixmap,
return GLTexture::List ();
}
+#ifdef USE_GLES
+EglTexture::EglTexture () :
+ damaged (true),
+ damage (None),
+ updateMipMap (true)
+{
+}
+
+EglTexture::~EglTexture ()
+{
+ GLuint temp = name ();
+ glBindTexture (target (), name ());
+
+ glDeleteTextures (1, &temp);
+
+ glBindTexture (target (), 0);
+
+ boundPixmapTex.erase (damage);
+ XDamageDestroy (screen->dpy (), damage);
+}
+
+GLTexture::List
+EglTexture::bindPixmapToTexture (Pixmap pixmap,
+ int width,
+ int height,
+ int depth)
+{
+ if ((int) width > GL::maxTextureSize || (int) height > GL::maxTextureSize ||
+ !GL::textureFromPixmap)
+ return GLTexture::List ();
+
+ GLTexture::List rv (1);
+ EglTexture *tex = NULL;
+ EGLImageKHR eglImage = NULL;
+ GLTexture::Matrix matrix = _identity_matrix;
+
+ const EGLint img_attribs[] = {
+ EGL_IMAGE_PRESERVED_KHR, EGL_TRUE,
+ EGL_NONE
+ };
+
+ eglImage = GL::createImage (eglGetDisplay (screen->dpy ()),
+ EGL_NO_CONTEXT, EGL_NATIVE_PIXMAP_KHR,
+ (EGLClientBuffer)pixmap, img_attribs);
+
+ if (eglImage == EGL_NO_IMAGE_KHR)
+ {
+ compLogMessage ("core", CompLogLevelWarn,
+ "eglCreateImageKHR failed");
+
+ return GLTexture::List ();
+ }
+
+ matrix.xx = 1.0f / width;
+ matrix.yy = 1.0f / height;
+ matrix.y0 = 0.0f;
+
+ tex = new EglTexture ();
+ tex->setData (GL_TEXTURE_2D, matrix, true);
+ tex->setGeometry (0, 0, width, height);
+
+ rv[0] = tex;
+
+ glBindTexture (GL_TEXTURE_2D, tex->name ());
+
+ GL::eglImageTargetTexture (GL_TEXTURE_2D, (GLeglImageOES)eglImage);
+ GL::destroyImage (eglGetDisplay (screen->dpy ()), eglImage);
+
+ tex->setFilter (GL_NEAREST);
+ tex->setWrap (GL_CLAMP_TO_EDGE);
+
+ glBindTexture (GL_TEXTURE_2D, 0);
+
+ tex->damage = XDamageCreate (screen->dpy (), pixmap,
+ XDamageReportRawRectangles);
+ boundPixmapTex[tex->damage] = tex;
+
+ return rv;
+}
+
+void
+EglTexture::enable (GLTexture::Filter filter)
+{
+ glBindTexture (target (), name ());
+ GLTexture::enable (filter);
+
+ if (damaged)
+ updateMipMap = true;
+
+ if (this->filter () == GL_LINEAR_MIPMAP_LINEAR && updateMipMap)
+ {
+ GL::generateMipmap (target ());
+ updateMipMap = false;
+ }
+ damaged = false;
+}
+#else
+
TfpTexture::TfpTexture () :
pixmap (0),
damaged (true),
@@ -614,3 +735,5 @@ TfpTexture::enable (GLTexture::Filter filter)
}
damaged = false;
}
+#endif
+
diff --git a/plugins/opengl/src/vertexbuffer.cpp b/plugins/opengl/src/vertexbuffer.cpp
new file mode 100644
index 0000000..d2f59af
--- /dev/null
+++ b/plugins/opengl/src/vertexbuffer.cpp
@@ -0,0 +1,414 @@
+/*
+ * Copyright © 2011 Linaro Ltd.
+ *
+ * Permission to use, copy, modify, distribute, and sell this software
+ * and its documentation for any purpose is hereby granted without
+ * fee, provided that the above copyright notice appear in all copies
+ * and that both that copyright notice and this permission notice
+ * appear in supporting documentation, and that the name of
+ * Linaro Ltd. not be used in advertising or publicity pertaining to
+ * distribution of the software without specific, written prior permission.
+ * Linaro Ltd. makes no representations about the suitability of this
+ * software for any purpose. It is provided "as is" without express or
+ * implied warranty.
+ *
+ * LINARO LTD. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
+ * NO EVENT SHALL LINARO LTD. BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
+ * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * Authors: Travis Watkins <travis.watkins@linaro.org>
+ */
+
+#define GL_GLEXT_PROTOTYPES
+
+#include <vector>
+#include <iostream>
+
+#ifdef USE_GLES
+#include <GLES2/gl2.h>
+#else
+#include <GL/gl.h>
+#include <GL/glext.h>
+#endif
+
+#include <opengl/vertexbuffer.h>
+
+#include "privates.h"
+
+GLVertexBuffer *PrivateVertexBuffer::streamingBuffer = NULL;
+
+GLVertexBuffer::GLVertexBuffer () :
+ priv (new PrivateVertexBuffer ())
+{
+ priv->usage = GL_STATIC_DRAW;
+}
+
+GLVertexBuffer::GLVertexBuffer (GLenum usage) :
+ priv (new PrivateVertexBuffer ())
+{
+ priv->usage = usage;
+}
+
+GLVertexBuffer::~GLVertexBuffer ()
+{
+ delete priv;
+}
+
+GLVertexBuffer *GLVertexBuffer::streamingBuffer ()
+{
+ if (PrivateVertexBuffer::streamingBuffer == NULL)
+ PrivateVertexBuffer::streamingBuffer = new GLVertexBuffer
+ (GL_STREAM_DRAW);
+ return PrivateVertexBuffer::streamingBuffer;
+}
+
+void GLVertexBuffer::begin (GLenum primitiveType)
+{
+ priv->primitiveType = primitiveType;
+
+ priv->vertexData.clear ();
+ priv->normalData.clear ();
+ priv->colorData.clear ();
+ priv->textureData.clear ();
+}
+
+void GLVertexBuffer::begin ()
+{
+ begin (GL_TRIANGLES);
+}
+
+int GLVertexBuffer::end ()
+{
+ if (!GL::vbo)
+ return 0;
+
+ if (!priv->vertexData.size ())
+ return -1;
+
+ GL::bindBuffer (GL_ARRAY_BUFFER, priv->vertexBuffer);
+ GL::bufferData (GL_ARRAY_BUFFER,
+ sizeof(GLfloat) * priv->vertexData.size () * 3,
+ &priv->vertexData[0], priv->usage);
+
+ if (priv->normalData.size ())
+ {
+ GL::bindBuffer (GL_ARRAY_BUFFER, priv->normalBuffer);
+ GL::bufferData (GL_ARRAY_BUFFER,
+ sizeof(GLfloat) * priv->normalData.size () * 3,
+ &priv->normalData[0], priv->usage);
+ }
+
+ if (priv->colorData.size ())
+ {
+ GL::bindBuffer (GL_ARRAY_BUFFER, priv->colorBuffer);
+ GL::bufferData (GL_ARRAY_BUFFER,
+ sizeof(GLfloat) * priv->colorData.size () * 4,
+ &priv->colorData[0], priv->usage);
+ }
+
+ if (priv->textureData.size ())
+ {
+ for (unsigned int i = 0; i < priv->textureData.size (); i++)
+ {
+ GL::bindBuffer (GL_ARRAY_BUFFER, priv->textureBuffers[i]);
+ GL::bufferData (GL_ARRAY_BUFFER,
+ sizeof(GLfloat) * priv->textureData[i].size () * 2,
+ &priv->textureData[i][0], priv->usage);
+ }
+ }
+
+ GL::bindBuffer (GL_ARRAY_BUFFER, 0);
+
+ return 0;
+}
+
+void GLVertexBuffer::addVertices (GLuint nVertices, GLfloat *vertices)
+{
+ priv->vertexData.reserve (priv->vertexData.size () + (nVertices * 3));
+
+ for (GLuint i = 0; i < nVertices * 3; i++)
+ {
+ priv->vertexData.push_back (vertices[i]);
+ }
+}
+
+void GLVertexBuffer::addNormals (GLuint nNormals, GLfloat *normals)
+{
+ priv->normalData.reserve (priv->normalData.size () + (nNormals * 3));
+
+ for (GLuint i = 0; i < nNormals * 3; i++)
+ {
+ priv->normalData.push_back (normals[i]);
+ }
+}
+
+void GLVertexBuffer::addColors (GLuint nColors, GLushort *colors)
+{
+ priv->colorData.reserve (priv->colorData.size () + (nColors * 4));
+
+ for (GLuint i = 0; i < nColors * 4; i++)
+ {
+ priv->colorData.push_back ((colors[i] & 0xFF) / 255.0f);
+ }
+}
+
+void GLVertexBuffer::addTexCoords (GLuint texture,
+ GLuint nTexcoords,
+ GLfloat *texcoords)
+{
+ //four textures max (zero indexed)
+ if (texture > 3)
+ return;
+
+ while (texture >= priv->textureData.size ())
+ {
+ std::vector<GLfloat> temp;
+ priv->textureData.push_back (temp);
+ }
+
+ priv->textureData[texture].reserve (priv->textureData.size () +
+ (nTexcoords * 2));
+
+ for (GLuint i = 0; i < nTexcoords * 2; i++)
+ {
+ priv->textureData[texture].push_back (texcoords[i]);
+ }
+}
+
+void GLVertexBuffer::setProgram (GLProgram *program)
+{
+ priv->program = program;
+}
+
+int GLVertexBuffer::render (const GLMatrix &modelview)
+{
+ const GLWindowPaintAttrib attrib = { OPAQUE, BRIGHT, COLOR, 0, 0, 0, 0 };
+
+ return render (modelview, attrib);
+}
+
+int GLVertexBuffer::render (const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib)
+{
+ GLScreen *gScreen = GLScreen::get (screen);
+ GLMatrix *projection = gScreen->projectionMatrix ();
+
+ return render (*projection, modelview, attrib);
+}
+
+int GLVertexBuffer::render (const GLMatrix &projection,
+ const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib)
+{
+ if (!priv->vertexData.size ())
+ return -1;
+
+ glEnable (GL_BLEND);
+
+ if (GL::vbo)
+ return priv->render (projection, modelview, attrib);
+ else
+ return priv->legacyRender (projection, modelview, attrib);
+
+ glDisable (GL_BLEND);
+}
+
+PrivateVertexBuffer::PrivateVertexBuffer () :
+ program (NULL)
+{
+ if (!GL::vbo)
+ return;
+
+ GL::genBuffers (1, &vertexBuffer);
+ GL::genBuffers (1, &normalBuffer);
+ GL::genBuffers (1, &colorBuffer);
+
+ textureBuffers.reserve (4);
+ GL::genBuffers (4, &textureBuffers[0]);
+}
+
+PrivateVertexBuffer::~PrivateVertexBuffer ()
+{
+ if (!GL::vbo)
+ return;
+
+ GL::deleteBuffers (1, &vertexBuffer);
+ GL::deleteBuffers (1, &normalBuffer);
+ GL::deleteBuffers (1, &colorBuffer);
+ GL::deleteBuffers (4, &textureBuffers[0]);
+}
+
+int PrivateVertexBuffer::render (const GLMatrix &projection,
+ const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib)
+{
+ GLfloat params[4] = {0, 0, 0, 0};
+ GLfloat attribs[3] = {1, 1, 1};
+ GLint index = 0;
+
+ if (program == NULL)
+ {
+ std::cerr << "no program defined!" << std::endl;
+ return -1;
+ }
+
+ program->bind ();
+ if (!program->valid ())
+ {
+ return -1;
+ }
+
+ program->setUniform ("projection", projection);
+ program->setUniform ("modelview", modelview);
+
+ index = program->attributeLocation ("position");
+ glEnableVertexAttribArray (index);
+ GL::bindBuffer (GL_ARRAY_BUFFER, vertexBuffer);
+ glVertexAttribPointer (index, 3, GL_FLOAT, GL_FALSE, 0, 0);
+
+ //use default normal
+ if (normalData.size () == 0)
+ {
+ program->setUniform3f ("singleNormal", 0.0f, 0.0f, -1.0f);
+ }
+ // special case a single normal and apply it to the entire operation
+ else if (normalData.size () == 3)
+ {
+ program->setUniform3f ("singleNormal",
+ normalData[0], normalData[1], normalData[2]);
+ }
+ else if (normalData.size () > 3)
+ {
+ index = program->attributeLocation ("normal");
+ glEnableVertexAttribArray (index);
+ GL::bindBuffer (GL_ARRAY_BUFFER, normalBuffer);
+ glVertexAttribPointer (index, 3, GL_FLOAT, GL_FALSE, 0, 0);
+ }
+
+ // special case a single color and apply it to the entire operation
+ if (colorData.size () == 4)
+ {
+ program->setUniform4f ("singleColor", colorData[0],
+ colorData[1], colorData[2], colorData[3]);
+ params[0] = 1.0;
+ }
+ else if (colorData.size () > 4)
+ {
+ index = program->attributeLocation ("color");
+ glEnableVertexAttribArray (index);
+ GL::bindBuffer (GL_ARRAY_BUFFER, colorBuffer);
+ glVertexAttribPointer (index, 4, GL_FLOAT, GL_FALSE, 0, 0);
+ params[1] = 1.0;
+ }
+
+ //divide number of textures by 4 to get 0-1 range
+ params[2] = textureData.size () / 4.0f;
+
+ for (int i = textureData.size () - 1; i >= 0; i--)
+ {
+ char name[10];
+
+ snprintf (name, 10, "texCoord%d", i);
+ index = program->attributeLocation (name);
+
+ glEnableVertexAttribArray (index);
+ GL::bindBuffer (GL_ARRAY_BUFFER, textureBuffers[i]);
+ glVertexAttribPointer (index, 2, GL_FLOAT, GL_FALSE, 0, 0);
+
+ snprintf (name, 9, "texture%d", i);
+ program->setUniform (name, i);
+ }
+
+ //convert paint attribs to 0-1 range
+ attribs[0] = attrib.opacity / 65535.0f;
+ attribs[1] = attrib.brightness / 65535.0f;
+ attribs[2] = attrib.saturation / 65535.0f;
+ program->setUniform3f ("paintAttrib", attribs[0], attribs[1], attribs[2]);
+
+ program->setUniform4f ("params", params[0], params[1], params[2], params[3]);
+ glDrawArrays (primitiveType, 0, vertexData.size () / 3);
+
+ GL::bindBuffer (GL_ARRAY_BUFFER, 0);
+ program->unbind ();
+
+ return 0;
+}
+
+int PrivateVertexBuffer::legacyRender (const GLMatrix &projection,
+ const GLMatrix &modelview,
+ const GLWindowPaintAttrib &attrib)
+{
+ #ifndef USE_GLES
+ glMatrixMode (GL_PROJECTION);
+ glPushMatrix ();
+ glLoadMatrixf (projection.getMatrix ());
+
+ glMatrixMode (GL_MODELVIEW);
+ glPushMatrix ();
+ glLoadMatrixf (modelview.getMatrix ());
+
+ glEnableClientState (GL_VERTEX_ARRAY);
+ glVertexPointer (3, GL_FLOAT, 0, &vertexData[0]);
+
+ //use default normal
+ if (normalData.size () == 0)
+ {
+ glNormal3f (0.0f, 0.0f, -1.0f);
+ }
+ // special case a single normal and apply it to the entire operation
+ else if (normalData.size () == 3)
+ {
+ glNormal3fv (&normalData[0]);
+ }
+ else if (normalData.size () > 3)
+ {
+ glEnableClientState (GL_NORMAL_ARRAY);
+ glNormalPointer (GL_FLOAT, 0, &normalData[0]);
+ }
+
+ // special case a single color and apply it to the entire operation
+ if (colorData.size () == 4)
+ {
+ glColor4fv (&colorData[0]);
+ }
+ else if (colorData.size () > 4)
+ {
+ glEnableClientState (GL_COLOR_ARRAY);
+ glColorPointer (4, GL_FLOAT, 0, &colorData[0]);
+ }
+
+ for (int i = textureData.size () - 1; i >= 0; i--)
+ {
+ GL::clientActiveTexture (GL_TEXTURE0_ARB + i);
+ glEnableClientState (GL_TEXTURE_COORD_ARRAY);
+ glTexCoordPointer (2, GL_FLOAT, 0, &textureData[i][0]);
+ }
+
+ glDrawArrays (primitiveType, 0, vertexData.size () / 3);
+
+ glDisableClientState (GL_VERTEX_ARRAY);
+ glDisableClientState (GL_NORMAL_ARRAY);
+ glDisableClientState (GL_COLOR_ARRAY);
+
+ for (int i = textureData.size (); i > 0; i--)
+ {
+ GL::clientActiveTexture (GL_TEXTURE0_ARB + i);
+ glDisableClientState (GL_TEXTURE_COORD_ARRAY);
+ }
+
+ GL::clientActiveTexture (GL_TEXTURE0_ARB);
+
+ glMatrixMode (GL_PROJECTION);
+ glPopMatrix ();
+
+ glMatrixMode (GL_MODELVIEW);
+ glPopMatrix ();
+ #endif
+
+ return 0;
+}
+
diff --git a/plugins/opengl/src/window.cpp b/plugins/opengl/src/window.cpp
index 850c109..01fc150 100644
--- a/plugins/opengl/src/window.cpp
+++ b/plugins/opengl/src/window.cpp
@@ -57,7 +57,7 @@ PrivateGLWindow::PrivateGLWindow (CompWindow *w,
updateReg (true),
clip (),
bindFailed (false),
- geometry (),
+ vertexBuffer (new GLVertexBuffer ()),
icons ()
{
paint.xScale = 1.0f;
@@ -71,6 +71,7 @@ PrivateGLWindow::PrivateGLWindow (CompWindow *w,
PrivateGLWindow::~PrivateGLWindow ()
{
+ delete vertexBuffer;
}
void
@@ -132,11 +133,11 @@ GLWindowInterface::glPaint (const GLWindowPaintAttrib &attrib,
WRAPABLE_DEF (glPaint, attrib, transform, region, mask)
bool
-GLWindowInterface::glDraw (const GLMatrix &transform,
- GLFragment::Attrib &fragment,
- const CompRegion &region,
- unsigned int mask)
- WRAPABLE_DEF (glDraw, transform, fragment, region, mask)
+GLWindowInterface::glDraw (const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ const CompRegion &region,
+ unsigned int mask)
+ WRAPABLE_DEF (glDraw, transform, attrib, region, mask)
void
GLWindowInterface::glAddGeometry (const GLTexture::MatrixList &matrix,
@@ -148,14 +149,11 @@ GLWindowInterface::glAddGeometry (const GLTexture::MatrixList &matrix,
maxGridWidth, maxGridHeight)
void
-GLWindowInterface::glDrawTexture (GLTexture *texture,
- GLFragment::Attrib &fragment,
- unsigned int mask)
- WRAPABLE_DEF (glDrawTexture, texture, fragment, mask)
-
-void
-GLWindowInterface::glDrawGeometry ()
- WRAPABLE_DEF (glDrawGeometry)
+GLWindowInterface::glDrawTexture (GLTexture *texture,
+ const GLMatrix &transform,
+ const GLWindowPaintAttrib &attrib,
+ unsigned int mask)
+ WRAPABLE_DEF (glDrawTexture, texture, transform, attrib, mask)
const CompRegion &
GLWindow::clip () const
@@ -223,76 +221,10 @@ GLWindow::updatePaintAttribs ()
priv->paint.saturation = cw->saturation ();
}
-GLWindow::Geometry &
-GLWindow::geometry ()
-{
- return priv->geometry;
-}
-
-GLWindow::Geometry::Geometry () :
- vertices (NULL),
- vertexSize (0),
- vertexStride (0),
- indices (NULL),
- indexSize (0),
- vCount (0),
- texUnits (0),
- texCoordSize (0),
- indexCount (0)
-{
-}
-
-GLWindow::Geometry::~Geometry ()
-{
- if (vertices)
- free (vertices);
-
- if (indices)
- free (indices);
-}
-
-void
-GLWindow::Geometry::reset ()
-{
- vCount = indexCount = 0;
-}
-
-bool
-GLWindow::Geometry::moreVertices (int newSize)
-{
- if (newSize > vertexSize)
- {
- GLfloat *nVertices;
-
- nVertices = (GLfloat *)
- realloc (vertices, sizeof (GLfloat) * newSize);
- if (!nVertices)
- return false;
-
- vertices = nVertices;
- vertexSize = newSize;
- }
-
- return true;
-}
-
-bool
-GLWindow::Geometry::moreIndices (int newSize)
+GLVertexBuffer *
+GLWindow::vertexBuffer ()
{
- if (newSize > indexSize)
- {
- GLushort *nIndices;
-
- nIndices = (GLushort *)
- realloc (indices, sizeof (GLushort) * newSize);
- if (!nIndices)
- return false;
-
- indices = nIndices;
- indexSize = newSize;
- }
-
- return true;
+ return priv->vertexBuffer;
}
const GLTexture::List &
@@ -335,6 +267,19 @@ GLWindow::getIcon (int width, int height)
}
void
+GLWindow::addShaders (std::string name,
+ std::string vertex_shader,
+ std::string fragment_shader)
+{
+ GLShaderData *data = new GLShaderData;
+ data->name = name;
+ data->vertex_shader = vertex_shader;
+ data->fragment_shader = fragment_shader;
+
+ priv->shaders.push_back(data);
+}
+
+void
PrivateGLWindow::updateFrameRegion (CompRegion &region)
{
window->updateFrameRegion (region);
diff --git a/plugins/resize/src/resize.cpp b/plugins/resize/src/resize.cpp
index ac8f671..84cee80 100644
--- a/plugins/resize/src/resize.cpp
+++ b/plugins/resize/src/resize.cpp
@@ -1527,13 +1527,22 @@ ResizeScreen::glPaintRectangle (const GLScreenPaintAttrib &sAttrib,
unsigned short *borderColor,
unsigned short *fillColor)
{
- BoxRec box;
- GLMatrix sTransform (transform);
- GLint origSrc, origDst;
- float_t fc[4], bc[4];
-
+ GLVertexBuffer *streamingBuffer = GLVertexBuffer::streamingBuffer ();
+ BoxRec box;
+ GLMatrix sTransform (transform);
+ GLfloat vertexData[12];
+ GLint origSrc, origDst, origSrcAlpha, origDstAlpha;
+ GLushort fc[4], bc[4];
+
+#ifdef USE_GLES
+ glGetIntegerv (GL_BLEND_SRC_RGB, &origSrc);
+ glGetIntegerv (GL_BLEND_DST_RGB, &origDst);
+ glGetIntegerv (GL_BLEND_SRC_ALPHA, &origSrcAlpha);
+ glGetIntegerv (GL_BLEND_DST_ALPHA, &origDstAlpha);
+#else
glGetIntegerv (GL_BLEND_SRC, &origSrc);
glGetIntegerv (GL_BLEND_DST, &origDst);
+#endif
/* Premultiply the alpha values */
@@ -1544,43 +1553,58 @@ ResizeScreen::glPaintRectangle (const GLScreenPaintAttrib &sAttrib,
getPaintRectangle (&box);
- glPushMatrix ();
+ vertexData[0] = box.x1;
+ vertexData[1] = box.y1;
+ vertexData[2] = 0.0f;
+ vertexData[3] = box.x1;
+ vertexData[4] = box.y2;
+ vertexData[5] = 0.0f;
+ vertexData[6] = box.x2;
+ vertexData[7] = box.y1;
+ vertexData[8] = 0.0f;
+ vertexData[9] = box.x2;
+ vertexData[10] = box.y2;
+ vertexData[11] = 0.0f;
sTransform.toScreenSpace (output, -DEFAULT_Z_CAMERA);
- glLoadMatrixf (sTransform.getMatrix ());
-
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
- glEnable (GL_BLEND);
glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
/* fill rectangle */
if (fillColor)
{
- fc[3] = (float) fillColor[3] / (float) 65535.0f;
- fc[0] = ((float) fillColor[0] / 65535.0f) * fc[3];
- fc[1] = ((float) fillColor[1] / 65535.0f) * fc[3];
- fc[2] = ((float) fillColor[2] / 65535.0f) * fc[3];
+ fc[3] = fillColor[3];
+ fc[0] = fillColor[0] * fc[3];
+ fc[1] = fillColor[1] * fc[3];
+ fc[2] = fillColor[2] * fc[3];
+
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+ streamingBuffer->addColors (1, fc);
+ streamingBuffer->addVertices (4, vertexData);
- glColor4f (fc[0], fc[1], fc[2], fc[3]);
- glRecti (box.x1, box.y2, box.x2, box.y1);
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
}
/* draw outline */
- glColor4f (bc[0], bc[1], bc[2], bc[3]);
glLineWidth (2.0);
- glBegin (GL_LINE_LOOP);
- glVertex2i (box.x1, box.y1);
- glVertex2i (box.x2, box.y1);
- glVertex2i (box.x2, box.y2);
- glVertex2i (box.x1, box.y2);
- glEnd ();
-
- /* clean up */
- glColor4usv (defaultColor);
- glDisable (GL_BLEND);
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
- glPopMatrix ();
+ streamingBuffer->begin (GL_LINE_LOOP);
+
+ streamingBuffer->addColors (1, borderColor);
+
+ vertexData[7] = box.y2;
+ vertexData[10] = box.y1;
+ streamingBuffer->addVertices (4, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (sTransform);
+
+#ifdef USE_GLES
+ glBlendFuncSeparate (origSrc, origDst,
+ origSrcAlpha, origDstAlpha);
+#else
+ glBlendFunc (origSrc, origDst);
+#endif
}
bool
@@ -1643,9 +1667,9 @@ ResizeWindow::glPaint (const GLWindowPaintAttrib &attrib,
status = gWindow->glPaint (attrib, transform, region,
mask | PAINT_WINDOW_NO_CORE_INSTANCE_MASK);
- GLFragment::Attrib fragment (gWindow->lastPaintAttrib ());
+ GLWindowPaintAttrib lastAttrib (gWindow->lastPaintAttrib ());
- if (window->alpha () || fragment.getOpacity () != OPAQUE)
+ if (window->alpha () || lastAttrib.opacity != OPAQUE)
mask |= PAINT_WINDOW_TRANSLUCENT_MASK;
rScreen->getPaintRectangle (&box);
@@ -1663,13 +1687,8 @@ ResizeWindow::glPaint (const GLWindowPaintAttrib &attrib,
(rScreen->geometry.y - y) / yScale - yOrigin,
0.0f);
- glPushMatrix ();
- glLoadMatrixf (wTransform.getMatrix ());
-
- gWindow->glDraw (wTransform, fragment, region,
+ gWindow->glDraw (wTransform, lastAttrib, region,
mask | PAINT_WINDOW_TRANSFORMED_MASK);
-
- glPopMatrix ();
}
else
{
diff --git a/plugins/rotate/CMakeLists.txt b/plugins/rotate/CMakeLists.txt
index bda1446..05a9a8f 100644
--- a/plugins/rotate/CMakeLists.txt
+++ b/plugins/rotate/CMakeLists.txt
@@ -2,4 +2,4 @@ find_package (Compiz REQUIRED)
include (CompizPlugin)
-compiz_plugin(rotate PLUGINDEPS composite opengl cube) \ No newline at end of file
+#compiz_plugin(rotate PLUGINDEPS composite opengl cube)
diff --git a/plugins/scale/src/scale.cpp b/plugins/scale/src/scale.cpp
index 5ada86c..3b7a813 100644
--- a/plugins/scale/src/scale.cpp
+++ b/plugins/scale/src/scale.cpp
@@ -226,26 +226,19 @@ ScaleWindow::scalePaintDecoration (const GLWindowPaintAttrib& attrib,
GLTexture::MatrixList ml (1);
ml[0] = icon->matrix ();
- priv->gWindow->geometry ().reset ();
+ priv->gWindow->vertexBuffer ()->begin ();
if (width && height)
priv->gWindow->glAddGeometry (ml, iconReg, iconReg);
- if (priv->gWindow->geometry ().vCount)
- {
- GLFragment::Attrib fragment (sAttrib);
- GLMatrix wTransform (transform);
-
- wTransform.scale (scale, scale, 1.0f);
- wTransform.translate (x / scale, y / scale, 0.0f);
+ priv->gWindow->vertexBuffer ()->end ();
- glPushMatrix ();
- glLoadMatrixf (wTransform.getMatrix ());
+ GLMatrix wTransform (transform);
- priv->gWindow->glDrawTexture (icon, fragment, mask);
+ wTransform.scale (scale, scale, 1.0f);
+ wTransform.translate (x / scale, y / scale, 0.0f);
- glPopMatrix ();
- }
+ priv->gWindow->glDrawTexture (icon, wTransform, sAttrib, mask);
}
}
}
@@ -327,13 +320,13 @@ PrivateScaleWindow::glPaint (const GLWindowPaintAttrib& attrib,
if (scaled)
{
- GLFragment::Attrib fragment (gWindow->lastPaintAttrib ());
+ GLWindowPaintAttrib lastAttrib (gWindow->lastPaintAttrib ());
GLMatrix wTransform (transform);
if (mask & PAINT_WINDOW_OCCLUSION_DETECTION_MASK)
return false;
- if (window->alpha () || fragment.getOpacity () != OPAQUE)
+ if (window->alpha () || lastAttrib.opacity != OPAQUE)
mask |= PAINT_WINDOW_TRANSLUCENT_MASK;
wTransform.translate (window->x (), window->y (), 0.0f);
@@ -341,14 +334,9 @@ PrivateScaleWindow::glPaint (const GLWindowPaintAttrib& attrib,
wTransform.translate (tx / scale - window->x (),
ty / scale - window->y (), 0.0f);
- glPushMatrix ();
- glLoadMatrixf (wTransform.getMatrix ());
-
- gWindow->glDraw (wTransform, fragment, region,
+ gWindow->glDraw (wTransform, lastAttrib, region,
mask | PAINT_WINDOW_TRANSFORMED_MASK);
- glPopMatrix ();
-
sWindow->scalePaintDecoration (sAttrib, transform, region, mask);
}
}
diff --git a/plugins/screenshot/src/screenshot.cpp b/plugins/screenshot/src/screenshot.cpp
index 2ba0a01..f0aae91 100644
--- a/plugins/screenshot/src/screenshot.cpp
+++ b/plugins/screenshot/src/screenshot.cpp
@@ -238,6 +238,10 @@ ShotScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
CompOutput *output,
unsigned int mask)
{
+ GLVertexBuffer *streamingBuffer = GLVertexBuffer::streamingBuffer ();
+ GLMatrix transform (matrix);
+ GLfloat vertexData[12];
+ GLushort colorData[4];
bool status;
status = gScreen->glPaintOutput (attrib, matrix, region, output, mask);
@@ -253,31 +257,52 @@ ShotScreen::glPaintOutput (const GLScreenPaintAttrib &attrib,
if (mGrabIndex)
{
- glPushMatrix ();
-
- glTranslatef (-0.5f, -0.5f, -DEFAULT_Z_CAMERA);
- glScalef (1.0f / output->width (),
- -1.0f / output->height (),
- 1.0f);
- glTranslatef (-output->region ()->extents.x1,
- -output->region ()->extents.y2,
- 0.0f);
-
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
- glEnable (GL_BLEND);
- glColor4us (0x2fff, 0x2fff, 0x4fff, 0x4fff);
- glRecti (x1, y2, x2, y1);
- glColor4us (0x2fff, 0x2fff, 0x4fff, 0x9fff);
- glBegin (GL_LINE_LOOP);
- glVertex2i (x1, y1);
- glVertex2i (x2, y1);
- glVertex2i (x2, y2);
- glVertex2i (x1, y2);
- glEnd ();
- glColor4usv (defaultColor);
- glDisable (GL_BLEND);
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
- glPopMatrix ();
+ vertexData[0] = x1;
+ vertexData[1] = y1;
+ vertexData[2] = 0.0f;
+ vertexData[3] = x1;
+ vertexData[4] = y2;
+ vertexData[5] = 0.0f;
+ vertexData[6] = x2;
+ vertexData[7] = y1;
+ vertexData[8] = 0.0f;
+ vertexData[9] = x2;
+ vertexData[10] = y2;
+ vertexData[11] = 0.0f;
+
+ colorData[0] = 0x2f;
+ colorData[1] = 0x2f;
+ colorData[2] = 0x4f;
+ colorData[3] = 0x4f;
+
+ transform.translate (-0.5f, -0.5f, -DEFAULT_Z_CAMERA);
+ transform.scale (1.0f / output->width (),
+ -1.0f / output->height (),
+ 1.0f);
+ transform.translate (-output->region ()->extents.x1,
+ -output->region ()->extents.y2,
+ 0.0f);
+
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
+ streamingBuffer->addColors (1, colorData);
+ streamingBuffer->addVertices (4, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (transform);
+
+ streamingBuffer->begin (GL_LINE_LOOP);
+
+ vertexData[6] = x2;
+ vertexData[7] = y2;
+ vertexData[9] = x2;
+ vertexData[10] = y1;
+ colorData [3] = 0x9f;
+ streamingBuffer->addColors (1, colorData);
+ streamingBuffer->addVertices (4, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (transform);
}
}
diff --git a/plugins/switcher/src/switcher.cpp b/plugins/switcher/src/switcher.cpp
index c8d8580..faeeb05 100644
--- a/plugins/switcher/src/switcher.cpp
+++ b/plugins/switcher/src/switcher.cpp
@@ -29,25 +29,25 @@ COMPIZ_PLUGIN_20090315 (switcher, SwitchPluginVTable)
static float _boxVertices[] =
{
- -(WIDTH >> 1), 0,
- -(WIDTH >> 1), BOX_WIDTH,
- (WIDTH >> 1), BOX_WIDTH,
- (WIDTH >> 1), 0,
-
- -(WIDTH >> 1), BOX_WIDTH,
- -(WIDTH >> 1), HEIGHT - BOX_WIDTH,
- -(WIDTH >> 1) + BOX_WIDTH, HEIGHT - BOX_WIDTH,
- -(WIDTH >> 1) + BOX_WIDTH, 0,
-
- (WIDTH >> 1) - BOX_WIDTH, BOX_WIDTH,
- (WIDTH >> 1) - BOX_WIDTH, HEIGHT - BOX_WIDTH,
- (WIDTH >> 1), HEIGHT - BOX_WIDTH,
- (WIDTH >> 1), 0,
-
- -(WIDTH >> 1), HEIGHT - BOX_WIDTH,
- -(WIDTH >> 1), HEIGHT,
- (WIDTH >> 1), HEIGHT,
- (WIDTH >> 1), HEIGHT - BOX_WIDTH
+ -(WIDTH >> 1), BOX_WIDTH, 0.0f,
+ -(WIDTH >> 1), 0.0f, 0.0f,
+ (WIDTH >> 1), BOX_WIDTH, 0.0f,
+ (WIDTH >> 1), 0.0f, 0.0f,
+
+ -(WIDTH >> 1), HEIGHT - BOX_WIDTH, 0.0f,
+ -(WIDTH >> 1), BOX_WIDTH, 0.0f,
+ -(WIDTH >> 1) + BOX_WIDTH, HEIGHT - BOX_WIDTH, 0.0f,
+ -(WIDTH >> 1) + BOX_WIDTH, 0.0f, 0.0f,
+
+ (WIDTH >> 1) - BOX_WIDTH, HEIGHT - BOX_WIDTH, 0.0f,
+ (WIDTH >> 1) - BOX_WIDTH, BOX_WIDTH, 0.0f,
+ (WIDTH >> 1), HEIGHT - BOX_WIDTH, 0.0f,
+ (WIDTH >> 1), 0.0f, 0.0f,
+
+ -(WIDTH >> 1), HEIGHT, 0.0f,
+ -(WIDTH >> 1), HEIGHT - BOX_WIDTH, 0.0f,
+ (WIDTH >> 1), HEIGHT, 0.0f,
+ (WIDTH >> 1), HEIGHT - BOX_WIDTH, 0.0f,
};
@@ -797,9 +797,6 @@ SwitchScreen::glPaintOutput (const GLScreenPaintAttrib &sAttrib,
sTransform.toScreenSpace (output, -DEFAULT_Z_CAMERA);
- glPushMatrix ();
- glLoadMatrixf (sTransform.getMatrix ());
-
if (!switcher->destroyed () &&
switcher->isViewable () &&
sw->cWindow->damaged ())
@@ -807,8 +804,6 @@ SwitchScreen::glPaintOutput (const GLScreenPaintAttrib &sAttrib,
sw->gWindow->glPaint (sw->gWindow->paintAttrib (),
sTransform, infiniteRegion, 0);
}
-
- glPopMatrix ();
}
}
else
@@ -948,8 +943,10 @@ SwitchWindow::glPaint (const GLWindowPaintAttrib &attrib,
const CompRegion &region,
unsigned int mask)
{
- int zoomType = NORMAL_WINDOW_MASK;
- bool status;
+ GLVertexBuffer *streamingBuffer = GLVertexBuffer::streamingBuffer ();
+ GLMatrix wTransform (transform);
+ int zoomType = NORMAL_WINDOW_MASK;
+ bool status;
if (window->id () == sScreen->popupWindow)
{
@@ -973,17 +970,14 @@ SwitchWindow::glPaint (const GLWindowPaintAttrib &attrib,
x = x1 + sScreen->pos;
y = g.y () + SPACE;
- glPushAttrib (GL_SCISSOR_BIT);
-
glEnable (GL_SCISSOR_TEST);
glScissor (x1, 0, x2 - x1, screen->height ());
foreach (CompWindow *w, sScreen->windows)
{
if (x + WIDTH > x1)
- SwitchWindow::get (w)->paintThumb (
- gWindow->lastPaintAttrib (), transform,
- mask, x, y);
+ SwitchWindow::get (w)->paintThumb (gWindow->lastPaintAttrib (),
+ transform, mask, x, y);
x += WIDTH;
}
@@ -992,31 +986,30 @@ SwitchWindow::glPaint (const GLWindowPaintAttrib &attrib,
if (x > x2)
break;
- SwitchWindow::get (w)->paintThumb (
- gWindow->lastPaintAttrib (), transform,
- mask, x, y);
+ SwitchWindow::get (w)->paintThumb (gWindow->lastPaintAttrib (),
+ transform, mask, x, y);
x += WIDTH;
}
- glPopAttrib ();
+ glDisable (GL_SCISSOR_TEST);
cx = g.x () + (g.width () >> 1);
+ wTransform.translate (cx, y, 0.0f);
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
- glEnable (GL_BLEND);
for (i = 0; i < 4; i++)
+ {
color[i] = (unsigned int)sScreen->fgColor[i] *
- gWindow->lastPaintAttrib ().opacity /
- 0xffff;
- glColor4usv (color);
- glPushMatrix ();
- glTranslatef (cx, y, 0.0f);
- glVertexPointer (2, GL_FLOAT, 0, _boxVertices);
- glDrawArrays (GL_QUADS, 0, 16);
- glPopMatrix ();
- glColor4usv (defaultColor);
- glDisable (GL_BLEND);
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
+ gWindow->lastPaintAttrib ().opacity /
+ 0xffff;
+ }
+
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
+ streamingBuffer->addColors (1, color);
+ streamingBuffer->addVertices (16, _boxVertices);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (wTransform, attrib);
}
else if (window == sScreen->selectedWindow)
{
diff --git a/plugins/water/CMakeLists.txt b/plugins/water/CMakeLists.txt
index 2d2542b..f3f36ad 100644
--- a/plugins/water/CMakeLists.txt
+++ b/plugins/water/CMakeLists.txt
@@ -2,4 +2,4 @@ find_package (Compiz REQUIRED)
include (CompizPlugin)
-compiz_plugin(water PLUGINDEPS composite opengl) \ No newline at end of file
+#compiz_plugin(water PLUGINDEPS composite opengl)
diff --git a/plugins/wobbly/CMakeLists.txt b/plugins/wobbly/CMakeLists.txt
index 49886f8..415f6cb 100644
--- a/plugins/wobbly/CMakeLists.txt
+++ b/plugins/wobbly/CMakeLists.txt
@@ -2,4 +2,4 @@ find_package (Compiz REQUIRED)
include (CompizPlugin)
-compiz_plugin(wobbly PLUGINDEPS composite opengl)
+#compiz_plugin(wobbly PLUGINDEPS composite opengl)
diff --git a/plugins/zoom/src/zoom.cpp b/plugins/zoom/src/zoom.cpp
index 7231342..1041695 100644
--- a/plugins/zoom/src/zoom.cpp
+++ b/plugins/zoom/src/zoom.cpp
@@ -153,8 +153,11 @@ ZoomScreen::glPaintOutput (const GLScreenPaintAttrib &sAttrib,
CompOutput *output,
unsigned int mask)
{
- GLMatrix zTransform (transform);
- bool status;
+ GLVertexBuffer *streamingBuffer = GLVertexBuffer::streamingBuffer ();
+ GLfloat vertexData[12];
+ GLushort colorData[4];
+ GLMatrix zTransform (transform);
+ bool status;
if ((unsigned int) output->id () != (unsigned int) ~0 &&
(zoomed & (1 << (unsigned int) output->id ())))
@@ -214,25 +217,44 @@ ZoomScreen::glPaintOutput (const GLScreenPaintAttrib &sAttrib,
if (grabIndex)
{
+ vertexData[0] = x1;
+ vertexData[1] = y1;
+ vertexData[2] = 0.0f;
+ vertexData[3] = x1;
+ vertexData[4] = y2;
+ vertexData[5] = 0.0f;
+ vertexData[6] = x2;
+ vertexData[7] = y1;
+ vertexData[8] = 0.0f;
+ vertexData[9] = x2;
+ vertexData[10] = y2;
+ vertexData[11] = 0.0f;
+
+ colorData[0] = 0x2fff;
+ colorData[1] = 0x2fff;
+ colorData[2] = 0x4fff;
+ colorData[3] = 0x4fff;
+
zTransform.toScreenSpace (output, -DEFAULT_Z_CAMERA);
- glPushMatrix ();
- glLoadMatrixf (zTransform.getMatrix ());
- glDisableClientState (GL_TEXTURE_COORD_ARRAY);
- glEnable (GL_BLEND);
- glColor4us (0x2fff, 0x2fff, 0x4fff, 0x4fff);
- glRecti (x1, y2, x2, y1);
- glColor4us (0x2fff, 0x2fff, 0x4fff, 0x9fff);
- glBegin (GL_LINE_LOOP);
- glVertex2i (x1, y1);
- glVertex2i (x2, y1);
- glVertex2i (x2, y2);
- glVertex2i (x1, y2);
- glEnd ();
- glColor4usv (defaultColor);
- glDisable (GL_BLEND);
- glEnableClientState (GL_TEXTURE_COORD_ARRAY);
- glPopMatrix ();
+ streamingBuffer->begin (GL_TRIANGLE_STRIP);
+
+ streamingBuffer->addColors (1, colorData);
+ streamingBuffer->addVertices (4, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (zTransform);
+
+ streamingBuffer->begin (GL_LINE_LOOP);
+
+ colorData[3] = 0x9fff;
+ vertexData[7] = y2;
+ vertexData[10] = y1;
+ streamingBuffer->addColors (1, colorData);
+ streamingBuffer->addVertices (4, vertexData);
+
+ streamingBuffer->end ();
+ streamingBuffer->render (zTransform);
}
}
diff --git a/src/event.cpp b/src/event.cpp
index c79cd2b..b1094b9 100644
--- a/src/event.cpp
+++ b/src/event.cpp
@@ -1104,6 +1104,17 @@ CompScreen::handleEvent (XEvent *event)
w->moveInputFocusToOtherWindow ();
w->destroy ();
}
+ else
+ {
+ foreach (CoreWindow *cw, priv->createdWindows)
+ {
+ if (cw->priv->id == event->xdestroywindow.window)
+ {
+ priv->createdWindows.remove (cw);
+ break;
+ }
+ }
+ }
break;
case MapNotify:
diff --git a/src/plugin.cpp b/src/plugin.cpp
index 10afaab..16dfa7d 100644
--- a/src/plugin.cpp
+++ b/src/plugin.cpp
@@ -154,12 +154,10 @@ dlloaderLoadPlugin (CompPlugin *p,
return false;
}
- int open_flags = RTLD_LAZY;
+ int open_flags = RTLD_LAZY | RTLD_GLOBAL;
#ifdef DEBUG
// Do not unload the library during dlclose.
open_flags |= RTLD_NODELETE;
- // Make the symbols available globally
- open_flags |= RTLD_GLOBAL;
#endif
dlhand = dlopen (file.c_str (), open_flags);
if (dlhand)