gl-renderer: Add support for SHM buffers in RGB565 format

dev
Tomeu Vizoso 12 years ago committed by Kristian Høgsberg
parent bee45a14cd
commit 12072b6a7c
  1. 57
      src/gl-renderer.c

@ -1109,6 +1109,8 @@ gl_renderer_flush_damage(struct weston_surface *surface)
struct gl_renderer *gr = get_renderer(surface->compositor); struct gl_renderer *gr = get_renderer(surface->compositor);
struct gl_surface_state *gs = get_surface_state(surface); struct gl_surface_state *gs = get_surface_state(surface);
struct weston_buffer *buffer = gs->buffer_ref.buffer; struct weston_buffer *buffer = gs->buffer_ref.buffer;
GLenum format;
int pixel_type;
#ifdef GL_UNPACK_ROW_LENGTH #ifdef GL_UNPACK_ROW_LENGTH
pixman_box32_t *rectangles; pixman_box32_t *rectangles;
@ -1133,12 +1135,28 @@ gl_renderer_flush_damage(struct weston_surface *surface)
if (!pixman_region32_not_empty(&gs->texture_damage)) if (!pixman_region32_not_empty(&gs->texture_damage))
goto done; goto done;
switch (wl_shm_buffer_get_format(buffer->shm_buffer)) {
case WL_SHM_FORMAT_XRGB8888:
case WL_SHM_FORMAT_ARGB8888:
format = GL_BGRA_EXT;
pixel_type = GL_UNSIGNED_BYTE;
break;
case WL_SHM_FORMAT_RGB565:
format = GL_RGB;
pixel_type = GL_UNSIGNED_SHORT_5_6_5;
break;
default:
weston_log("warning: unknown shm buffer format\n");
format = GL_BGRA_EXT;
pixel_type = GL_UNSIGNED_BYTE;
}
glBindTexture(GL_TEXTURE_2D, gs->textures[0]); glBindTexture(GL_TEXTURE_2D, gs->textures[0]);
if (!gr->has_unpack_subimage) { if (!gr->has_unpack_subimage) {
glTexImage2D(GL_TEXTURE_2D, 0, GL_BGRA_EXT, glTexImage2D(GL_TEXTURE_2D, 0, format,
gs->pitch, buffer->height, 0, gs->pitch, buffer->height, 0,
GL_BGRA_EXT, GL_UNSIGNED_BYTE, format, pixel_type,
wl_shm_buffer_get_data(buffer->shm_buffer)); wl_shm_buffer_get_data(buffer->shm_buffer));
goto done; goto done;
@ -1154,7 +1172,7 @@ gl_renderer_flush_damage(struct weston_surface *surface)
glPixelStorei(GL_UNPACK_SKIP_ROWS, 0); glPixelStorei(GL_UNPACK_SKIP_ROWS, 0);
glTexSubImage2D(GL_TEXTURE_2D, 0, glTexSubImage2D(GL_TEXTURE_2D, 0,
0, 0, gs->pitch, buffer->height, 0, 0, gs->pitch, buffer->height,
GL_BGRA_EXT, GL_UNSIGNED_BYTE, data); format, pixel_type, data);
goto done; goto done;
} }
@ -1168,7 +1186,7 @@ gl_renderer_flush_damage(struct weston_surface *surface)
glPixelStorei(GL_UNPACK_SKIP_ROWS, r.y1); glPixelStorei(GL_UNPACK_SKIP_ROWS, r.y1);
glTexSubImage2D(GL_TEXTURE_2D, 0, r.x1, r.y1, glTexSubImage2D(GL_TEXTURE_2D, 0, r.x1, r.y1,
r.x2 - r.x1, r.y2 - r.y1, r.x2 - r.x1, r.y2 - r.y1,
GL_BGRA_EXT, GL_UNSIGNED_BYTE, data); format, pixel_type, data);
} }
#endif #endif
@ -1207,18 +1225,38 @@ gl_renderer_attach_shm(struct weston_surface *es, struct weston_buffer *buffer,
struct weston_compositor *ec = es->compositor; struct weston_compositor *ec = es->compositor;
struct gl_renderer *gr = get_renderer(ec); struct gl_renderer *gr = get_renderer(ec);
struct gl_surface_state *gs = get_surface_state(es); struct gl_surface_state *gs = get_surface_state(es);
int pitch;
buffer->shm_buffer = shm_buffer; buffer->shm_buffer = shm_buffer;
buffer->width = wl_shm_buffer_get_width(shm_buffer); buffer->width = wl_shm_buffer_get_width(shm_buffer);
buffer->height = wl_shm_buffer_get_height(shm_buffer); buffer->height = wl_shm_buffer_get_height(shm_buffer);
switch (wl_shm_buffer_get_format(shm_buffer)) {
case WL_SHM_FORMAT_XRGB8888:
gs->shader = &gr->texture_shader_rgbx;
pitch = wl_shm_buffer_get_stride(shm_buffer) / 4;
break;
case WL_SHM_FORMAT_ARGB8888:
gs->shader = &gr->texture_shader_rgba;
pitch = wl_shm_buffer_get_stride(shm_buffer) / 4;
break;
case WL_SHM_FORMAT_RGB565:
gs->shader = &gr->texture_shader_rgbx;
pitch = wl_shm_buffer_get_stride(shm_buffer) / 2;
break;
default:
weston_log("warning: unknown shm buffer format\n");
gs->shader = &gr->texture_shader_rgba;
pitch = wl_shm_buffer_get_stride(shm_buffer) / 4;
}
/* Only allocate a texture if it doesn't match existing one. /* Only allocate a texture if it doesn't match existing one.
* If a switch from DRM allocated buffer to a SHM buffer is * If a switch from DRM allocated buffer to a SHM buffer is
* happening, we need to allocate a new texture buffer. */ * happening, we need to allocate a new texture buffer. */
if (wl_shm_buffer_get_stride(shm_buffer) / 4 != gs->pitch || if (pitch != gs->pitch ||
buffer->height != gs->height || buffer->height != gs->height ||
gs->buffer_type != BUFFER_TYPE_SHM) { gs->buffer_type != BUFFER_TYPE_SHM) {
gs->pitch = wl_shm_buffer_get_stride(shm_buffer) / 4; gs->pitch = pitch;
gs->height = buffer->height; gs->height = buffer->height;
gs->target = GL_TEXTURE_2D; gs->target = GL_TEXTURE_2D;
gs->buffer_type = BUFFER_TYPE_SHM; gs->buffer_type = BUFFER_TYPE_SHM;
@ -1230,11 +1268,6 @@ gl_renderer_attach_shm(struct weston_surface *es, struct weston_buffer *buffer,
gs->pitch, buffer->height, 0, gs->pitch, buffer->height, 0,
GL_BGRA_EXT, GL_UNSIGNED_BYTE, NULL); GL_BGRA_EXT, GL_UNSIGNED_BYTE, NULL);
} }
if (wl_shm_buffer_get_format(shm_buffer) == WL_SHM_FORMAT_XRGB8888)
gs->shader = &gr->texture_shader_rgbx;
else
gs->shader = &gr->texture_shader_rgba;
} }
static void static void
@ -1904,6 +1937,8 @@ gl_renderer_create(struct weston_compositor *ec, EGLNativeDisplayType display,
ec->capabilities |= WESTON_CAP_ROTATION_ANY; ec->capabilities |= WESTON_CAP_ROTATION_ANY;
ec->capabilities |= WESTON_CAP_CAPTURE_YFLIP; ec->capabilities |= WESTON_CAP_CAPTURE_YFLIP;
wl_display_add_shm_format(ec->wl_display, WL_SHM_FORMAT_RGB565);
return 0; return 0;
err_egl: err_egl:

Loading…
Cancel
Save