static cairo_t *
_cairo_paginated_context_create (void *target)
{
    cairo_paginated_surface_t *surface = target;

    if (_cairo_surface_is_subsurface (&surface->base))
	surface = (cairo_paginated_surface_t *)
	    _cairo_surface_subsurface_get_target (&surface->base);

    return surface->recording_surface->backend->create_context (target);
}
Пример #2
0
static cairo_status_t
_cairo_gl_surface_operand_init (cairo_gl_operand_t *operand,
				const cairo_pattern_t *_src,
				cairo_gl_surface_t *dst,
				const cairo_rectangle_int_t *sample,
				const cairo_rectangle_int_t *extents,
				cairo_bool_t use_texgen)
{
    const cairo_surface_pattern_t *src = (cairo_surface_pattern_t *)_src;
    cairo_gl_surface_t *surface;
    cairo_surface_attributes_t *attributes;
    cairo_int_status_t status;

    surface = (cairo_gl_surface_t *) src->surface;
    if (surface->base.type != CAIRO_SURFACE_TYPE_GL)
	return CAIRO_INT_STATUS_UNSUPPORTED;

    if (surface->base.backend->type != CAIRO_SURFACE_TYPE_GL) {
	if (_cairo_surface_is_subsurface (&surface->base))
	    return _cairo_gl_subsurface_operand_init (operand, _src, dst,
						      sample, extents,
						      use_texgen);

	return CAIRO_INT_STATUS_UNSUPPORTED;
    }

    if (surface->base.device && surface->base.device != dst->base.device)
	return CAIRO_INT_STATUS_UNSUPPORTED;

    if (surface->base.device && ! _cairo_gl_surface_is_texture (surface))
	return CAIRO_INT_STATUS_UNSUPPORTED;

    status = _cairo_gl_surface_resolve_multisampling (surface);
    if (unlikely (status))
	return status;

    _cairo_gl_operand_copy(operand, &surface->operand);

    attributes = &operand->texture.attributes;
    cairo_matrix_multiply (&attributes->matrix,
			   &src->base.matrix,
			   &attributes->matrix);

    attributes->extend = src->base.extend;
    attributes->filter = src->base.filter;
    attributes->has_component_alpha = src->base.has_component_alpha;

    operand->texture.texgen = use_texgen;
    return CAIRO_STATUS_SUCCESS;
}
Пример #3
0
static cairo_int_status_t
_analyze_recording_surface_pattern (cairo_analysis_surface_t *surface,
				    const cairo_pattern_t    *pattern)
{
    const cairo_surface_pattern_t *surface_pattern;
    cairo_analysis_surface_t *tmp;
    cairo_surface_t *source, *proxy;
    cairo_matrix_t p2d;
    cairo_status_t status, analysis_status;

    assert (pattern->type == CAIRO_PATTERN_TYPE_SURFACE);
    surface_pattern = (const cairo_surface_pattern_t *) pattern;
    assert (surface_pattern->surface->type == CAIRO_SURFACE_TYPE_RECORDING);
    source = surface_pattern->surface;

    proxy = _cairo_surface_has_snapshot (source, &proxy_backend);
    if (proxy != NULL) {
	/* nothing untoward found so far */
	return CAIRO_STATUS_SUCCESS;
    }

    tmp = (cairo_analysis_surface_t *)
	_cairo_analysis_surface_create (surface->target);
    if (unlikely (tmp->base.status))
	return tmp->base.status;
    proxy = attach_proxy (source, &tmp->base);

    p2d = pattern->matrix;
    status = cairo_matrix_invert (&p2d);
    assert (status == CAIRO_STATUS_SUCCESS);

    cairo_matrix_multiply (&tmp->ctm, &p2d, &surface->ctm);
    tmp->has_ctm = ! _cairo_matrix_is_identity (&tmp->ctm);

    if (_cairo_surface_is_snapshot (source))
	source = _cairo_surface_snapshot_get_target (source);
    if (_cairo_surface_is_subsurface (source))
	source = _cairo_surface_subsurface_get_target (source);

    status = _cairo_recording_surface_replay_and_create_regions (source,
								 &tmp->base);
    analysis_status = tmp->has_unsupported ? CAIRO_INT_STATUS_IMAGE_FALLBACK : CAIRO_INT_STATUS_SUCCESS;
    detach_proxy (proxy);
    cairo_surface_destroy (&tmp->base);

    if (unlikely (status))
	return status;

    return analysis_status;
}
Пример #4
0
static void
_gl_pattern_fix_reference_count (const cairo_pattern_t *pattern)
{
   cairo_pattern_type_t pattern_type = cairo_pattern_get_type ((cairo_pattern_t *)pattern);

   /* We need to increase reference count on surface and gradient if
      the original_source_pattern is a cairo_gl_source_t type. */
    if (pattern_type == CAIRO_PATTERN_TYPE_SURFACE) {

	cairo_surface_pattern_t *surface_pattern = (cairo_surface_pattern_t *)pattern;
	cairo_surface_t *pattern_surface = surface_pattern->surface;

	if (cairo_surface_get_type (pattern_surface) == CAIRO_SURFACE_TYPE_GL &&
	    ! pattern_surface->device &&
	    ! _cairo_surface_is_subsurface (pattern_surface)) {

	    cairo_gl_source_t *_source = (cairo_gl_source_t *)pattern_surface;

	    switch (_source->operand.type) {
	    case CAIRO_GL_OPERAND_TEXTURE:
		cairo_surface_reference (&(_source->operand.texture.owns_surface)->base);
		break;
	    case CAIRO_GL_OPERAND_LINEAR_GRADIENT:
	    case CAIRO_GL_OPERAND_RADIAL_GRADIENT_A0:
	    case CAIRO_GL_OPERAND_RADIAL_GRADIENT_NONE:
	    case CAIRO_GL_OPERAND_RADIAL_GRADIENT_EXT:
		_cairo_gl_gradient_reference (_source->operand.gradient.gradient);
		break;
	    default:
	    case CAIRO_GL_OPERAND_NONE:
	    case CAIRO_GL_OPERAND_CONSTANT:
	    case CAIRO_GL_OPERAND_COUNT:
		break;
	    }
	}
    }
}