Big giant rendering commit from work so I can continue at home.
Signed-off-by: Chris Michael <cp.michael@samsung.com>
This commit is contained in:
parent
ef6225a87c
commit
e50261ae34
|
@ -126,6 +126,7 @@ void *alloca (size_t);
|
|||
# include <GLES2/gl2.h>
|
||||
# include <GLES2/gl2ext.h>
|
||||
# include <EGL/egl.h>
|
||||
# include <EGL/eglext.h>
|
||||
# endif
|
||||
|
||||
# ifdef HAVE_HAL
|
||||
|
|
|
@ -289,6 +289,8 @@ e_compositor_damage_calculate(E_Compositor *comp)
|
|||
Eina_List *l;
|
||||
pixman_region32_t clip, opaque;
|
||||
|
||||
printf("E_Comp Damage Calculate\n");
|
||||
|
||||
/* check for valid compositor */
|
||||
if (!comp) return;
|
||||
|
||||
|
@ -367,6 +369,14 @@ _e_comp_cb_surface_create(struct wl_client *client, struct wl_resource *resource
|
|||
return;
|
||||
}
|
||||
|
||||
/* ask the renderer to create any internal representation of this surface
|
||||
* that it may need */
|
||||
if (!comp->renderer->surface_create(es))
|
||||
{
|
||||
e_surface_destroy(es);
|
||||
return;
|
||||
}
|
||||
|
||||
/* set surface plane to compositor primary plane */
|
||||
es->plane = &comp->plane;
|
||||
|
||||
|
@ -386,7 +396,7 @@ static void
|
|||
_e_comp_cb_surface_destroy(struct wl_resource *resource)
|
||||
{
|
||||
E_Surface *es;
|
||||
E_Surface_Frame *cb;
|
||||
E_Surface_Frame *cb, *cbnext;
|
||||
|
||||
printf("E_Comp Surface Destroy\n");
|
||||
|
||||
|
@ -403,7 +413,7 @@ _e_comp_cb_surface_destroy(struct wl_resource *resource)
|
|||
if (es->mapped) e_surface_unmap(es);
|
||||
|
||||
/* remove any pending frame callbacks */
|
||||
EINA_LIST_FREE(es->pending.frames, cb)
|
||||
wl_list_for_each_safe(cb, cbnext, &es->pending.frames, link)
|
||||
wl_resource_destroy(&cb->resource);
|
||||
|
||||
pixman_region32_fini(&es->pending.damage);
|
||||
|
@ -417,6 +427,9 @@ _e_comp_cb_surface_destroy(struct wl_resource *resource)
|
|||
/* remove any buffer references */
|
||||
e_buffer_reference(&es->buffer.reference, NULL);
|
||||
|
||||
if (_e_comp->renderer->surface_destroy)
|
||||
_e_comp->renderer->surface_destroy(es);
|
||||
|
||||
/* free regions */
|
||||
pixman_region32_fini(&es->damage);
|
||||
pixman_region32_fini(&es->opaque);
|
||||
|
@ -424,7 +437,7 @@ _e_comp_cb_surface_destroy(struct wl_resource *resource)
|
|||
pixman_region32_fini(&es->clip);
|
||||
|
||||
/* remove any active frame callbacks */
|
||||
EINA_LIST_FREE(es->frames, cb)
|
||||
wl_list_for_each_safe(cb, cbnext, &es->frames, link)
|
||||
wl_resource_destroy(&cb->resource);
|
||||
|
||||
/* free the surface structure */
|
||||
|
|
|
@ -54,7 +54,6 @@ struct _E_Compositor
|
|||
Eina_List *inputs;
|
||||
Eina_List *surfaces;
|
||||
|
||||
void (*attach) (E_Surface *es, struct wl_buffer *buffer);
|
||||
void (*cb_ping) (void *surface, unsigned int serial);
|
||||
};
|
||||
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
/* local function prototypes */
|
||||
static void _e_output_cb_bind(struct wl_client *client, void *data, unsigned int version EINA_UNUSED, unsigned int id);
|
||||
static void _e_output_cb_unbind(struct wl_resource *resource);
|
||||
static void _e_output_cb_idle_repaint(void *data);
|
||||
|
||||
EAPI void
|
||||
e_output_init(E_Output *output, E_Compositor *comp, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h, unsigned int transform)
|
||||
|
@ -18,6 +19,10 @@ e_output_init(E_Output *output, E_Compositor *comp, Evas_Coord x, Evas_Coord y,
|
|||
output->dirty = EINA_TRUE;
|
||||
output->transform = transform;
|
||||
|
||||
pixman_region32_union(&comp->plane.damage, &comp->plane.damage,
|
||||
&output->repaint.region);
|
||||
e_output_repaint_schedule(output);
|
||||
|
||||
wl_list_init(&output->wl.resources);
|
||||
|
||||
wl_signal_init(&output->signals.frame);
|
||||
|
@ -50,12 +55,75 @@ EAPI void
|
|||
e_output_repaint(E_Output *output, unsigned int secs)
|
||||
{
|
||||
E_Compositor *comp;
|
||||
E_Surface *es;
|
||||
E_Surface_Frame *cb, *cbnext;
|
||||
pixman_region32_t damage;
|
||||
Eina_List *l;
|
||||
struct wl_list frames;
|
||||
|
||||
printf("Output Repaint\n");
|
||||
|
||||
comp = output->compositor;
|
||||
|
||||
/* TODO: assign planes */
|
||||
EINA_LIST_FOREACH(comp->surfaces, l, es)
|
||||
{
|
||||
if (es->plane != &comp->plane) continue;
|
||||
e_surface_damage_below(es);
|
||||
es->plane = &comp->plane;
|
||||
e_surface_damage(es);
|
||||
}
|
||||
|
||||
wl_list_init(&frames);
|
||||
EINA_LIST_FOREACH(comp->surfaces, l, es)
|
||||
{
|
||||
if (es->output != output) continue;
|
||||
wl_list_insert_list(&frames, &es->frames);
|
||||
wl_list_init(&es->frames);
|
||||
}
|
||||
|
||||
e_compositor_damage_calculate(comp);
|
||||
|
||||
pixman_region32_init(&damage);
|
||||
pixman_region32_intersect(&damage, &comp->plane.damage,
|
||||
&output->repaint.region);
|
||||
pixman_region32_subtract(&damage, &damage, &comp->plane.clip);
|
||||
|
||||
if (output->cb_repaint) output->cb_repaint(output, &damage);
|
||||
pixman_region32_fini(&damage);
|
||||
output->repaint.needed = EINA_FALSE;
|
||||
|
||||
/* TODO: comp repick ? */
|
||||
|
||||
wl_event_loop_dispatch(comp->wl.input_loop, 0);
|
||||
|
||||
/* send surface frame callback done */
|
||||
wl_list_for_each_safe(cb, cbnext, &frames, link)
|
||||
{
|
||||
wl_callback_send_done(&cb->resource, secs);
|
||||
wl_resource_destroy(&cb->resource);
|
||||
}
|
||||
}
|
||||
|
||||
EAPI void
|
||||
e_output_repaint_schedule(E_Output *output)
|
||||
{
|
||||
E_Compositor *comp;
|
||||
struct wl_event_loop *loop;
|
||||
|
||||
printf("Output Repaint Schedule\n");
|
||||
|
||||
comp = output->compositor;
|
||||
|
||||
loop = wl_display_get_event_loop(comp->wl.display);
|
||||
output->repaint.needed = EINA_TRUE;
|
||||
if (output->repaint.scheduled) return;
|
||||
|
||||
wl_event_loop_add_idle(loop, _e_output_cb_idle_repaint, output);
|
||||
output->repaint.scheduled = EINA_TRUE;
|
||||
|
||||
if (comp->wl.input_loop_source)
|
||||
wl_event_source_remove(comp->wl.input_loop_source);
|
||||
comp->wl.input_loop_source = NULL;
|
||||
}
|
||||
|
||||
/* local functions */
|
||||
|
@ -95,3 +163,14 @@ _e_output_cb_unbind(struct wl_resource *resource)
|
|||
wl_list_remove(&resource->link);
|
||||
free(resource);
|
||||
}
|
||||
|
||||
static void
|
||||
_e_output_cb_idle_repaint(void *data)
|
||||
{
|
||||
E_Output *output;
|
||||
|
||||
if (!(output = data)) return;
|
||||
|
||||
if (output->cb_repaint_start)
|
||||
output->cb_repaint_start(output);
|
||||
}
|
||||
|
|
|
@ -33,6 +33,9 @@ struct _E_Output
|
|||
|
||||
struct
|
||||
{
|
||||
pixman_region32_t region;
|
||||
pixman_region32_t prev_damage;
|
||||
|
||||
Eina_Bool needed : 1;
|
||||
Eina_Bool scheduled : 1;
|
||||
} repaint;
|
||||
|
@ -50,16 +53,19 @@ struct _E_Output
|
|||
struct wl_signal destroy;
|
||||
} signals;
|
||||
|
||||
void *state;
|
||||
|
||||
/* TODO: add backlight and dpms support */
|
||||
|
||||
void (*cb_repaint_start)(E_Output *output);
|
||||
void (*cb_repaint)(E_Output *output, E_Region *damage);
|
||||
void (*cb_repaint)(E_Output *output, pixman_region32_t *damage);
|
||||
void (*cb_destroy)(E_Output *output);
|
||||
};
|
||||
|
||||
EAPI void e_output_init(E_Output *output, E_Compositor *comp, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h, unsigned int transform);
|
||||
EAPI void e_output_shutdown(E_Output *output);
|
||||
EAPI void e_output_repaint(E_Output *output, unsigned int secs);
|
||||
EAPI void e_output_repaint_schedule(E_Output *output);
|
||||
|
||||
# endif
|
||||
#endif
|
||||
|
|
|
@ -1,14 +1,55 @@
|
|||
#include "e.h"
|
||||
|
||||
typedef struct _E_Renderer_Output_State E_Renderer_Output_State;
|
||||
typedef struct _E_Renderer_Surface_State E_Renderer_Surface_State;
|
||||
|
||||
struct _E_Renderer_Output_State
|
||||
{
|
||||
#ifdef HAVE_WAYLAND_EGL
|
||||
EGLSurface surface;
|
||||
pixman_region32_t buffer[2];
|
||||
#endif
|
||||
pixman_image_t *shadow;
|
||||
void *shadow_buffer;
|
||||
pixman_image_t *hw_buffer;
|
||||
};
|
||||
|
||||
struct _E_Renderer_Surface_State
|
||||
{
|
||||
#ifdef HAVE_WAYLAND_EGL
|
||||
GLfloat color[4];
|
||||
GLuint textures[3];
|
||||
GLenum target;
|
||||
|
||||
EGLImageKHR images[3];
|
||||
|
||||
E_Shader *shader;
|
||||
|
||||
pixman_region32_t texture_damage;
|
||||
|
||||
int num_text;
|
||||
int num_images;
|
||||
int pitch, height;
|
||||
#endif
|
||||
pixman_image_t *image;
|
||||
E_Buffer_Reference buffer_reference;
|
||||
};
|
||||
|
||||
/* local function prototypes */
|
||||
static int _e_renderer_cb_pixels_read(E_Output *output, int format, void *pixels, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h);
|
||||
static void _e_renderer_region_repaint(E_Surface *surface, E_Output *output, pixman_region32_t *region, pixman_region32_t *surface_region, pixman_op_t pixman_op);
|
||||
static void _e_renderer_surfaces_repaint(E_Output *output, pixman_region32_t *damage);
|
||||
static void _e_renderer_surface_draw(E_Surface *surface, E_Output *output, pixman_region32_t *damage);
|
||||
static Eina_Bool _e_renderer_cb_pixels_read(E_Output *output, int format, void *pixels, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h);
|
||||
static void _e_renderer_cb_output_buffer_set(E_Output *output, pixman_image_t *buffer);
|
||||
static void _e_renderer_cb_output_repaint(E_Output *output, pixman_region32_t *damage);
|
||||
static void void _e_renderer_cb_damage_flush)(E_Surface *surface);
|
||||
static void void _e_renderer_cb_attach(E_Surface *surface, struct wl_buffer *buffer);
|
||||
static int _e_renderer_cb_surface_create(E_Surface *surface);
|
||||
static void _e_renderer_cb_damage_flush(E_Surface *surface);
|
||||
static void _e_renderer_cb_attach(E_Surface *surface, struct wl_buffer *buffer);
|
||||
static Eina_Bool _e_renderer_cb_output_create(E_Output *output, unsigned int window);
|
||||
static void _e_renderer_cb_output_destroy(E_Output *output);
|
||||
static Eina_Bool _e_renderer_cb_surface_create(E_Surface *surface);
|
||||
static void _e_renderer_cb_surface_destroy(E_Surface *surface);
|
||||
static void _e_renderer_cb_surface_color_set(E_Surface *surface, int r, int g, int b, int a);
|
||||
static void _e_renderer_cb_destroy)(E_Compositor *comp);
|
||||
static void _e_renderer_cb_destroy(E_Compositor *comp);
|
||||
|
||||
EAPI Eina_Bool
|
||||
e_renderer_create(E_Compositor *comp)
|
||||
|
@ -18,11 +59,17 @@ e_renderer_create(E_Compositor *comp)
|
|||
/* try to allocate space for new renderer */
|
||||
if (!(rend = E_NEW(E_Renderer, 1))) return EINA_FALSE;
|
||||
|
||||
/* FIXME: Vary these based on software or gl
|
||||
* NB: This code current ONLY does software */
|
||||
|
||||
/* setup renderer functions */
|
||||
rend->pixels_read = _e_renderer_cb_pixels_read;
|
||||
rend->output_buffer_set = _e_renderer_cb_output_buffer_set;
|
||||
rend->output_repaint = _e_renderer_cb_output_repaint;
|
||||
rend->damage_flush = _e_renderer_cb_damage_flush;
|
||||
rend->attach = _e_renderer_cb_attach;
|
||||
rend->output_create = _e_renderer_cb_output_create;
|
||||
rend->output_destroy = _e_renderer_cb_output_destroy;
|
||||
rend->surface_create = _e_renderer_cb_surface_create;
|
||||
rend->surface_destroy = _e_renderer_cb_surface_destroy;
|
||||
rend->surface_color_set = _e_renderer_cb_surface_color_set;
|
||||
|
@ -34,40 +81,285 @@ e_renderer_create(E_Compositor *comp)
|
|||
}
|
||||
|
||||
/* local functions */
|
||||
static int
|
||||
static void
|
||||
_e_renderer_region_repaint(E_Surface *surface, E_Output *output, pixman_region32_t *region, pixman_region32_t *surf_region, pixman_op_t pixman_op)
|
||||
{
|
||||
E_Renderer *rend;
|
||||
E_Renderer_Output_State *out_state;
|
||||
E_Renderer_Surface_State *surf_state;
|
||||
pixman_region32_t fregion;
|
||||
pixman_fixed_t fw = 0, fh = 0;
|
||||
|
||||
printf("E_Renderer Region Repaint\n");
|
||||
|
||||
rend = output->compositor->renderer;
|
||||
out_state = output->state;
|
||||
surf_state = surface->state;
|
||||
|
||||
pixman_region32_init(&fregion);
|
||||
if (surf_region)
|
||||
{
|
||||
pixman_region32_copy(&fregion, surf_region);
|
||||
pixman_region32_translate(&fregion,
|
||||
surface->geometry.x, surface->geometry.y);
|
||||
pixman_region32_intersect(&fregion, &fregion, region);
|
||||
}
|
||||
else
|
||||
pixman_region32_copy(&fregion, region);
|
||||
|
||||
pixman_image_set_clip_region32(out_state->shadow, &fregion);
|
||||
pixman_image_set_filter(surf_state->image, PIXMAN_FILTER_NEAREST, NULL, 0);
|
||||
|
||||
pixman_image_composite32(pixman_op, surf_state->image, NULL,
|
||||
out_state->shadow, 0, 0, 0, 0, 0, 0,
|
||||
pixman_image_get_width(out_state->shadow),
|
||||
pixman_image_get_height(out_state->shadow));
|
||||
pixman_image_set_clip_region32(out_state->shadow, NULL);
|
||||
pixman_region32_fini(&fregion);
|
||||
}
|
||||
|
||||
static void
|
||||
_e_renderer_surfaces_repaint(E_Output *output, pixman_region32_t *damage)
|
||||
{
|
||||
E_Compositor *comp;
|
||||
Eina_List *l;
|
||||
E_Surface *es;
|
||||
|
||||
printf("E_Renderer Surfaces Repaint\n");
|
||||
|
||||
comp = output->compositor;
|
||||
EINA_LIST_FOREACH(comp->surfaces, l, es)
|
||||
{
|
||||
if (es->plane == &comp->plane)
|
||||
_e_renderer_surface_draw(es, output, damage);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
_e_renderer_surface_draw(E_Surface *surface, E_Output *output, pixman_region32_t *damage)
|
||||
{
|
||||
E_Renderer_Surface_State *state;
|
||||
pixman_region32_t repaint, blend;
|
||||
|
||||
printf("E_Renderer Surface Draw\n");
|
||||
|
||||
if (!surface) return;
|
||||
if (!surface->output) surface->output = output;
|
||||
if (surface->output != output) return;
|
||||
|
||||
if (!(state = surface->state)) return;
|
||||
|
||||
if (!state->image) return;
|
||||
|
||||
pixman_region32_init(&repaint);
|
||||
pixman_region32_intersect(&repaint, &surface->opaque, damage);
|
||||
pixman_region32_subtract(&repaint, &repaint, &surface->clip);
|
||||
|
||||
if (!pixman_region32_not_empty(&repaint))
|
||||
{
|
||||
pixman_region32_fini(&repaint);
|
||||
return;
|
||||
}
|
||||
|
||||
/* TODO: handle transforms ? */
|
||||
|
||||
pixman_region32_init_rect(&blend, 0, 0,
|
||||
surface->geometry.w, surface->geometry.h);
|
||||
pixman_region32_subtract(&blend, &blend, &surface->opaque);
|
||||
|
||||
if (pixman_region32_not_empty(&surface->opaque))
|
||||
_e_renderer_region_repaint(surface, output, &repaint,
|
||||
&surface->opaque, PIXMAN_OP_SRC);
|
||||
|
||||
if (pixman_region32_not_empty(&blend))
|
||||
_e_renderer_region_repaint(surface, output, &repaint,
|
||||
&blend, PIXMAN_OP_OVER);
|
||||
|
||||
pixman_region32_fini(&blend);
|
||||
pixman_region32_fini(&repaint);
|
||||
}
|
||||
|
||||
static Eina_Bool
|
||||
_e_renderer_cb_pixels_read(E_Output *output, int format, void *pixels, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h)
|
||||
{
|
||||
return 1;
|
||||
E_Renderer_Output_State *state;
|
||||
pixman_image_t *buffer;
|
||||
|
||||
printf("E_Renderer Pixels Read\n");
|
||||
|
||||
if (!(state = output->state)) return EINA_FALSE;
|
||||
if (!state->hw_buffer) return EINA_FALSE;
|
||||
|
||||
buffer =
|
||||
pixman_image_create_bits(format, w, h, pixels,
|
||||
(PIXMAN_FORMAT_BPP(format) / 8) * w);
|
||||
|
||||
pixman_image_composite32(PIXMAN_OP_SRC, state->hw_buffer, NULL,
|
||||
buffer, 0, 0, 0, 0, 0, 0,
|
||||
pixman_image_get_width(state->hw_buffer),
|
||||
pixman_image_get_height(state->hw_buffer));
|
||||
pixman_image_set_transform(state->hw_buffer, NULL);
|
||||
pixman_image_unref(buffer);
|
||||
|
||||
return EINA_TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
_e_renderer_cb_output_buffer_set(E_Output *output, pixman_image_t *buffer)
|
||||
{
|
||||
E_Renderer_Output_State *state;
|
||||
|
||||
printf("E_Renderer Output Buffer Set\n");
|
||||
|
||||
state = output->state;
|
||||
if (state->hw_buffer) pixman_image_unref(state->hw_buffer);
|
||||
state->hw_buffer = buffer;
|
||||
if (state->hw_buffer)
|
||||
{
|
||||
/* output->compositor->read_format; */
|
||||
pixman_image_ref(state->hw_buffer);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
_e_renderer_cb_output_repaint(E_Output *output, pixman_region32_t *damage)
|
||||
{
|
||||
E_Renderer_Output_State *state;
|
||||
pixman_region32_t region;
|
||||
|
||||
printf("E_Renderer Output Repaint\n");
|
||||
|
||||
state = output->state;
|
||||
if (!state->hw_buffer) return;
|
||||
|
||||
/* repaint surfaces */
|
||||
_e_renderer_surfaces_repaint(output, damage);
|
||||
|
||||
/* copy to hw */
|
||||
pixman_region32_init(®ion);
|
||||
pixman_region32_copy(®ion, damage);
|
||||
|
||||
/* global to output ? */
|
||||
|
||||
pixman_image_set_clip_region32(state->hw_buffer, ®ion);
|
||||
pixman_image_composite32(PIXMAN_OP_SRC, state->shadow, NULL,
|
||||
state->hw_buffer, 0, 0, 0, 0, 0, 0,
|
||||
pixman_image_get_width(state->hw_buffer),
|
||||
pixman_image_get_height(state->hw_buffer));
|
||||
pixman_image_set_clip_region32(state->hw_buffer, NULL);
|
||||
pixman_region32_copy(&output->repaint.prev_damage, damage);
|
||||
|
||||
wl_signal_emit(&output->signals.frame, output);
|
||||
}
|
||||
|
||||
static void void
|
||||
_e_renderer_cb_damage_flush)(E_Surface *surface)
|
||||
static void
|
||||
_e_renderer_cb_damage_flush(E_Surface *surface)
|
||||
{
|
||||
|
||||
printf("E_Renderer Damage Flush\n");
|
||||
}
|
||||
|
||||
static void void
|
||||
static void
|
||||
_e_renderer_cb_attach(E_Surface *surface, struct wl_buffer *buffer)
|
||||
{
|
||||
E_Renderer_Surface_State *state;
|
||||
pixman_format_code_t format;
|
||||
Evas_Coord w = 0, h = 0;
|
||||
void *data;
|
||||
int stride = 0;
|
||||
|
||||
state = surface->state;
|
||||
|
||||
e_buffer_reference(&state->buffer_reference, buffer);
|
||||
|
||||
if (state->image) pixman_image_unref(state->image);
|
||||
state->image = NULL;
|
||||
|
||||
if (!buffer) return;
|
||||
|
||||
printf("E_Renderer Attach\n");
|
||||
|
||||
switch (wl_shm_buffer_get_format(buffer))
|
||||
{
|
||||
case WL_SHM_FORMAT_XRGB8888:
|
||||
format = PIXMAN_x8r8g8b8;
|
||||
break;
|
||||
case WL_SHM_FORMAT_ARGB8888:
|
||||
format = PIXMAN_a8r8g8b8;
|
||||
break;
|
||||
}
|
||||
|
||||
w = wl_shm_buffer_get_width(buffer);
|
||||
h = wl_shm_buffer_get_height(buffer);
|
||||
data = wl_shm_buffer_get_data(buffer);
|
||||
stride = wl_shm_buffer_get_stride(buffer);
|
||||
|
||||
state->image = pixman_image_create_bits(format, w, h, data, stride);
|
||||
}
|
||||
|
||||
static int
|
||||
static Eina_Bool
|
||||
_e_renderer_cb_output_create(E_Output *output, unsigned int window)
|
||||
{
|
||||
E_Renderer_Output_State *state;
|
||||
|
||||
/* try to allocate space for output state */
|
||||
if (!(state = E_NEW(E_Renderer_Output_State, 1)))
|
||||
return EINA_FALSE;
|
||||
|
||||
state->shadow_buffer = malloc(output->w * output->h * sizeof(int));
|
||||
if (!state->shadow_buffer) return EINA_FALSE;
|
||||
|
||||
state->shadow =
|
||||
pixman_image_create_bits(PIXMAN_x8r8g8b8, output->w, output->h,
|
||||
state->shadow_buffer, output->w * sizeof(int));
|
||||
if (!state->shadow)
|
||||
{
|
||||
free(state->shadow_buffer);
|
||||
free(state);
|
||||
return EINA_FALSE;
|
||||
}
|
||||
|
||||
output->state = state;
|
||||
|
||||
return EINA_TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
_e_renderer_cb_output_destroy(E_Output *output)
|
||||
{
|
||||
printf("E_Renderer Output Destroy\n");
|
||||
}
|
||||
|
||||
static Eina_Bool
|
||||
_e_renderer_cb_surface_create(E_Surface *surface)
|
||||
{
|
||||
return 1;
|
||||
E_Renderer_Surface_State *state;
|
||||
|
||||
if (!(state = E_NEW(E_Renderer_Surface_State, 1)))
|
||||
return EINA_FALSE;
|
||||
|
||||
printf("E_Renderer Surface Create\n");
|
||||
|
||||
surface->state = state;
|
||||
|
||||
return EINA_TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
_e_renderer_cb_surface_destroy(E_Surface *surface)
|
||||
{
|
||||
E_Renderer_Surface_State *state;
|
||||
|
||||
printf("E_Renderer Surface Destroy\n");
|
||||
|
||||
if ((state = surface->state))
|
||||
{
|
||||
if (state->image) pixman_image_unref(state->image);
|
||||
state->image = NULL;
|
||||
}
|
||||
|
||||
e_buffer_reference(&state->buffer_reference, NULL);
|
||||
|
||||
E_FREE(state);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -77,8 +369,8 @@ _e_renderer_cb_surface_color_set(E_Surface *surface, int r, int g, int b, int a)
|
|||
}
|
||||
|
||||
static void
|
||||
_e_renderer_cb_destroy)(E_Compositor *comp)
|
||||
_e_renderer_cb_destroy(E_Compositor *comp)
|
||||
{
|
||||
|
||||
printf("E_Renderer Destroy\n");
|
||||
}
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ typedef struct _E_Renderer E_Renderer;
|
|||
# define EGL_TEXTURE_Y_U_V_WL 0x31D7
|
||||
# define EGL_TEXTURE_Y_UV_WL 0x31D8
|
||||
# define EGL_TEXTURE_Y_XUXV_WL 0x31D9
|
||||
# define EGL_TEXTURE_EXTERNAL_WL 0x31DA
|
||||
|
||||
struct wl_display;
|
||||
struct wl_buffer;
|
||||
# ifdef EGL_EGLEXT_PROTOTYPES
|
||||
|
@ -26,6 +26,15 @@ typedef EGLBoolean (EGLAPIENTRYP PFNEGLBINDWAYLANDDISPLAYWL) (EGLDisplay dpy, st
|
|||
typedef EGLBoolean (EGLAPIENTRYP PFNEGLUNBINDWAYLANDDISPLAYWL) (EGLDisplay dpy, struct wl_display *display);
|
||||
typedef EGLBoolean (EGLAPIENTRYP PFNEGLQUERYWAYLANDBUFFERWL) (EGLDisplay dpy, struct wl_buffer *buffer, EGLint attribute, EGLint *value);
|
||||
# endif
|
||||
|
||||
# ifndef EGL_TEXTURE_EXTERNAL_WL
|
||||
# define EGL_TEXTURE_EXTERNAL_WL 0x31DA
|
||||
# endif
|
||||
|
||||
# ifndef EGL_BUFFER_AGE_EXT
|
||||
# define EGL_BUFFER_AGE_EXT 0x313D
|
||||
# endif
|
||||
|
||||
# endif
|
||||
|
||||
struct _E_Renderer
|
||||
|
@ -52,7 +61,7 @@ struct _E_Renderer
|
|||
|
||||
Eina_Bool have_unpack : 1;
|
||||
Eina_Bool have_bind : 1;
|
||||
Eina_bool have_external : 1;
|
||||
Eina_Bool have_external : 1;
|
||||
Eina_Bool have_buffer_age : 1;
|
||||
|
||||
struct
|
||||
|
@ -69,11 +78,14 @@ struct _E_Renderer
|
|||
} shaders;
|
||||
# endif
|
||||
|
||||
int (*pixels_read)(E_Output *output, int format, void *pixels, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h);
|
||||
Eina_Bool (*pixels_read)(E_Output *output, int format, void *pixels, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h);
|
||||
void (*output_buffer_set)(E_Output *output, pixman_image_t *buffer);
|
||||
void (*output_repaint)(E_Output *output, pixman_region32_t *damage);
|
||||
void (*damage_flush)(E_Surface *surface);
|
||||
void (*attach)(E_Surface *surface, struct wl_buffer *buffer);
|
||||
int (*surface_create)(E_Surface *surface);
|
||||
Eina_Bool (*output_create)(E_Output *output, unsigned int window);
|
||||
void (*output_destroy)(E_Output *output);
|
||||
Eina_Bool (*surface_create)(E_Surface *surface);
|
||||
void (*surface_destroy)(E_Surface *surface);
|
||||
void (*surface_color_set)(E_Surface *surface, int r, int g, int b, int a);
|
||||
void (*destroy)(E_Compositor *comp);
|
||||
|
|
|
@ -38,6 +38,8 @@ e_surface_new(unsigned int id)
|
|||
|
||||
/* initialize the link */
|
||||
wl_list_init(&es->wl.link);
|
||||
wl_list_init(&es->frames);
|
||||
wl_list_init(&es->pending.frames);
|
||||
|
||||
pixman_region32_init(&es->damage);
|
||||
pixman_region32_init(&es->opaque);
|
||||
|
@ -84,7 +86,7 @@ e_surface_attach(E_Surface *es, struct wl_buffer *buffer)
|
|||
}
|
||||
|
||||
/* call renderer attach */
|
||||
if (_e_comp->attach) _e_comp->attach(es, buffer);
|
||||
if (_e_comp->renderer->attach) _e_comp->renderer->attach(es, buffer);
|
||||
}
|
||||
|
||||
EAPI void
|
||||
|
@ -103,7 +105,18 @@ e_surface_damage(E_Surface *es)
|
|||
pixman_region32_union_rect(&es->damage, &es->damage,
|
||||
0, 0, es->geometry.w, es->geometry.h);
|
||||
|
||||
/* TODO: schedule repaint */
|
||||
e_surface_repaint_schedule(es);
|
||||
}
|
||||
|
||||
EAPI void
|
||||
e_surface_damage_below(E_Surface *es)
|
||||
{
|
||||
pixman_region32_t damage;
|
||||
|
||||
pixman_region32_init(&damage);
|
||||
pixman_region32_subtract(&damage, &es->opaque, &es->clip);
|
||||
pixman_region32_union(&es->plane->damage, &es->plane->damage, &damage);
|
||||
pixman_region32_fini(&damage);
|
||||
}
|
||||
|
||||
EAPI void
|
||||
|
@ -129,7 +142,10 @@ e_surface_damage_calculate(E_Surface *es, pixman_region32_t *opaque)
|
|||
{
|
||||
/* if this is an shm buffer, flush any pending damage */
|
||||
if (wl_buffer_is_shm(es->buffer.reference.buffer))
|
||||
e_compositor_damage_flush(_e_comp, es);
|
||||
{
|
||||
if (_e_comp->renderer->damage_flush)
|
||||
_e_comp->renderer->damage_flush(es);
|
||||
}
|
||||
}
|
||||
|
||||
/* TODO: handle transforms */
|
||||
|
@ -147,49 +163,6 @@ e_surface_damage_calculate(E_Surface *es, pixman_region32_t *opaque)
|
|||
pixman_region32_copy(&es->clip, opaque);
|
||||
}
|
||||
|
||||
EAPI void
|
||||
e_surface_buffer_set(E_Surface *es, struct wl_buffer *buffer)
|
||||
{
|
||||
pixman_format_code_t format;
|
||||
Evas_Coord w = 0, h = 0;
|
||||
int stride = 0;
|
||||
void *pixels;
|
||||
|
||||
/* check for valid surface */
|
||||
if (!es) return;
|
||||
|
||||
/* destory any existing image */
|
||||
/* if (es->image) pixman_image_unref(es->image); */
|
||||
/* es->image = NULL; */
|
||||
|
||||
/* check for valid buffer */
|
||||
if (!buffer) return;
|
||||
|
||||
/* get buffer format */
|
||||
switch (wl_shm_buffer_get_format(buffer))
|
||||
{
|
||||
case WL_SHM_FORMAT_XRGB8888:
|
||||
format = PIXMAN_x8r8g8b8;
|
||||
break;
|
||||
case WL_SHM_FORMAT_ARGB8888:
|
||||
format = PIXMAN_a8r8g8b8;
|
||||
break;
|
||||
default:
|
||||
e_buffer_reference(&es->buffer.reference, NULL);
|
||||
return;
|
||||
break;
|
||||
}
|
||||
|
||||
/* get buffer information */
|
||||
w = wl_shm_buffer_get_width(buffer);
|
||||
h = wl_shm_buffer_get_height(buffer);
|
||||
pixels = wl_shm_buffer_get_data(buffer);
|
||||
stride = wl_shm_buffer_get_stride(buffer);
|
||||
|
||||
/* create surface image */
|
||||
/* es->image = pixman_image_create_bits(format, w, h, pixels, stride); */
|
||||
}
|
||||
|
||||
EAPI void
|
||||
e_surface_show(E_Surface *es)
|
||||
{
|
||||
|
@ -199,6 +172,21 @@ e_surface_show(E_Surface *es)
|
|||
/* ecore_evas_show(es->ee); */
|
||||
}
|
||||
|
||||
EAPI void
|
||||
e_surface_repaint_schedule(E_Surface *es)
|
||||
{
|
||||
E_Output *output;
|
||||
Eina_List *l;
|
||||
|
||||
printf("E_Surface Repaint Schedule\n");
|
||||
|
||||
EINA_LIST_FOREACH(_e_comp->outputs, l, output)
|
||||
{
|
||||
if (es->output == output)
|
||||
e_output_repaint_schedule(output);
|
||||
}
|
||||
}
|
||||
|
||||
/* local functions */
|
||||
static void
|
||||
_e_surface_cb_destroy(struct wl_client *client EINA_UNUSED, struct wl_resource *resource)
|
||||
|
@ -310,12 +298,11 @@ _e_surface_cb_commit(struct wl_client *client EINA_UNUSED, struct wl_resource *r
|
|||
pixman_region32_intersect(&es->input, &es->input, &es->pending.input);
|
||||
|
||||
/* add any pending frame callbacks to main list and free pending */
|
||||
EINA_LIST_FREE(es->pending.frames, cb)
|
||||
es->frames = eina_list_append(es->frames, cb);
|
||||
wl_list_insert_list(&es->frames, &es->pending.frames);
|
||||
wl_list_init(&es->pending.frames);
|
||||
|
||||
/* schedule repaint */
|
||||
/* evas_damage_rectangle_add(es->evas, es->damage->x, es->damage->y, */
|
||||
/* es->damage->w, es->damage->h); */
|
||||
e_surface_repaint_schedule(es);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -334,8 +321,6 @@ _e_surface_cb_frame(struct wl_client *client, struct wl_resource *resource, unsi
|
|||
return;
|
||||
}
|
||||
|
||||
cb->surface = es;
|
||||
|
||||
/* setup the callback object */
|
||||
cb->resource.object.interface = &wl_callback_interface;
|
||||
cb->resource.object.id = id;
|
||||
|
@ -347,7 +332,7 @@ _e_surface_cb_frame(struct wl_client *client, struct wl_resource *resource, unsi
|
|||
wl_client_add_resource(client, &cb->resource);
|
||||
|
||||
/* append the callback to pending frames */
|
||||
es->pending.frames = eina_list_prepend(es->pending.frames, cb);
|
||||
wl_list_insert(es->pending.frames.prev, &cb->link);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -413,20 +398,12 @@ _e_surface_cb_buffer_destroy(struct wl_listener *listener, void *data EINA_UNUSE
|
|||
static void
|
||||
_e_surface_frame_cb_destroy(struct wl_resource *resource)
|
||||
{
|
||||
E_Surface *es;
|
||||
E_Surface_Frame *cb;
|
||||
|
||||
/* try to cast the resource to our callback */
|
||||
if (!(cb = resource->data)) return;
|
||||
|
||||
es = cb->surface;
|
||||
wl_list_remove(&cb->link);
|
||||
|
||||
/* remove this callback from the pending frames callback list */
|
||||
es->pending.frames = eina_list_remove(es->pending.frames, cb);
|
||||
|
||||
/* remove this callback from the frames callback list */
|
||||
es->frames = eina_list_remove(es->frames, cb);
|
||||
|
||||
/* free the callback structure */
|
||||
E_FREE(cb);
|
||||
}
|
||||
|
|
|
@ -25,7 +25,7 @@ struct _E_Surface
|
|||
{
|
||||
struct wl_buffer *buffer;
|
||||
struct wl_listener buffer_destroy;
|
||||
Eina_List *frames;
|
||||
struct wl_list frames;
|
||||
|
||||
pixman_region32_t damage, opaque, input;
|
||||
|
||||
|
@ -37,10 +37,11 @@ struct _E_Surface
|
|||
pixman_region32_t opaque;
|
||||
pixman_region32_t clip;
|
||||
pixman_region32_t input;
|
||||
/* pixman_image_t *image; */
|
||||
|
||||
Eina_List *frames;
|
||||
struct wl_list frames;
|
||||
|
||||
E_Plane *plane;
|
||||
E_Output *output;
|
||||
|
||||
struct
|
||||
{
|
||||
|
@ -53,6 +54,8 @@ struct _E_Surface
|
|||
|
||||
Eina_Bool mapped : 1;
|
||||
|
||||
void *state;
|
||||
|
||||
void (*map)(E_Surface *surface, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h);
|
||||
void (*unmap)(E_Surface *surface);
|
||||
void (*configure)(E_Surface *surface, Evas_Coord x, Evas_Coord y, Evas_Coord w, Evas_Coord h);
|
||||
|
@ -60,18 +63,19 @@ struct _E_Surface
|
|||
|
||||
struct _E_Surface_Frame
|
||||
{
|
||||
E_Surface *surface;
|
||||
struct wl_resource resource;
|
||||
struct wl_list link;
|
||||
};
|
||||
|
||||
EAPI E_Surface *e_surface_new(unsigned int id);
|
||||
EAPI void e_surface_attach(E_Surface *es, struct wl_buffer *buffer);
|
||||
EAPI void e_surface_unmap(E_Surface *es);
|
||||
EAPI void e_surface_damage(E_Surface *es);
|
||||
EAPI void e_surface_damage_below(E_Surface *es);
|
||||
EAPI void e_surface_destroy(E_Surface *es);
|
||||
EAPI void e_surface_damage_calculate(E_Surface *es, pixman_region32_t *opaque);
|
||||
EAPI void e_surface_buffer_set(E_Surface *es, struct wl_buffer *buffer);
|
||||
EAPI void e_surface_show(E_Surface *es);
|
||||
EAPI void e_surface_repaint_schedule(E_Surface *es);
|
||||
|
||||
# endif
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue