glamor: Concentrate and reduce some coords processing code.

Concentrate the verties and texture coords processing code to a new
file glamor_utils.h. Change most of the code to macro. Will have some
performance benefit on slow machine. And reduce most of the duplicate
code when calculate the normalized coords.

Signed-off-by: Zhigang Gong <zhigang.gong@linux.intel.com>
This commit is contained in:
Zhigang Gong 2011-06-22 14:33:38 +08:00
parent 355334fcd9
commit ca1908e11d
8 changed files with 287 additions and 275 deletions

View File

@ -199,11 +199,13 @@ glamor_copy_n_to_n_textured(DrawablePtr src,
PixmapPtr src_pixmap = glamor_get_drawable_pixmap(src);
PixmapPtr dst_pixmap = glamor_get_drawable_pixmap(dst);
int i;
float vertices[4][2], texcoords[4][2];
float vertices[8], texcoords[8];
glamor_pixmap_private *src_pixmap_priv;
glamor_pixmap_private *dst_pixmap_priv;
int src_x_off, src_y_off, dst_x_off, dst_y_off;
enum glamor_pixmap_status src_status = GLAMOR_NONE;
GLfloat dst_xscale, dst_yscale, src_xscale, src_yscale;
src_pixmap_priv = glamor_get_pixmap_private(src_pixmap);
dst_pixmap_priv = glamor_get_pixmap_private(dst_pixmap);
@ -237,6 +239,9 @@ glamor_copy_n_to_n_textured(DrawablePtr src,
}
glamor_set_destination_pixmap_priv_nc(dst_pixmap_priv);
pixmap_priv_get_scale(dst_pixmap_priv, &dst_xscale, &dst_yscale);
pixmap_priv_get_scale(src_pixmap_priv, &src_xscale, &src_yscale);
glamor_get_drawable_deltas(dst, dst_pixmap, &dst_x_off, &dst_y_off);
glamor_get_drawable_deltas(src, src_pixmap, &src_x_off, &src_y_off);
@ -258,42 +263,25 @@ glamor_copy_n_to_n_textured(DrawablePtr src,
assert(GLEW_ARB_fragment_shader);
glUseProgramObjectARB(glamor_priv->finish_access_prog[0]);
for (i = 0; i < nbox; i++) {
vertices[0][0] = v_from_x_coord_x(dst_pixmap, box[i].x1 + dst_x_off);
vertices[1][0] = v_from_x_coord_x(dst_pixmap, box[i].x2 + dst_x_off);
vertices[2][0] = v_from_x_coord_x(dst_pixmap, box[i].x2 + dst_x_off);
vertices[3][0] = v_from_x_coord_x(dst_pixmap, box[i].x1 + dst_x_off);
texcoords[0][0] = t_from_x_coord_x(src_pixmap, box[i].x1 + dx);
texcoords[1][0] = t_from_x_coord_x(src_pixmap, box[i].x2 + dx);
texcoords[2][0] = t_from_x_coord_x(src_pixmap, box[i].x2 + dx);
texcoords[3][0] = t_from_x_coord_x(src_pixmap, box[i].x1 + dx);
glamor_set_normalize_vcoords(dst_xscale, dst_yscale,
box[i].x1 + dst_x_off,
box[i].y1 + dst_y_off,
box[i].x2 + dst_x_off,
box[i].y2 + dst_y_off,
glamor_priv->yInverted,
vertices);
if(glamor_priv->yInverted) {
glamor_set_normalize_tcoords(src_xscale, src_yscale,
box[i].x1 + dx, box[i].y1 + dy,
box[i].x2 + dx, box[i].y2 + dy,
glamor_priv->yInverted,
texcoords);
vertices[0][1] = v_from_x_coord_y_inverted(dst_pixmap, box[i].y1 + dst_y_off);
vertices[1][1] = v_from_x_coord_y_inverted(dst_pixmap, box[i].y1 + dst_y_off);
vertices[2][1] = v_from_x_coord_y_inverted(dst_pixmap, box[i].y2 + dst_y_off);
vertices[3][1] = v_from_x_coord_y_inverted(dst_pixmap, box[i].y2 + dst_y_off);
texcoords[0][1] = t_from_x_coord_y_inverted(src_pixmap, box[i].y1 + dy);
texcoords[1][1] = t_from_x_coord_y_inverted(src_pixmap, box[i].y1 + dy);
texcoords[2][1] = t_from_x_coord_y_inverted(src_pixmap, box[i].y2 + dy);
texcoords[3][1] = t_from_x_coord_y_inverted(src_pixmap, box[i].y2 + dy);
} else {
vertices[0][1] = v_from_x_coord_y(dst_pixmap, box[i].y1 + dst_y_off);
vertices[1][1] = v_from_x_coord_y(dst_pixmap, box[i].y1 + dst_y_off);
vertices[2][1] = v_from_x_coord_y(dst_pixmap, box[i].y2 + dst_y_off);
vertices[3][1] = v_from_x_coord_y(dst_pixmap, box[i].y2 + dst_y_off);
texcoords[0][1] = t_from_x_coord_y(src_pixmap, box[i].y1 + dy);
texcoords[1][1] = t_from_x_coord_y(src_pixmap, box[i].y1 + dy);
texcoords[2][1] = t_from_x_coord_y(src_pixmap, box[i].y2 + dy);
texcoords[3][1] = t_from_x_coord_y(src_pixmap, box[i].y2 + dy);
}
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
}
glUseProgramObjectARB(0);

View File

@ -146,14 +146,16 @@ glamor_solid(PixmapPtr pixmap, int x, int y, int width, int height,
{
ScreenPtr screen = pixmap->drawable.pScreen;
glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
glamor_pixmap_private *pixmap_priv = glamor_get_pixmap_private(pixmap);
int x1 = x;
int x2 = x + width;
int y1 = y;
int y2 = y + height;
GLfloat color[4];
float vertices[4][2];
if (glamor_set_destination_pixmap(pixmap)) {
float vertices[8];
GLfloat xscale, yscale;
if (!GLAMOR_PIXMAP_PRIV_HAS_FBO(pixmap_priv)) {
glamor_fallback("dest has no fbo.\n");
goto fail;
}
@ -162,6 +164,9 @@ glamor_solid(PixmapPtr pixmap, int x, int y, int width, int height,
glamor_fallback("Failedto set planemask in glamor_solid.\n");
goto fail;
}
glamor_set_destination_pixmap_priv_nc(pixmap_priv);
glUseProgramObjectARB(glamor_priv->solid_prog);
glamor_get_rgba_from_pixel(fg_pixel,
&color[0],
@ -174,22 +179,11 @@ glamor_solid(PixmapPtr pixmap, int x, int y, int width, int height,
glVertexPointer(2, GL_FLOAT, sizeof(float) * 2, vertices);
glEnableClientState(GL_VERTEX_ARRAY);
vertices[0][0] = v_from_x_coord_x(pixmap, x1);
vertices[1][0] = v_from_x_coord_x(pixmap, x2);
vertices[2][0] = v_from_x_coord_x(pixmap, x2);
vertices[3][0] = v_from_x_coord_x(pixmap, x1);
if (glamor_priv->yInverted) {
vertices[0][1] = v_from_x_coord_y_inverted(pixmap, y1);
vertices[1][1] = v_from_x_coord_y_inverted(pixmap, y1);
vertices[2][1] = v_from_x_coord_y_inverted(pixmap, y2);
vertices[3][1] = v_from_x_coord_y_inverted(pixmap, y2);
} else {
vertices[0][1] = v_from_x_coord_y(pixmap, y1);
vertices[1][1] = v_from_x_coord_y(pixmap, y1);
vertices[2][1] = v_from_x_coord_y(pixmap, y2);
vertices[3][1] = v_from_x_coord_y(pixmap, y2);
}
pixmap_priv_get_scale(pixmap_priv, &xscale, &yscale);
glamor_set_normalize_vcoords(xscale, yscale, x1, y1, x2, y2,
glamor_priv->yInverted,
vertices);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glDisableClientState(GL_VERTEX_ARRAY);

View File

@ -42,11 +42,17 @@ glamor_get_spans(DrawablePtr drawable,
PixmapPtr pixmap = glamor_get_drawable_pixmap(drawable);
GLenum format, type;
int ax;
glamor_screen_private *glamor_priv =
glamor_get_screen_private(drawable->pScreen);
glamor_screen_private *glamor_priv = glamor_get_screen_private(drawable->pScreen);
glamor_pixmap_private *pixmap_priv = glamor_get_pixmap_private(pixmap);
int i;
uint8_t *readpixels_dst = (uint8_t *)dst;
int x_off, y_off;
if (!GLAMOR_PIXMAP_PRIV_HAS_FBO(pixmap_priv)) {
glamor_fallback("pixmap has no fbo.\n");
goto fail;
}
if (glamor_get_tex_format_type_from_pixmap(pixmap,
&format,
&type,
@ -57,10 +63,8 @@ glamor_get_spans(DrawablePtr drawable,
goto fail;
}
if (glamor_set_destination_pixmap(pixmap)) {
glamor_fallback("pixmap has no fbo.\n");
goto fail;
}
glamor_set_destination_pixmap_priv_nc(pixmap_priv);
glamor_get_drawable_deltas(drawable, pixmap, &x_off, &y_off);
for (i = 0; i < count; i++) {
if (glamor_priv->yInverted) {

View File

@ -505,44 +505,6 @@ glamor_pm_is_solid(DrawablePtr drawable, unsigned long planemask)
extern int glamor_debug_level;
static inline float
v_from_x_coord_x(PixmapPtr pixmap, int x)
{
return (float)x / pixmap->drawable.width * 2.0 - 1.0;
}
static inline float
v_from_x_coord_y(PixmapPtr pixmap, int y)
{
return (float)y / pixmap->drawable.height * -2.0 + 1.0;
}
static inline float
v_from_x_coord_y_inverted(PixmapPtr pixmap, int y)
{
return (float)y / pixmap->drawable.height * 2.0 - 1.0;
}
static inline float
t_from_x_coord_x(PixmapPtr pixmap, int x)
{
return (float)x / pixmap->drawable.width;
}
static inline float
t_from_x_coord_y(PixmapPtr pixmap, int y)
{
return 1.0 - (float)y / pixmap->drawable.height;
}
static inline float
t_from_x_coord_y_inverted(PixmapPtr pixmap, int y)
{
return (float)y / pixmap->drawable.height;
}
/* glamor.c */
PixmapPtr glamor_get_drawable_pixmap(DrawablePtr drawable);
@ -791,4 +753,7 @@ glamor_picture_format_fixup(PicturePtr picture, glamor_pixmap_private *pixmap_pr
#define GLAMOR_PIXMAP_DYNAMIC_UPLOAD
#include"glamor_utils.h"
#endif /* GLAMOR_PRIV_H */

View File

@ -87,17 +87,6 @@ glamor_init_putimage_shaders(ScreenPtr screen)
glUseProgramObjectARB(0);
}
static int
y_flip(PixmapPtr pixmap, int y)
{
ScreenPtr screen = pixmap->drawable.pScreen;
PixmapPtr screen_pixmap = screen->GetScreenPixmap(screen);
if (pixmap == screen_pixmap)
return (pixmap->drawable.height - 1) - y;
else
return y;
}
/* Do an XYBitmap putimage. The bits are byte-aligned rows of bitmap
* data (where each row starts at a bit index of left_pad), and the
@ -110,6 +99,21 @@ y_flip(PixmapPtr pixmap, int y)
* case we might be better off just doing the fg/bg choosing in the CPU
* and just draw the resulting texture to the destination.
*/
#if 0
static int
y_flip(PixmapPtr pixmap, int y)
{
ScreenPtr screen = pixmap->drawable.pScreen;
PixmapPtr screen_pixmap = screen->GetScreenPixmap(screen);
if (pixmap == screen_pixmap)
return (pixmap->drawable.height - 1) - y;
else
return y;
}
static void
glamor_put_image_xybitmap(DrawablePtr drawable, GCPtr gc,
int x, int y, int w, int h, int left_pad,
@ -124,25 +128,27 @@ glamor_put_image_xybitmap(DrawablePtr drawable, GCPtr gc,
RegionPtr clip;
BoxPtr box;
int nbox;
float dest_coords[4][2];
float dest_coords[8];
const float bitmap_coords[8] = {
0.0, 0.0,
1.0, 0.0,
1.0, 1.0,
0.0, 1.0,
};
GLfloat xscale, yscale;
glamor_pixmap_private *pixmap_priv;
pixmap_priv = glamor_get_pixmap_private(pixmap);
pixmap_priv_get_scale(pixmap_priv, &xscale, &yscale);
dest_coords[0][0] = v_from_x_coord_x(pixmap, x);
dest_coords[0][1] = v_from_x_coord_y(pixmap, y);
dest_coords[1][0] = v_from_x_coord_x(pixmap, x + w);
dest_coords[1][1] = v_from_x_coord_y(pixmap, y);
dest_coords[2][0] = v_from_x_coord_x(pixmap, x + w);
dest_coords[2][1] = v_from_x_coord_y(pixmap, y + h);
dest_coords[3][0] = v_from_x_coord_x(pixmap, x);
dest_coords[3][1] = v_from_x_coord_y(pixmap, y + h);
glamor_set_normalize_vcoords(xscale, yscale,
x, y,
x + w, y + h,
glamor_priv->yInverted,
dest_coords);
glamor_fallback("glamor_put_image_xybitmap: disabled\n");
glamor_fallback("glamor_put_image_xybitmap: disabled\n");
goto fail;
if (glamor_priv->put_image_xybitmap_prog == 0) {
@ -237,6 +243,8 @@ fail:
glamor_finish_access(drawable);
}
}
#endif
void
glamor_put_image(DrawablePtr drawable, GCPtr gc, int depth, int x, int y,
@ -252,13 +260,13 @@ glamor_put_image(DrawablePtr drawable, GCPtr gc, int depth, int x, int y,
int nbox;
int src_stride = PixmapBytePad(w, drawable->depth);
int x_off, y_off;
float vertices[4][2], texcoords[4][2];
float vertices[8], texcoords[8];
GLfloat xscale, yscale, txscale, tyscale;
GLuint tex;
int ax = 0;
if (image_format == XYBitmap) {
assert(depth == 1);
glamor_put_image_xybitmap(drawable, gc, x, y, w, h,
left_pad, image_format, bits);
goto fail;
return;
}
@ -319,8 +327,12 @@ glamor_put_image(DrawablePtr drawable, GCPtr gc, int depth, int x, int y,
y += drawable->y;
glamor_get_drawable_deltas(drawable, pixmap, &x_off, &y_off);
clip = fbGetCompositeClip(gc);
txscale = 1.0/w;
tyscale = 1.0/h;
pixmap_priv_get_scale(pixmap_priv, &xscale, &yscale);
for (nbox = REGION_NUM_RECTS(clip),
pbox = REGION_RECTS(clip);
nbox--;
@ -330,7 +342,6 @@ glamor_put_image(DrawablePtr drawable, GCPtr gc, int depth, int x, int y,
int y1 = y;
int x2 = x + w;
int y2 = y + h;
float src_x1, src_x2, src_y1, src_y2;
if (x1 < pbox->x1)
x1 = pbox->x1;
@ -343,41 +354,18 @@ glamor_put_image(DrawablePtr drawable, GCPtr gc, int depth, int x, int y,
if (x1 >= x2 || y1 >= y2)
continue;
src_x1 = (float)(x1 - x) / w;
src_y1 = (float)(y1 - y) / h;
src_x2 = (float)(x2 - x) / w;
src_y2 = (float)(y2 - y) / h;
glamor_set_normalize_tcoords( txscale, tyscale,
x1 - x, y1 - y,
x2 - x, y2 - y,
1,
texcoords);
vertices[0][0] = v_from_x_coord_x(pixmap, x1 + x_off);
vertices[1][0] = v_from_x_coord_x(pixmap, x2 + x_off);
vertices[2][0] = v_from_x_coord_x(pixmap, x2 + x_off);
vertices[3][0] = v_from_x_coord_x(pixmap, x1 + x_off);
glamor_set_normalize_vcoords( xscale, yscale,
x1 + x_off, y1 + y_off,
x2 + x_off, y2 + y_off,
glamor_priv->yInverted,
vertices);
texcoords[0][0] = src_x1;
texcoords[0][1] = src_y1;
texcoords[1][0] = src_x2;
texcoords[1][1] = src_y1;
texcoords[2][0] = src_x2;
texcoords[2][1] = src_y2;
texcoords[3][0] = src_x1;
texcoords[3][1] = src_y2;
if (glamor_priv->yInverted) {
vertices[0][1] = v_from_x_coord_y_inverted(pixmap, y1 + y_off);
vertices[1][1] = v_from_x_coord_y_inverted(pixmap, y1 + y_off);
vertices[2][1] = v_from_x_coord_y_inverted(pixmap, y2 + y_off);
vertices[3][1] = v_from_x_coord_y_inverted(pixmap, y2 + y_off);
} else {
vertices[0][1] = v_from_x_coord_y(pixmap, y1 + y_off);
vertices[1][1] = v_from_x_coord_y(pixmap, y1 + y_off);
vertices[2][1] = v_from_x_coord_y(pixmap, y2 + y_off);
vertices[3][1] = v_from_x_coord_y(pixmap, y2 + y_off);
}
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
}

View File

@ -533,41 +533,6 @@ good_dest_format(PicturePtr picture)
}
}
static inline float
xFixedToFloat(pixman_fixed_t val)
{
return ((float)xFixedToInt(val) + ((float)xFixedFrac(val) / 65536.0));
}
static void
glamor_set_transformed_point(PicturePtr picture, PixmapPtr pixmap,
float *texcoord, int x, int y)
{
float result[3];
int i;
float tx, ty;
ScreenPtr screen = picture->pDrawable->pScreen;
glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
if (picture->transform) {
for (i = 0; i < 3; i++) {
result[i] = (xFixedToFloat(picture->transform->matrix[i][0]) * x +
xFixedToFloat(picture->transform->matrix[i][1]) * y +
xFixedToFloat(picture->transform->matrix[i][2]));
}
tx = result[0] / result[2];
ty = result[1] / result[2];
} else {
tx = x;
ty = y;
}
texcoord[0] = t_from_x_coord_x(pixmap, tx);
if (glamor_priv->yInverted)
texcoord[1] = t_from_x_coord_y_inverted(pixmap, ty);
else
texcoord[1] = t_from_x_coord_y(pixmap, ty);
}
static void
glamor_setup_composite_vbo(ScreenPtr screen)
{
@ -756,6 +721,8 @@ glamor_composite_with_shader(CARD8 op,
glamor_pixmap_private *source_pixmap_priv = NULL;
glamor_pixmap_private *mask_pixmap_priv = NULL;
glamor_pixmap_private *dest_pixmap_priv = NULL;
GLfloat dst_xscale, dst_yscale;
GLfloat mask_xscale = 1, mask_yscale = 1, src_xscale = 1, src_yscale = 1;
struct shader_key key;
glamor_composite_shader *shader;
RegionRec region;
@ -768,6 +735,8 @@ glamor_composite_with_shader(CARD8 op,
enum glamor_pixmap_status source_status = GLAMOR_NONE;
enum glamor_pixmap_status mask_status = GLAMOR_NONE;
PictFormatShort saved_source_format = 0;
float src_matrix[9], mask_matrix[9];
dest_pixmap_priv = glamor_get_pixmap_private(dest_pixmap);
if (!GLAMOR_PIXMAP_PRIV_HAS_FBO(dest_pixmap_priv)) {
@ -972,14 +941,24 @@ glamor_composite_with_shader(CARD8 op,
glamor_get_drawable_deltas(dest->pDrawable, dest_pixmap,
&dest_x_off, &dest_y_off);
pixmap_priv_get_scale(dest_pixmap_priv, &dst_xscale, &dst_yscale);
if (source_pixmap) {
glamor_get_drawable_deltas(source->pDrawable, source_pixmap,
&source_x_off, &source_y_off);
pixmap_priv_get_scale(source_pixmap_priv, &src_xscale, &src_yscale);
glamor_picture_get_matrixf(source, src_matrix);
}
if (mask_pixmap) {
glamor_get_drawable_deltas(mask->pDrawable, mask_pixmap,
&mask_x_off, &mask_y_off);
pixmap_priv_get_scale(mask_pixmap_priv, &mask_xscale, &mask_yscale);
glamor_picture_get_matrixf(mask, mask_matrix);
}
while (nrect--) {
INT16 x_source;
INT16 y_source;
@ -1025,65 +1004,41 @@ glamor_composite_with_shader(CARD8 op,
box = REGION_RECTS(&region);
for (i = 0; i < REGION_NUM_RECTS(&region); i++) {
vertices[0] = v_from_x_coord_x(dest_pixmap,
box[i].x1 + dest_x_off);
vertices[2] = v_from_x_coord_x(dest_pixmap,
box[i].x2 + dest_x_off);
vertices[4] = v_from_x_coord_x(dest_pixmap,
box[i].x2 + dest_x_off);
vertices[6] = v_from_x_coord_x(dest_pixmap,
box[i].x1 + dest_x_off);
int vx1 = box[i].x1 + dest_x_off;
int vx2 = box[i].x2 + dest_x_off;
int vy1 = box[i].y1 + dest_y_off;
int vy2 = box[i].y2 + dest_y_off;
glamor_set_normalize_vcoords(dst_xscale, dst_yscale, vx1, vy1, vx2, vy2,
glamor_priv->yInverted, vertices);
if (glamor_priv->yInverted) {
vertices[1] = v_from_x_coord_y_inverted(dest_pixmap,
box[i].y1 + dest_y_off);
vertices[3] = v_from_x_coord_y_inverted(dest_pixmap,
box[i].y1 + dest_y_off);
vertices[5] = v_from_x_coord_y_inverted(dest_pixmap,
box[i].y2 + dest_y_off);
vertices[7] = v_from_x_coord_y_inverted(dest_pixmap,
box[i].y2 + dest_y_off);
} else {
vertices[1] = v_from_x_coord_y(dest_pixmap,
box[i].y1 + dest_y_off);
vertices[3] = v_from_x_coord_y(dest_pixmap,
box[i].y1 + dest_y_off);
vertices[5] = v_from_x_coord_y(dest_pixmap,
box[i].y2 + dest_y_off);
vertices[7] = v_from_x_coord_y(dest_pixmap,
box[i].y2 + dest_y_off);
}
if (key.source != SHADER_SOURCE_SOLID) {
int tx1 = box[i].x1 + x_source - x_dest;
int ty1 = box[i].y1 + y_source - y_dest;
int tx2 = box[i].x2 + x_source - x_dest;
int ty2 = box[i].y2 + y_source - y_dest;
glamor_set_transformed_point(source, source_pixmap,
source_texcoords + 0, tx1, ty1);
glamor_set_transformed_point(source, source_pixmap,
source_texcoords + 2, tx2, ty1);
glamor_set_transformed_point(source, source_pixmap,
source_texcoords + 4, tx2, ty2);
glamor_set_transformed_point(source, source_pixmap,
source_texcoords + 6, tx1, ty2);
}
if (source->transform)
glamor_set_transformed_normalize_tcoords(src_matrix, src_xscale, src_yscale,
tx1, ty1, tx2, ty2,
glamor_priv->yInverted,
source_texcoords);
else
glamor_set_normalize_tcoords(src_xscale, src_yscale, tx1, ty1, tx2, ty2,
glamor_priv->yInverted, source_texcoords);
}
if (key.mask != SHADER_MASK_NONE && key.mask != SHADER_MASK_SOLID) {
float tx1 = box[i].x1 + x_mask - x_dest;
float ty1 = box[i].y1 + y_mask - y_dest;
float tx2 = box[i].x2 + x_mask - x_dest;
float ty2 = box[i].y2 + y_mask - y_dest;
glamor_set_transformed_point(mask, mask_pixmap,
mask_texcoords + 0, tx1, ty1);
glamor_set_transformed_point(mask, mask_pixmap,
mask_texcoords + 2, tx2, ty1);
glamor_set_transformed_point(mask, mask_pixmap,
mask_texcoords + 4, tx2, ty2);
glamor_set_transformed_point(mask, mask_pixmap,
mask_texcoords + 6, tx1, ty2);
if (mask->transform)
glamor_set_transformed_normalize_tcoords(mask_matrix, mask_xscale, mask_yscale,
tx1, ty1, tx2, ty2,
glamor_priv->yInverted,
mask_texcoords);
else
glamor_set_normalize_tcoords(mask_xscale, mask_yscale, tx1, ty1, tx2, ty2,
glamor_priv->yInverted, mask_texcoords);
}
glamor_emit_composite_rect(screen, source_texcoords,
mask_texcoords, vertices);

View File

@ -88,70 +88,64 @@ glamor_tile(PixmapPtr pixmap, PixmapPtr tile,
int tile_x2 = tile_x + width;
int tile_y1 = tile_y;
int tile_y2 = tile_y + height;
glamor_pixmap_private *tile_priv = glamor_get_pixmap_private(tile);
float vertices[4][2];
float source_texcoords[4][2];
float vertices[8];
float source_texcoords[8];
GLfloat dst_xscale, dst_yscale, src_xscale, src_yscale;
glamor_pixmap_private *src_pixmap_priv;
glamor_pixmap_private *dst_pixmap_priv;
src_pixmap_priv = glamor_get_pixmap_private(tile);
dst_pixmap_priv = glamor_get_pixmap_private(pixmap);
if (glamor_priv->tile_prog == 0) {
glamor_fallback("Tiling unsupported\n");
goto fail;
}
if (glamor_set_destination_pixmap(pixmap)) {
glamor_fallback("dest has no fbo.");
goto fail;
if (GLAMOR_PIXMAP_PRIV_HAS_FBO(dst_pixmap_priv)) {
glamor_fallback("dest has no fbo.");
goto fail;
}
if (tile_priv->gl_tex == 0) {
glamor_fallback("Non-texture tile pixmap\n");
goto fail;
if (!GLAMOR_PIXMAP_PRIV_HAS_FBO(src_pixmap_priv)) {
/* XXX dynamic uploading candidate. */
glamor_fallback("Non-texture tile pixmap\n");
goto fail;
}
if (!glamor_set_planemask(pixmap, planemask)) {
glamor_fallback("unsupported planemask %lx\n", planemask);
goto fail;
}
glamor_set_destination_pixmap_priv_nc(dst_pixmap_priv);
pixmap_priv_get_scale(dst_pixmap_priv, &dst_xscale, &dst_yscale);
pixmap_priv_get_scale(src_pixmap_priv, &src_xscale, &src_yscale);
glamor_set_alu(alu);
glUseProgramObjectARB(glamor_priv->tile_prog);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, tile_priv->tex);
glBindTexture(GL_TEXTURE_2D, src_pixmap_priv->tex);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glEnable(GL_TEXTURE_2D);
vertices[0][0] = v_from_x_coord_x(pixmap, x1);
vertices[1][0] = v_from_x_coord_x(pixmap, x2);
vertices[2][0] = v_from_x_coord_x(pixmap, x2);
vertices[3][0] = v_from_x_coord_x(pixmap, x1);
source_texcoords[0][0] = t_from_x_coord_x(tile, tile_x1);
source_texcoords[1][0] = t_from_x_coord_x(tile, tile_x2);
source_texcoords[2][0] = t_from_x_coord_x(tile, tile_x2);
source_texcoords[3][0] = t_from_x_coord_x(tile, tile_x1);
if (glamor_priv->yInverted) {
vertices[0][1] = v_from_x_coord_y_inverted(pixmap, y1);
vertices[1][1] = v_from_x_coord_y_inverted(pixmap, y1);
vertices[2][1] = v_from_x_coord_y_inverted(pixmap, y2);
vertices[3][1] = v_from_x_coord_y_inverted(pixmap, y2);
glamor_set_normalize_vcoords(dst_xscale, dst_yscale,
x1, y1,x2, y2,
glamor_priv->yInverted,
vertices);
source_texcoords[0][1] = t_from_x_coord_y_inverted(tile, tile_y1);
source_texcoords[1][1] = t_from_x_coord_y_inverted(tile, tile_y1);
source_texcoords[2][1] = t_from_x_coord_y_inverted(tile, tile_y2);
source_texcoords[3][1] = t_from_x_coord_y_inverted(tile, tile_y2);
} else {
glamor_set_normalize_tcoords(src_xscale, src_yscale,
tile_x1, tile_y1,
tile_x2, tile_y2,
glamor_priv->yInverted,
source_texcoords);
vertices[0][1] = v_from_x_coord_y(pixmap, y1);
vertices[1][1] = v_from_x_coord_y(pixmap, y1);
vertices[2][1] = v_from_x_coord_y(pixmap, y2);
vertices[3][1] = v_from_x_coord_y(pixmap, y2);
source_texcoords[0][1] = t_from_x_coord_y(tile, tile_y1);
source_texcoords[1][1] = t_from_x_coord_y(tile, tile_y1);
source_texcoords[2][1] = t_from_x_coord_y(tile, tile_y2);
source_texcoords[3][1] = t_from_x_coord_y(tile, tile_y2);
}
glVertexPointer(2, GL_FLOAT, sizeof(float) * 2, vertices);
glEnableClientState(GL_VERTEX_ARRAY);

124
glamor/glamor_utils.h Normal file
View File

@ -0,0 +1,124 @@
#ifndef GLAMOR_PRIV_H
#error This file can only be included by glamor_priv.h
#endif
#ifndef __GLAMOR_UTILS_H__
#define __GLAMOR_UTILS_H__
#define v_from_x_coord_x(_xscale_, _x_) ( 2 * (_x_) * (_xscale_) - 1.0)
#define v_from_x_coord_y(_yscale_, _y_) (-2 * (_y_) * (_yscale_) + 1.0)
#define v_from_x_coord_y_inverted(_yscale_, _y_) (2 * (_y_) * (_yscale_) - 1.0)
#define t_from_x_coord_x(_xscale_, _x_) ((_x_) * (_xscale_))
#define t_from_x_coord_y(_yscale_, _y_) (1.0 - (_y_) * (_yscale_))
#define t_from_x_coord_y_inverted(_yscale_, _y_) ((_y_) * (_yscale_))
#define pixmap_priv_get_scale(_pixmap_priv_, _pxscale_, _pyscale_) \
do { \
*(_pxscale_) = 1.0 / (_pixmap_priv_)->container->drawable.width; \
*(_pyscale_) = 1.0 / (_pixmap_priv_)->container->drawable.height; \
} while(0)
#define xFixedToFloat(_val_) ((float)xFixedToInt(_val_) \
+ ((float)xFixedFrac(_val_) / 65536.0))
#define glamor_picture_get_matrixf(_picture_, _matrix_) \
do { \
int _i_; \
if ((_picture_)->transform) \
{ \
for(_i_ = 0; _i_ < 3; _i_++) \
{ \
(_matrix_)[_i_ * 3 + 0] = \
xFixedToFloat((_picture_)->transform->matrix[_i_][0]); \
(_matrix_)[_i_ * 3 + 1] = \
xFixedToFloat((_picture_)->transform->matrix[_i_][1]); \
(_matrix_)[_i_ * 3 + 2] = \
xFixedToFloat((_picture_)->transform->matrix[_i_][2]); \
} \
} \
} while(0)
#define glamor_set_transformed_point(matrix, xscale, yscale, texcoord, \
x, y, yInverted) \
do { \
float result[4]; \
int i; \
float tx, ty; \
\
for (i = 0; i < 3; i++) { \
result[i] = (matrix)[i * 3] * (x) + (matrix)[i * 3 + 1] * (y) \
+ (matrix)[i * 3 + 2]; \
} \
tx = result[0] / result[2]; \
ty = result[1] / result[2]; \
\
(texcoord)[0] = t_from_x_coord_x(xscale, tx); \
if (yInverted) \
(texcoord)[1] = t_from_x_coord_y_inverted(yscale, ty); \
else \
(texcoord)[1] = t_from_x_coord_y(yscale, ty); \
} while(0)
#define glamor_set_transformed_normalize_tcoords( matrix, \
xscale, \
yscale, \
tx1, ty1, tx2, ty2, \
yInverted, texcoords) \
do { \
glamor_set_transformed_point(matrix, xscale, yscale, \
texcoords, tx1, ty1, \
yInverted); \
glamor_set_transformed_point(matrix, xscale, yscale, \
texcoords + 2, tx2, ty1, \
yInverted); \
glamor_set_transformed_point(matrix, xscale, yscale, \
texcoords + 4, tx2, ty2, \
yInverted); \
glamor_set_transformed_point(matrix, xscale, yscale, \
texcoords + 6, tx1, ty2, \
yInverted); \
} while (0)
#define glamor_set_normalize_tcoords(xscale, yscale, x1, y1, x2, y2, \
yInverted, vertices) \
do { \
(vertices)[0] = t_from_x_coord_x(xscale, x1); \
(vertices)[2] = t_from_x_coord_x(xscale, x2); \
(vertices)[4] = (vertices)[2]; \
(vertices)[6] = (vertices)[0]; \
if (yInverted) { \
(vertices)[1] = t_from_x_coord_y_inverted(yscale, y1); \
(vertices)[5] = t_from_x_coord_y_inverted(yscale, y2); \
} \
else { \
(vertices)[1] = t_from_x_coord_y(yscale, y1); \
(vertices)[5] = t_from_x_coord_y(yscale, y2); \
} \
(vertices)[3] = (vertices)[1]; \
(vertices)[7] = (vertices)[5]; \
} while(0)
#define glamor_set_normalize_vcoords(xscale, yscale, x1, y1, x2, y2, \
yInverted, vertices) \
do { \
(vertices)[0] = v_from_x_coord_x(xscale, x1); \
(vertices)[2] = v_from_x_coord_x(xscale, x2); \
(vertices)[4] = (vertices)[2]; \
(vertices)[6] = (vertices)[0]; \
if (yInverted) { \
(vertices)[1] = v_from_x_coord_y_inverted(yscale, y1); \
(vertices)[5] = v_from_x_coord_y_inverted(yscale, y2); \
} \
else { \
(vertices)[1] = v_from_x_coord_y(yscale, y1); \
(vertices)[5] = v_from_x_coord_y(yscale, y2); \
} \
(vertices)[3] = (vertices)[1]; \
(vertices)[7] = (vertices)[5]; \
} while(0)
#endif