b=344571, upgrade cairo to 1.2.0+cvs, r+sr=stuart

This commit is contained in:
vladimir%pobox.com 2006-07-13 20:19:38 +00:00
Родитель e1d18649e8
Коммит d5026056ca
127 изменённых файлов: 8663 добавлений и 6810 удалений

Просмотреть файл

@ -12,7 +12,7 @@ http://www.cairographics.org/.
VERSIONS:
cairo 1.1.1 (cvs - 2006-06-03)
cairo 1.3.1 (cvs - 2006-07-13)
glitz 0.5.2 (cvs - 2006-01-10)
***** NOTE FOR VISUAL C++ 6.0 *****

Просмотреть файл

Просмотреть файл

Просмотреть файл

Просмотреть файл

Просмотреть файл

@ -88,6 +88,7 @@ CSRCS = \
cairo-pattern.c \
cairo-pen.c \
cairo-polygon.c \
cairo-rectangle.c \
cairo-region.c \
cairo-scaled-font.c \
cairo-scaled-font-subsets.c \
@ -134,7 +135,8 @@ ifeq ($(MOZ_WIDGET_TOOLKIT),gtk2)
CSRCS += cairo-font-subset.c \
cairo-base85-stream.c \
cairo-pdf-surface.c \
cairo-ps-surface.c
cairo-ps-surface.c \
cairo-type1-subset.c
EXPORTS += cairo-ps.h cairo-pdf.h
endif

Просмотреть файл

@ -43,13 +43,13 @@ typedef struct {
int height;
cairo_surface_t *target;
cairo_bool_t fallback;
} cairo_analysis_surface_t;
static cairo_int_status_t
_cairo_analysis_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_analysis_surface_t *surface = abstract_surface;
@ -255,5 +255,3 @@ _cairo_analysis_surface_has_unsupported (cairo_surface_t *abstract_surface)
return surface->fallback;
}

Просмотреть файл

@ -190,7 +190,7 @@ _cairo_arc_in_direction (cairo_t *cr,
_cairo_arc_in_direction (cr, xc, yc, radius,
angle_min, angle_mid,
dir);
_cairo_arc_in_direction (cr, xc, yc, radius,
angle_mid, angle_max,
dir);
@ -238,7 +238,7 @@ _cairo_arc_in_direction (cairo_t *cr,
* @radius: the radius of the arc
* @angle1: the start angle, in radians
* @angle2: the end angle, in radians
*
*
* Compute a path for the given arc and append it onto the current
* path within @cr. The arc will be accurate within the current
* tolerance and given the current transformation.
@ -267,7 +267,7 @@ _cairo_arc_path (cairo_t *cr,
* @ctm: the current transformation matrix
* @tolerance: the current tolerance value
* @path: the path onto which th earc will be appended
*
*
* Compute a path for the given arc (defined in the negative
* direction) and append it onto the current path within @cr. The arc
* will be accurate within the current tolerance and given the current

Просмотреть файл

@ -39,7 +39,7 @@
/**
* _cairo_array_init:
*
*
* Initialize a new cairo_array object to store objects each of size
* @element_size.
*
@ -66,7 +66,7 @@ _cairo_array_init (cairo_array_t *array, int element_size)
* _cairo_array_init_snapshot:
* @array: A #cairo_array_t to be initialized as a snapshot
* @other: The #cairo_array_t from which to create the snapshot
*
*
* Initialize @array as an immutable copy of @other. It is an error to
* call an array-modifying function (other than _cairo_array_fini) on
* @array after calling this function.
@ -104,7 +104,7 @@ _cairo_array_fini (cairo_array_t *array)
/**
* _cairo_array_grow_by:
*
*
* Increase the size of @array (if needed) so that there are at least
* @additional free spaces in the array. The actual size of the array
* is always increased by doubling as many times as necessary.
@ -153,7 +153,7 @@ _cairo_array_grow_by (cairo_array_t *array, int additional)
/**
* _cairo_array_truncate:
*
*
* Truncate size of the array to @num_elements if less than the
* current size. No memory is actually freed. The stored objects
* beyond @num_elements are simply "forgotten".
@ -169,7 +169,7 @@ _cairo_array_truncate (cairo_array_t *array, int num_elements)
/**
* _cairo_array_index:
*
*
* Return value: A pointer to object stored at @index. If the
* resulting value is assigned to a pointer to an object of the same
* element_size as initially passed to _cairo_array_init() then that
@ -210,7 +210,7 @@ _cairo_array_index (cairo_array_t *array, int index)
/**
* _cairo_array_copy_element:
*
*
* Copy a single element out of the array from index @index into the
* location pointed to by @dst.
**/
@ -222,7 +222,7 @@ _cairo_array_copy_element (cairo_array_t *array, int index, void *dst)
/**
* _cairo_array_append:
*
*
* Append a single item onto the array by growing the array by at
* least one element, then copying element_size bytes from @element
* into the array. The address of the resulting object within the
@ -245,7 +245,7 @@ _cairo_array_append (cairo_array_t *array,
/**
* _cairo_array_append:
*
*
* Append one or more items onto the array by growing the array by
* @num_elements, then copying @num_elements * element_size bytes from
* @elements into the array.
@ -275,12 +275,12 @@ _cairo_array_append_multiple (cairo_array_t *array,
/**
* _cairo_array_allocate:
*
*
* Allocate space at the end of the array for @num_elements additional
* elements, providing the address of the new memory chunk in
* @elements. This memory will be unitialized, but will be accounted
* for in the return value of _cairo_array_num_elements().
*
*
* Return value: CAIRO_STATUS_SUCCESS if successful or
* CAIRO_STATUS_NO_MEMORY if insufficient memory is available for the
* operation.
@ -309,7 +309,7 @@ _cairo_array_allocate (cairo_array_t *array,
/**
* _cairo_array_num_elements:
*
*
* Return value: The number of elements stored in @array.
**/
int
@ -329,7 +329,7 @@ typedef struct {
/**
* _cairo_user_data_array_init:
* @array: a #cairo_user_data_array_t
*
*
* Initializes a #cairo_user_data_array_t structure for future
* use. After initialization, the array has no keys. Call
* _cairo_user_data_array_fini() to free any allocated memory
@ -344,7 +344,7 @@ _cairo_user_data_array_init (cairo_user_data_array_t *array)
/**
* _cairo_user_data_array_fini:
* @array: a #cairo_user_data_array_t
*
*
* Destroys all current keys in the user data array and deallocates
* any memory allocated for the array itself.
**/
@ -369,11 +369,11 @@ _cairo_user_data_array_fini (cairo_user_data_array_t *array)
* @array: a #cairo_user_data_array_t
* @key: the address of the #cairo_user_data_key_t the user data was
* attached to
*
*
* Returns user data previously attached using the specified
* key. If no user data has been attached with the given key this
* function returns %NULL.
*
*
* Return value: the user data previously attached or %NULL.
**/
void *
@ -406,7 +406,7 @@ _cairo_user_data_array_get_data (cairo_user_data_array_t *array,
* @destroy: a #cairo_destroy_func_t which will be called when the
* user data array is destroyed or when new user data is attached using the
* same key.
*
*
* Attaches user data to a user data array. To remove user data,
* call this function with the key that was used to set it and %NULL
* for @data.
@ -460,4 +460,3 @@ _cairo_user_data_array_set_data (cairo_user_data_array_t *array,
return CAIRO_STATUS_SUCCESS;
}

Просмотреть файл

@ -1,3 +1,4 @@
/* -*- Mode: c; c-basic-offset: 4; tab-width: 8; indent-tabs-mode: t; -*- */
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2004 Calum Robinson
@ -53,8 +54,11 @@
/* If this isn't defined, we must be building on non-intel,
* hence it will be 0.
*/
#ifndef kCGBitmapByteOrder32Host
#define kCGBitmapByteOrder32Host 0
#ifdef __BIG_ENDIAN__
#define CG_BITMAP_BYTE_ORDER_FLAG 0
#else /* Little endian. */
/* x86, and will be a 10.4u SDK; ByteOrder32Host will be defined */
#define CG_BITMAP_BYTE_ORDER_FLAG kCGBitmapByteOrder32Host
#endif
typedef struct _cairo_atsui_font_face cairo_atsui_font_face_t;
@ -76,7 +80,6 @@ struct _cairo_atsui_font {
ATSUFontID fontID;
};
struct _cairo_atsui_font_face {
cairo_font_face_t base;
ATSUFontID font_id;
@ -116,7 +119,7 @@ static const cairo_font_face_backend_t _cairo_atsui_font_face_backend = {
_cairo_atsui_font_face_scaled_font_create
};
cairo_public cairo_font_face_t *
cairo_font_face_t *
cairo_atsui_font_face_create_for_atsu_font_id (ATSUFontID font_id)
{
cairo_atsui_font_face_t *font_face;
@ -134,8 +137,6 @@ cairo_atsui_font_face_create_for_atsu_font_id (ATSUFontID font_id)
return &font_face->base;
}
static CGAffineTransform
CGAffineTransformMakeWithCairoFontScale(const cairo_matrix_t *scale)
{
@ -186,7 +187,7 @@ _cairo_atsui_font_set_metrics (cairo_atsui_font_t *font)
if (err == noErr) {
cairo_font_extents_t extents;
extents.ascent = metrics.ascent;
extents.descent = -metrics.descent;
extents.height = metrics.capHeight;
@ -218,6 +219,8 @@ _cairo_atsui_font_create_scaled (cairo_font_face_t *font_face,
cairo_status_t status;
font = malloc(sizeof(cairo_atsui_font_t));
if (font == NULL)
return CAIRO_STATUS_NO_MEMORY;
_cairo_scaled_font_init(&font->base, font_face, font_matrix, ctm, options,
&cairo_atsui_scaled_font_backend);
@ -315,12 +318,9 @@ _cairo_atsui_font_create_toy(cairo_toy_font_face_t *toy_face,
kFontNoLanguageCode, &fontID);
}
/* Need to specify more tags, e.g. kATSUHangingInhibitFactorTag */
/* Should use ATSU Variations to exactly specify weight and slant */
ATSUAttributeTag styleTags[] =
{ kATSUQDItalicTag, kATSUQDBoldfaceTag, kATSUFontTag };
ATSUAttributeValuePtr styleValues[] =
{ &isItalic, &isBold, &fontID };
ATSUAttributeValuePtr styleValues[] = { &isItalic, &isBold, &fontID };
ByteCount styleSizes[] =
{ sizeof(Boolean), sizeof(Boolean), sizeof(ATSUFontID) };
@ -346,28 +346,6 @@ _cairo_atsui_font_fini(void *abstract_font)
ATSUDisposeStyle(font->unscaled_style);
}
cairo_bool_t
_cairo_scaled_font_is_atsui (cairo_scaled_font_t *sfont)
{
return (sfont->backend == &cairo_atsui_scaled_font_backend);
}
ATSUStyle
_cairo_atsui_scaled_font_get_atsu_style (cairo_scaled_font_t *sfont)
{
cairo_atsui_font_t *afont = (cairo_atsui_font_t *) sfont;
return afont->style;
}
ATSUFontID
_cairo_atsui_scaled_font_get_atsu_font_id (cairo_scaled_font_t *sfont)
{
cairo_atsui_font_t *afont = (cairo_atsui_font_t *) sfont;
return afont->fontID;
}
static cairo_status_t
_cairo_atsui_font_init_glyph_metrics (cairo_atsui_font_t *font,
cairo_scaled_glyph_t *scaled_glyph)
@ -392,9 +370,9 @@ _cairo_atsui_font_init_glyph_metrics (cairo_atsui_font_t *font,
extents.x_bearing = metricsH.sideBearing.x;
extents.y_bearing = metricsV.advance.y;
extents.width =
extents.width =
metricsH.advance.x - metricsH.sideBearing.x - metricsH.otherSideBearing.x;
extents.height =
extents.height =
-metricsV.advance.y - metricsV.sideBearing.y - metricsV.otherSideBearing.y;
extents.x_advance = metricsH.advance.x;
extents.y_advance = 0;
@ -406,7 +384,7 @@ _cairo_atsui_font_init_glyph_metrics (cairo_atsui_font_t *font,
return CAIRO_STATUS_SUCCESS;
}
static OSStatus
static OSStatus
_move_to (const Float32Point *point,
void *callback_data)
{
@ -420,7 +398,7 @@ _move_to (const Float32Point *point,
return noErr;
}
static OSStatus
static OSStatus
_line_to (const Float32Point *point,
void *callback_data)
{
@ -429,7 +407,7 @@ _line_to (const Float32Point *point,
_cairo_path_fixed_line_to (path,
_cairo_fixed_from_double(point->x),
_cairo_fixed_from_double(point->y));
return noErr;
}
@ -448,7 +426,7 @@ _curve_to (const Float32Point *point1,
_cairo_fixed_from_double(point2->y),
_cairo_fixed_from_double(point3->x),
_cairo_fixed_from_double(point3->y));
return noErr;
}
@ -463,7 +441,7 @@ _close_path (void *callback_data)
return noErr;
}
static cairo_status_t
static cairo_status_t
_cairo_atsui_scaled_font_init_glyph_path (cairo_atsui_font_t *scaled_font,
cairo_scaled_glyph_t *scaled_glyph)
{
@ -497,7 +475,7 @@ _cairo_atsui_scaled_font_init_glyph_path (cairo_atsui_font_t *scaled_font,
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
static cairo_int_status_t
_cairo_atsui_font_scaled_glyph_init (void *abstract_font,
cairo_scaled_glyph_t *scaled_glyph,
cairo_scaled_glyph_info_t info)
@ -520,12 +498,12 @@ _cairo_atsui_font_scaled_glyph_init (void *abstract_font,
return CAIRO_STATUS_SUCCESS;
}
static cairo_int_status_t
static cairo_int_status_t
_cairo_atsui_font_text_to_glyphs (void *abstract_font,
double x,
double y,
const char *utf8,
cairo_glyph_t **glyphs,
cairo_glyph_t **glyphs,
int *num_glyphs)
{
cairo_status_t status = CAIRO_STATUS_SUCCESS;
@ -557,7 +535,7 @@ _cairo_atsui_font_text_to_glyphs (void *abstract_font,
&glyphCount);
*num_glyphs = glyphCount - 1;
*glyphs =
*glyphs =
(cairo_glyph_t *) malloc(*num_glyphs * (sizeof (cairo_glyph_t)));
if (*glyphs == NULL) {
return CAIRO_STATUS_NO_MEMORY;
@ -571,15 +549,15 @@ _cairo_atsui_font_text_to_glyphs (void *abstract_font,
free (utf16);
ATSUDirectReleaseLayoutDataArrayPtr(NULL,
ATSUDirectReleaseLayoutDataArrayPtr(NULL,
kATSUDirectDataLayoutRecordATSLayoutRecordCurrent,
(void *) &layoutRecords);
ATSUDisposeTextLayout(textLayout);
return CAIRO_STATUS_SUCCESS;
}
static cairo_int_status_t
static cairo_int_status_t
_cairo_atsui_font_old_show_glyphs (void *abstract_font,
cairo_operator_t op,
cairo_pattern_t *pattern,
@ -594,106 +572,130 @@ _cairo_atsui_font_old_show_glyphs (void *abstract_font,
int num_glyphs)
{
cairo_atsui_font_t *font = abstract_font;
CGContextRef myBitmapContext;
CGColorSpaceRef colorSpace;
CGContextRef myBitmapContext = 0, drawingContext;
CGColorSpaceRef colorSpace = 0;
cairo_image_surface_t *destImageSurface;
int i, bits_per_comp, alpha;
void *extra = NULL;
cairo_bool_t can_draw_directly;
cairo_rectangle_int16_t rect;
cairo_rectangle_fixed_t rect = {dest_x, dest_y, width, height};
_cairo_surface_acquire_dest_image(generic_surface,
&rect,
&destImageSurface,
&rect,
&extra);
/* Check if we can draw directly to the destination surface */
can_draw_directly = _cairo_surface_is_quartz (generic_surface) &&
_cairo_pattern_is_opaque_solid (pattern) &&
op == CAIRO_OPERATOR_OVER;
/* Create a CGBitmapContext for the dest surface for drawing into */
if (destImageSurface->depth == 1) {
colorSpace = CGColorSpaceCreateDeviceGray();
bits_per_comp = 1;
alpha = kCGImageAlphaNone;
} else if (destImageSurface->depth == 8) {
colorSpace = CGColorSpaceCreateDeviceGray();
bits_per_comp = 8;
alpha = kCGImageAlphaNone;
} else if (destImageSurface->depth == 24) {
colorSpace = CGColorSpaceCreateDeviceRGB();
bits_per_comp = 8;
alpha = kCGImageAlphaNoneSkipFirst | kCGBitmapByteOrder32Host;
} else if (destImageSurface->depth == 32) {
colorSpace = CGColorSpaceCreateDeviceRGB();
bits_per_comp = 8;
alpha = kCGImageAlphaPremultipliedFirst | kCGBitmapByteOrder32Host;
if (!can_draw_directly) {
rect.x = dest_x;
rect.y = dest_y;
rect.width = width;
rect.height = height;
_cairo_surface_acquire_dest_image(generic_surface,
&rect,
&destImageSurface,
&rect,
&extra);
/* Create a CGBitmapContext for the dest surface for drawing into */
if (destImageSurface->depth == 1) {
colorSpace = CGColorSpaceCreateDeviceGray();
bits_per_comp = 1;
alpha = kCGImageAlphaNone;
} else if (destImageSurface->depth == 8) {
colorSpace = CGColorSpaceCreateDeviceGray();
bits_per_comp = 8;
alpha = kCGImageAlphaNone;
} else if (destImageSurface->depth == 24) {
colorSpace = CGColorSpaceCreateDeviceRGB();
bits_per_comp = 8;
alpha = kCGImageAlphaNoneSkipFirst | CG_BITMAP_BYTE_ORDER_FLAG;
} else if (destImageSurface->depth == 32) {
colorSpace = CGColorSpaceCreateDeviceRGB();
bits_per_comp = 8;
alpha = kCGImageAlphaPremultipliedFirst | CG_BITMAP_BYTE_ORDER_FLAG;
} else {
// not reached
return CAIRO_INT_STATUS_UNSUPPORTED;
}
myBitmapContext = CGBitmapContextCreate(destImageSurface->data,
destImageSurface->width,
destImageSurface->height,
bits_per_comp,
destImageSurface->stride,
colorSpace,
alpha);
CGColorSpaceRelease(colorSpace);
CGContextTranslateCTM(myBitmapContext, 0, destImageSurface->height);
CGContextScaleCTM(myBitmapContext, 1.0f, -1.0f);
drawingContext = myBitmapContext;
} else {
// not reached
return CAIRO_INT_STATUS_UNSUPPORTED;
drawingContext = ((cairo_quartz_surface_t *)generic_surface)->context;
CGContextSaveGState (drawingContext);
}
myBitmapContext = CGBitmapContextCreate(destImageSurface->data,
destImageSurface->width,
destImageSurface->height,
bits_per_comp,
destImageSurface->stride,
colorSpace,
alpha);
CGContextTranslateCTM(myBitmapContext, 0, destImageSurface->height);
CGContextScaleCTM(myBitmapContext, 1.0f, -1.0f);
ATSFontRef atsFont = FMGetATSFontRefFromFont(font->fontID);
CGFontRef cgFont = CGFontCreateWithPlatformFont(&atsFont);
CGContextSetFont(myBitmapContext, cgFont);
CGContextSetFont(drawingContext, cgFont);
CGAffineTransform textTransform =
CGAffineTransformMakeWithCairoFontScale(&font->base.scale);
textTransform = CGAffineTransformScale(textTransform, 1.0f, -1.0f);
CGContextSetFontSize(myBitmapContext, 1.0);
CGContextSetTextMatrix(myBitmapContext, textTransform);
CGContextSetFontSize(drawingContext, 1.0);
CGContextSetTextMatrix(drawingContext, textTransform);
if (pattern->type == CAIRO_PATTERN_TYPE_SOLID &&
_cairo_pattern_is_opaque_solid(pattern))
{
cairo_solid_pattern_t *solid = (cairo_solid_pattern_t *)pattern;
CGContextSetRGBFillColor(myBitmapContext,
CGContextSetRGBFillColor(drawingContext,
solid->color.red,
solid->color.green,
solid->color.blue, 1.0f);
} else {
CGContextSetRGBFillColor(myBitmapContext, 0.0f, 0.0f, 0.0f, 0.0f);
CGContextSetRGBFillColor(drawingContext, 0.0f, 0.0f, 0.0f, 0.0f);
}
if (_cairo_surface_is_quartz (generic_surface)) {
cairo_quartz_surface_t *surface = (cairo_quartz_surface_t *)generic_surface;
if (surface->clip_region) {
pixman_box16_t *boxes = pixman_region_rects (surface->clip_region);
int num_boxes = pixman_region_num_rects (surface->clip_region);
CGRect stack_rects[10];
CGRect *rects;
int i;
if (num_boxes > 10)
rects = malloc (sizeof (CGRect) * num_boxes);
else
rects = stack_rects;
for (i = 0; i < num_boxes; i++) {
rects[i].origin.x = boxes[i].x1;
rects[i].origin.y = boxes[i].y1;
rects[i].size.width = boxes[i].x2 - boxes[i].x1;
rects[i].size.height = boxes[i].y2 - boxes[i].y1;
}
CGContextClipToRects (myBitmapContext, rects, num_boxes);
if (rects != stack_rects)
free(rects);
}
} else {
/* XXX: Need to get the text clipped */
if (_cairo_surface_is_quartz (generic_surface)) {
cairo_quartz_surface_t *surface = (cairo_quartz_surface_t *)generic_surface;
if (surface->clip_region) {
pixman_box16_t *boxes = pixman_region_rects (surface->clip_region);
int num_boxes = pixman_region_num_rects (surface->clip_region);
CGRect stack_rects[10];
CGRect *rects;
int i;
/* XXX: Return-value of malloc needs to be checked for
* NULL. Can someone fix this who is more familiar with
* the cleanup needed in this function?
*/
if (num_boxes > 10)
rects = malloc (sizeof (CGRect) * num_boxes);
else
rects = stack_rects;
for (i = 0; i < num_boxes; i++) {
rects[i].origin.x = boxes[i].x1;
rects[i].origin.y = boxes[i].y1;
rects[i].size.width = boxes[i].x2 - boxes[i].x1;
rects[i].size.height = boxes[i].y2 - boxes[i].y1;
}
CGContextClipToRects (drawingContext, rects, num_boxes);
if (rects != stack_rects)
free(rects);
}
} else {
/* XXX: Need to get the text clipped */
}
/* TODO - bold and italic text
*
* We could draw the text using ATSUI and get bold, italics
@ -701,29 +703,52 @@ _cairo_atsui_font_old_show_glyphs (void *abstract_font,
* that we don't really need...
*/
for (i = 0; i < num_glyphs; i++) {
CGGlyph theGlyph = glyphs[i].index;
CGContextShowGlyphsAtPoint(myBitmapContext,
CGContextShowGlyphsAtPoint(drawingContext,
glyphs[i].x,
glyphs[i].y,
&theGlyph, 1);
}
if (!can_draw_directly) {
CGContextRelease(myBitmapContext);
CGColorSpaceRelease(colorSpace);
CGContextRelease(myBitmapContext);
_cairo_surface_release_dest_image(generic_surface,
&rect,
destImageSurface,
&rect,
extra);
_cairo_surface_release_dest_image(generic_surface,
&rect,
destImageSurface,
&rect,
extra);
} else {
CGContextRestoreGState (drawingContext);
}
return CAIRO_STATUS_SUCCESS;
}
cairo_bool_t
_cairo_scaled_font_is_atsui (cairo_scaled_font_t *sfont)
{
return (sfont->backend == &cairo_atsui_scaled_font_backend);
}
ATSUStyle
_cairo_atsui_scaled_font_get_atsu_style (cairo_scaled_font_t *sfont)
{
cairo_atsui_font_t *afont = (cairo_atsui_font_t *) sfont;
return afont->style;
}
ATSUFontID
_cairo_atsui_scaled_font_get_atsu_font_id (cairo_scaled_font_t *sfont)
{
cairo_atsui_font_t *afont = (cairo_atsui_font_t *) sfont;
return afont->fontID;
}
const cairo_scaled_font_backend_t cairo_atsui_scaled_font_backend = {
CAIRO_FONT_TYPE_ATSUI,
_cairo_atsui_font_create_toy,

Просмотреть файл

@ -1,5 +1,5 @@
/* cairo_output_stream.c: Output stream abstraction
*
*
* Copyright © 2005 Red Hat, Inc
*
* This library is free software; you can redistribute it and/or
@ -35,8 +35,10 @@
*/
#include "cairoint.h"
#include "cairo-output-stream-private.h"
typedef struct _cairo_base85_stream {
cairo_output_stream_t base;
cairo_output_stream_t *output;
unsigned char four_tuple[4];
int pending;
@ -49,7 +51,7 @@ _expand_four_tuple_to_five (unsigned char four_tuple[4],
{
uint32_t value;
int digit, i;
value = four_tuple[0] << 24 | four_tuple[1] << 16 | four_tuple[2] << 8 | four_tuple[3];
if (all_zero)
*all_zero = TRUE;
@ -63,11 +65,11 @@ _expand_four_tuple_to_five (unsigned char four_tuple[4],
}
static cairo_status_t
_cairo_base85_stream_write (void *closure,
const unsigned char *data,
unsigned int length)
_cairo_base85_stream_write (cairo_output_stream_t *base,
const unsigned char *data,
unsigned int length)
{
cairo_base85_stream_t *stream = closure;
cairo_base85_stream_t *stream = (cairo_base85_stream_t *) base;
const unsigned char *ptr = data;
unsigned char five_tuple[5];
cairo_bool_t is_zero;
@ -89,10 +91,9 @@ _cairo_base85_stream_write (void *closure,
}
static cairo_status_t
_cairo_base85_stream_close (void *closure)
_cairo_base85_stream_close (cairo_output_stream_t *base)
{
cairo_status_t status;
cairo_base85_stream_t *stream = closure;
cairo_base85_stream_t *stream = (cairo_base85_stream_t *) base;
unsigned char five_tuple[5];
if (stream->pending) {
@ -104,11 +105,7 @@ _cairo_base85_stream_close (void *closure)
/* Mark end of base85 data */
_cairo_output_stream_printf (stream->output, "~>");
status = _cairo_output_stream_get_status (stream->output);
free (stream);
return status;
return _cairo_output_stream_get_status (stream->output);
}
cairo_output_stream_t *
@ -120,11 +117,11 @@ _cairo_base85_stream_create (cairo_output_stream_t *output)
if (stream == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil;
_cairo_output_stream_init (&stream->base,
_cairo_base85_stream_write,
_cairo_base85_stream_close);
stream->output = output;
stream->pending = 0;
return _cairo_output_stream_create (_cairo_base85_stream_write,
_cairo_base85_stream_close,
stream);
return &stream->base;
}

Просмотреть файл

@ -58,4 +58,3 @@ CAIRO_END_DECLS
#endif /* CAIRO_HAS_BEOS_SURFACE */
#endif /* CAIRO_BEOS_H */

Просмотреть файл

@ -57,7 +57,6 @@ static void
_cairo_cache_shrink_to_accomodate (cairo_cache_t *cache,
unsigned long additional);
static cairo_status_t
_cairo_cache_init (cairo_cache_t *cache,
cairo_cache_keys_equal_func_t keys_equal,
@ -104,7 +103,7 @@ _cairo_cache_fini (cairo_cache_t *cache)
* @keys_equal: a function to return %TRUE if two keys are equal
* @entry_destroy: destroy notifier for cache entries
* @max_size: the maximum size for this cache
*
*
* Creates a new cache using the keys_equal() function to determine
* the equality of entries.
*
@ -131,8 +130,8 @@ _cairo_cache_fini (cairo_cache_t *cache)
* _cairo_cache_freeze() and _cairo_cache_thaw() calls can be
* used to establish a window during which no automatic removal of
* entries will occur.
*
* Return value:
*
* Return value:
**/
cairo_cache_t *
_cairo_cache_create (cairo_cache_keys_equal_func_t keys_equal,
@ -158,7 +157,7 @@ _cairo_cache_create (cairo_cache_keys_equal_func_t keys_equal,
/**
* _cairo_cache_destroy:
* @cache: a cache to destroy
*
*
* Immediately destroys the given cache, freeing all resources
* associated with it. As part of this process, the entry_destroy()
* function, (as passed to _cairo_cache_create()), will be called for
@ -176,7 +175,7 @@ _cairo_cache_destroy (cairo_cache_t *cache)
* _cairo_cache_freeze:
* @cache: a cache with some precious entries in it (or about to be
* added)
*
*
* Disable the automatic ejection of entries from the cache. For as
* long as the cache is "frozen", calls to _cairo_cache_insert() will
* add new entries to the cache regardless of how large the cache
@ -198,7 +197,7 @@ _cairo_cache_freeze (cairo_cache_t *cache)
* _cairo_cache_thaw:
* @cache: a cache, just after the entries in it have become less
* precious
*
*
* Cancels the effects of _cairo_cache_freeze().
*
* When a number of calls to _cairo_cache_thaw() is made corresponding
@ -224,11 +223,11 @@ _cairo_cache_thaw (cairo_cache_t *cache)
* @cache: a cache
* @key: the key of interest
* @entry_return: pointer for return value
*
*
* Performs a lookup in @cache looking for an entry which has a key
* that matches @key, (as determined by the keys_equal() function
* passed to _cairo_cache_create()).
*
*
* Return value: %TRUE if there is an entry in the cache that matches
* @key, (which will now be in *entry_return). %FALSE otherwise, (in
* which case *entry_return will be %NULL).
@ -246,9 +245,9 @@ _cairo_cache_lookup (cairo_cache_t *cache,
/**
* _cairo_cache_remove_random:
* @cache: a cache
*
*
* Remove a random entry from the cache.
*
*
* Return value: CAIRO_STATUS_SUCCESS if an entry was successfully
* removed. CAIRO_INT_STATUS_CACHE_EMPTY if there are no entries that
* can be removed.
@ -271,7 +270,7 @@ _cairo_cache_remove_random (cairo_cache_t *cache)
* _cairo_cache_shrink_to_accomodate:
* @cache: a cache
* @additional: additional size requested in bytes
*
*
* If cache is not frozen, eject entries randomly until the size of
* the cache is at least @additional bytes less than
* cache->max_size. That is, make enough room to accomodate a new
@ -300,11 +299,11 @@ _cairo_cache_shrink_to_accomodate (cairo_cache_t *cache,
* _cairo_cache_insert:
* @cache: a cache
* @entry: an entry to be inserted
*
*
* Insert @entry into the cache. If an entry exists in the cache with
* a matching key, then the old entry will be removed first, (and the
* entry_destroy() callback will be called on it).
*
*
* Return value: CAIRO_STATUS_SUCCESS if successful or
* CAIRO_STATUS_NO_MEMORY if insufficient memory is available.
**/
@ -330,7 +329,7 @@ _cairo_cache_insert (cairo_cache_t *cache,
* _cairo_cache_remove:
* @cache: a cache
* @entry: an entry that exists in the cache
*
*
* Remove an existing entry from the cache.
*
* (NOTE: If any caller wanted access to a non-static version of this
@ -356,7 +355,7 @@ _cairo_cache_remove (cairo_cache_t *cache,
* @cache: a cache
* @cache_callback: function to be called for each entry
* @closure: additional argument to be passed to @cache_callback
*
*
* Call @cache_callback for each entry in the cache, in a
* non-specified order.
**/
@ -379,4 +378,3 @@ _cairo_hash_string (const char *c)
hash = ((hash << 5) + hash) + *c++;
return hash;
}

Просмотреть файл

@ -51,7 +51,7 @@ struct _cairo_clip {
cairo_clip_mode_t mode;
/*
* Mask-based clipping for cases where the backend
* Mask-based clipping for cases where the backend
* clipping isn't sufficiently able.
*
* The rectangle here represents the
@ -61,7 +61,7 @@ struct _cairo_clip {
* clip paths
*/
cairo_surface_t *surface;
cairo_rectangle_fixed_t surface_rect;
cairo_rectangle_int16_t surface_rect;
/*
* Surface clip serial number to store
* in the surface when this clip is set
@ -105,7 +105,7 @@ _cairo_clip_clip (cairo_clip_t *clip,
cairo_private cairo_status_t
_cairo_clip_intersect_to_rectangle (cairo_clip_t *clip,
cairo_rectangle_fixed_t *rectangle);
cairo_rectangle_int16_t *rectangle);
cairo_private cairo_status_t
_cairo_clip_intersect_to_region (cairo_clip_t *clip,
@ -117,7 +117,7 @@ _cairo_clip_combine_to_surface (cairo_clip_t *clip,
cairo_surface_t *dst,
int dst_x,
int dst_y,
const cairo_rectangle_fixed_t *extents);
const cairo_rectangle_int16_t *extents);
cairo_private void
_cairo_clip_translate (cairo_clip_t *clip,
@ -133,9 +133,4 @@ _cairo_clip_extract_rectangles (cairo_clip_t *clip,
cairo_clip_rect_t *rectangles_out,
int *num_rectangles_out);
cairo_private void
_cairo_clip_translate (cairo_clip_t *clip,
cairo_fixed_t tx,
cairo_fixed_t ty);
#endif /* CAIRO_CLIP_PRIVATE_H */

Просмотреть файл

@ -114,13 +114,13 @@ _cairo_clip_reset (cairo_clip_t *clip)
_cairo_clip_path_destroy (clip->path);
clip->path = NULL;
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
_cairo_clip_intersect_to_rectangle (cairo_clip_t *clip,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
if (!clip)
return CAIRO_STATUS_SUCCESS;
@ -133,11 +133,11 @@ _cairo_clip_intersect_to_rectangle (cairo_clip_t *clip,
pixman_region16_t *intersection;
cairo_status_t status = CAIRO_STATUS_SUCCESS;
pixman_region_status_t pixman_status;
intersection = _cairo_region_create_from_rectangle (rectangle);
if (intersection == NULL)
return CAIRO_STATUS_NO_MEMORY;
pixman_status = pixman_region_intersect (intersection,
clip->region,
intersection);
@ -176,11 +176,11 @@ _cairo_clip_intersect_to_region (cairo_clip_t *clip,
pixman_region16_t *clip_rect;
pixman_region_status_t pixman_status;
cairo_status_t status = CAIRO_STATUS_SUCCESS;
clip_rect = _cairo_region_create_from_rectangle (&clip->surface_rect);
if (clip_rect == NULL)
return CAIRO_STATUS_NO_MEMORY;
pixman_status = pixman_region_intersect (region,
clip_rect,
region);
@ -206,24 +206,24 @@ _cairo_clip_combine_to_surface (cairo_clip_t *clip,
cairo_surface_t *dst,
int dst_x,
int dst_y,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_pattern_union_t pattern;
cairo_status_t status;
_cairo_pattern_init_for_surface (&pattern.surface, clip->surface);
status = _cairo_surface_composite (op,
&pattern.base,
NULL,
dst,
extents->x - clip->surface_rect.x,
extents->y - clip->surface_rect.y,
extents->y - clip->surface_rect.y,
0, 0,
extents->x - dst_x,
extents->y - dst_y,
extents->width, extents->height);
_cairo_pattern_fini (&pattern.base);
return status;
@ -298,11 +298,11 @@ _cairo_clip_intersect_region (cairo_clip_t *clip,
if (clip->mode != CAIRO_CLIP_MODE_REGION)
return CAIRO_INT_STATUS_UNSUPPORTED;
status = _cairo_traps_extract_region (traps, &region);
if (status)
return status;
if (region == NULL)
return CAIRO_INT_STATUS_UNSUPPORTED;
@ -311,13 +311,13 @@ _cairo_clip_intersect_region (cairo_clip_t *clip,
clip->region = region;
} else {
pixman_region16_t *intersection = pixman_region_create();
if (pixman_region_intersect (intersection,
if (pixman_region_intersect (intersection,
clip->region, region)
== PIXMAN_REGION_STATUS_SUCCESS) {
pixman_region_destroy (clip->region);
clip->region = intersection;
} else {
} else {
status = CAIRO_STATUS_NO_MEMORY;
}
pixman_region_destroy (region);
@ -336,7 +336,7 @@ _cairo_clip_intersect_mask (cairo_clip_t *clip,
{
cairo_pattern_union_t pattern;
cairo_box_t extents;
cairo_rectangle_fixed_t surface_rect, target_rect;
cairo_rectangle_int16_t surface_rect, target_rect;
cairo_surface_t *surface;
cairo_status_t status;
@ -369,7 +369,7 @@ _cairo_clip_intersect_mask (cairo_clip_t *clip,
_cairo_traps_translate (traps, -surface_rect.x, -surface_rect.y);
_cairo_pattern_init_solid (&pattern.solid, CAIRO_COLOR_WHITE);
status = _cairo_surface_composite_trapezoids (CAIRO_OPERATOR_IN,
&pattern.base,
surface,
@ -433,16 +433,7 @@ _cairo_clip_clip (cairo_clip_t *clip,
{
cairo_status_t status;
cairo_traps_t traps;
cairo_path_fixed_t path_transformed;
if (_cairo_surface_has_device_offset_or_scale (target)) {
_cairo_path_fixed_init_copy (&path_transformed, path);
_cairo_path_fixed_offset (&path_transformed,
_cairo_fixed_from_double (target->device_x_offset),
_cairo_fixed_from_double (target->device_y_offset));
path = &path_transformed;
}
status = _cairo_clip_intersect_path (clip,
path, fill_rule, tolerance,
antialias);
@ -452,7 +443,6 @@ _cairo_clip_clip (cairo_clip_t *clip,
if (status != CAIRO_INT_STATUS_UNSUPPORTED)
return status;
_cairo_traps_init (&traps);
status = _cairo_path_fixed_fill_to_traps (path,
fill_rule,
@ -466,15 +456,85 @@ _cairo_clip_clip (cairo_clip_t *clip,
goto bail;
status = _cairo_clip_intersect_mask (clip, &traps, antialias, target);
bail:
_cairo_traps_fini (&traps);
if (path == &path_transformed)
_cairo_path_fixed_fini (&path_transformed);
return status;
}
void
_cairo_clip_translate (cairo_clip_t *clip,
cairo_fixed_t tx,
cairo_fixed_t ty)
{
if (clip->region) {
pixman_region_translate (clip->region,
_cairo_fixed_integer_part (tx),
_cairo_fixed_integer_part (ty));
}
if (clip->surface) {
clip->surface_rect.x += _cairo_fixed_integer_part (tx);
clip->surface_rect.y += _cairo_fixed_integer_part (ty);
}
if (clip->path) {
cairo_clip_path_t *clip_path = clip->path;
cairo_matrix_t matrix;
cairo_matrix_init_translate (&matrix,
_cairo_fixed_to_double (tx),
_cairo_fixed_to_double (ty));
while (clip_path) {
_cairo_path_fixed_device_transform (&clip_path->path, &matrix);
clip_path = clip_path->prev;
}
}
}
static void
_cairo_clip_path_reapply_clip_path (cairo_clip_t *clip,
cairo_clip_path_t *clip_path)
{
if (clip_path->prev)
_cairo_clip_path_reapply_clip_path (clip, clip_path->prev);
_cairo_clip_intersect_path (clip,
&clip_path->path,
clip_path->fill_rule,
clip_path->tolerance,
clip_path->antialias);
}
void
_cairo_clip_init_deep_copy (cairo_clip_t *clip,
cairo_clip_t *other,
cairo_surface_t *target)
{
_cairo_clip_init (clip, target);
if (other->mode != clip->mode) {
/* We should reapply the original clip path in this case, and let
* whatever the right handling is happen */
} else {
if (other->region) {
clip->region = pixman_region_create ();
pixman_region_copy (clip->region, other->region);
}
if (other->surface) {
_cairo_surface_clone_similar (target, clip->surface, &clip->surface);
clip->surface_rect = other->surface_rect;
}
if (other->path) {
_cairo_clip_path_reapply_clip_path (clip, other->path);
}
}
}
cairo_bool_t
_cairo_clip_has_clip (cairo_clip_t *clip)
{
@ -524,70 +584,3 @@ _cairo_clip_extract_rectangles (cairo_clip_t *clip,
return _cairo_region_to_clip_rectangles (clip->region,
max_rectangles, rectangles_out, num_rectangles_out);
}
void
_cairo_clip_translate (cairo_clip_t *clip,
cairo_fixed_t tx,
cairo_fixed_t ty)
{
if (clip->region) {
pixman_region_translate (clip->region,
_cairo_fixed_integer_part (tx),
_cairo_fixed_integer_part (ty));
}
if (clip->surface) {
clip->surface_rect.x += _cairo_fixed_integer_part (tx);
clip->surface_rect.y += _cairo_fixed_integer_part (ty);
}
if (clip->path) {
cairo_clip_path_t *clip_path = clip->path;
while (clip_path) {
_cairo_path_fixed_offset (&clip_path->path, tx, ty);
clip_path = clip_path->prev;
}
}
}
static void
_cairo_clip_path_reapply_clip_path (cairo_clip_t *clip,
cairo_clip_path_t *clip_path)
{
if (clip_path->prev)
_cairo_clip_path_reapply_clip_path (clip, clip_path->prev);
_cairo_clip_intersect_path (clip,
&clip_path->path,
clip_path->fill_rule,
clip_path->tolerance,
clip_path->antialias);
}
void
_cairo_clip_init_deep_copy (cairo_clip_t *clip,
cairo_clip_t *other,
cairo_surface_t *target)
{
_cairo_clip_init (clip, target);
if (other->mode != clip->mode) {
/* We should reapply the original clip path in this case, and let
* whatever the right handling is happen */
} else {
if (other->region) {
clip->region = pixman_region_create ();
pixman_region_copy (clip->region, other->region);
}
if (other->surface) {
_cairo_surface_clone_similar (target, clip->surface, &clip->surface);
clip->surface_rect = other->surface_rect;
}
if (other->path) {
_cairo_clip_path_reapply_clip_path (clip, other->path);
}
}
}

Просмотреть файл

@ -35,11 +35,9 @@
#include "cairoint.h"
#include "cairo-clip-private.h"
/**
* cairo_debug_reset_static_data:
*
*
* Resets all static data within cairo to its original state,
* (ie. identical to the state at the time of program invocation). For
* example, all caches within cairo will be flushed empty.
@ -71,195 +69,3 @@ cairo_debug_reset_static_data (void)
_cairo_ft_font_reset_static_data ();
#endif
}
#if 0
/*
* clip dumper
*/
void
cairo_debug_dump_clip (struct _cairo_clip *clip,
FILE *fp)
{
fprintf (fp, "clip %p: %s ", (clip->mode == CAIRO_CLIP_MODE_PATH ? "PATH" :
clip->mode == CAIRO_CLIP_MODE_REGION ? "REGION" :
clip->mode == CAIRO_CLIP_MODE_MASK ? "MASK" :
"INVALID?!"));
if (clip->mode == CAIRO_CLIP_MODE_PATH) {
fprintf (fp, "\n=== clip path ===\n");
} else if (clip->mode == CAIRO_CLIP_MODE_REGION) {
if (!clip->region) {
fprintf (fp, "region = NULL");
} else if (pixman_region_num_rects (clip->region) == 1) {
pixman_box16_t *rects = pixman_region_rects (clip->region);
fprintf (fp, "region [%d %d %d %d]",
rects[0].x1, rects[0].y1,
rects[0].x2, rects[0].y2);
} else {
pixman_box16_t *rects = pixman_region_rects (clip->region);
int i, nr = pixman_region_num_rects(clip->region);
fprintf (fp, "region (%d rects)\n", nr);
for (i = 0; i < nr; i++) {
fprintf (fp, "rect %d: [%d %d %d %d]", i,
rects[nr].x1, rects[nr].y1,
rects[nr].x2, rects[nr].y2);
}
}
} else if (clip->mode == CAIRO_CLIP_MODE_MASK) {
fprintf (fp, "mask, surface: %p rect: [%d %d %d %d]", clip->surface,
clip->surface_rect.x, clip->surface_rect.y, clip->surface_rect.width, clip->surface_rect.height);
}
fprintf (fp, "\n");
}
/*
* path dumper
*/
typedef struct _cairo_debug_path_dump_closure {
unsigned int op_count;
FILE *fp;
} cairo_debug_path_dump_closure_t;
static cairo_status_t
_cairo_debug_path_move_to (void *closure,
cairo_point_t *point)
{
cairo_debug_path_dump_closure_t *fdc =
(cairo_debug_path_dump_closure_t*) closure;
fprintf (fdc->fp, "%d: moveto (%f, %f)\n",
fdc->op_count++,
_cairo_fixed_to_double(point->x),
_cairo_fixed_to_double(point->y));
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
_cairo_debug_path_line_to (void *closure,
cairo_point_t *point)
{
cairo_debug_path_dump_closure_t *fdc =
(cairo_debug_path_dump_closure_t*) closure;
fprintf (fdc->fp, "%d: lineto (%f, %f)\n",
fdc->op_count++,
_cairo_fixed_to_double(point->x),
_cairo_fixed_to_double(point->y));
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
_cairo_debug_path_curve_to (void *closure,
cairo_point_t *p0,
cairo_point_t *p1,
cairo_point_t *p2)
{
cairo_debug_path_dump_closure_t *fdc =
(cairo_debug_path_dump_closure_t*) closure;
fprintf (fdc->fp, "%d: curveto (%f, %f) (%f, %f) (%f, %f)\n",
fdc->op_count++,
_cairo_fixed_to_double(p0->x),
_cairo_fixed_to_double(p0->y),
_cairo_fixed_to_double(p1->x),
_cairo_fixed_to_double(p1->y),
_cairo_fixed_to_double(p2->x),
_cairo_fixed_to_double(p2->y));
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
_cairo_debug_path_close_path (void *closure)
{
cairo_debug_path_dump_closure_t *fdc =
(cairo_debug_path_dump_closure_t*) closure;
fprintf (fdc->fp, "%d: close\n",
fdc->op_count++);
return CAIRO_STATUS_SUCCESS;
}
/**
* cairo_debug_dump_path
* @path: a #cairo_path_fixed_t
* @fp: the file pointer where to dump the given path
*
* Dumps @path in human-readable form to @fp.
*/
void
cairo_debug_dump_path (cairo_path_fixed_t *path,
FILE *fp)
{
cairo_debug_path_dump_closure_t fdc;
fdc.fp = fp;
fdc.op_count = 0;
fprintf (fp, "=== path %p ===\n", path);
_cairo_path_fixed_interpret (path,
CAIRO_DIRECTION_FORWARD,
_cairo_debug_path_move_to,
_cairo_debug_path_line_to,
_cairo_debug_path_curve_to,
_cairo_debug_path_close_path,
&fdc);
fprintf (fp, "======================\n");
}
/*
* traps dumping
*/
/**
* cairo_debug_dump_traps
* @traps: a #cairo_traps_t
* @fp: the file pointer where to dump the traps
*
* Dumps @traps in human-readable form to @fp.
*/
void
cairo_debug_dump_traps (cairo_traps_t *traps,
FILE *fp)
{
fprintf (fp, "=== traps %p ===\n", traps);
fprintf (fp, "extents: (%f, %f) (%f, %f)\n",
_cairo_fixed_to_double (traps->extents.p1.x),
_cairo_fixed_to_double (traps->extents.p1.y),
_cairo_fixed_to_double (traps->extents.p2.x),
_cairo_fixed_to_double (traps->extents.p2.y));
cairo_debug_dump_trapezoid_array (traps->traps,
traps->num_traps,
fp);
fprintf (fp, "=======================\n");
}
/**
* cairo_debug_dump_trapezoid_array
* @traps: a #cairo_trapezoid_t pointer
* @num_traps: the number of trapezoids in @traps
* @fp: the file pointer where to dump the traps
*
* Dumps num_traps in the @traps array in human-readable form to @fp.
*/
void
cairo_debug_dump_trapezoid_array (cairo_trapezoid_t *traps,
int num_traps,
FILE *fp)
{
int i;
for (i = 0; i < num_traps; i++) {
fprintf (fp, "% 3d: t: %f b: %f l: (%f,%f)->(%f,%f) r: (%f,%f)->(%f,%f)\n",
i,
_cairo_fixed_to_double (traps[i].top),
_cairo_fixed_to_double (traps[i].bottom),
_cairo_fixed_to_double (traps[i].left.p1.x),
_cairo_fixed_to_double (traps[i].left.p1.y),
_cairo_fixed_to_double (traps[i].left.p2.x),
_cairo_fixed_to_double (traps[i].left.p2.y),
_cairo_fixed_to_double (traps[i].right.p1.x),
_cairo_fixed_to_double (traps[i].right.p1.y),
_cairo_fixed_to_double (traps[i].right.p2.x),
_cairo_fixed_to_double (traps[i].right.p2.y));
}
}
#endif

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -35,7 +35,7 @@
*/
#ifndef CAIRO_DIRECTFB_H
#define CAIRO_DIRECTFB_H
#define CAIRO_DIRECTFB_H
#include <cairo.h>
@ -43,18 +43,9 @@
CAIRO_BEGIN_DECLS
cairo_surface_t * cairo_directfb_surface_create (IDirectFB *dfb,IDirectFBSurface *surface);
cairo_surface_t * cairo_directfb_surface_create (IDirectFB *dfb,IDirectFBSurface *surface);
CAIRO_END_DECLS
#endif /*CAIRO_HAS_DIRECTFB_SURFACE*/
#endif /*CAIRO_DIRECTFB_H*/

Просмотреть файл

@ -52,10 +52,10 @@
#endif
#define CAIRO_VERSION_MAJOR 1
#define CAIRO_VERSION_MINOR 1
#define CAIRO_VERSION_MINOR 3
#define CAIRO_VERSION_MICRO 1
#define CAIRO_VERSION_STRING "1.1.1"
#define CAIRO_VERSION_STRING "1.3.1"
@PS_SURFACE_FEATURE@

Просмотреть файл

@ -46,7 +46,7 @@ static const cairo_font_options_t cairo_font_options_nil = {
/**
* _cairo_font_options_init_default:
* @options: a #cairo_font_options_t
*
*
* Initializes all fileds of the font options object to default values.
**/
void
@ -54,7 +54,7 @@ _cairo_font_options_init_default (cairo_font_options_t *options)
{
if (options == (cairo_font_options_t *)&cairo_font_options_nil)
return;
options->antialias = CAIRO_ANTIALIAS_DEFAULT;
options->subpixel_order = CAIRO_SUBPIXEL_ORDER_DEFAULT;
options->hint_style = CAIRO_HINT_STYLE_DEFAULT;
@ -76,7 +76,7 @@ _cairo_font_options_init_copy (cairo_font_options_t *options,
*
* Allocates a new font options object with all options initialized
* to default values.
*
*
* Return value: a newly allocated #cairo_font_options_t. Free with
* cairo_font_options_destroy(). This function always returns a
* valid pointer; if memory cannot be allocated, then a special
@ -102,7 +102,7 @@ cairo_font_options_create (void)
*
* Allocates a new font options object copying the option values from
* @original.
*
*
* Return value: a newly allocated #cairo_font_options_t. Free with
* cairo_font_options_destroy(). This function always returns a
* valid pointer; if memory cannot be allocated, then a special
@ -125,11 +125,11 @@ cairo_font_options_copy (const cairo_font_options_t *original)
/**
* cairo_font_options_destroy:
* @options: a #cairo_font_options_t
*
*
* Destroys a #cairo_font_options_t object created with with
* cairo_font_options_create() or cairo_font_options_copy().
**/
void
void
cairo_font_options_destroy (cairo_font_options_t *options)
{
if (options == (cairo_font_options_t *)&cairo_font_options_nil)
@ -141,10 +141,10 @@ cairo_font_options_destroy (cairo_font_options_t *options)
/**
* cairo_font_options_status:
* @options: a #cairo_font_options_t
*
*
* Checks whether an error has previously occurred for this
* font options object
*
*
* Return value: %CAIRO_STATUS_SUCCESS or %CAIRO_STATUS_NO_MEMORY
**/
cairo_status_t
@ -154,13 +154,13 @@ cairo_font_options_status (cairo_font_options_t *options)
return CAIRO_STATUS_NO_MEMORY;
else
return CAIRO_STATUS_SUCCESS;
}
}
/**
* cairo_font_options_merge:
* @options: a #cairo_font_options_t
* @other: another #cairo_font_options_t
*
*
* Merges non-default options from @other into @options, replacing
* existing values. This operation can be thought of as somewhat
* similar to compositing @other onto @options with the operation
@ -187,9 +187,9 @@ cairo_font_options_merge (cairo_font_options_t *options,
* cairo_font_options_equal:
* @options: a #cairo_font_options_t
* @other: another #cairo_font_options_t
*
*
* Compares two font options objects for equality.
*
*
* Return value: %TRUE if all fields of the two font options objects match
**/
cairo_bool_t
@ -205,11 +205,11 @@ cairo_font_options_equal (const cairo_font_options_t *options,
/**
* cairo_font_options_hash:
* @options: a #cairo_font_options_t
*
*
* Compute a hash for the font options object; this value will
* be useful when storing an object containing a cairo_font_options_t
* in a hash table.
*
*
* Return value: the hash value for the font options object.
* The return value can be cast to a 32-bit type if a
* 32-bit hash value is needed.
@ -219,7 +219,7 @@ cairo_font_options_hash (const cairo_font_options_t *options)
{
return ((options->antialias) |
(options->subpixel_order << 4) |
(options->hint_style << 8) |
(options->hint_style << 8) |
(options->hint_metrics << 16));
}
@ -227,7 +227,7 @@ cairo_font_options_hash (const cairo_font_options_t *options)
* cairo_font_options_set_antialias:
* @options: a #cairo_font_options_t
* @antialias: the new antialiasing mode
*
*
* Sets the antiliasing mode for the font options object. This
* specifies the type of antialiasing to do when rendering text.
**/
@ -237,16 +237,16 @@ cairo_font_options_set_antialias (cairo_font_options_t *options,
{
if (options == (cairo_font_options_t *)&cairo_font_options_nil)
return;
options->antialias = antialias;
}
/**
* cairo_font_options_get_antialias:
* @options: a #cairo_font_options_t
*
*
* Gets the antialising mode for the font options object.
*
*
* Return value: the antialiasing mode
**/
cairo_antialias_t
@ -259,7 +259,7 @@ cairo_font_options_get_antialias (const cairo_font_options_t *options)
* cairo_font_options_set_subpixel_order:
* @options: a #cairo_font_options_t
* @subpixel_order: the new subpixel order
*
*
* Sets the subpixel order for the font options object. The subpixel
* order specifies the order of color elements within each pixel on
* the display device when rendering with an antialiasing mode of
@ -272,17 +272,17 @@ cairo_font_options_set_subpixel_order (cairo_font_options_t *options,
{
if (options == (cairo_font_options_t *)&cairo_font_options_nil)
return;
options->subpixel_order = subpixel_order;
}
/**
* cairo_font_options_get_subpixel_order:
* @options: a #cairo_font_options_t
*
*
* Gets the subpixel order for the font options object.
* See the documentation for #cairo_subpixel_order_t for full details.
*
*
* Return value: the subpixel order for the font options object
**/
cairo_subpixel_order_t
@ -295,7 +295,7 @@ cairo_font_options_get_subpixel_order (const cairo_font_options_t *options)
* cairo_font_options_set_hint_style:
* @options: a #cairo_font_options_t
* @hint_style: the new hint style
*
*
* Sets the hint style for font outlines for the font options object.
* This controls whether to fit font outlines to the pixel grid,
* and if so, whether to optimize for fidelity or contrast.
@ -307,17 +307,17 @@ cairo_font_options_set_hint_style (cairo_font_options_t *options,
{
if (options == (cairo_font_options_t *)&cairo_font_options_nil)
return;
options->hint_style = hint_style;
}
/**
* cairo_font_options_get_hint_style:
* @options: a #cairo_font_options_t
*
*
* Gets the hint style for font outlines for the font options object.
* See the documentation for #cairo_hint_style_t for full details.
*
*
* Return value: the hint style for the font options object
**/
cairo_hint_style_t
@ -330,7 +330,7 @@ cairo_font_options_get_hint_style (const cairo_font_options_t *options)
* cairo_font_options_set_hint_metrics:
* @options: a #cairo_font_options_t
* @hint_metrics: the new metrics hinting mode
*
*
* Sets the metrics hinting mode for the font options object. This
* controls whether metrics are quantized to integer values in
* device units.
@ -349,10 +349,10 @@ cairo_font_options_set_hint_metrics (cairo_font_options_t *options,
/**
* cairo_font_options_get_hint_metrics:
* @options: a #cairo_font_options_t
*
*
* Gets the metrics hinting mode for the font options object.
* See the documentation for #cairo_hint_metrics_t for full details.
*
*
* Return value: the metrics hinting mode for the font options object
**/
cairo_hint_metrics_t

Просмотреть файл

@ -1,68 +0,0 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2004 Red Hat, Inc
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is Red Hat, Inc.
*
* Contributor(s):
* Kristian Høgsberg <krh@redhat.com>
*/
#include "cairoint.h"
#ifndef CAIRO_FONT_SUBSET_PRIVATE_H
#define CAIRO_FONT_SUBSET_PRIVATE_H
typedef struct cairo_font_subset_backend cairo_font_subset_backend_t;
typedef struct cairo_font_subset cairo_font_subset_t;
struct cairo_font_subset {
cairo_font_subset_backend_t *backend;
cairo_unscaled_font_t *unscaled_font;
unsigned int font_id;
char *base_font;
int num_glyphs;
int *widths;
long x_min, y_min, x_max, y_max;
long ascent, descent;
};
cairo_private int
_cairo_font_subset_use_glyph (cairo_font_subset_t *font, int glyph);
cairo_private cairo_status_t
_cairo_font_subset_generate (cairo_font_subset_t *font,
const char **data, unsigned long *length);
cairo_private void
_cairo_font_subset_destroy (cairo_font_subset_t *font);
cairo_private cairo_font_subset_t *
_cairo_font_subset_create (cairo_unscaled_font_t *unscaled_font);
#endif /* CAIRO_FONT_SUBSET_PRIVATE_H */

Просмотреть файл

@ -1,757 +0,0 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2004 Red Hat, Inc
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is Red Hat, Inc.
*
* Contributor(s):
* Kristian Høgsberg <krh@redhat.com>
*/
#include "cairoint.h"
#include "cairo-font-subset-private.h"
/* XXX: Eventually, we need to handle other font backends */
#include "cairo-ft-private.h"
#include <ft2build.h>
#include FT_FREETYPE_H
#include FT_OUTLINE_H
#include FT_TRUETYPE_TAGS_H
#include FT_TRUETYPE_TABLES_H
typedef struct ft_subset_glyph ft_subset_glyph_t;
struct ft_subset_glyph {
int parent_index;
unsigned long location;
};
struct cairo_font_subset_backend {
int (*use_glyph) (void *abstract_font,
int glyph);
cairo_status_t (*generate) (void *abstract_font,
const char **data,
unsigned long *length);
void (*destroy) (void *abstract_font);
};
typedef struct cairo_pdf_ft_font cairo_pdf_ft_font_t;
struct cairo_pdf_ft_font {
cairo_font_subset_t base;
ft_subset_glyph_t *glyphs;
FT_Face face;
int checksum_index;
cairo_array_t output;
int *parent_to_subset;
cairo_status_t status;
};
static int
cairo_pdf_ft_font_use_glyph (void *abstract_font, int glyph);
#define ARRAY_LENGTH(a) ( (sizeof (a)) / (sizeof ((a)[0])) )
#define SFNT_VERSION 0x00010000
#ifdef WORDS_BIGENDIAN
#define cpu_to_be16(v) (v)
#define be16_to_cpu(v) (v)
#define cpu_to_be32(v) (v)
#define be32_to_cpu(v) (v)
#else
static unsigned short
cpu_to_be16(unsigned short v)
{
return (v << 8) | (v >> 8);
}
static unsigned short
be16_to_cpu(unsigned short v)
{
return cpu_to_be16 (v);
}
static unsigned long
cpu_to_be32(unsigned long v)
{
return (cpu_to_be16 (v) << 16) | cpu_to_be16 (v >> 16);
}
static unsigned long
be32_to_cpu(unsigned long v)
{
return cpu_to_be32 (v);
}
#endif
static cairo_font_subset_backend_t cairo_pdf_ft_font_backend;
int
_cairo_font_subset_use_glyph (cairo_font_subset_t *font, int glyph)
{
return font->backend->use_glyph (font, glyph);
}
cairo_status_t
_cairo_font_subset_generate (cairo_font_subset_t *font,
const char **data, unsigned long *length)
{
return font->backend->generate (font, data, length);
}
void
_cairo_font_subset_destroy (cairo_font_subset_t *font)
{
font->backend->destroy (font);
}
cairo_font_subset_t *
_cairo_font_subset_create (cairo_unscaled_font_t *unscaled_font)
{
cairo_ft_unscaled_font_t *ft_unscaled_font;
FT_Face face;
cairo_pdf_ft_font_t *font;
unsigned long size;
int i, j;
/* XXX: Need to fix this to work with a general cairo_unscaled_font_t. */
if (! _cairo_unscaled_font_is_ft (unscaled_font))
return NULL;
ft_unscaled_font = (cairo_ft_unscaled_font_t *) unscaled_font;
face = _cairo_ft_unscaled_font_lock_face (ft_unscaled_font);
/* We currently only support freetype truetype fonts. */
size = 0;
if (!FT_IS_SFNT (face) ||
FT_Load_Sfnt_Table (face, TTAG_glyf, 0, NULL, &size) != 0)
return NULL;
font = malloc (sizeof (cairo_pdf_ft_font_t));
if (font == NULL)
return NULL;
font->base.unscaled_font = _cairo_unscaled_font_reference (unscaled_font);
font->base.backend = &cairo_pdf_ft_font_backend;
_cairo_array_init (&font->output, sizeof (char));
if (_cairo_array_grow_by (&font->output, 4096) != CAIRO_STATUS_SUCCESS)
goto fail1;
font->glyphs = calloc (face->num_glyphs + 1, sizeof (ft_subset_glyph_t));
if (font->glyphs == NULL)
goto fail2;
font->parent_to_subset = calloc (face->num_glyphs, sizeof (int));
if (font->parent_to_subset == NULL)
goto fail3;
font->base.num_glyphs = 1;
font->base.x_min = face->bbox.xMin;
font->base.y_min = face->bbox.yMin;
font->base.x_max = face->bbox.xMax;
font->base.y_max = face->bbox.yMax;
font->base.ascent = face->ascender;
font->base.descent = face->descender;
font->base.base_font = strdup (face->family_name);
if (font->base.base_font == NULL)
goto fail4;
for (i = 0, j = 0; font->base.base_font[j]; j++) {
if (font->base.base_font[j] == ' ')
continue;
font->base.base_font[i++] = font->base.base_font[j];
}
font->base.base_font[i] = '\0';
font->base.widths = calloc (face->num_glyphs, sizeof (int));
if (font->base.widths == NULL)
goto fail5;
_cairo_ft_unscaled_font_unlock_face (ft_unscaled_font);
font->status = CAIRO_STATUS_SUCCESS;
return &font->base;
fail5:
free (font->base.base_font);
fail4:
free (font->parent_to_subset);
fail3:
free (font->glyphs);
fail2:
_cairo_array_fini (&font->output);
fail1:
free (font);
return NULL;
}
static void
cairo_pdf_ft_font_destroy (void *abstract_font)
{
cairo_pdf_ft_font_t *font = abstract_font;
_cairo_unscaled_font_destroy (font->base.unscaled_font);
free (font->base.base_font);
free (font->parent_to_subset);
free (font->glyphs);
_cairo_array_fini (&font->output);
free (font);
}
static cairo_status_t
cairo_pdf_ft_font_allocate_write_buffer (cairo_pdf_ft_font_t *font,
size_t length,
unsigned char **buffer)
{
cairo_status_t status;
status = _cairo_array_allocate (&font->output, length, (void **) buffer);
if (status)
return status;
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
cairo_pdf_ft_font_write (cairo_pdf_ft_font_t *font,
const void *data, size_t length)
{
cairo_status_t status;
status = _cairo_array_append_multiple (&font->output, data, length);
if (status)
return status;
return CAIRO_STATUS_SUCCESS;
}
static void
cairo_pdf_ft_font_write_be16 (cairo_pdf_ft_font_t *font,
unsigned short value)
{
unsigned short be16_value;
be16_value = cpu_to_be16 (value);
cairo_pdf_ft_font_write (font, &be16_value, sizeof be16_value);
}
static void
cairo_pdf_ft_font_write_be32 (cairo_pdf_ft_font_t *font, unsigned long value)
{
unsigned long be32_value;
be32_value = cpu_to_be32 (value);
cairo_pdf_ft_font_write (font, &be32_value, sizeof be32_value);
}
static unsigned long
cairo_pdf_ft_font_align_output (cairo_pdf_ft_font_t *font)
{
int length, aligned, pad;
unsigned char *ignored;
length = _cairo_array_num_elements (&font->output);
aligned = (length + 3) & ~3;
pad = aligned - length;
if (pad)
cairo_pdf_ft_font_allocate_write_buffer (font, pad, &ignored);
return aligned;
}
static int
cairo_pdf_ft_font_write_cmap_table (cairo_pdf_ft_font_t *font, unsigned long tag)
{
int i;
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be16 (font, 1);
cairo_pdf_ft_font_write_be16 (font, 1);
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be32 (font, 12);
/* Output a format 6 encoding table. */
cairo_pdf_ft_font_write_be16 (font, 6);
cairo_pdf_ft_font_write_be16 (font, 10 + 2 * (font->base.num_glyphs - 1));
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be16 (font, 1); /* First glyph */
cairo_pdf_ft_font_write_be16 (font, font->base.num_glyphs - 1);
for (i = 1; i < font->base.num_glyphs; i++)
cairo_pdf_ft_font_write_be16 (font, i);
return font->status;
}
static int
cairo_pdf_ft_font_write_generic_table (cairo_pdf_ft_font_t *font,
unsigned long tag)
{
cairo_status_t status;
unsigned char *buffer;
unsigned long size;
size = 0;
FT_Load_Sfnt_Table (font->face, tag, 0, NULL, &size);
status = cairo_pdf_ft_font_allocate_write_buffer (font, size, &buffer);
/* XXX: Need to check status here. */
FT_Load_Sfnt_Table (font->face, tag, 0, buffer, &size);
return 0;
}
typedef struct composite_glyph composite_glyph_t;
struct composite_glyph {
unsigned short flags;
unsigned short index;
unsigned short args[7]; /* 1 to 7 arguments depending on value of flags */
};
typedef struct glyph_data glyph_data_t;
struct glyph_data {
short num_contours;
char data[8];
composite_glyph_t glyph;
};
/* composite_glyph_t flags */
#define ARG_1_AND_2_ARE_WORDS 0x0001
#define WE_HAVE_A_SCALE 0x0008
#define MORE_COMPONENTS 0x0020
#define WE_HAVE_AN_X_AND_Y_SCALE 0x0040
#define WE_HAVE_A_TWO_BY_TWO 0x0080
static void
cairo_pdf_ft_font_remap_composite_glyph (cairo_pdf_ft_font_t *font,
unsigned char *buffer)
{
glyph_data_t *glyph_data;
composite_glyph_t *composite_glyph;
int num_args;
int has_more_components;
unsigned short flags;
unsigned short index;
glyph_data = (glyph_data_t *) buffer;
if ((short)be16_to_cpu (glyph_data->num_contours) >= 0)
return;
composite_glyph = &glyph_data->glyph;
do {
flags = be16_to_cpu (composite_glyph->flags);
has_more_components = flags & MORE_COMPONENTS;
index = cairo_pdf_ft_font_use_glyph (font, be16_to_cpu (composite_glyph->index));
composite_glyph->index = cpu_to_be16 (index);
num_args = 1;
if (flags & ARG_1_AND_2_ARE_WORDS)
num_args += 1;
if (flags & WE_HAVE_A_SCALE)
num_args += 1;
else if (flags & WE_HAVE_AN_X_AND_Y_SCALE)
num_args += 2;
else if (flags & WE_HAVE_A_TWO_BY_TWO)
num_args += 3;
composite_glyph = (composite_glyph_t *) &(composite_glyph->args[num_args]);
} while (has_more_components);
}
static int
cairo_pdf_ft_font_write_glyf_table (cairo_pdf_ft_font_t *font,
unsigned long tag)
{
cairo_status_t status;
unsigned long start_offset, index, size;
TT_Header *header;
unsigned long begin, end;
unsigned char *buffer;
int i;
union {
unsigned char *bytes;
unsigned short *short_offsets;
unsigned long *long_offsets;
} u;
header = FT_Get_Sfnt_Table (font->face, ft_sfnt_head);
if (header->Index_To_Loc_Format == 0)
size = sizeof (short) * (font->face->num_glyphs + 1);
else
size = sizeof (long) * (font->face->num_glyphs + 1);
u.bytes = malloc (size);
if (u.bytes == NULL) {
font->status = CAIRO_STATUS_NO_MEMORY;
return font->status;
}
FT_Load_Sfnt_Table (font->face, TTAG_loca, 0, u.bytes, &size);
start_offset = _cairo_array_num_elements (&font->output);
for (i = 0; i < font->base.num_glyphs; i++) {
index = font->glyphs[i].parent_index;
if (header->Index_To_Loc_Format == 0) {
begin = be16_to_cpu (u.short_offsets[index]) * 2;
end = be16_to_cpu (u.short_offsets[index + 1]) * 2;
}
else {
begin = be32_to_cpu (u.long_offsets[index]);
end = be32_to_cpu (u.long_offsets[index + 1]);
}
size = end - begin;
font->glyphs[i].location =
cairo_pdf_ft_font_align_output (font) - start_offset;
status = cairo_pdf_ft_font_allocate_write_buffer (font, size, &buffer);
if (status)
break;
if (size != 0) {
FT_Load_Sfnt_Table (font->face, TTAG_glyf, begin, buffer, &size);
cairo_pdf_ft_font_remap_composite_glyph (font, buffer);
}
}
font->glyphs[i].location =
cairo_pdf_ft_font_align_output (font) - start_offset;
free (u.bytes);
return font->status;
}
static int
cairo_pdf_ft_font_write_head_table (cairo_pdf_ft_font_t *font,
unsigned long tag)
{
TT_Header *head;
head = FT_Get_Sfnt_Table (font->face, ft_sfnt_head);
cairo_pdf_ft_font_write_be32 (font, head->Table_Version);
cairo_pdf_ft_font_write_be32 (font, head->Font_Revision);
font->checksum_index = _cairo_array_num_elements (&font->output);
cairo_pdf_ft_font_write_be32 (font, 0);
cairo_pdf_ft_font_write_be32 (font, head->Magic_Number);
cairo_pdf_ft_font_write_be16 (font, head->Flags);
cairo_pdf_ft_font_write_be16 (font, head->Units_Per_EM);
cairo_pdf_ft_font_write_be32 (font, head->Created[0]);
cairo_pdf_ft_font_write_be32 (font, head->Created[1]);
cairo_pdf_ft_font_write_be32 (font, head->Modified[0]);
cairo_pdf_ft_font_write_be32 (font, head->Modified[1]);
cairo_pdf_ft_font_write_be16 (font, head->xMin);
cairo_pdf_ft_font_write_be16 (font, head->yMin);
cairo_pdf_ft_font_write_be16 (font, head->xMax);
cairo_pdf_ft_font_write_be16 (font, head->yMax);
cairo_pdf_ft_font_write_be16 (font, head->Mac_Style);
cairo_pdf_ft_font_write_be16 (font, head->Lowest_Rec_PPEM);
cairo_pdf_ft_font_write_be16 (font, head->Font_Direction);
cairo_pdf_ft_font_write_be16 (font, head->Index_To_Loc_Format);
cairo_pdf_ft_font_write_be16 (font, head->Glyph_Data_Format);
return font->status;
}
static int cairo_pdf_ft_font_write_hhea_table (cairo_pdf_ft_font_t *font, unsigned long tag)
{
TT_HoriHeader *hhea;
hhea = FT_Get_Sfnt_Table (font->face, ft_sfnt_hhea);
cairo_pdf_ft_font_write_be32 (font, hhea->Version);
cairo_pdf_ft_font_write_be16 (font, hhea->Ascender);
cairo_pdf_ft_font_write_be16 (font, hhea->Descender);
cairo_pdf_ft_font_write_be16 (font, hhea->Line_Gap);
cairo_pdf_ft_font_write_be16 (font, hhea->advance_Width_Max);
cairo_pdf_ft_font_write_be16 (font, hhea->min_Left_Side_Bearing);
cairo_pdf_ft_font_write_be16 (font, hhea->min_Right_Side_Bearing);
cairo_pdf_ft_font_write_be16 (font, hhea->xMax_Extent);
cairo_pdf_ft_font_write_be16 (font, hhea->caret_Slope_Rise);
cairo_pdf_ft_font_write_be16 (font, hhea->caret_Slope_Run);
cairo_pdf_ft_font_write_be16 (font, hhea->caret_Offset);
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be16 (font, 0);
cairo_pdf_ft_font_write_be16 (font, hhea->metric_Data_Format);
cairo_pdf_ft_font_write_be16 (font, font->base.num_glyphs);
return font->status;
}
static int
cairo_pdf_ft_font_write_hmtx_table (cairo_pdf_ft_font_t *font,
unsigned long tag)
{
cairo_status_t status;
unsigned long entry_size;
short *p;
int i;
for (i = 0; i < font->base.num_glyphs; i++) {
entry_size = 2 * sizeof (short);
status = cairo_pdf_ft_font_allocate_write_buffer (font, entry_size,
(unsigned char **) &p);
/* XXX: Need to check status here. */
FT_Load_Sfnt_Table (font->face, TTAG_hmtx,
font->glyphs[i].parent_index * entry_size,
(FT_Byte *) p, &entry_size);
font->base.widths[i] = be16_to_cpu (p[0]);
}
return font->status;
}
static int
cairo_pdf_ft_font_write_loca_table (cairo_pdf_ft_font_t *font,
unsigned long tag)
{
int i;
TT_Header *header;
header = FT_Get_Sfnt_Table (font->face, ft_sfnt_head);
if (header->Index_To_Loc_Format == 0) {
for (i = 0; i < font->base.num_glyphs + 1; i++)
cairo_pdf_ft_font_write_be16 (font, font->glyphs[i].location / 2);
}
else {
for (i = 0; i < font->base.num_glyphs + 1; i++)
cairo_pdf_ft_font_write_be32 (font, font->glyphs[i].location);
}
return font->status;
}
static int
cairo_pdf_ft_font_write_maxp_table (cairo_pdf_ft_font_t *font,
unsigned long tag)
{
TT_MaxProfile *maxp;
maxp = FT_Get_Sfnt_Table (font->face, ft_sfnt_maxp);
cairo_pdf_ft_font_write_be32 (font, maxp->version);
cairo_pdf_ft_font_write_be16 (font, font->base.num_glyphs);
cairo_pdf_ft_font_write_be16 (font, maxp->maxPoints);
cairo_pdf_ft_font_write_be16 (font, maxp->maxContours);
cairo_pdf_ft_font_write_be16 (font, maxp->maxCompositePoints);
cairo_pdf_ft_font_write_be16 (font, maxp->maxCompositeContours);
cairo_pdf_ft_font_write_be16 (font, maxp->maxZones);
cairo_pdf_ft_font_write_be16 (font, maxp->maxTwilightPoints);
cairo_pdf_ft_font_write_be16 (font, maxp->maxStorage);
cairo_pdf_ft_font_write_be16 (font, maxp->maxFunctionDefs);
cairo_pdf_ft_font_write_be16 (font, maxp->maxInstructionDefs);
cairo_pdf_ft_font_write_be16 (font, maxp->maxStackElements);
cairo_pdf_ft_font_write_be16 (font, maxp->maxSizeOfInstructions);
cairo_pdf_ft_font_write_be16 (font, maxp->maxComponentElements);
cairo_pdf_ft_font_write_be16 (font, maxp->maxComponentDepth);
return font->status;
}
typedef struct table table_t;
struct table {
unsigned long tag;
int (*write) (cairo_pdf_ft_font_t *font, unsigned long tag);
};
static const table_t truetype_tables[] = {
/* As we write out the glyf table we remap composite glyphs.
* Remapping composite glyphs will reference the sub glyphs the
* composite glyph is made up of. That needs to be done first so
* we have all the glyphs in the subset before going further. */
{ TTAG_glyf, cairo_pdf_ft_font_write_glyf_table },
{ TTAG_cmap, cairo_pdf_ft_font_write_cmap_table },
{ TTAG_cvt, cairo_pdf_ft_font_write_generic_table },
{ TTAG_fpgm, cairo_pdf_ft_font_write_generic_table },
{ TTAG_head, cairo_pdf_ft_font_write_head_table },
{ TTAG_hhea, cairo_pdf_ft_font_write_hhea_table },
{ TTAG_hmtx, cairo_pdf_ft_font_write_hmtx_table },
{ TTAG_loca, cairo_pdf_ft_font_write_loca_table },
{ TTAG_maxp, cairo_pdf_ft_font_write_maxp_table },
{ TTAG_name, cairo_pdf_ft_font_write_generic_table },
{ TTAG_prep, cairo_pdf_ft_font_write_generic_table },
};
static cairo_status_t
cairo_pdf_ft_font_write_offset_table (cairo_pdf_ft_font_t *font)
{
cairo_status_t status;
unsigned char *table_buffer;
size_t table_buffer_length;
unsigned short search_range, entry_selector, range_shift;
int num_tables;
num_tables = ARRAY_LENGTH (truetype_tables);
search_range = 1;
entry_selector = 0;
while (search_range * 2 <= num_tables) {
search_range *= 2;
entry_selector++;
}
search_range *= 16;
range_shift = num_tables * 16 - search_range;
cairo_pdf_ft_font_write_be32 (font, SFNT_VERSION);
cairo_pdf_ft_font_write_be16 (font, num_tables);
cairo_pdf_ft_font_write_be16 (font, search_range);
cairo_pdf_ft_font_write_be16 (font, entry_selector);
cairo_pdf_ft_font_write_be16 (font, range_shift);
/* XXX: Why are we allocating a table here and then ignoring the
* returned buffer? This should result in garbage in the output
* file, correct? Is this just unfinished code? -cworth. */
table_buffer_length = ARRAY_LENGTH (truetype_tables) * 16;
status = cairo_pdf_ft_font_allocate_write_buffer (font, table_buffer_length,
&table_buffer);
if (status)
return status;
return font->status;
}
static unsigned long
cairo_pdf_ft_font_calculate_checksum (cairo_pdf_ft_font_t *font,
unsigned long start, unsigned long end)
{
unsigned long *padded_end;
unsigned long *p;
unsigned long checksum;
char *data;
checksum = 0;
data = _cairo_array_index (&font->output, 0);
p = (unsigned long *) (data + start);
padded_end = (unsigned long *) (data + ((end + 3) & ~3));
while (p < padded_end)
checksum += *p++;
return checksum;
}
static void
cairo_pdf_ft_font_update_entry (cairo_pdf_ft_font_t *font, int index, unsigned long tag,
unsigned long start, unsigned long end)
{
unsigned long *entry;
entry = _cairo_array_index (&font->output, 12 + 16 * index);
entry[0] = cpu_to_be32 (tag);
entry[1] = cpu_to_be32 (cairo_pdf_ft_font_calculate_checksum (font, start, end));
entry[2] = cpu_to_be32 (start);
entry[3] = cpu_to_be32 (end - start);
}
static cairo_status_t
cairo_pdf_ft_font_generate (void *abstract_font,
const char **data, unsigned long *length)
{
cairo_ft_unscaled_font_t *ft_unscaled_font;
cairo_pdf_ft_font_t *font = abstract_font;
unsigned long start, end, next, checksum, *checksum_location;
int i;
/* XXX: It would be cleaner to do something besides this cast
* here. Perhaps cairo_pdf_ft_font_t should just have the
* cairo_ft_unscaled_font_t rather than having the generic
* cairo_unscaled_font_t in the base class? */
ft_unscaled_font = (cairo_ft_unscaled_font_t *) font->base.unscaled_font;
font->face = _cairo_ft_unscaled_font_lock_face (ft_unscaled_font);
if (cairo_pdf_ft_font_write_offset_table (font))
goto fail;
start = cairo_pdf_ft_font_align_output (font);
end = start;
end = 0;
for (i = 0; i < ARRAY_LENGTH (truetype_tables); i++) {
if (truetype_tables[i].write (font, truetype_tables[i].tag))
goto fail;
end = _cairo_array_num_elements (&font->output);
next = cairo_pdf_ft_font_align_output (font);
cairo_pdf_ft_font_update_entry (font, i, truetype_tables[i].tag,
start, end);
start = next;
}
checksum =
0xb1b0afba - cairo_pdf_ft_font_calculate_checksum (font, 0, end);
checksum_location = _cairo_array_index (&font->output, font->checksum_index);
*checksum_location = cpu_to_be32 (checksum);
*data = _cairo_array_index (&font->output, 0);
*length = _cairo_array_num_elements (&font->output);
fail:
_cairo_ft_unscaled_font_unlock_face (ft_unscaled_font);
font->face = NULL;
return font->status;
}
static int
cairo_pdf_ft_font_use_glyph (void *abstract_font, int glyph)
{
cairo_pdf_ft_font_t *font = abstract_font;
if (font->parent_to_subset[glyph] == 0) {
font->parent_to_subset[glyph] = font->base.num_glyphs;
font->glyphs[font->base.num_glyphs].parent_index = glyph;
font->base.num_glyphs++;
}
return font->parent_to_subset[glyph];
}
static cairo_font_subset_backend_t cairo_pdf_ft_font_backend = {
cairo_pdf_ft_font_use_glyph,
cairo_pdf_ft_font_generate,
cairo_pdf_ft_font_destroy
};

Просмотреть файл

@ -55,7 +55,7 @@ const cairo_font_face_t _cairo_font_face_nil = {
};
void
_cairo_font_face_init (cairo_font_face_t *font_face,
_cairo_font_face_init (cairo_font_face_t *font_face,
const cairo_font_face_backend_t *backend)
{
font_face->status = CAIRO_STATUS_SUCCESS;
@ -69,7 +69,7 @@ _cairo_font_face_init (cairo_font_face_t *font_face,
* cairo_font_face_reference:
* @font_face: a #cairo_font_face_t, (may be NULL in which case this
* function does nothing).
*
*
* Increases the reference count on @font_face by one. This prevents
* @font_face from being destroyed until a matching call to
* cairo_font_face_destroy() is made.
@ -97,7 +97,7 @@ cairo_font_face_reference (cairo_font_face_t *font_face)
/**
* cairo_font_face_destroy:
* @font_face: a #cairo_font_face_t
*
*
* Decreases the reference count on @font_face by one. If the result
* is zero, then @font_face and all associated resources are freed.
* See cairo_font_face_reference().
@ -133,8 +133,10 @@ cairo_font_face_destroy (cairo_font_face_t *font_face)
/**
* cairo_font_face_get_type:
* @font_face: a #cairo_font_face_t
*
*
* Return value: The type of @font_face. See #cairo_font_type_t.
*
* Since: 1.2
**/
cairo_font_type_t
cairo_font_face_get_type (cairo_font_face_t *font_face)
@ -145,10 +147,10 @@ cairo_font_face_get_type (cairo_font_face_t *font_face)
/**
* cairo_font_face_status:
* @font_face: a #cairo_font_face_t
*
*
* Checks whether an error has previously occurred for this
* font face
*
*
* Return value: %CAIRO_STATUS_SUCCESS or another error such as
* %CAIRO_STATUS_NO_MEMORY.
**/
@ -163,11 +165,11 @@ cairo_font_face_status (cairo_font_face_t *font_face)
* @font_face: a #cairo_font_face_t
* @key: the address of the #cairo_user_data_key_t the user data was
* attached to
*
*
* Return user data previously attached to @font_face using the specified
* key. If no user data has been attached with the given key this
* function returns %NULL.
*
*
* Return value: the user data previously attached or %NULL.
**/
void *
@ -186,7 +188,7 @@ cairo_font_face_get_user_data (cairo_font_face_t *font_face,
* @destroy: a #cairo_destroy_func_t which will be called when the
* font face is destroyed or when new user data is attached using the
* same key.
*
*
* Attach user data to @font_face. To remove user data from a font face,
* call this function with the key that was used to set it and %NULL
* for @data.
@ -202,7 +204,7 @@ cairo_font_face_set_user_data (cairo_font_face_t *font_face,
{
if (font_face->ref_count == -1)
return CAIRO_STATUS_NO_MEMORY;
return _cairo_user_data_array_set_data (&font_face->user_data,
key, user_data, destroy);
}
@ -252,7 +254,7 @@ _cairo_toy_font_face_hash_table_unlock (void)
/**
* _cairo_toy_font_face_init_key:
*
*
* Initialize those portions of cairo_toy_font_face_t needed to use
* it as a hash table key, including the hash code buried away in
* font_face->base.hash_entry. No memory allocation is performed here
@ -277,7 +279,7 @@ _cairo_toy_font_face_init_key (cairo_toy_font_face_t *key,
hash = _cairo_hash_string (family);
hash += ((unsigned long) slant) * 1607;
hash += ((unsigned long) weight) * 1451;
key->base.hash_entry.hash = hash;
}
@ -328,17 +330,17 @@ _cairo_toy_font_face_keys_equal (const void *key_a,
* @family: a font family name, encoded in UTF-8
* @slant: the slant for the font
* @weight: the weight for the font
*
*
* Creates a font face from a triplet of family, slant, and weight.
* These font faces are used in implementation of the the #cairo_t "toy"
* font API.
*
*
* Return value: a newly created #cairo_font_face_t, destroy with
* cairo_font_face_destroy()
**/
cairo_font_face_t *
_cairo_toy_font_face_create (const char *family,
cairo_font_slant_t slant,
_cairo_toy_font_face_create (const char *family,
cairo_font_slant_t slant,
cairo_font_weight_t weight)
{
cairo_status_t status;
@ -350,7 +352,7 @@ _cairo_toy_font_face_create (const char *family,
goto UNWIND;
_cairo_toy_font_face_init_key (&key, family, slant, weight);
/* Return existing font_face if it exists in the hash table. */
if (_cairo_hash_table_lookup (hash_table,
&key.base.hash_entry,
@ -400,9 +402,9 @@ _cairo_toy_font_face_destroy (void *abstract_face)
assert (hash_table != NULL);
_cairo_hash_table_remove (hash_table, &font_face->base.hash_entry);
_cairo_toy_font_face_hash_table_unlock ();
_cairo_toy_font_face_fini (font_face);
}
@ -427,7 +429,7 @@ static const cairo_font_face_backend_t _cairo_toy_font_face_backend = {
};
void
_cairo_unscaled_font_init (cairo_unscaled_font_t *unscaled_font,
_cairo_unscaled_font_init (cairo_unscaled_font_t *unscaled_font,
const cairo_unscaled_font_backend_t *backend)
{
unscaled_font->ref_count = 1;
@ -447,7 +449,7 @@ _cairo_unscaled_font_reference (cairo_unscaled_font_t *unscaled_font)
void
_cairo_unscaled_font_destroy (cairo_unscaled_font_t *unscaled_font)
{
{
if (unscaled_font == NULL)
return;

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -64,6 +64,9 @@ _cairo_ft_unscaled_font_lock_face (cairo_ft_unscaled_font_t *unscaled);
cairo_private void
_cairo_ft_unscaled_font_unlock_face (cairo_ft_unscaled_font_t *unscaled);
cairo_bool_t
_cairo_ft_scaled_font_is_vertical (cairo_scaled_font_t *scaled_font);
CAIRO_END_DECLS
#endif /* CAIRO_HAS_FT_FONT */

Просмотреть файл

@ -111,9 +111,9 @@ _cairo_glitz_surface_create_similar (void *abstract_src,
static cairo_status_t
_cairo_glitz_surface_get_image (cairo_glitz_surface_t *surface,
cairo_rectangle_fixed_t *interest,
cairo_rectangle_int16_t *interest,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *rect_out)
cairo_rectangle_int16_t *rect_out)
{
cairo_image_surface_t *image;
int x1, y1, x2, y2;
@ -318,9 +318,9 @@ _cairo_glitz_surface_release_source_image (void *abstract_surface,
static cairo_status_t
_cairo_glitz_surface_acquire_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect_out,
cairo_rectangle_int16_t *image_rect_out,
void **image_extra)
{
cairo_glitz_surface_t *surface = abstract_surface;
@ -340,9 +340,9 @@ _cairo_glitz_surface_acquire_dest_image (void *abstract_surfa
static void
_cairo_glitz_surface_release_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra)
{
cairo_glitz_surface_t *surface = abstract_surface;
@ -353,7 +353,6 @@ _cairo_glitz_surface_release_dest_image (void *abstract_surfa
cairo_surface_destroy (&image->base);
}
static cairo_status_t
_cairo_glitz_surface_clone_similar (void *abstract_surface,
cairo_surface_t *src,
@ -921,13 +920,14 @@ static cairo_int_status_t
_cairo_glitz_surface_fill_rectangles (void *abstract_dst,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int n_rects)
{
cairo_glitz_surface_t *dst = abstract_dst;
cairo_glitz_surface_t *src;
if (op == CAIRO_OPERATOR_SOURCE)
{
switch (op) {
case CAIRO_OPERATOR_SOURCE: {
glitz_color_t glitz_color;
glitz_color.red = color->red_short;
@ -937,11 +937,14 @@ _cairo_glitz_surface_fill_rectangles (void *abstract_dst,
glitz_set_rectangles (dst->surface, &glitz_color,
(glitz_rectangle_t *) rects, n_rects);
}
else
{
cairo_glitz_surface_t *src;
} break;
case CAIRO_OPERATOR_CLEAR: {
static glitz_color_t glitz_color = { 0, 0, 0, 0 };
glitz_set_rectangles (dst->surface, &glitz_color,
(glitz_rectangle_t *) rects, n_rects);
} break;
default:
if (op == CAIRO_OPERATOR_SATURATE)
return CAIRO_INT_STATUS_UNSUPPORTED;
@ -972,6 +975,7 @@ _cairo_glitz_surface_fill_rectangles (void *abstract_dst,
}
cairo_surface_destroy (&src->base);
break;
}
if (glitz_surface_get_status (dst->surface) == GLITZ_STATUS_NOT_SUPPORTED)
@ -1257,7 +1261,7 @@ _cairo_glitz_surface_set_clip_region (void *abstract_surface,
static cairo_int_status_t
_cairo_glitz_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_glitz_surface_t *surface = abstract_surface;
@ -1956,8 +1960,8 @@ _cairo_glitz_surface_old_show_glyphs (cairo_scaled_font_t *scaled_font,
if (glyph_private->area->width)
{
x_offset = scaled_glyphs[i]->surface->base.device_x_offset;
y_offset = scaled_glyphs[i]->surface->base.device_y_offset;
x_offset = scaled_glyphs[i]->surface->base.device_transform.x0;
y_offset = scaled_glyphs[i]->surface->base.device_transform.y0;
x1 = floor (glyphs[i].x + 0.5) + x_offset;
y1 = floor (glyphs[i].y + 0.5) + y_offset;
@ -1993,8 +1997,8 @@ _cairo_glitz_surface_old_show_glyphs (cairo_scaled_font_t *scaled_font,
glyph_private = scaled_glyphs[i]->surface_private;
}
x_offset = scaled_glyphs[i]->surface->base.device_x_offset;
y_offset = scaled_glyphs[i]->surface->base.device_y_offset;
x_offset = scaled_glyphs[i]->surface->base.device_transform.x0;
y_offset = scaled_glyphs[i]->surface->base.device_transform.y0;
x1 = floor (glyphs[i].x + 0.5) + x_offset;
y1 = floor (glyphs[i].y + 0.5) + y_offset;
@ -2149,10 +2153,27 @@ _cairo_glitz_surface_get_backend (void)
return &cairo_glitz_surface_backend;
}
static cairo_content_t
_glitz_format_to_content (glitz_format_t * format)
{
assert (format->color.fourcc == GLITZ_FOURCC_RGB);
if (format->color.alpha_size != 0) {
if (format->color.red_size != 0 &&
format->color.green_size != 0 &&
format->color.blue_size != 0)
return CAIRO_CONTENT_COLOR_ALPHA;
else
return CAIRO_CONTENT_ALPHA;
}
return CAIRO_CONTENT_COLOR;
}
cairo_surface_t *
cairo_glitz_surface_create (glitz_surface_t *surface)
{
cairo_glitz_surface_t *crsurface;
glitz_format_t *format;
if (surface == NULL)
return (cairo_surface_t*) &_cairo_surface_nil;
@ -2163,14 +2184,14 @@ cairo_glitz_surface_create (glitz_surface_t *surface)
return (cairo_surface_t*) &_cairo_surface_nil;
}
/* XXX: The content value here might be totally wrong. */
format = glitz_surface_get_format (surface);
_cairo_surface_init (&crsurface->base, &cairo_glitz_surface_backend,
CAIRO_CONTENT_COLOR_ALPHA);
_glitz_format_to_content(format));
glitz_surface_reference (surface);
crsurface->surface = surface;
crsurface->format = glitz_surface_get_format (surface);
crsurface->format = format;
crsurface->clip = NULL;
return (cairo_surface_t *) crsurface;

Просмотреть файл

@ -40,7 +40,7 @@
struct _cairo_gstate {
cairo_operator_t op;
double tolerance;
cairo_antialias_t antialias;

Просмотреть файл

@ -88,7 +88,7 @@ _cairo_gstate_create (cairo_surface_t *target)
status = _cairo_gstate_init (gstate, target);
if (status) {
free (gstate);
return NULL;
return NULL;
}
return gstate;
@ -111,11 +111,11 @@ _cairo_gstate_init (cairo_gstate_t *gstate,
gstate->scaled_font = NULL;
cairo_matrix_init_scale (&gstate->font_matrix,
CAIRO_GSTATE_DEFAULT_FONT_SIZE,
CAIRO_GSTATE_DEFAULT_FONT_SIZE,
CAIRO_GSTATE_DEFAULT_FONT_SIZE);
_cairo_font_options_init_default (&gstate->font_options);
_cairo_clip_init (&gstate->clip, target);
gstate->target = cairo_surface_reference (target);
@ -145,7 +145,7 @@ static cairo_status_t
_cairo_gstate_init_copy (cairo_gstate_t *gstate, cairo_gstate_t *other)
{
cairo_status_t status;
gstate->op = other->op;
gstate->tolerance = other->tolerance;
@ -309,8 +309,8 @@ _cairo_gstate_redirect_target (cairo_gstate_t *gstate, cairo_surface_t *child)
/* The clip is in surface backend coordinates for the previous target;
* translate it into the child's backend coordinates. */
_cairo_clip_translate (&gstate->clip,
_cairo_fixed_from_double (child->device_x_offset - gstate->parent_target->device_x_offset),
_cairo_fixed_from_double (child->device_y_offset - gstate->parent_target->device_y_offset));
_cairo_fixed_from_double (child->device_transform.x0 - gstate->parent_target->device_transform.x0),
_cairo_fixed_from_double (child->device_transform.y0 - gstate->parent_target->device_transform.y0));
}
/**
@ -394,7 +394,7 @@ _cairo_gstate_set_source (cairo_gstate_t *gstate,
cairo_pattern_destroy (gstate->source);
gstate->source = source;
gstate->source_ctm_inverse = gstate->ctm_inverse;
return CAIRO_STATUS_SUCCESS;
}
@ -499,7 +499,7 @@ _cairo_gstate_set_dash (cairo_gstate_t *gstate, double *dash, int num_dashes, do
if (gstate->stroke_style.dash)
free (gstate->stroke_style.dash);
gstate->stroke_style.num_dashes = num_dashes;
if (gstate->stroke_style.num_dashes == 0) {
@ -515,7 +515,7 @@ _cairo_gstate_set_dash (cairo_gstate_t *gstate, double *dash, int num_dashes, do
}
memcpy (gstate->stroke_style.dash, dash, gstate->stroke_style.num_dashes * sizeof (double));
dash_total = 0.0;
for (i = 0; i < gstate->stroke_style.num_dashes; i++) {
if (gstate->stroke_style.dash[i] < 0)
@ -567,7 +567,7 @@ _cairo_gstate_translate (cairo_gstate_t *gstate, double tx, double ty)
cairo_matrix_t tmp;
_cairo_gstate_unset_scaled_font (gstate);
cairo_matrix_init_translate (&tmp, tx, ty);
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
@ -586,7 +586,7 @@ _cairo_gstate_scale (cairo_gstate_t *gstate, double sx, double sy)
return CAIRO_STATUS_INVALID_MATRIX;
_cairo_gstate_unset_scaled_font (gstate);
cairo_matrix_init_scale (&tmp, sx, sy);
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
@ -602,7 +602,7 @@ _cairo_gstate_rotate (cairo_gstate_t *gstate, double angle)
cairo_matrix_t tmp;
_cairo_gstate_unset_scaled_font (gstate);
cairo_matrix_init_rotate (&tmp, angle);
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
@ -619,7 +619,7 @@ _cairo_gstate_transform (cairo_gstate_t *gstate,
cairo_matrix_t tmp;
_cairo_gstate_unset_scaled_font (gstate);
tmp = *matrix;
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
@ -636,7 +636,7 @@ _cairo_gstate_set_matrix (cairo_gstate_t *gstate,
cairo_status_t status;
_cairo_gstate_unset_scaled_font (gstate);
gstate->ctm = *matrix;
gstate->ctm_inverse = *matrix;
@ -651,7 +651,7 @@ cairo_status_t
_cairo_gstate_identity_matrix (cairo_gstate_t *gstate)
{
_cairo_gstate_unset_scaled_font (gstate);
cairo_matrix_init_identity (&gstate->ctm);
cairo_matrix_init_identity (&gstate->ctm_inverse);
@ -696,15 +696,17 @@ void
_cairo_gstate_user_to_backend (cairo_gstate_t *gstate, double *x, double *y)
{
cairo_matrix_transform_point (&gstate->ctm, x, y);
cairo_matrix_transform_point (&gstate->target->device_transform, x, y);
}
void
_cairo_gstate_backend_to_user (cairo_gstate_t *gstate, double *x, double *y)
{
cairo_matrix_transform_point (&gstate->target->device_transform_inverse, x, y);
cairo_matrix_transform_point (&gstate->ctm_inverse, x, y);
}
/* XXX: NYI
/* XXX: NYI
cairo_status_t
_cairo_gstate_stroke_to_path (cairo_gstate_t *gstate)
{
@ -723,7 +725,6 @@ _cairo_gstate_copy_transformed_pattern (cairo_gstate_t *gstate,
{
cairo_surface_pattern_t *surface_pattern;
cairo_surface_t *surface;
cairo_matrix_t offset_matrix;
_cairo_pattern_init_copy (pattern, original);
_cairo_pattern_transform (pattern, ctm_inverse);
@ -731,12 +732,8 @@ _cairo_gstate_copy_transformed_pattern (cairo_gstate_t *gstate,
if (cairo_pattern_get_type (original) == CAIRO_PATTERN_TYPE_SURFACE) {
surface_pattern = (cairo_surface_pattern_t *) original;
surface = surface_pattern->surface;
if (_cairo_surface_has_device_offset_or_scale (surface)) {
cairo_matrix_init_translate (&offset_matrix,
surface->device_x_offset,
surface->device_y_offset);
_cairo_pattern_transform (pattern, &offset_matrix);
}
if (_cairo_surface_has_device_transform (surface))
_cairo_pattern_transform (pattern, &surface->device_transform);
}
}
@ -787,7 +784,7 @@ _cairo_gstate_paint (cairo_gstate_t *gstate)
/**
* _cairo_operator_bounded_by_mask:
* @op: a #cairo_operator_t
*
*
* A bounded operator is one where mask pixel
* of zero results in no effect on the destination image.
*
@ -818,7 +815,7 @@ _cairo_operator_bounded_by_mask (cairo_operator_t op)
case CAIRO_OPERATOR_DEST_ATOP:
return FALSE;
}
ASSERT_NOT_REACHED;
return FALSE;
}
@ -826,7 +823,7 @@ _cairo_operator_bounded_by_mask (cairo_operator_t op)
/**
* _cairo_operator_bounded_by_source:
* @op: a #cairo_operator_t
*
*
* A bounded operator is one where source pixels of zero
* (in all four components, r, g, b and a) effect no change
* in the resulting destination image.
@ -858,7 +855,7 @@ _cairo_operator_bounded_by_source (cairo_operator_t op)
case CAIRO_OPERATOR_DEST_ATOP:
return FALSE;
}
ASSERT_NOT_REACHED;
return FALSE;
}
@ -923,7 +920,7 @@ _cairo_gstate_stroke (cairo_gstate_t *gstate, cairo_path_fixed_t *path)
gstate->antialias);
_cairo_pattern_fini (&source_pattern.base);
return status;
}
@ -959,52 +956,6 @@ BAIL:
return status;
}
/* XXX We currently have a confusing mix of boxes and rectangles as
* exemplified by this function. A cairo_box_t is a rectangular area
* represented by the coordinates of the upper left and lower right
* corners, expressed in fixed point numbers. A cairo_rectangle_fixed_t is
* also a rectangular area, but represented by the upper left corner
* and the width and the height, as integer numbers.
*
* This function converts a cairo_box_t to a cairo_rectangle_fixed_t by
* increasing the area to the nearest integer coordinates. We should
* standardize on cairo_rectangle_fixed_t and cairo_rectangle_fixed_t, and
* this function could be renamed to the more reasonable
* _cairo_rectangle_fixed_round.
*/
void
_cairo_box_round_to_rectangle (cairo_box_t *box, cairo_rectangle_fixed_t *rectangle)
{
rectangle->x = _cairo_fixed_integer_floor (box->p1.x);
rectangle->y = _cairo_fixed_integer_floor (box->p1.y);
rectangle->width = _cairo_fixed_integer_ceil (box->p2.x) - rectangle->x;
rectangle->height = _cairo_fixed_integer_ceil (box->p2.y) - rectangle->y;
}
void
_cairo_rectangle_intersect (cairo_rectangle_fixed_t *dest, cairo_rectangle_fixed_t *src)
{
int x1, y1, x2, y2;
x1 = MAX (dest->x, src->x);
y1 = MAX (dest->y, src->y);
x2 = MIN (dest->x + dest->width, src->x + src->width);
y2 = MIN (dest->y + dest->height, src->y + src->height);
if (x1 >= x2 || y1 >= y2) {
dest->x = 0;
dest->y = 0;
dest->width = 0;
dest->height = 0;
} else {
dest->x = x1;
dest->y = y1;
dest->width = x2 - x1;
dest->height = y2 - y1;
}
}
cairo_status_t
_cairo_gstate_fill (cairo_gstate_t *gstate, cairo_path_fixed_t *path)
{
@ -1013,11 +964,11 @@ _cairo_gstate_fill (cairo_gstate_t *gstate, cairo_path_fixed_t *path)
if (gstate->source->status)
return gstate->source->status;
status = _cairo_surface_set_clip (gstate->target, &gstate->clip);
if (status)
return status;
_cairo_gstate_copy_transformed_source (gstate, &pattern.base);
status = _cairo_surface_fill (gstate->target,
@ -1029,7 +980,7 @@ _cairo_gstate_fill (cairo_gstate_t *gstate, cairo_path_fixed_t *path)
gstate->antialias);
_cairo_pattern_fini (&pattern.base);
return status;
}
@ -1055,7 +1006,7 @@ _cairo_gstate_in_fill (cairo_gstate_t *gstate,
goto BAIL;
*inside_ret = _cairo_traps_contain (&traps, x, y);
BAIL:
_cairo_traps_fini (&traps);
@ -1099,9 +1050,9 @@ _cairo_gstate_stroke_extents (cairo_gstate_t *gstate,
cairo_status_t status;
cairo_traps_t traps;
cairo_box_t extents;
_cairo_traps_init (&traps);
status = _cairo_path_fixed_stroke_to_traps (path,
&gstate->stroke_style,
&gstate->ctm,
@ -1120,10 +1071,10 @@ _cairo_gstate_stroke_extents (cairo_gstate_t *gstate,
_cairo_gstate_backend_to_user (gstate, x1, y1);
_cairo_gstate_backend_to_user (gstate, x2, y2);
BAIL:
_cairo_traps_fini (&traps);
return status;
}
@ -1136,16 +1087,16 @@ _cairo_gstate_fill_extents (cairo_gstate_t *gstate,
cairo_status_t status;
cairo_traps_t traps;
cairo_box_t extents;
_cairo_traps_init (&traps);
status = _cairo_path_fixed_fill_to_traps (path,
gstate->fill_rule,
gstate->tolerance,
&traps);
if (status)
goto BAIL;
_cairo_traps_extents (&traps, &extents);
*x1 = _cairo_fixed_to_double (extents.p1.x);
@ -1155,10 +1106,10 @@ _cairo_gstate_fill_extents (cairo_gstate_t *gstate,
_cairo_gstate_backend_to_user (gstate, x1, y1);
_cairo_gstate_backend_to_user (gstate, x2, y2);
BAIL:
_cairo_traps_fini (&traps);
return status;
}
@ -1176,24 +1127,6 @@ _cairo_gstate_clip (cairo_gstate_t *gstate, cairo_path_fixed_t *path)
gstate->antialias, gstate->target);
}
cairo_bool_t
_cairo_gstate_has_clip (cairo_gstate_t *gstate)
{
return _cairo_clip_has_clip (&gstate->clip);
}
cairo_bool_t
_cairo_gstate_extract_clip_rectangles (cairo_gstate_t *gstate,
int max_rectangles,
cairo_clip_rect_t *rectangles_out,
int *num_rectangles_out)
{
return _cairo_clip_extract_rectangles (&gstate->clip,
max_rectangles,
rectangles_out,
num_rectangles_out);
}
static void
_cairo_gstate_unset_scaled_font (cairo_gstate_t *gstate)
{
@ -1204,9 +1137,9 @@ _cairo_gstate_unset_scaled_font (cairo_gstate_t *gstate)
}
cairo_status_t
_cairo_gstate_select_font_face (cairo_gstate_t *gstate,
const char *family,
cairo_font_slant_t slant,
_cairo_gstate_select_font_face (cairo_gstate_t *gstate,
const char *family,
cairo_font_slant_t slant,
cairo_font_weight_t weight)
{
cairo_font_face_t *font_face;
@ -1222,7 +1155,7 @@ _cairo_gstate_select_font_face (cairo_gstate_t *gstate,
}
cairo_status_t
_cairo_gstate_set_font_size (cairo_gstate_t *gstate,
_cairo_gstate_set_font_size (cairo_gstate_t *gstate,
double size)
{
_cairo_gstate_unset_scaled_font (gstate);
@ -1233,7 +1166,7 @@ _cairo_gstate_set_font_size (cairo_gstate_t *gstate,
}
cairo_status_t
_cairo_gstate_set_font_matrix (cairo_gstate_t *gstate,
_cairo_gstate_set_font_matrix (cairo_gstate_t *gstate,
const cairo_matrix_t *matrix)
{
_cairo_gstate_unset_scaled_font (gstate);
@ -1277,13 +1210,13 @@ _cairo_gstate_get_font_face (cairo_gstate_t *gstate,
status = _cairo_gstate_ensure_font_face (gstate);
if (status)
return status;
*font_face = gstate->font_face;
return CAIRO_STATUS_SUCCESS;
}
/*
/*
* Like everything else in this file, fonts involve Too Many Coordinate Spaces;
* it is easy to get confused about what's going on.
*
@ -1300,7 +1233,7 @@ _cairo_gstate_get_font_face (cairo_gstate_t *gstate,
* Metrics are returned in user space, whether they are obtained from
* the currently selected font in a #cairo_t or from a #cairo_scaled_font_t
* which is a font specialized to a particular scale matrix, CTM, and target
* surface.
* surface.
*
* The font's view
* ---------------
@ -1334,9 +1267,9 @@ _cairo_gstate_get_font_face (cairo_gstate_t *gstate,
* around.
*
* In order to perform any action on a font, we must build an object
* called a cairo_font_scale_t; this contains the central 2x2 matrix
* called a cairo_font_scale_t; this contains the central 2x2 matrix
* resulting from "font matrix * CTM".
*
*
* We pass this to the font when making requests of it, which causes it to
* reply for a particular [user request, device] combination, under the CTM
* (to accomodate the "zoom in" == "bigger fonts" issue above).
@ -1373,31 +1306,31 @@ _cairo_gstate_ensure_font_face (cairo_gstate_t *gstate)
else
gstate->font_face = font_face;
}
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
_cairo_gstate_ensure_scaled_font (cairo_gstate_t *gstate)
{
cairo_status_t status;
cairo_font_options_t options;
if (gstate->scaled_font)
return CAIRO_STATUS_SUCCESS;
status = _cairo_gstate_ensure_font_face (gstate);
if (status)
return status;
cairo_surface_get_font_options (gstate->target, &options);
cairo_font_options_merge (&options, &gstate->font_options);
gstate->scaled_font = cairo_scaled_font_create (gstate->font_face,
&gstate->font_matrix,
&gstate->ctm,
&options);
if (!gstate->scaled_font)
return CAIRO_STATUS_NO_MEMORY;
@ -1405,7 +1338,7 @@ _cairo_gstate_ensure_scaled_font (cairo_gstate_t *gstate)
}
cairo_status_t
_cairo_gstate_get_font_extents (cairo_gstate_t *gstate,
_cairo_gstate_get_font_extents (cairo_gstate_t *gstate,
cairo_font_extents_t *extents)
{
cairo_status_t status = _cairo_gstate_ensure_scaled_font (gstate);
@ -1418,7 +1351,7 @@ _cairo_gstate_get_font_extents (cairo_gstate_t *gstate,
}
cairo_status_t
_cairo_gstate_text_to_glyphs (cairo_gstate_t *gstate,
_cairo_gstate_text_to_glyphs (cairo_gstate_t *gstate,
const char *utf8,
double x,
double y,
@ -1430,7 +1363,7 @@ _cairo_gstate_text_to_glyphs (cairo_gstate_t *gstate,
status = _cairo_gstate_ensure_scaled_font (gstate);
if (status)
return status;
status = _cairo_scaled_font_text_to_glyphs (gstate->scaled_font, x, y,
utf8, glyphs, num_glyphs);
@ -1441,25 +1374,25 @@ _cairo_gstate_text_to_glyphs (cairo_gstate_t *gstate,
}
cairo_status_t
_cairo_gstate_set_font_face (cairo_gstate_t *gstate,
_cairo_gstate_set_font_face (cairo_gstate_t *gstate,
cairo_font_face_t *font_face)
{
if (font_face && font_face->status)
return font_face->status;
if (font_face != gstate->font_face) {
cairo_font_face_destroy (gstate->font_face);
gstate->font_face = cairo_font_face_reference (font_face);
}
_cairo_gstate_unset_scaled_font (gstate);
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
_cairo_gstate_glyph_extents (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_text_extents_t *extents)
{
@ -1477,8 +1410,8 @@ _cairo_gstate_glyph_extents (cairo_gstate_t *gstate,
}
cairo_status_t
_cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
_cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
int num_glyphs)
{
cairo_status_t status;
@ -1500,13 +1433,13 @@ _cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
transformed_glyphs = malloc (num_glyphs * sizeof(cairo_glyph_t));
if (transformed_glyphs == NULL)
return CAIRO_STATUS_NO_MEMORY;
for (i = 0; i < num_glyphs; ++i)
{
transformed_glyphs[i] = glyphs[i];
_cairo_gstate_user_to_backend (gstate,
&transformed_glyphs[i].x,
&transformed_glyphs[i].y);
_cairo_gstate_user_to_device (gstate,
&transformed_glyphs[i].x,
&transformed_glyphs[i].y);
}
_cairo_gstate_copy_transformed_source (gstate, &source_pattern.base);
@ -1526,7 +1459,7 @@ _cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
cairo_status_t
_cairo_gstate_glyph_path (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_path_fixed_t *path)
{
@ -1537,16 +1470,16 @@ _cairo_gstate_glyph_path (cairo_gstate_t *gstate,
status = _cairo_gstate_ensure_scaled_font (gstate);
if (status)
return status;
transformed_glyphs = malloc (num_glyphs * sizeof(cairo_glyph_t));
if (transformed_glyphs == NULL)
return CAIRO_STATUS_NO_MEMORY;
for (i = 0; i < num_glyphs; ++i)
{
transformed_glyphs[i] = glyphs[i];
_cairo_gstate_user_to_backend (gstate,
&(transformed_glyphs[i].x),
&(transformed_glyphs[i].x),
&(transformed_glyphs[i].y));
}
@ -1572,3 +1505,21 @@ _cairo_gstate_get_antialias (cairo_gstate_t *gstate)
{
return gstate->antialias;
}
cairo_bool_t
_cairo_gstate_has_clip (cairo_gstate_t *gstate)
{
return _cairo_clip_has_clip (&gstate->clip);
}
cairo_bool_t
_cairo_gstate_extract_clip_rectangles (cairo_gstate_t *gstate,
int max_rectangles,
cairo_clip_rect_t *rectangles_out,
int *num_rectangles_out)
{
return _cairo_clip_extract_rectangles (&gstate->clip,
max_rectangles,
rectangles_out,
num_rectangles_out);
}

Просмотреть файл

@ -47,7 +47,7 @@
* DEAD: Entry had been live in the past. A dead entry can be reused
* but does not terminate a search for an exact entry.
* Appears in the table as a pointer to DEAD_ENTRY.
*
*
* LIVE: Entry is currently being used.
* Appears in the table as any non-NULL, non-DEAD_ENTRY pointer.
*/
@ -130,7 +130,7 @@ struct _cairo_hash_table {
/**
* _cairo_hash_table_create:
* @keys_equal: a function to return TRUE if two keys are equal
*
*
* Creates a new hash table which will use the keys_equal() function
* to compare hash keys. Data is provided to the hash table in the
* form of user-derived versions of cairo_hash_entry_t. A hash entry
@ -140,12 +140,12 @@ struct _cairo_hash_table {
* will be necessary, (as in _cairo_hash_table_insert).
*
* See #cairo_hash_entry_t for more details.
*
*
* Return value: the new hash table or NULL if out of memory.
**/
cairo_hash_table_t *
_cairo_hash_table_create (cairo_hash_keys_equal_func_t keys_equal)
{
{
cairo_hash_table_t *hash_table;
hash_table = malloc (sizeof (cairo_hash_table_t));
@ -172,7 +172,7 @@ _cairo_hash_table_create (cairo_hash_keys_equal_func_t keys_equal)
/**
* _cairo_hash_table_destroy:
* @hash_table: an empty hash table to destroy
*
*
* Immediately destroys the given hash table, freeing all resources
* associated with it.
*
@ -196,7 +196,7 @@ _cairo_hash_table_destroy (cairo_hash_table_t *hash_table)
assert (hash_table->live_entries == 0);
/* No iterators can be running. Otherwise, halt. */
assert (hash_table->iterating == 0);
free (hash_table->entries);
hash_table->entries = NULL;
@ -212,7 +212,7 @@ _cairo_hash_table_destroy (cairo_hash_table_t *hash_table)
* @key_unique: If TRUE, then caller asserts that no key already
* exists that will compare equal to #key, so search can be
* optimized. If unsure, set to FALSE and the code will always work.
*
*
* Search the hashtable for a live entry for which
* hash_table->keys_equal returns true. If no such entry exists then
* return the first available (free or dead entry).
@ -231,10 +231,10 @@ static cairo_hash_entry_t **
_cairo_hash_table_lookup_internal (cairo_hash_table_t *hash_table,
cairo_hash_entry_t *key,
cairo_bool_t key_is_unique)
{
{
cairo_hash_entry_t **entry, **first_available = NULL;
unsigned long table_size, i, idx, step;
table_size = hash_table->arrangement->size;
idx = key->hash % table_size;
@ -264,7 +264,7 @@ _cairo_hash_table_lookup_internal (cairo_hash_table_t *hash_table,
return entry;
}
if (step == 0) {
if (step == 0) {
step = key->hash % hash_table->arrangement->rehash;
if (step == 0)
step = 1;
@ -275,7 +275,7 @@ _cairo_hash_table_lookup_internal (cairo_hash_table_t *hash_table,
idx -= table_size;
}
/*
/*
* The table should not have permitted you to get here if you were just
* looking for a free slot: there should have been room.
*/
@ -287,11 +287,11 @@ _cairo_hash_table_lookup_internal (cairo_hash_table_t *hash_table,
/**
* _cairo_hash_table_resize:
* @hash_table: a hash table
*
*
* Resize the hash table if the number of entries has gotten much
* bigger or smaller than the ideal number of entries for the current
* size.
*
*
* Return value: CAIRO_STATUS_SUCCESS if successful or
* CAIRO_STATUS_NO_MEMORY if out of memory.
**/
@ -328,9 +328,9 @@ _cairo_hash_table_resize (cairo_hash_table_t *hash_table)
new_size = tmp.arrangement->size;
tmp.entries = calloc (new_size, sizeof (cairo_hash_entry_t*));
if (tmp.entries == NULL)
if (tmp.entries == NULL)
return CAIRO_STATUS_NO_MEMORY;
for (i = 0; i < hash_table->arrangement->size; ++i) {
if (ENTRY_IS_LIVE (hash_table->entries[i])) {
entry = _cairo_hash_table_lookup_internal (&tmp,
@ -353,11 +353,11 @@ _cairo_hash_table_resize (cairo_hash_table_t *hash_table)
* @hash_table: a hash table
* @key: the key of interest
* @entry_return: pointer for return value.
*
*
* Performs a lookup in @hash_table looking for an entry which has a
* key that matches @key, (as determined by the keys_equal() function
* passed to _cairo_hash_table_create).
*
*
* Return value: TRUE if there is an entry in the hash table that
* matches the given key, (which will now be in *entry_return). FALSE
* otherwise, (in which case *entry_return will be NULL).
@ -384,7 +384,7 @@ _cairo_hash_table_lookup (cairo_hash_table_t *hash_table,
* _cairo_hash_table_random_entry:
* @hash_table: a hash table
* @predicate: a predicate function, or NULL for any entry.
*
*
* Find a random entry in the hash table satisfying the given
* @predicate. A NULL @predicate is taken as equivalent to a function
* which always returns TRUE, (eg. any entry in the table will do).
@ -424,7 +424,7 @@ _cairo_hash_table_random_entry (cairo_hash_table_t *hash_table,
return *entry;
}
if (step == 0) {
if (step == 0) {
step = hash % hash_table->arrangement->rehash;
if (step == 0)
step = 1;
@ -442,7 +442,7 @@ _cairo_hash_table_random_entry (cairo_hash_table_t *hash_table,
* _cairo_hash_table_insert:
* @hash_table: a hash table
* @key_and_value: an entry to be inserted
*
*
* Insert the entry #key_and_value into the hash table.
*
* WARNING: It is a fatal error if an entry exists in the hash table
@ -454,7 +454,7 @@ _cairo_hash_table_random_entry (cairo_hash_table_t *hash_table,
* Instead of using insert to replace an entry, consider just editing
* the entry obtained with _cairo_hash_table_lookup. Or if absolutely
* necessary, use _cairo_hash_table_remove first.
*
*
* Return value: CAIRO_STATUS_SUCCESS if successful or
* CAIRO_STATUS_NO_MEMORY if insufficient memory is available.
**/
@ -464,13 +464,13 @@ _cairo_hash_table_insert (cairo_hash_table_t *hash_table,
{
cairo_status_t status;
cairo_hash_entry_t **entry;
/* Insert is illegal while an iterator is running. */
assert (hash_table->iterating == 0);
entry = _cairo_hash_table_lookup_internal (hash_table,
key_and_value, FALSE);
if (ENTRY_IS_LIVE(*entry))
{
/* User is being bad, let's crash. */
@ -491,7 +491,7 @@ _cairo_hash_table_insert (cairo_hash_table_t *hash_table,
* _cairo_hash_table_remove:
* @hash_table: a hash table
* @key: key of entry to be removed
*
*
* Remove an entry from the hash table which has a key that matches
* @key, if any (as determined by the keys_equal() function passed to
* _cairo_hash_table_create).
@ -529,7 +529,7 @@ _cairo_hash_table_remove (cairo_hash_table_t *hash_table,
* @hash_table: a hash table
* @hash_callback: function to be called for each live entry
* @closure: additional argument to be passed to @hash_callback
*
*
* Call @hash_callback for each live entry in the hash table, in a
* non-specified order.
*
@ -549,7 +549,7 @@ _cairo_hash_table_foreach (cairo_hash_table_t *hash_table,
if (hash_table == NULL)
return;
/* Mark the table for iteration */
++hash_table->iterating;
for (i = 0; i < hash_table->arrangement->size; i++) {

Просмотреть файл

@ -105,7 +105,7 @@ _cairo_hull_vertex_compare (const void *av, const void *bv)
/*
* Use the point's ids to ensure a total ordering.
* a well-defined ordering, and avoid setting discard on
* both points.
* both points.
*/
if (a_dist < b_dist || (a_dist == b_dist && a->id < b->id)) {
a->discard = 1;

Просмотреть файл

@ -44,11 +44,15 @@ _cairo_format_bpp (cairo_format_t format)
return 1;
case CAIRO_FORMAT_A8:
return 8;
case CAIRO_FORMAT_RGB16_565:
return 16;
case CAIRO_FORMAT_RGB24:
case CAIRO_FORMAT_ARGB32:
default:
return 32;
}
ASSERT_NOT_REACHED;
return 32;
}
cairo_surface_t *
@ -90,34 +94,54 @@ _cairo_format_from_pixman_format (pixman_format_t *pixman_format)
pixman_format_get_masks (pixman_format, &bpp, &am, &rm, &gm, &bm);
if (bpp == 32 &&
am == 0xff000000 &&
rm == 0x00ff0000 &&
gm == 0x0000ff00 &&
bm == 0x000000ff)
return CAIRO_FORMAT_ARGB32;
switch (bpp) {
case 32:
if (am == 0xff000000 &&
rm == 0x00ff0000 &&
gm == 0x0000ff00 &&
bm == 0x000000ff)
return CAIRO_FORMAT_ARGB32;
if (am == 0x0 &&
rm == 0x00ff0000 &&
gm == 0x0000ff00 &&
bm == 0x000000ff)
return CAIRO_FORMAT_RGB24;
break;
case 16:
if (am == 0x0 &&
rm == 0xf800 &&
gm == 0x07e0 &&
bm == 0x001f)
return CAIRO_FORMAT_RGB16_565;
break;
case 8:
if (am == 0xff &&
rm == 0x0 &&
gm == 0x0 &&
bm == 0x0)
return CAIRO_FORMAT_A8;
break;
case 1:
if (am == 0x1 &&
rm == 0x0 &&
gm == 0x0 &&
bm == 0x0)
return CAIRO_FORMAT_A1;
break;
}
if (bpp == 32 &&
am == 0x0 &&
rm == 0x00ff0000 &&
gm == 0x0000ff00 &&
bm == 0x000000ff)
return CAIRO_FORMAT_RGB24;
if (bpp == 8 &&
am == 0xff &&
rm == 0x0 &&
gm == 0x0 &&
bm == 0x0)
return CAIRO_FORMAT_A8;
if (bpp == 1 &&
am == 0x1 &&
rm == 0x0 &&
gm == 0x0 &&
bm == 0x0)
return CAIRO_FORMAT_A1;
fprintf (stderr,
"Error: Cairo does not yet support the requested image format:\n"
"\tDepth: %d\n"
"\tAlpha mask: 0x%08x\n"
"\tRed mask: 0x%08x\n"
"\tGreen mask: 0x%08x\n"
"\tBlue mask: 0x%08x\n"
"Please file an enhacement request (quoting the above) at:\n"
PACKAGE_BUGREPORT "\n",
bpp, am, rm, gm, bm);
ASSERT_NOT_REACHED;
return (cairo_format_t) -1;
}
@ -172,6 +196,9 @@ _create_pixman_format (cairo_format_t format)
case CAIRO_FORMAT_A8:
return pixman_format_create (PIXMAN_FORMAT_NAME_A8);
break;
case CAIRO_FORMAT_RGB16_565:
return pixman_format_create (PIXMAN_FORMAT_NAME_RGB16_565);
break;
case CAIRO_FORMAT_RGB24:
return pixman_format_create (PIXMAN_FORMAT_NAME_RGB24);
break;
@ -184,10 +211,10 @@ _create_pixman_format (cairo_format_t format)
/**
* cairo_image_surface_create:
* @format: format of pixels in the surface to create
* @format: format of pixels in the surface to create
* @width: width of the surface, in pixels
* @height: height of the surface, in pixels
*
*
* Creates an image surface of the specified format and
* dimensions. Initially the surface contents are all
* 0. (Specifically, within each pixel, each color or alpha channel
@ -257,7 +284,7 @@ _cairo_image_surface_create_with_content (cairo_content_t content,
* in the buffer. Having this be specified separate from @width
* allows for padding at the end of rows, or for writing
* to a subportion of a larger image.
*
*
* Creates an image surface for the provided pixel data. The output
* buffer must be kept around until the #cairo_surface_t is destroyed
* or cairo_surface_finish() is called on the surface. The initial
@ -295,7 +322,7 @@ cairo_image_surface_create_for_data (unsigned char *data,
_cairo_error (CAIRO_STATUS_NO_MEMORY);
return (cairo_surface_t*) &_cairo_surface_nil;
}
pixman_image = pixman_image_create_for_data ((pixman_bits_t *) data, pixman_format,
width, height,
_cairo_format_bpp (format),
@ -328,12 +355,60 @@ _cairo_image_surface_create_for_data_with_content (unsigned char *data,
width, height, stride);
}
/**
* cairo_image_surface_get_data:
* @surface: a #cairo_image_surface_t
*
* Get a pointer to the data of the image surface, for direct
* inspection or modification.
*
* Return value: a pointer to the image data of this surface or NULL
* if @surface is not an image surface.
*
* Since: 1.2
**/
unsigned char *
cairo_image_surface_get_data (cairo_surface_t *surface)
{
cairo_image_surface_t *image_surface = (cairo_image_surface_t *) surface;
if (!_cairo_surface_is_image (surface)) {
_cairo_error (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return NULL;
}
return image_surface->data;
}
/**
* cairo_image_surface_get_format:
* @surface: a #cairo_image_surface_t
*
* Get the format of the surface.
*
* Return value: the format of the surface
*
* Since: 1.2
**/
cairo_format_t
cairo_image_surface_get_format (cairo_surface_t *surface)
{
cairo_image_surface_t *image_surface = (cairo_image_surface_t *) surface;
if (!_cairo_surface_is_image (surface)) {
_cairo_error (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return 0;
}
return image_surface->format;
}
/**
* cairo_image_surface_get_width:
* @surface: a #cairo_image_surface_t
*
*
* Get the width of the image surface in pixels.
*
*
* Return value: the width of the surface in pixels.
**/
int
@ -352,9 +427,9 @@ cairo_image_surface_get_width (cairo_surface_t *surface)
/**
* cairo_image_surface_get_height:
* @surface: a #cairo_image_surface_t
*
*
* Get the height of the image surface in pixels.
*
*
* Return value: the height of the surface in pixels.
**/
int
@ -370,6 +445,33 @@ cairo_image_surface_get_height (cairo_surface_t *surface)
return image_surface->height;
}
/**
* cairo_image_surface_get_stride:
* @surface: a #cairo_image_surface_t
*
* Get the stride of the image surface in bytes
*
* Return value: the stride of the image surface in bytes (or 0 if
* @surface is not an image surface). The stride is the distance in
* bytes from the beginning of one row of the image data to the
* beginning of the next row.
*
* Since: 1.2
**/
int
cairo_image_surface_get_stride (cairo_surface_t *surface)
{
cairo_image_surface_t *image_surface = (cairo_image_surface_t *) surface;
if (!_cairo_surface_is_image (surface)) {
_cairo_error (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return 0;
}
return image_surface->stride;
}
cairo_format_t
_cairo_format_from_content (cairo_content_t content)
{
@ -393,6 +495,7 @@ _cairo_content_from_format (cairo_format_t format)
case CAIRO_FORMAT_ARGB32:
return CAIRO_CONTENT_COLOR_ALPHA;
case CAIRO_FORMAT_RGB24:
case CAIRO_FORMAT_RGB16_565:
return CAIRO_CONTENT_COLOR;
case CAIRO_FORMAT_A8:
case CAIRO_FORMAT_A1:
@ -446,7 +549,7 @@ _cairo_image_surface_acquire_source_image (void *abstract_sur
{
*image_out = abstract_surface;
*image_extra = NULL;
return CAIRO_STATUS_SUCCESS;
}
@ -459,13 +562,13 @@ _cairo_image_surface_release_source_image (void *abstract_surf
static cairo_status_t
_cairo_image_surface_acquire_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect_out,
cairo_rectangle_int16_t *image_rect_out,
void **image_extra)
{
cairo_image_surface_t *surface = abstract_surface;
image_rect_out->x = 0;
image_rect_out->y = 0;
image_rect_out->width = surface->width;
@ -473,15 +576,15 @@ _cairo_image_surface_acquire_dest_image (void *abstract_surfa
*image_out = surface;
*image_extra = NULL;
return CAIRO_STATUS_SUCCESS;
}
static void
_cairo_image_surface_release_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra)
{
}
@ -497,8 +600,8 @@ _cairo_image_surface_clone_similar (void *abstract_surface,
*clone_out = cairo_surface_reference (src);
return CAIRO_STATUS_SUCCESS;
}
}
return CAIRO_INT_STATUS_UNSUPPORTED;
}
@ -550,7 +653,7 @@ _cairo_image_surface_set_attributes (cairo_image_surface_t *surface,
cairo_surface_attributes_t *attributes)
{
cairo_int_status_t status;
status = _cairo_image_surface_set_matrix (surface, &attributes->matrix);
if (status)
return status;
@ -569,9 +672,9 @@ _cairo_image_surface_set_attributes (cairo_image_surface_t *surface,
pixman_image_set_repeat (surface->pixman_image, PIXMAN_REPEAT_PAD);
break;
}
status = _cairo_image_surface_set_filter (surface, attributes->filter);
return status;
}
@ -650,7 +753,7 @@ _cairo_image_surface_composite (cairo_operator_t op,
&src_attr, &mask_attr);
if (status)
return status;
status = _cairo_image_surface_set_attributes (src, &src_attr);
if (status)
goto CLEANUP_SURFACES;
@ -660,7 +763,7 @@ _cairo_image_surface_composite (cairo_operator_t op,
status = _cairo_image_surface_set_attributes (mask, &mask_attr);
if (status)
goto CLEANUP_SURFACES;
pixman_composite (_pixman_operator (op),
src->pixman_image,
mask->pixman_image,
@ -684,7 +787,7 @@ _cairo_image_surface_composite (cairo_operator_t op,
dst_x, dst_y,
width, height);
}
if (!_cairo_operator_bounded_by_source (op))
status = _cairo_surface_composite_fixup_unbounded (&dst->base,
&src_attr, src->width, src->height,
@ -698,9 +801,9 @@ _cairo_image_surface_composite (cairo_operator_t op,
CLEANUP_SURFACES:
if (mask)
_cairo_pattern_release_surface (mask_pattern, &mask->base, &mask_attr);
_cairo_pattern_release_surface (src_pattern, &src->base, &src_attr);
return status;
}
@ -708,7 +811,7 @@ static cairo_int_status_t
_cairo_image_surface_fill_rectangles (void *abstract_surface,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects)
{
cairo_image_surface_t *surface = abstract_surface;
@ -727,20 +830,6 @@ _cairo_image_surface_fill_rectangles (void *abstract_surface,
return CAIRO_STATUS_SUCCESS;
}
static cairo_bool_t
_cairo_image_surface_is_alpha_only (cairo_image_surface_t *surface)
{
int bpp, alpha, red, green, blue;
if (surface->format != (cairo_format_t) -1)
return surface->format == CAIRO_FORMAT_A1 || surface->format == CAIRO_FORMAT_A8;
pixman_format_get_masks (pixman_image_get_format (surface->pixman_image),
&bpp, &alpha, &red, &green, &blue);
return red == 0 && blue == 0 && green == 0;
}
static cairo_int_status_t
_cairo_image_surface_composite_trapezoids (cairo_operator_t op,
cairo_pattern_t *pattern,
@ -780,7 +869,7 @@ _cairo_image_surface_composite_trapezoids (cairo_operator_t op,
*/
if (op == CAIRO_OPERATOR_ADD &&
_cairo_pattern_is_opaque_solid (pattern) &&
_cairo_image_surface_is_alpha_only (dst) &&
dst->base.content == CAIRO_CONTENT_ALPHA &&
!dst->has_clip &&
antialias != CAIRO_ANTIALIAS_NONE)
{
@ -881,7 +970,7 @@ _cairo_image_surface_set_clip_region (void *abstract_surface,
static cairo_int_status_t
_cairo_image_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_image_surface_t *surface = abstract_surface;
@ -896,9 +985,9 @@ _cairo_image_surface_get_extents (void *abstract_surface,
/**
* _cairo_surface_is_image:
* @surface: a #cairo_surface_t
*
*
* Checks if a surface is an #cairo_image_surface_t
*
*
* Return value: TRUE if the surface is an image surface
**/
cairo_bool_t

Просмотреть файл

@ -335,7 +335,7 @@ _cairo_lzw_compress (unsigned char *data, unsigned long *size_in_out)
_lzw_buf_init (&buf, *size_in_out);
_lzw_symbol_table_init (&table);
/* The LZW header is a clear table code. */
_lzw_buf_store_bits (&buf, LZW_CODE_CLEAR_TABLE, code_bits);

Просмотреть файл

@ -48,7 +48,7 @@ _cairo_matrix_compute_adjoint (cairo_matrix_t *matrix);
/**
* cairo_matrix_init_identity:
* @matrix: a #cairo_matrix_t
*
*
* Modifies @matrix to be an identity transformation.
**/
void
@ -70,7 +70,7 @@ slim_hidden_def(cairo_matrix_init_identity);
* @yy: yy component of the affine transformation
* @x0: X translation component of the affine transformation
* @y0: Y translation component of the affine transformation
*
*
* Sets @matrix to be the affine transformation given by
* @xx, @yx, @xy, @yy, @x0, @y0. The transformation is given
* by:
@ -94,14 +94,14 @@ slim_hidden_def(cairo_matrix_init);
/**
* _cairo_matrix_get_affine:
* @matrix: a @cairo_matrix_t
* @matrix: a #cairo_matrix_t
* @xx: location to store xx component of matrix
* @yx: location to store yx component of matrix
* @xy: location to store xy component of matrix
* @yy: location to store yy component of matrix
* @x0: location to store x0 (X-translation component) of matrix, or %NULL
* @y0: location to store y0 (Y-translation component) of matrix, or %NULL
*
*
* Gets the matrix values for the affine tranformation that @matrix represents.
* See cairo_matrix_init().
*
@ -135,7 +135,7 @@ _cairo_matrix_get_affine (const cairo_matrix_t *matrix,
* @matrix: a cairo_matrix_t
* @tx: amount to translate in the X direction
* @ty: amount to translate in the Y direction
*
*
* Initializes @matrix to a transformation that translates by @tx and
* @ty in the X and Y dimensions, respectively.
**/
@ -155,7 +155,7 @@ slim_hidden_def(cairo_matrix_init_translate);
* @matrix: a cairo_matrix_t
* @tx: amount to translate in the X direction
* @ty: amount to translate in the Y direction
*
*
* Applies a translation by @tx, @ty to the transformation in
* @matrix. The effect of the new transformation is to first translate
* the coordinates by @tx and @ty, then apply the original transformation
@ -176,7 +176,7 @@ cairo_matrix_translate (cairo_matrix_t *matrix, double tx, double ty)
* @matrix: a cairo_matrix_t
* @sx: scale factor in the X direction
* @sy: scale factor in the Y direction
*
*
* Initializes @matrix to a transformation that scales by @sx and @sy
* in the X and Y dimensions, respectively.
**/
@ -196,7 +196,7 @@ slim_hidden_def(cairo_matrix_init_scale);
* @matrix: a #cairo_matrix_t
* @sx: scale factor in the X direction
* @sy: scale factor in the Y direction
*
*
* Applies scaling by @tx, @ty to the transformation in @matrix. The
* effect of the new transformation is to first scale the coordinates
* by @sx and @sy, then apply the original transformation to the coordinates.
@ -220,7 +220,7 @@ slim_hidden_def(cairo_matrix_scale);
* the positive X axis toward the positive Y axis. With the default
* axis orientation of cairo, positive angles rotate in a clockwise
* direction.
*
*
* Initialized @matrix to a transformation that rotates by @radians.
**/
void
@ -242,13 +242,13 @@ slim_hidden_def(cairo_matrix_init_rotate);
/**
* cairo_matrix_rotate:
* @matrix: a @cairo_matrix_t
* @matrix: a #cairo_matrix_t
* @radians: angle of rotation, in radians. The direction of rotation
* is defined such that positive angles rotate in the direction from
* the positive X axis toward the positive Y axis. With the default
* axis orientation of cairo, positive angles rotate in a clockwise
* direction.
*
*
* Applies rotation by @radians to the transformation in
* @matrix. The effect of the new transformation is to first rotate the
* coordinates by @radians, then apply the original transformation
@ -266,10 +266,10 @@ cairo_matrix_rotate (cairo_matrix_t *matrix, double radians)
/**
* cairo_matrix_multiply:
* @result: a @cairo_matrix_t in which to store the result
* @a: a @cairo_matrix_t
* @b: a @cairo_matrix_t
*
* @result: a #cairo_matrix_t in which to store the result
* @a: a #cairo_matrix_t
* @b: a #cairo_matrix_t
*
* Multiplies the affine transformations in @a and @b together
* and stores the result in @result. The effect of the resulting
* transformation is to first apply the transformation in @a to the
@ -304,12 +304,12 @@ slim_hidden_def(cairo_matrix_multiply);
/**
* cairo_matrix_transform_distance:
* @matrix: a @cairo_matrix_t
* @matrix: a #cairo_matrix_t
* @dx: X component of a distance vector. An in/out parameter
* @dy: Y component of a distance vector. An in/out parameter
*
*
* Transforms the distance vector (@dx,@dy) by @matrix. This is
* similar to cairo_matrix_transform() except that the translation
* similar to cairo_matrix_transform_point() except that the translation
* components of the transformation are ignored. The calculation of
* the returned vector is as follows:
*
@ -338,10 +338,10 @@ slim_hidden_def(cairo_matrix_transform_distance);
/**
* cairo_matrix_transform_point:
* @matrix: a @cairo_matrix_t
* @matrix: a #cairo_matrix_t
* @x: X position. An in/out parameter
* @y: Y position. An in/out parameter
*
*
* Transforms the point (@x, @y) by @matrix.
**/
void
@ -442,13 +442,13 @@ _cairo_matrix_compute_adjoint (cairo_matrix_t *matrix)
/**
* cairo_matrix_invert:
* @matrix: a @cairo_matrix_t
*
* @matrix: a #cairo_matrix_t
*
* Changes @matrix to be the inverse of it's original value. Not
* all transformation matrices have inverses; if the matrix
* collapses points together (it is <firstterm>degenerate</firstterm>),
* then it has no inverse and this function will fail.
*
*
* Returns: If @matrix has an inverse, modifies @matrix to
* be the inverse matrix and returns %CAIRO_STATUS_SUCCESS. Otherwise,
* returns %CAIRO_STATUS_INVALID_MATRIX.
@ -460,7 +460,7 @@ cairo_matrix_invert (cairo_matrix_t *matrix)
double det;
_cairo_matrix_compute_determinant (matrix, &det);
if (det == 0)
return CAIRO_STATUS_INVALID_MATRIX;
@ -501,7 +501,7 @@ _cairo_matrix_compute_scale_factors (const cairo_matrix_t *matrix,
double x = x_major != 0;
double y = x == 0;
double major, minor;
cairo_matrix_transform_distance (matrix, &x, &y);
major = sqrt(x*x + y*y);
/*
@ -511,7 +511,7 @@ _cairo_matrix_compute_scale_factors (const cairo_matrix_t *matrix,
det = -det;
if (major)
minor = det / major;
else
else
minor = 0.0;
if (x_major)
{
@ -528,7 +528,15 @@ _cairo_matrix_compute_scale_factors (const cairo_matrix_t *matrix,
return CAIRO_STATUS_SUCCESS;
}
cairo_bool_t
cairo_bool_t
_cairo_matrix_is_identity (const cairo_matrix_t *matrix)
{
return (matrix->xx == 1.0 && matrix->yx == 0.0 &&
matrix->xy == 0.0 && matrix->yy == 1.0 &&
matrix->x0 == 0.0 && matrix->y0 == 0.0);
}
cairo_bool_t
_cairo_matrix_is_integer_translation(const cairo_matrix_t *m,
int *itx, int *ity)
{
@ -556,149 +564,114 @@ _cairo_matrix_is_integer_translation(const cairo_matrix_t *m,
return TRUE;
}
cairo_bool_t
_cairo_matrix_is_integer_translation_and_scale(const cairo_matrix_t *m,
int *itx, int *ity, int *sx, int *sy)
{
cairo_fixed_t x0_fixed, y0_fixed, xx_fixed, yy_fixed;
if ((m->yx != 0.0) || (m->yy != 0.0))
return FALSE;
x0_fixed = _cairo_fixed_from_double (m->x0);
y0_fixed = _cairo_fixed_from_double (m->y0);
xx_fixed = _cairo_fixed_from_double (m->xx);
yy_fixed = _cairo_fixed_from_double (m->yy);
if (!_cairo_fixed_is_integer(x0_fixed) ||
!_cairo_fixed_is_integer(y0_fixed) ||
!_cairo_fixed_is_integer(xx_fixed) ||
!_cairo_fixed_is_integer(yy_fixed))
return FALSE;
if (itx)
*itx = _cairo_fixed_integer_part(x0_fixed);
if (ity)
*ity = _cairo_fixed_integer_part(y0_fixed);
if (sx)
*sx = _cairo_fixed_integer_part(xx_fixed);
if (sy)
*sy = _cairo_fixed_integer_part(yy_fixed);
return TRUE;
}
/*
A circle in user space is transformed into an ellipse in device space.
The following is a derivation of a formula to calculate the length of the
major axis for this ellipse; this is useful for error bounds calculations.
Thanks to Walter Brisken <wbrisken@aoc.nrao.edu> for this derivation:
1. First some notation:
All capital letters represent vectors in two dimensions. A prime '
All capital letters represent vectors in two dimensions. A prime '
represents a transformed coordinate. Matrices are written in underlined
form, ie _R_. Lowercase letters represent scalar real values.
2. The question has been posed: What is the maximum expansion factor
2. The question has been posed: What is the maximum expansion factor
achieved by the linear transformation
X' = X _R_
where _R_ is a real-valued 2x2 matrix with entries:
_R_ = [a b]
[c d] .
In other words, what is the maximum radius, MAX[ |X'| ], reached for any
In other words, what is the maximum radius, MAX[ |X'| ], reached for any
X on the unit circle ( |X| = 1 ) ?
3. Some useful formulae
(A) through (C) below are standard double-angle formulae. (D) is a lesser
known result and is derived below:
(A) sin²(θ) = (1 - cos(2*θ))/2
(B) cos²(θ) = (1 + cos(2*θ))/2
(C) sin(θ)*cos(θ) = sin(2*θ)/2
(D) MAX[a*cos(θ) + b*sin(θ)] = sqrt(a² + b²)
Proof of (D):
find the maximum of the function by setting the derivative to zero:
-a*sin(θ)+b*cos(θ) = 0
From this it follows that
tan(θ) = b/a
and hence
From this it follows that
tan(θ) = b/a
and hence
sin(θ) = b/sqrt(a² + b²)
and
and
cos(θ) = a/sqrt(a² + b²)
Thus the maximum value is
MAX[a*cos(θ) + b*sin(θ)] = (a² + b²)/sqrt(a² + b²)
= sqrt(a² + b²)
4. Derivation of maximum expansion
To find MAX[ |X'| ] we search brute force method using calculus. The unit
circle on which X is constrained is to be parameterized by t:
X(θ) = (cos(θ), sin(θ))
Thus
Thus
X'(θ) = X(θ) * _R_ = (cos(θ), sin(θ)) * [a b]
[c d]
= (a*cos(θ) + c*sin(θ), b*cos(θ) + d*sin(θ)).
Define
Define
r(θ) = |X'(θ)|
Thus
r²(θ) = (a*cos(θ) + c*sin(θ))² + (b*cos(θ) + d*sin(θ))²
= (a² + b²)*cos²(θ) + (c² + d²)*sin²(θ)
+ 2*(a*c + b*d)*cos(θ)*sin(θ)
= (a² + b²)*cos²(θ) + (c² + d²)*sin²(θ)
+ 2*(a*c + b*d)*cos(θ)*sin(θ)
Now apply the double angle formulae (A) to (C) from above:
r²(θ) = (a² + b² + c² + d²)/2
r²(θ) = (a² + b² + c² + d²)/2
+ (a² + b² - c² - d²)*cos(2*θ)/2
+ (a*c + b*d)*sin(2*θ)
= f + g*cos(φ) + h*sin(φ)
Where
f = (a² + b² + c² + d²)/2
g = (a² + b² - c² - d²)/2
h = (a*c + d*d)
φ = 2*θ
It is clear that MAX[ |X'| ] = sqrt(MAX[ r² ]). Here we determine MAX[ r² ]
using (D) from above:
MAX[ r² ] = f + sqrt(g² + h²)
And finally
MAX[ |X'| ] = sqrt( f + sqrt(g² + h²) )
Which is the solution to this problem.
Walter Brisken
2004/10/08

Просмотреть файл

@ -59,6 +59,15 @@
static const cairo_surface_backend_t cairo_meta_surface_backend;
/* Currently all meta surfaces do have a size which should be passed
* in as the maximum size of any target surface against which the
* meta-surface will ever be replayed.
*
* XXX: The naming of "pixels" in the size here is a misnomer. It's
* actually a size in whatever device-space units are desired (again,
* according to the intended replay target). This should likely also
* be changed to use doubles not ints.
*/
cairo_surface_t *
_cairo_meta_surface_create (cairo_content_t content,
int width_pixels,
@ -128,7 +137,7 @@ _cairo_meta_surface_finish (void *abstract_surface)
_cairo_pattern_fini (&command->mask.mask.base);
free (command);
break;
case CAIRO_COMMAND_STROKE:
_cairo_pattern_fini (&command->stroke.source.base);
_cairo_path_fixed_fini (&command->stroke.path);
@ -231,9 +240,9 @@ _cairo_meta_surface_paint (void *abstract_surface,
cairo_command_paint_t *command;
/* An optimisation that takes care to not replay what was done
* before surface is cleared. We don't erase recorded commands
* before surface is cleared. We don't erase recorded commands
* since we may have earlier snapshots of this surface. */
if (op == CAIRO_OPERATOR_CLEAR && !meta->is_clipped)
if (op == CAIRO_OPERATOR_CLEAR && !meta->is_clipped)
meta->replay_start_idx = meta->commands.num_elements;
command = malloc (sizeof (cairo_command_paint_t));
@ -246,7 +255,7 @@ _cairo_meta_surface_paint (void *abstract_surface,
status = _init_pattern_with_snapshot (&command->source.base, source);
if (status)
goto CLEANUP_COMMAND;
status = _cairo_array_append (&meta->commands, &command);
if (status)
goto CLEANUP_SOURCE;
@ -284,7 +293,7 @@ _cairo_meta_surface_mask (void *abstract_surface,
status = _init_pattern_with_snapshot (&command->mask.base, mask);
if (status)
goto CLEANUP_SOURCE;
status = _cairo_array_append (&meta->commands, &command);
if (status)
goto CLEANUP_MASK;
@ -314,7 +323,7 @@ _cairo_meta_surface_stroke (void *abstract_surface,
cairo_status_t status;
cairo_meta_surface_t *meta = abstract_surface;
cairo_command_stroke_t *command;
command = malloc (sizeof (cairo_command_stroke_t));
if (command == NULL)
return CAIRO_STATUS_NO_MEMORY;
@ -537,22 +546,20 @@ _cairo_meta_surface_intersect_clip_path (void *dst,
return CAIRO_STATUS_SUCCESS;
}
/* A meta-surface is logically unbounded, but when it is used as a
* source, the drawing code can optimize based on the extents of the
* surface.
*
* XXX: The optimization being attempted here would only actually work
* if the meta-surface kept track of its extents as commands were
* added to it.
/* Currently, we're using as the "size" of a meta surface the largest
* surface size against which the meta-surface is expected to be
* replayed, (as passed in to _cairo_meta_surface_create).
*/
static cairo_int_status_t
_cairo_meta_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_meta_surface_t *surface = abstract_surface;
rectangle->x = 0;
rectangle->y = 0;
rectangle->width = CAIRO_MAXSHORT;
rectangle->height = CAIRO_MAXSHORT;
rectangle->width = surface->width_pixels;
rectangle->height = surface->height_pixels;
return CAIRO_STATUS_SUCCESS;
}
@ -560,9 +567,9 @@ _cairo_meta_surface_get_extents (void *abstract_surface,
/**
* _cairo_surface_is_meta:
* @surface: a #cairo_surface_t
*
*
* Checks if a surface is a #cairo_meta_surface_t
*
*
* Return value: TRUE if the surface is a meta surface
**/
cairo_bool_t
@ -598,7 +605,7 @@ static const cairo_surface_backend_t cairo_meta_surface_backend = {
/* Here are the 5 basic drawing operations, (which are in some
* sense the only things that cairo_meta_surface should need to
* implement). */
_cairo_meta_surface_paint,
_cairo_meta_surface_mask,
_cairo_meta_surface_stroke,
@ -621,7 +628,7 @@ _cairo_meta_surface_replay (cairo_surface_t *surface,
meta = (cairo_meta_surface_t *) surface;
status = CAIRO_STATUS_SUCCESS;
_cairo_clip_init (&clip, target);
_cairo_clip_init (&clip, target);
num_elements = meta->commands.num_elements;
elements = _cairo_array_index (&meta->commands, 0);

Просмотреть файл

@ -1,119 +0,0 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2006 Keith Packard
* Copyright © 2006 Red Hat, Inc
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is University of Southern
* California.
*
* Contributor(s):
* Carl D. Worth <cworth@cworth.org>
* Keith Packard <keithp@keithp.com>
*/
#include "cairoint.h"
/* The analysis here assumes destination alpha semantics (that is
* CAIRO_CONTENT_COLOR_ALPHA). More things can be considered opaque
* otherwise (CAIRO_CONTENT_COLOR) so we'll probably want to add a
* cairo_content_t parameter to this function
*
* We also need a definition of what "opaque" means. Is it, "does not
* requiring 'knowing' the original contents of destination, nor does
* it set the destination alpha to anything but 1.0" ?
*/
cairo_bool_t
_cairo_operator_always_opaque (cairo_operator_t op)
{
switch (op) {
case CAIRO_OPERATOR_CLEAR:
return FALSE;
case CAIRO_OPERATOR_SOURCE:
return FALSE;
case CAIRO_OPERATOR_OVER:
case CAIRO_OPERATOR_IN:
case CAIRO_OPERATOR_OUT:
case CAIRO_OPERATOR_ATOP:
return FALSE;
case CAIRO_OPERATOR_DEST:
return TRUE;
case CAIRO_OPERATOR_DEST_OVER:
case CAIRO_OPERATOR_DEST_IN:
case CAIRO_OPERATOR_DEST_OUT:
case CAIRO_OPERATOR_DEST_ATOP:
return FALSE;
case CAIRO_OPERATOR_XOR:
case CAIRO_OPERATOR_ADD:
case CAIRO_OPERATOR_SATURATE:
return FALSE;
}
return FALSE;
}
/* As above, we'll probably want to add a cairo_content_t parameter to
* this function
*
* We also need a definition of what "translucent" means.
*/
cairo_bool_t
_cairo_operator_always_translucent (cairo_operator_t op)
{
switch (op) {
case CAIRO_OPERATOR_CLEAR:
return TRUE;
case CAIRO_OPERATOR_SOURCE:
return FALSE;
case CAIRO_OPERATOR_OVER:
case CAIRO_OPERATOR_IN:
case CAIRO_OPERATOR_OUT:
case CAIRO_OPERATOR_ATOP:
return FALSE;
case CAIRO_OPERATOR_DEST:
return FALSE;
case CAIRO_OPERATOR_DEST_OVER:
case CAIRO_OPERATOR_DEST_IN:
case CAIRO_OPERATOR_DEST_OUT:
case CAIRO_OPERATOR_DEST_ATOP:
return FALSE;
case CAIRO_OPERATOR_XOR:
case CAIRO_OPERATOR_ADD:
case CAIRO_OPERATOR_SATURATE:
return TRUE;
}
return TRUE;
}

Просмотреть файл

@ -1,5 +1,5 @@
/* cairo_output_stream.c: Output stream abstraction
*
/* cairo-output-stream.c: Output stream abstraction
*
* Copyright © 2005 Red Hat, Inc
*
* This library is free software; you can redistribute it and/or
@ -38,24 +38,35 @@
#include <locale.h>
#include <ctype.h>
#include "cairoint.h"
#include "cairo-output-stream-private.h"
#ifdef _MSC_VER
#define snprintf _snprintf
#endif /* _MSC_VER */
struct _cairo_output_stream {
cairo_write_func_t write_func;
cairo_close_func_t close_func;
void *closure;
unsigned long position;
cairo_status_t status;
cairo_bool_t closed;
};
cairo_private void
_cairo_output_stream_init (cairo_output_stream_t *stream,
cairo_output_stream_write_func_t write_func,
cairo_output_stream_close_func_t close_func)
{
stream->write_func = write_func;
stream->close_func = close_func;
stream->position = 0;
stream->status = CAIRO_STATUS_SUCCESS;
stream->closed = FALSE;
}
cairo_private void
_cairo_output_stream_fini (cairo_output_stream_t *stream)
{
_cairo_output_stream_close (stream);
}
const cairo_output_stream_t cairo_output_stream_nil = {
NULL, /* write_func */
NULL, /* close_func */
NULL, /* closure */
0, /* position */
CAIRO_STATUS_NO_MEMORY,
FALSE /* closed */
@ -64,31 +75,59 @@ const cairo_output_stream_t cairo_output_stream_nil = {
static const cairo_output_stream_t cairo_output_stream_nil_write_error = {
NULL, /* write_func */
NULL, /* close_func */
NULL, /* closure */
0, /* position */
CAIRO_STATUS_WRITE_ERROR,
FALSE /* closed */
};
typedef struct _cairo_output_stream_with_closure {
cairo_output_stream_t base;
cairo_write_func_t write_func;
cairo_close_func_t close_func;
void *closure;
} cairo_output_stream_with_closure_t;
static cairo_status_t
closure_write (cairo_output_stream_t *stream,
const unsigned char *data, unsigned int length)
{
cairo_output_stream_with_closure_t *stream_with_closure =
(cairo_output_stream_with_closure_t *) stream;
return stream_with_closure->write_func (stream_with_closure->closure,
data, length);
}
static cairo_status_t
closure_close (cairo_output_stream_t *stream)
{
cairo_output_stream_with_closure_t *stream_with_closure =
(cairo_output_stream_with_closure_t *) stream;
if (stream_with_closure->close_func != NULL)
return stream_with_closure->close_func (stream_with_closure->closure);
else
return CAIRO_STATUS_SUCCESS;
}
cairo_output_stream_t *
_cairo_output_stream_create (cairo_write_func_t write_func,
cairo_close_func_t close_func,
void *closure)
{
cairo_output_stream_t *stream;
cairo_output_stream_with_closure_t *stream;
stream = malloc (sizeof (cairo_output_stream_t));
stream = malloc (sizeof (cairo_output_stream_with_closure_t));
if (stream == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil;
_cairo_output_stream_init (&stream->base, closure_write, closure_close);
stream->write_func = write_func;
stream->close_func = close_func;
stream->closure = closure;
stream->position = 0;
stream->status = CAIRO_STATUS_SUCCESS;
stream->closed = FALSE;
return stream;
return &stream->base;
}
void
@ -106,7 +145,7 @@ _cairo_output_stream_close (cairo_output_stream_t *stream)
}
if (stream->close_func) {
status = stream->close_func (stream->closure);
status = stream->close_func (stream);
if (status)
stream->status = status;
}
@ -120,7 +159,7 @@ _cairo_output_stream_destroy (cairo_output_stream_t *stream)
if (stream == NULL)
return;
_cairo_output_stream_close (stream);
_cairo_output_stream_fini (stream);
free (stream);
}
@ -134,7 +173,7 @@ _cairo_output_stream_write (cairo_output_stream_t *stream,
if (stream->status)
return;
stream->status = stream->write_func (stream->closure, data, length);
stream->status = stream->write_func (stream, data, length);
stream->position += length;
}
@ -180,20 +219,20 @@ _cairo_dtostr (char *buffer, size_t size, double d)
int decimal_len;
snprintf (buffer, size, "%f", d);
locale_data = localeconv ();
decimal_point = locale_data->decimal_point;
decimal_point_len = strlen (decimal_point);
assert (decimal_point_len != 0);
p = buffer;
if (*p == '+' || *p == '-')
p++;
while (isdigit (*p))
p++;
if (strncmp (p, decimal_point, decimal_point_len) == 0) {
*p = '.';
decimal_len = strlen (p + decimal_point_len);
@ -209,11 +248,10 @@ _cairo_dtostr (char *buffer, size_t size, double d)
p--;
}
}
return p + 1 - buffer;
}
enum {
LENGTH_MODIFIER_LONG = 0x100
};
@ -230,9 +268,9 @@ void
_cairo_output_stream_vprintf (cairo_output_stream_t *stream,
const char *fmt, va_list ap)
{
char buffer[512];
char *p;
const char *f;
char buffer[512], single_fmt[32];
char *p, *end;
const char *f, *start;
int length_modifier;
if (stream->status)
@ -251,10 +289,16 @@ _cairo_output_stream_vprintf (cairo_output_stream_t *stream,
continue;
}
start = f;
f++;
_cairo_output_stream_write (stream, buffer, p - buffer);
p = buffer;
if (*f == '0')
f++;
if (isdigit (*f)) {
strtol (f, &end, 10);
f = end;
}
length_modifier = 0;
if (*f == 'l') {
@ -262,28 +306,40 @@ _cairo_output_stream_vprintf (cairo_output_stream_t *stream,
f++;
}
/* Reuse the format string for this conversion. */
memcpy (single_fmt, start, f + 1 - start);
single_fmt[f + 1 - start] = '\0';
/* Flush contents of buffer before snprintf()'ing into it. */
_cairo_output_stream_write (stream, buffer, p - buffer);
p = buffer;
/* We group signed and unsigned together in this switch, the
* only thing that matters here is the size of the arguments,
* since we're just passing the data through to sprintf(). */
switch (*f | length_modifier) {
case '%':
buffer[0] = *f;
buffer[1] = 0;
break;
case 'd':
snprintf (buffer, sizeof buffer, "%d", va_arg (ap, int));
case 'u':
case 'o':
case 'x':
case 'X':
snprintf (buffer, sizeof buffer, single_fmt, va_arg (ap, int));
break;
case 'd' | LENGTH_MODIFIER_LONG:
snprintf (buffer, sizeof buffer, "%ld", va_arg (ap, long int));
break;
case 'u':
snprintf (buffer, sizeof buffer, "%u", va_arg (ap, unsigned int));
break;
case 'u' | LENGTH_MODIFIER_LONG:
snprintf (buffer, sizeof buffer, "%lu", va_arg (ap, long unsigned int));
break;
case 'o':
snprintf (buffer, sizeof buffer, "%o", va_arg (ap, int));
case 'o' | LENGTH_MODIFIER_LONG:
case 'x' | LENGTH_MODIFIER_LONG:
case 'X' | LENGTH_MODIFIER_LONG:
snprintf (buffer, sizeof buffer,
single_fmt, va_arg (ap, long int));
break;
case 's':
snprintf (buffer, sizeof buffer, "%s", va_arg (ap, const char *));
snprintf (buffer, sizeof buffer,
single_fmt, va_arg (ap, const char *));
break;
case 'f':
_cairo_dtostr (buffer, sizeof buffer, va_arg (ap, double));
@ -298,7 +354,7 @@ _cairo_output_stream_vprintf (cairo_output_stream_t *stream,
p = buffer + strlen (buffer);
f++;
}
_cairo_output_stream_write (stream, buffer, p - buffer);
}
@ -327,43 +383,49 @@ _cairo_output_stream_get_status (cairo_output_stream_t *stream)
return stream->status;
}
/* Maybe this should be a configure time option, so embedded targets
* don't have to pull in stdio. */
static cairo_status_t
stdio_write (void *closure, const unsigned char *data, unsigned int length)
{
FILE *file = closure;
if (fwrite (data, 1, length, file) != length)
typedef struct _stdio_stream {
cairo_output_stream_t base;
FILE *file;
} stdio_stream_t;
static cairo_status_t
stdio_write (cairo_output_stream_t *base,
const unsigned char *data, unsigned int length)
{
stdio_stream_t *stream = (stdio_stream_t *) base;
if (fwrite (data, 1, length, stream->file) != length)
return CAIRO_STATUS_WRITE_ERROR;
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
stdio_flush (void *closure)
stdio_flush (cairo_output_stream_t *base)
{
FILE *file = closure;
stdio_stream_t *stream = (stdio_stream_t *) base;
fflush (file);
fflush (stream->file);
if (ferror (file))
if (ferror (stream->file))
return CAIRO_STATUS_WRITE_ERROR;
else
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
stdio_close (void *closure)
stdio_close (cairo_output_stream_t *base)
{
cairo_status_t status;
FILE *file = closure;
stdio_stream_t *stream = (stdio_stream_t *) base;
status = stdio_flush (closure);
status = stdio_flush (base);
fclose (file);
fclose (stream->file);
return status;
}
@ -371,20 +433,96 @@ stdio_close (void *closure)
cairo_output_stream_t *
_cairo_output_stream_create_for_file (FILE *file)
{
stdio_stream_t *stream;
if (file == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil_write_error;
return _cairo_output_stream_create (stdio_write, stdio_flush, file);
stream = malloc (sizeof *stream);
if (stream == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil;
_cairo_output_stream_init (&stream->base, stdio_write, stdio_flush);
stream->file = file;
return &stream->base;
}
cairo_output_stream_t *
_cairo_output_stream_create_for_filename (const char *filename)
{
stdio_stream_t *stream;
FILE *file;
file = fopen (filename, "wb");
if (file == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil_write_error;
return _cairo_output_stream_create (stdio_write, stdio_close, file);
stream = malloc (sizeof *stream);
if (stream == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil;
_cairo_output_stream_init (&stream->base, stdio_write, stdio_close);
stream->file = file;
return &stream->base;
}
typedef struct _memory_stream {
cairo_output_stream_t base;
cairo_array_t array;
} memory_stream_t;
static cairo_status_t
memory_write (cairo_output_stream_t *base,
const unsigned char *data, unsigned int length)
{
memory_stream_t *stream = (memory_stream_t *) base;
return _cairo_array_append_multiple (&stream->array, data, length);
}
static cairo_status_t
memory_close (cairo_output_stream_t *base)
{
memory_stream_t *stream = (memory_stream_t *) base;
_cairo_array_fini (&stream->array);
return CAIRO_STATUS_SUCCESS;
}
cairo_output_stream_t *
_cairo_memory_stream_create (void)
{
memory_stream_t *stream;
stream = malloc (sizeof *stream);
if (stream == NULL)
return (cairo_output_stream_t *) &cairo_output_stream_nil;
_cairo_output_stream_init (&stream->base, memory_write, memory_close);
_cairo_array_init (&stream->array, 1);
return &stream->base;
}
void
_cairo_memory_stream_copy (cairo_output_stream_t *base,
cairo_output_stream_t *dest)
{
memory_stream_t *stream = (memory_stream_t *) base;
_cairo_output_stream_write (dest,
_cairo_array_index (&stream->array, 0),
_cairo_array_num_elements (&stream->array));
}
int
_cairo_memory_stream_length (cairo_output_stream_t *base)
{
memory_stream_t *stream = (memory_stream_t *) base;
return _cairo_array_num_elements (&stream->array);
}

Просмотреть файл

@ -159,7 +159,7 @@ _cairo_paginated_surface_finish (void *abstract_surface)
cairo_surface_destroy (surface->meta);
cairo_surface_destroy (surface->target);
return CAIRO_STATUS_SUCCESS;
}
@ -170,14 +170,14 @@ _cairo_paginated_surface_acquire_source_image (void *abstract_surface,
{
cairo_paginated_surface_t *surface = abstract_surface;
cairo_surface_t *image;
cairo_rectangle_fixed_t extents;
cairo_rectangle_int16_t extents;
_cairo_surface_get_extents (surface->target, &extents);
image = _cairo_image_surface_create_with_content (surface->content,
extents.width,
extents.height);
_cairo_meta_surface_replay (surface->meta, image);
*image_out = (cairo_image_surface_t*) image;
@ -214,16 +214,23 @@ _paint_page (cairo_paginated_surface_t *surface)
cairo_surface_destroy (analysis);
return status;
}
if (_cairo_analysis_surface_has_unsupported (analysis))
{
double x_scale = surface->base.x_fallback_resolution / 72.0;
double y_scale = surface->base.y_fallback_resolution / 72.0;
cairo_matrix_t matrix;
image = _cairo_image_surface_create_with_content (surface->content,
surface->width,
surface->height);
surface->width * x_scale,
surface->height * y_scale);
_cairo_surface_set_device_scale (image, x_scale, y_scale);
_cairo_meta_surface_replay (surface->meta, image);
pattern = cairo_pattern_create_for_surface (image);
cairo_matrix_init_scale (&matrix, x_scale, y_scale);
cairo_pattern_set_matrix (pattern, &matrix);
_cairo_surface_paint (surface->target, CAIRO_OPERATOR_SOURCE, pattern);
@ -237,7 +244,7 @@ _paint_page (cairo_paginated_surface_t *surface)
}
cairo_surface_destroy (analysis);
return CAIRO_STATUS_SUCCESS;
}
@ -317,7 +324,7 @@ _cairo_paginated_surface_intersect_clip_path (void *abstract_surface,
static cairo_int_status_t
_cairo_paginated_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_paginated_surface_t *surface = abstract_surface;
@ -448,7 +455,7 @@ _cairo_paginated_surface_snapshot (void *abstract_other)
#if 0
return _cairo_surface_snapshot (other->meta);
#else
cairo_rectangle_fixed_t extents;
cairo_rectangle_int16_t extents;
cairo_surface_t *surface;
_cairo_surface_get_extents (other->target, &extents);

Просмотреть файл

@ -87,13 +87,13 @@ _cairo_path_bounder_add_point (cairo_path_bounder_t *bounder, cairo_point_t *poi
if (bounder->has_point) {
if (point->x < bounder->min_x)
bounder->min_x = point->x;
if (point->y < bounder->min_y)
bounder->min_y = point->y;
if (point->x > bounder->max_x)
bounder->max_x = point->x;
if (point->y > bounder->max_y)
bounder->max_y = point->y;
} else {
@ -104,7 +104,7 @@ _cairo_path_bounder_add_point (cairo_path_bounder_t *bounder, cairo_point_t *poi
bounder->has_point = 1;
}
return CAIRO_STATUS_SUCCESS;
}

Просмотреть файл

@ -369,7 +369,7 @@ _cairo_path_data_create_real (cairo_path_fixed_t *path_fixed,
* cairo_path_destroy:
* @path: a path previously returned by either cairo_copy_path() or
* cairo_copy_path_flat().
*
*
* Immediately releases all memory associated with @path. After a call
* to cairo_path_destroy() the @path pointer is no longer valid and
* should not be used further.
@ -394,11 +394,11 @@ cairo_path_destroy (cairo_path_t *path)
* _cairo_path_data_create:
* @path: a fixed-point, device-space path to be converted and copied
* @gstate: the current graphics state
*
*
* Creates a user-space #cairo_path_t copy of the given device-space
* @path. The @gstate parameter provides the inverse CTM for the
* conversion.
*
*
* Return value: the new copy of the path. If there is insufficient
* memory a pointer to a special static cairo_path_nil will be
* returned instead with status==CAIRO_STATUS_NO_MEMORY and
@ -415,12 +415,12 @@ _cairo_path_data_create (cairo_path_fixed_t *path,
* _cairo_path_data_create_flat:
* @path: a fixed-point, device-space path to be flattened, converted and copied
* @gstate: the current graphics state
*
*
* Creates a flattened, user-space #cairo_path_t copy of the given
* device-space @path. The @gstate parameter provide the inverse CTM
* for the conversion, as well as the tolerance value to control the
* accuracy of the flattening.
*
*
* Return value: the flattened copy of the path. If there is insufficient
* memory a pointer to a special static cairo_path_nil will be
* returned instead with status==CAIRO_STATUS_NO_MEMORY and
@ -437,9 +437,9 @@ _cairo_path_data_create_flat (cairo_path_fixed_t *path,
* _cairo_path_data_append_to_context:
* @path: the path data to be appended
* @cr: a cairo context
*
*
* Append @path to the current path within @cr.
*
*
* Return value: CAIRO_STATUS_INVALID_PATH_DATA if the data in @path
* is invalid, and CAIRO_STATUS_SUCCESS otherwise.
**/

Просмотреть файл

@ -94,7 +94,7 @@ _cairo_filler_move_to (void *closure, cairo_point_t *point)
status = _cairo_polygon_close (polygon);
if (status)
return status;
status = _cairo_polygon_move_to (polygon, point);
if (status)
return status;
@ -205,4 +205,3 @@ BAIL:
return status;
}

Просмотреть файл

@ -50,6 +50,8 @@ typedef struct cairo_stroker {
cairo_point_t current_point;
cairo_point_t first_point;
cairo_bool_t has_sub_path;
cairo_bool_t has_current_face;
cairo_stroke_face_t current_face;
@ -161,9 +163,10 @@ _cairo_stroker_init (cairo_stroker_t *stroker,
_cairo_pen_init (&stroker->pen,
stroke_style->line_width / 2.0,
tolerance, ctm);
stroker->has_current_face = FALSE;
stroker->has_first_face = FALSE;
stroker->has_sub_path = FALSE;
if (stroker->style->dash)
_cairo_stroker_start_dash (stroker);
@ -205,7 +208,8 @@ _cairo_stroker_join (cairo_stroker_t *stroker, cairo_stroke_face_t *in, cairo_st
if (in->cw.x == out->cw.x
&& in->cw.y == out->cw.y
&& in->ccw.x == out->ccw.x
&& in->ccw.y == out->ccw.y) {
&& in->ccw.y == out->ccw.y)
{
return CAIRO_STATUS_SUCCESS;
}
@ -286,7 +290,7 @@ _cairo_stroker_join (cairo_stroker_t *stroker, cairo_stroke_face_t *in, cairo_st
* in · out = cos (psi)
*
* 2 <= ml² (1 - in · out)
*
*
*/
if (2 <= ml * ml * (1 - in_dot_out)) {
double x1, y1, x2, y2;
@ -295,7 +299,7 @@ _cairo_stroker_join (cairo_stroker_t *stroker, cairo_stroke_face_t *in, cairo_st
cairo_polygon_t polygon;
cairo_point_t outer;
/*
/*
* we've got the points already transformed to device
* space, but need to do some computation with them and
* also need to transform the slope from user space to
@ -307,14 +311,14 @@ _cairo_stroker_join (cairo_stroker_t *stroker, cairo_stroke_face_t *in, cairo_st
dx1 = in->usr_vector.x;
dy1 = in->usr_vector.y;
cairo_matrix_transform_distance (stroker->ctm, &dx1, &dy1);
/* outer point of outgoing line face */
x2 = _cairo_fixed_to_double (outpt->x);
y2 = _cairo_fixed_to_double (outpt->y);
dx2 = out->usr_vector.x;
dy2 = out->usr_vector.y;
cairo_matrix_transform_distance (stroker->ctm, &dx2, &dy2);
/*
* Compute the location of the outer corner of the miter.
* That's pretty easy -- just the intersection of the two
@ -329,7 +333,7 @@ _cairo_stroker_join (cairo_stroker_t *stroker, cairo_stroke_face_t *in, cairo_st
mx = (my - y1) * dx1 / dy1 + x1;
else
mx = (my - y2) * dx2 / dy2 + x2;
/*
* Draw the quadrilateral
*/
@ -368,7 +372,7 @@ _cairo_stroker_add_cap (cairo_stroker_t *stroker, cairo_stroke_face_t *f)
if (stroker->style->line_cap == CAIRO_LINE_CAP_BUTT)
return CAIRO_STATUS_SUCCESS;
switch (stroker->style->line_cap) {
case CAIRO_LINE_CAP_ROUND: {
int i;
@ -459,10 +463,26 @@ _cairo_stroker_add_trailing_cap (cairo_stroker_t *stroker,
return _cairo_stroker_add_cap (stroker, face);
}
static void
_compute_face (cairo_point_t *point, cairo_slope_t *slope, cairo_stroker_t *stroker, cairo_stroke_face_t *face);
static cairo_status_t
_cairo_stroker_add_caps (cairo_stroker_t *stroker)
{
cairo_status_t status;
/* check for a degenerative sub_path */
if (stroker->has_sub_path
&& !stroker->has_first_face
&& !stroker->has_current_face
&& stroker->style->line_cap == CAIRO_LINE_JOIN_ROUND)
{
/* pick an arbitrary slope to use */
cairo_slope_t slope = {1, 0};
_compute_face (&stroker->first_point, &slope, stroker, &stroker->first_face);
stroker->has_first_face = stroker->has_current_face = TRUE;
stroker->current_face = stroker->first_face;
}
if (stroker->has_first_face) {
status = _cairo_stroker_add_leading_cap (stroker, &stroker->first_face);
@ -507,7 +527,7 @@ _compute_face (cairo_point_t *point, cairo_slope_t *slope, cairo_stroker_t *stro
usr_vector.x = line_dx;
usr_vector.y = line_dy;
/*
/*
* rotate to get a line_width/2 vector along the face, note that
* the vector must be rotated the right direction in device space,
* but by 90° in user space. So, the rotation depends on
@ -563,12 +583,8 @@ _cairo_stroker_add_sub_edge (cairo_stroker_t *stroker, cairo_point_t *p1, cairo_
fields from start. */
_compute_face (p2, slope, stroker, end);
if (p1->x == p2->x && p1->y == p2->y) {
/* XXX: Need to rethink how this case should be handled, (both
here and in _compute_face). The key behavior is that
degenerate paths should draw as much as possible. */
if (p1->x == p2->x && p1->y == p2->y)
return CAIRO_STATUS_SUCCESS;
}
/* XXX: I should really check the return value of the
move_to/line_to functions here to catch out of memory
@ -609,8 +625,9 @@ _cairo_stroker_move_to (void *closure, cairo_point_t *point)
stroker->first_point = *point;
stroker->current_point = *point;
stroker->has_first_face = 0;
stroker->has_current_face = 0;
stroker->has_first_face = FALSE;
stroker->has_current_face = FALSE;
stroker->has_sub_path = FALSE;
return CAIRO_STATUS_SUCCESS;
}
@ -635,16 +652,13 @@ _cairo_stroker_line_to (void *closure, cairo_point_t *point)
cairo_point_t *p2 = point;
cairo_slope_t slope;
if (p1->x == p2->x && p1->y == p2->y) {
/* XXX: Need to rethink how this case should be handled, (both
here and in cairo_stroker_add_sub_edge and in _compute_face). The
key behavior is that degenerate paths should draw as much
as possible. */
stroker->has_sub_path = TRUE;
if (p1->x == p2->x && p1->y == p2->y)
return CAIRO_STATUS_SUCCESS;
}
_cairo_slope_init (&slope, p1, p2);
status = _cairo_stroker_add_sub_edge (stroker, p1, p2, &slope, &start, &end);
if (status)
return status;
@ -656,11 +670,11 @@ _cairo_stroker_line_to (void *closure, cairo_point_t *point)
} else {
if (!stroker->has_first_face) {
stroker->first_face = start;
stroker->has_first_face = 1;
stroker->has_first_face = TRUE;
}
}
stroker->current_face = end;
stroker->has_current_face = 1;
stroker->has_current_face = TRUE;
stroker->current_point = *point;
@ -679,19 +693,14 @@ _cairo_stroker_line_to_dashed (void *closure, cairo_point_t *point)
double dx, dy;
double dx2, dy2;
cairo_point_t fd1, fd2;
int first = 1;
cairo_bool_t first = TRUE;
cairo_stroke_face_t sub_start, sub_end;
cairo_point_t *p1 = &stroker->current_point;
cairo_point_t *p2 = point;
cairo_slope_t slope;
if (p1->x == p2->x && p1->y == p2->y) {
/* XXX: Need to rethink how this case should be handled, (both
here and in cairo_stroker_add_sub_edge and in _compute_face). The
key behavior is that degenerate paths should draw as much
as possible. */
if (p1->x == p2->x && p1->y == p2->y)
return CAIRO_STATUS_SUCCESS;
}
_cairo_slope_init (&slope, p1, p2);
@ -742,7 +751,7 @@ _cairo_stroker_line_to_dashed (void *closure, cairo_point_t *point)
} else {
if (!stroker->has_first_face) {
stroker->first_face = sub_start;
stroker->has_first_face = 1;
stroker->has_first_face = TRUE;
} else {
status = _cairo_stroker_add_leading_cap (stroker, &sub_start);
if (status)
@ -763,7 +772,7 @@ _cairo_stroker_line_to_dashed (void *closure, cairo_point_t *point)
* through
*/
stroker->current_face = sub_end;
stroker->has_current_face = 1;
stroker->has_current_face = TRUE;
}
} else {
/*
@ -778,11 +787,11 @@ _cairo_stroker_line_to_dashed (void *closure, cairo_point_t *point)
}
}
if (!remain)
stroker->has_current_face = 0;
stroker->has_current_face = FALSE;
}
_cairo_stroker_step_dash (stroker, tmp);
fd1 = fd2;
first = 0;
first = FALSE;
}
stroker->current_point = *point;
@ -822,12 +831,12 @@ _cairo_stroker_curve_to (void *closure,
} else {
if (!stroker->has_first_face) {
stroker->first_face = start;
stroker->has_first_face = 1;
stroker->has_first_face = TRUE;
}
}
stroker->current_face = end;
stroker->has_current_face = 1;
stroker->has_current_face = TRUE;
extra_points[0] = start.cw;
extra_points[0].x -= start.point.x;
extra_points[0].y -= start.point.y;
@ -840,7 +849,7 @@ _cairo_stroker_curve_to (void *closure,
extra_points[3] = end.ccw;
extra_points[3].x -= end.point.x;
extra_points[3].y -= end.point.y;
status = _cairo_pen_add_points (&pen, extra_points, 4);
if (status)
goto CLEANUP_PEN;
@ -943,10 +952,15 @@ _cairo_stroker_close_path (void *closure)
status = _cairo_stroker_join (stroker, &stroker->current_face, &stroker->first_face);
if (status)
return status;
} else {
status = _cairo_stroker_add_caps (stroker);
if (status)
return status;
}
stroker->has_first_face = 0;
stroker->has_current_face = 0;
stroker->has_sub_path = FALSE;
stroker->has_first_face = FALSE;
stroker->has_current_face = FALSE;
return CAIRO_STATUS_SUCCESS;
}

Просмотреть файл

@ -482,7 +482,7 @@ _cairo_path_arg_buf_add_points (cairo_path_arg_buf_t *arg_buf,
#define CAIRO_PATH_OP_MAX_ARGS 3
static int const num_args[] =
static int const num_args[] =
{
1, /* cairo_path_move_to */
1, /* cairo_path_op_line_to */
@ -604,13 +604,29 @@ _cairo_path_fixed_offset_and_scale (cairo_path_fixed_t *path,
}
}
void
_cairo_path_fixed_offset (cairo_path_fixed_t *path,
cairo_fixed_t offx,
cairo_fixed_t offy)
{
_cairo_path_fixed_offset_and_scale (path, offx, offy,
CAIRO_FIXED_ONE,
CAIRO_FIXED_ONE);
}
/**
* _cairo_path_fixed_device_transform:
* @path: a #cairo_path_fixed_t to be transformed
* @device_transform: a matrix with only scaling/translation (no rotation or shear)
*
* Transform the fixed-point path according to the scaling and
* translation of the given matrix. This function assert()s that the
* given matrix has no rotation or shear elements, (that is, xy and yx
* are 0.0).
**/
void
_cairo_path_fixed_device_transform (cairo_path_fixed_t *path,
cairo_matrix_t *device_transform)
{
assert (device_transform->yx == 0.0 && device_transform->xy == 0.0);
/* XXX: FRAGILE: I'm not really sure whether we're doing the
* "right" thing here if there is both scaling and translation in
* the matrix. But for now, the internals guarantee that we won't
* really ever have both going on. */
_cairo_path_fixed_offset_and_scale (path,
_cairo_fixed_from_double (device_transform->x0),
_cairo_fixed_from_double (device_transform->y0),
_cairo_fixed_from_double (device_transform->xx),
_cairo_fixed_from_double (device_transform->yy));
}

Просмотреть файл

@ -86,7 +86,7 @@ _cairo_pattern_nil_for_status (cairo_status_t status)
* @pattern: a pattern
* @status: a status value indicating an error, (eg. not
* CAIRO_STATUS_SUCCESS)
*
*
* Sets pattern->status to @status and calls _cairo_error;
*
* All assignments of an error status to pattern->status should happen
@ -113,7 +113,7 @@ _cairo_pattern_set_error (cairo_pattern_t *pattern,
static void
_cairo_pattern_init (cairo_pattern_t *pattern, cairo_pattern_type_t type)
{
pattern->type = type;
pattern->type = type;
pattern->ref_count = 1;
pattern->status = CAIRO_STATUS_SUCCESS;
@ -135,14 +135,14 @@ _cairo_gradient_pattern_init_copy (cairo_gradient_pattern_t *pattern,
{
cairo_linear_pattern_t *dst = (cairo_linear_pattern_t *) pattern;
cairo_linear_pattern_t *src = (cairo_linear_pattern_t *) other;
*dst = *src;
}
else
{
cairo_radial_pattern_t *dst = (cairo_radial_pattern_t *) pattern;
cairo_radial_pattern_t *src = (cairo_radial_pattern_t *) other;
*dst = *src;
}
@ -154,7 +154,7 @@ _cairo_gradient_pattern_init_copy (cairo_gradient_pattern_t *pattern,
_cairo_pattern_set_error (&pattern->base, CAIRO_STATUS_NO_MEMORY);
return;
}
memcpy (pattern->stops, other->stops,
other->n_stops * sizeof (pixman_gradient_stop_t));
}
@ -179,7 +179,7 @@ _cairo_pattern_init_copy (cairo_pattern_t *pattern,
case CAIRO_PATTERN_TYPE_SURFACE: {
cairo_surface_pattern_t *dst = (cairo_surface_pattern_t *) pattern;
cairo_surface_pattern_t *src = (cairo_surface_pattern_t *) other;
*dst = *src;
cairo_surface_reference (dst->surface);
} break;
@ -187,11 +187,11 @@ _cairo_pattern_init_copy (cairo_pattern_t *pattern,
case CAIRO_PATTERN_TYPE_RADIAL: {
cairo_gradient_pattern_t *dst = (cairo_gradient_pattern_t *) pattern;
cairo_gradient_pattern_t *src = (cairo_gradient_pattern_t *) other;
_cairo_gradient_pattern_init_copy (dst, src);
} break;
}
pattern->ref_count = 1;
}
@ -204,14 +204,14 @@ _cairo_pattern_fini (cairo_pattern_t *pattern)
case CAIRO_PATTERN_TYPE_SURFACE: {
cairo_surface_pattern_t *surface_pattern =
(cairo_surface_pattern_t *) pattern;
cairo_surface_destroy (surface_pattern->surface);
} break;
case CAIRO_PATTERN_TYPE_LINEAR:
case CAIRO_PATTERN_TYPE_RADIAL: {
cairo_gradient_pattern_t *gradient =
(cairo_gradient_pattern_t *) pattern;
if (gradient->stops)
free (gradient->stops);
} break;
@ -238,7 +238,7 @@ _cairo_pattern_init_for_surface (cairo_surface_pattern_t *pattern,
}
_cairo_pattern_init (&pattern->base, CAIRO_PATTERN_TYPE_SURFACE);
pattern->surface = cairo_surface_reference (surface);
}
@ -298,12 +298,12 @@ _cairo_pattern_create_solid (const cairo_color_t *color)
* @red: red component of the color
* @green: green component of the color
* @blue: blue component of the color
*
*
* Creates a new cairo_pattern_t corresponding to an opaque color. The
* color components are floating point numbers in the range 0 to 1.
* If the values passed in are outside that range, they will be
* clamped.
*
*
* Return value: the newly created #cairo_pattern_t if succesful, or
* an error pattern in case of no memory. The caller owns the
* returned object and should call cairo_pattern_destroy() when
@ -338,12 +338,12 @@ cairo_pattern_create_rgb (double red, double green, double blue)
* @green: green component of the color
* @blue: blue component of the color
* @alpha: alpha component of the color
*
*
* Creates a new cairo_pattern_t corresponding to a translucent color.
* The color components are floating point numbers in the range 0 to
* 1. If the values passed in are outside that range, they will be
* clamped.
*
*
* Return value: the newly created #cairo_pattern_t if succesful, or
* an error pattern in case of no memory. The caller owns the
* returned object and should call cairo_pattern_destroy() when
@ -376,10 +376,10 @@ cairo_pattern_create_rgba (double red, double green, double blue,
/**
* cairo_pattern_create_for_surface:
* @surface: the surface
*
* @surface: the surface
*
* Create a new cairo_pattern_t for the given surface.
*
*
* Return value: the newly created #cairo_pattern_t if succesful, or
* an error pattern in case of no memory. The caller owns the
* returned object and should call cairo_pattern_destroy() when
@ -413,11 +413,11 @@ cairo_pattern_create_for_surface (cairo_surface_t *surface)
/**
* cairo_pattern_create_linear:
* @x0: x coordinate of the start point
* @y0: y coordinate of the start point
* @x1: x coordinate of the end point
* @y1: y coordinate of the end point
*
* @x0: x coordinate of the start point
* @y0: y coordinate of the start point
* @x1: x coordinate of the end point
* @y1: y coordinate of the end point
*
* Create a new linear gradient cairo_pattern_t along the line defined
* by (x0, y0) and (x1, y1). Before using the gradient pattern, a
* number of color stops should be defined using
@ -427,7 +427,7 @@ cairo_pattern_create_for_surface (cairo_surface_t *surface)
* Note: The coordinates here are in pattern space. For a new pattern,
* pattern space is identical to user space, but the relationship
* between the spaces can be changed with cairo_pattern_set_matrix().
*
*
* Return value: the newly created #cairo_pattern_t if succesful, or
* an error pattern in case of no memory. The caller owns the
* returned object and should call cairo_pattern_destroy() when
@ -461,7 +461,7 @@ cairo_pattern_create_linear (double x0, double y0, double x1, double y1)
* @cx1: x coordinate for the center of the end circle
* @cy1: y coordinate for the center of the end circle
* @radius1: radius of the end cirle
*
*
* Creates a new radial gradient cairo_pattern_t between the two
* circles defined by (x0, y0, c0) and (x1, y1, c0). Before using the
* gradient pattern, a number of color stops should be defined using
@ -471,7 +471,7 @@ cairo_pattern_create_linear (double x0, double y0, double x1, double y1)
* Note: The coordinates here are in pattern space. For a new pattern,
* pattern space is identical to user space, but the relationship
* between the spaces can be changed with cairo_pattern_set_matrix().
*
*
* Return value: the newly created #cairo_pattern_t if succesful, or
* an error pattern in case of no memory. The caller owns the
* returned object and should call cairo_pattern_destroy() when
@ -486,7 +486,7 @@ cairo_pattern_create_radial (double cx0, double cy0, double radius0,
double cx1, double cy1, double radius1)
{
cairo_radial_pattern_t *pattern;
pattern = malloc (sizeof (cairo_radial_pattern_t));
if (pattern == NULL) {
_cairo_error (CAIRO_STATUS_NO_MEMORY);
@ -501,7 +501,7 @@ cairo_pattern_create_radial (double cx0, double cy0, double radius0,
/**
* cairo_pattern_reference:
* @pattern: a #cairo_pattern_t
*
*
* Increases the reference count on @pattern by one. This prevents
* @pattern from being destroyed until a matching call to
* cairo_pattern_destroy() is made.
@ -527,8 +527,10 @@ cairo_pattern_reference (cairo_pattern_t *pattern)
/**
* cairo_pattern_get_type:
* @pattern: a #cairo_pattern_t
*
*
* Return value: The type of @pattern. See #cairo_pattern_type_t.
*
* Since: 1.2
**/
cairo_pattern_type_t
cairo_pattern_get_type (cairo_pattern_t *pattern)
@ -539,10 +541,10 @@ cairo_pattern_get_type (cairo_pattern_t *pattern)
/**
* cairo_pattern_status:
* @pattern: a #cairo_pattern_t
*
*
* Checks whether an error has previously occurred for this
* pattern.
*
*
* Return value: %CAIRO_STATUS_SUCCESS, %CAIRO_STATUS_NO_MEMORY, or
* %CAIRO_STATUS_PATTERN_TYPE_MISMATCH.
**/
@ -555,7 +557,7 @@ cairo_pattern_status (cairo_pattern_t *pattern)
/**
* cairo_pattern_destroy:
* @pattern: a #cairo_pattern_t
*
*
* Decreases the reference count on @pattern by one. If the result is
* zero, then @pattern and all associated resources are freed. See
* cairo_pattern_reference().
@ -630,7 +632,7 @@ _cairo_pattern_add_color_stop (cairo_gradient_pattern_t *pattern,
* @red: red component of color
* @green: green component of color
* @blue: blue component of color
*
*
* Adds an opaque color stop to a gradient pattern. The offset
* specifies the location along the gradient's control vector. For
* example, a linear gradient's control vector is from (x0,y0) to
@ -677,7 +679,7 @@ cairo_pattern_add_color_stop_rgb (cairo_pattern_t *pattern,
* @green: green component of color
* @blue: blue component of color
* @alpha: alpha component of color
*
*
* Adds a translucent color stop to a gradient pattern. The offset
* specifies the location along the gradient's control vector. For
* example, a linear gradient's control vector is from (x0,y0) to
@ -722,7 +724,7 @@ cairo_pattern_add_color_stop_rgba (cairo_pattern_t *pattern,
* cairo_pattern_set_matrix:
* @pattern: a #cairo_pattern_t
* @matrix: a #cairo_matrix_t
*
*
* Sets the pattern's transformation matrix to @matrix. This matrix is
* a transformation from user space to pattern space.
*
@ -764,7 +766,7 @@ cairo_pattern_set_matrix (cairo_pattern_t *pattern,
* cairo_pattern_get_matrix:
* @pattern: a #cairo_pattern_t
* @matrix: return value for the matrix
*
*
* Stores the pattern's transformation matrix into @matrix.
**/
void
@ -813,7 +815,7 @@ cairo_pattern_set_extend (cairo_pattern_t *pattern, cairo_extend_t extend)
*
* Gets the current extend mode for a pattern. See #cairo_extend_t
* for details on the semantics of each extend strategy.
*
*
* Return value: the current extend strategy used for drawing the
* pattern.
**/
@ -874,7 +876,7 @@ _cairo_linear_pattern_classify (cairo_linear_pattern_t *pattern,
/* transform fragment into pattern space */
double qx = a * qx_device + c * qy_device + tx;
double qy = b * qx_device + d * qy_device + ty;
factors[i] = _cairo_fixed_from_double (((dx * qx + dy * qy) - start) * scale);
}
@ -1046,7 +1048,7 @@ _cairo_pattern_acquire_surface_for_solid (cairo_solid_pattern_t *pattern,
attribs->extend = CAIRO_EXTEND_REPEAT;
attribs->filter = CAIRO_FILTER_NEAREST;
attribs->acquired = FALSE;
return CAIRO_STATUS_SUCCESS;
}
@ -1061,7 +1063,7 @@ _cairo_pattern_acquire_surface_for_solid (cairo_solid_pattern_t *pattern,
*
* Return value: %TRUE if the pattern is an opaque, solid color.
**/
cairo_bool_t
cairo_bool_t
_cairo_pattern_is_opaque_solid (const cairo_pattern_t *pattern)
{
cairo_solid_pattern_t *solid;
@ -1078,7 +1080,7 @@ static cairo_bool_t
_gradient_is_opaque (const cairo_gradient_pattern_t *gradient)
{
int i;
for (i = 0; i < gradient->n_stops; i++)
if (! CAIRO_ALPHA_IS_OPAQUE (gradient->stops[i].color.alpha))
return FALSE;
@ -1105,11 +1107,11 @@ _cairo_pattern_is_opaque (const cairo_pattern_t *abstract_pattern)
case CAIRO_PATTERN_TYPE_SOLID:
return _cairo_pattern_is_opaque_solid (abstract_pattern);
case CAIRO_PATTERN_TYPE_SURFACE:
return _cairo_surface_is_opaque (pattern->surface.surface);
return cairo_surface_get_content (pattern->surface.surface) == CAIRO_CONTENT_COLOR;
case CAIRO_PATTERN_TYPE_LINEAR:
case CAIRO_PATTERN_TYPE_RADIAL:
return _gradient_is_opaque (&pattern->gradient.base);
}
}
ASSERT_NOT_REACHED;
return FALSE;
@ -1129,11 +1131,11 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern,
int tx, ty;
attr->acquired = FALSE;
if (_cairo_surface_is_image (dst))
{
cairo_image_surface_t *image;
status = _cairo_surface_acquire_source_image (pattern->surface,
&image,
&attr->extra);
@ -1147,7 +1149,7 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern,
{
status = _cairo_surface_clone_similar (dst, pattern->surface, out);
}
attr->extend = pattern->base.extend;
attr->filter = pattern->base.filter;
if (_cairo_matrix_is_integer_translation (&pattern->base.matrix,
@ -1163,7 +1165,7 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern,
attr->matrix = pattern->base.matrix;
attr->x_offset = attr->y_offset = 0;
}
return status;
}
@ -1178,10 +1180,10 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern,
* @surface_out: location to store a pointer to a surface
* @attributes: surface attributes that destination backend should apply to
* the returned surface
*
*
* A convenience function to obtain a surface to use as the source for
* drawing on @dst.
*
*
* Return value: %CAIRO_STATUS_SUCCESS if a surface was stored in @surface_out.
**/
cairo_int_status_t
@ -1195,7 +1197,7 @@ _cairo_pattern_acquire_surface (cairo_pattern_t *pattern,
cairo_surface_attributes_t *attributes)
{
cairo_status_t status;
if (pattern->status) {
*surface_out = NULL;
attributes->acquired = FALSE;
@ -1205,7 +1207,7 @@ _cairo_pattern_acquire_surface (cairo_pattern_t *pattern,
switch (pattern->type) {
case CAIRO_PATTERN_TYPE_SOLID: {
cairo_solid_pattern_t *src = (cairo_solid_pattern_t *) pattern;
status = _cairo_pattern_acquire_surface_for_solid (src, dst,
x, y, width, height,
surface_out,
@ -1257,7 +1259,7 @@ _cairo_pattern_acquire_surface (cairo_pattern_t *pattern,
} break;
case CAIRO_PATTERN_TYPE_SURFACE: {
cairo_surface_pattern_t *src = (cairo_surface_pattern_t *) pattern;
status = _cairo_pattern_acquire_surface_for_surface (src, dst,
x, y, width, height,
surface_out,
@ -1275,7 +1277,7 @@ _cairo_pattern_acquire_surface (cairo_pattern_t *pattern,
* @pattern: a #cairo_pattern_t
* @surface: a surface obtained by _cairo_pattern_acquire_surface
* @attributes: attributes obtained by _cairo_pattern_acquire_surface
*
*
* Releases resources obtained by _cairo_pattern_acquire_surface.
**/
void
@ -1365,12 +1367,12 @@ _cairo_pattern_acquire_surfaces (cairo_pattern_t *src,
}
_cairo_pattern_init_copy (&mask_tmp.base, mask);
status = _cairo_pattern_acquire_surface (&mask_tmp.base, dst,
mask_x, mask_y,
width, height,
mask_out, mask_attributes);
if (status)
_cairo_pattern_release_surface (&src_tmp.base,
*src_out, src_attributes);
@ -1383,7 +1385,7 @@ _cairo_pattern_acquire_surfaces (cairo_pattern_t *src,
/**
* _cairo_pattern_get_extents:
*
*
* Return the "target-space" extents of @pattern in @extents.
*
* For unbounded patterns, the @extents will be initialized with
@ -1395,13 +1397,13 @@ _cairo_pattern_acquire_surfaces (cairo_pattern_t *src,
**/
cairo_status_t
_cairo_pattern_get_extents (cairo_pattern_t *pattern,
cairo_rectangle_fixed_t *extents)
cairo_rectangle_int16_t *extents)
{
if (pattern->extend == CAIRO_EXTEND_NONE &&
pattern->type == CAIRO_PATTERN_TYPE_SURFACE)
{
cairo_status_t status;
cairo_rectangle_fixed_t surface_extents;
cairo_rectangle_int16_t surface_extents;
cairo_surface_pattern_t *surface_pattern =
(cairo_surface_pattern_t *) pattern;
cairo_surface_t *surface = surface_pattern->surface;
@ -1426,9 +1428,9 @@ _cairo_pattern_get_extents (cairo_pattern_t *pattern,
y = surface_extents.y + sy * surface_extents.height;
cairo_matrix_transform_point (&imatrix, &x, &y);
if (x < 0) x = 0;
if (x > CAIRO_MAXSHORT) x = CAIRO_MAXSHORT;
if (x > INT16_MAX) x = INT16_MAX;
if (y < 0) y = 0;
if (y > CAIRO_MAXSHORT) y = CAIRO_MAXSHORT;
if (y > INT16_MAX) y = INT16_MAX;
lx = floor (x); rx = ceil (x);
ty = floor (y); by = ceil (y);
if (!set) {
@ -1457,8 +1459,8 @@ _cairo_pattern_get_extents (cairo_pattern_t *pattern,
extents->x = 0;
extents->y = 0;
extents->width = CAIRO_MAXSHORT;
extents->height = CAIRO_MAXSHORT;
extents->width = INT16_MAX;
extents->height = INT16_MAX;
return CAIRO_STATUS_SUCCESS;
}

Просмотреть файл

@ -43,6 +43,7 @@
#include "cairo-ft-private.h"
#include "cairo-paginated-surface-private.h"
#include "cairo-path-fixed-private.h"
#include "cairo-output-stream-private.h"
#include <time.h>
#include <zlib.h>
@ -110,8 +111,6 @@ typedef struct _cairo_pdf_surface {
double width;
double height;
double x_dpi;
double y_dpi;
cairo_array_t objects;
cairo_array_t pages;
@ -138,7 +137,6 @@ typedef struct _cairo_pdf_surface {
cairo_paginated_mode_t paginated_mode;
} cairo_pdf_surface_t;
#define PDF_SURFACE_DPI_DEFAULT 300
#define PDF_SURFACE_MAX_GLYPHS_PER_FONT 256
static cairo_pdf_resource_t
@ -269,8 +267,6 @@ _cairo_pdf_surface_create_for_stream_internal (cairo_output_stream_t *output,
surface->width = width;
surface->height = height;
surface->x_dpi = PDF_SURFACE_DPI_DEFAULT;
surface->y_dpi = PDF_SURFACE_DPI_DEFAULT;
_cairo_array_init (&surface->objects, sizeof (cairo_pdf_object_t));
_cairo_array_init (&surface->pages, sizeof (cairo_pdf_resource_t));
@ -309,13 +305,13 @@ _cairo_pdf_surface_create_for_stream_internal (cairo_output_stream_t *output,
/**
* cairo_pdf_surface_create_for_stream:
* @write: a #cairo_write_func_t to accept the output data
* @closure: the closure argument for @write
* @write_func: a #cairo_write_func_t to accept the output data
* @closure: the closure argument for @write_func
* @width_in_points: width of the surface, in points (1 point == 1/72.0 inch)
* @height_in_points: height of the surface, in points (1 point == 1/72.0 inch)
*
* Creates a PDF surface of the specified size in points to be written
* incrementally to the stream represented by @write and @closure.
* incrementally to the stream represented by @write_func and @closure.
*
* Return value: a pointer to the newly created surface. The caller
* owns the surface and should call cairo_surface_destroy when done
@ -324,9 +320,11 @@ _cairo_pdf_surface_create_for_stream_internal (cairo_output_stream_t *output,
* This function always returns a valid pointer, but it will return a
* pointer to a "nil" surface if an error such as out of memory
* occurs. You can use cairo_surface_status() to check for this.
*
* Since: 1.2
*/
cairo_surface_t *
cairo_pdf_surface_create_for_stream (cairo_write_func_t write,
cairo_pdf_surface_create_for_stream (cairo_write_func_t write_func,
void *closure,
double width_in_points,
double height_in_points)
@ -334,7 +332,7 @@ cairo_pdf_surface_create_for_stream (cairo_write_func_t write,
cairo_status_t status;
cairo_output_stream_t *output;
output = _cairo_output_stream_create (write, NULL, closure);
output = _cairo_output_stream_create (write_func, NULL, closure);
status = _cairo_output_stream_get_status (output);
if (status) {
_cairo_error (status);
@ -362,6 +360,8 @@ cairo_pdf_surface_create_for_stream (cairo_write_func_t write,
* This function always returns a valid pointer, but it will return a
* pointer to a "nil" surface if an error such as out of memory
* occurs. You can use cairo_surface_status() to check for this.
*
* Since: 1.2
**/
cairo_surface_t *
cairo_pdf_surface_create (const char *filename,
@ -412,36 +412,6 @@ _extract_pdf_surface (cairo_surface_t *surface,
return CAIRO_STATUS_SUCCESS;
}
/**
* cairo_pdf_surface_set_dpi:
* @surface: a PDF cairo_surface_t
* @x_dpi: horizontal dpi
* @y_dpi: vertical dpi
*
* Set the horizontal and vertical resolution for image fallbacks.
* When the pdf backend needs to fall back to image overlays, it will
* use this resolution. These DPI values are not used for any other
* purpose, (in particular, they do not have any bearing on the size
* passed to cairo_pdf_surface_create() nor on the CTM).
**/
void
cairo_pdf_surface_set_dpi (cairo_surface_t *surface,
double x_dpi,
double y_dpi)
{
cairo_pdf_surface_t *pdf_surface;
cairo_status_t status;
status = _extract_pdf_surface (surface, &pdf_surface);
if (status) {
_cairo_surface_set_error (surface, CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return;
}
pdf_surface->x_dpi = x_dpi;
pdf_surface->y_dpi = y_dpi;
}
/**
* cairo_pdf_surface_set_size:
* @surface: a PDF cairo_surface_t
@ -456,6 +426,8 @@ cairo_pdf_surface_set_dpi (cairo_surface_t *surface,
* this is to call this function immediately after creating the
* surface or immediately after completing a page with either
* cairo_show_page() or cairo_copy_page().
*
* Since: 1.2
**/
void
cairo_pdf_surface_set_size (cairo_surface_t *surface,
@ -740,7 +712,6 @@ emit_smask (cairo_pdf_surface_t *surface,
return status;
}
/* Emit image data into the given surface, providing a resource that
* can be used to reference the data in image_ret. */
static cairo_status_t
@ -829,7 +800,6 @@ emit_image (cairo_pdf_surface_t *surface,
" /BitsPerComponent 8\r\n" \
" /Filter /FlateDecode\r\n"
if (need_smask)
*image_ret = _cairo_pdf_surface_open_stream (surface,
IMAGE_DICTIONARY
@ -892,7 +862,7 @@ emit_surface_pattern (cairo_pdf_surface_t *surface,
cairo_matrix_t cairo_p2d, pdf_p2d;
cairo_extend_t extend = cairo_pattern_get_extend (&pattern->base);
int xstep, ystep;
cairo_rectangle_fixed_t surface_extents;
cairo_rectangle_int16_t surface_extents;
/* XXX: Should do something clever here for PDF source surfaces ? */
@ -1351,7 +1321,7 @@ _cairo_pdf_surface_show_page (void *abstract_surface)
static cairo_int_status_t
_cairo_pdf_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_pdf_surface_t *surface = abstract_surface;
@ -1616,44 +1586,239 @@ _cairo_pdf_surface_write_pages (cairo_pdf_surface_t *surface)
"endobj\r\n");
}
static void
_cairo_pdf_surface_emit_glyph (cairo_pdf_surface_t *surface,
cairo_scaled_font_t *scaled_font,
unsigned long scaled_font_glyph_index,
unsigned int subset_glyph_index,
cairo_pdf_resource_t *glyph_ret)
static cairo_status_t
_cairo_pdf_surface_emit_type1_font_subset (cairo_pdf_surface_t *surface,
cairo_scaled_font_subset_t *font_subset)
{
cairo_pdf_resource_t stream, descriptor, subset_resource;
cairo_status_t status;
cairo_pdf_font_t font;
cairo_type1_subset_t subset;
unsigned long length, compressed_length;
char *compressed;
int i;
char name[64];
snprintf (name, sizeof name, "CairoFont-%d-%d",
font_subset->font_id, font_subset->subset_id);
status = _cairo_type1_subset_init (&subset, name, font_subset);
if (status)
return status;
/* We ignore the zero-trailer and set Length3 to 0. */
length = subset.header_length + subset.data_length;
compressed = compress_dup (subset.data, length, &compressed_length);
if (compressed == NULL) {
_cairo_type1_subset_fini (&subset);
return CAIRO_STATUS_NO_MEMORY;
}
stream = _cairo_pdf_surface_new_object (surface);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Filter /FlateDecode\r\n"
" /Length %lu\r\n"
" /Length1 %lu\r\n"
" /Length2 %lu\r\n"
" /Length3 0\r\n"
">>\r\n"
"stream\r\n",
stream.id,
compressed_length,
subset.header_length,
subset.data_length);
_cairo_output_stream_write (surface->output, compressed, compressed_length);
_cairo_output_stream_printf (surface->output,
"\r\n"
"endstream\r\n"
"endobj\r\n");
free (compressed);
descriptor = _cairo_pdf_surface_new_object (surface);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Type /FontDescriptor\r\n"
" /FontName /%s\r\n"
" /Flags 4\r\n"
" /FontBBox [ %ld %ld %ld %ld ]\r\n"
" /ItalicAngle 0\r\n"
" /Ascent %ld\r\n"
" /Descent %ld\r\n"
" /CapHeight 500\r\n"
" /StemV 80\r\n"
" /StemH 80\r\n"
" /FontFile %u 0 R\r\n"
">>\r\n"
"endobj\r\n",
descriptor.id,
subset.base_font,
subset.x_min,
subset.y_min,
subset.x_max,
subset.y_max,
subset.ascent,
subset.descent,
stream.id);
subset_resource = _cairo_pdf_surface_new_object (surface);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Type /Font\r\n"
" /Subtype /Type1\r\n"
" /BaseFont /%s\r\n"
" /FirstChar 0\r\n"
" /LastChar %d\r\n"
" /FontDescriptor %d 0 R\r\n"
" /Widths [",
subset_resource.id,
subset.base_font,
font_subset->num_glyphs,
descriptor.id);
for (i = 0; i < font_subset->num_glyphs; i++)
_cairo_output_stream_printf (surface->output,
" %d",
subset.widths[i]);
_cairo_output_stream_printf (surface->output,
" ]\r\n"
">>\r\n"
"endobj\r\n");
font.font_id = font_subset->font_id;
font.subset_id = font_subset->subset_id;
font.subset_resource = subset_resource;
_cairo_array_append (&surface->fonts, &font);
_cairo_type1_subset_fini (&subset);
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
_cairo_pdf_surface_emit_truetype_font_subset (cairo_pdf_surface_t *surface,
cairo_scaled_font_subset_t *font_subset)
{
cairo_pdf_resource_t stream, descriptor, subset_resource;
cairo_status_t status;
cairo_pdf_font_t font;
cairo_truetype_subset_t subset;
unsigned long compressed_length;
char *compressed;
int i;
status = _cairo_truetype_subset_init (&subset, font_subset);
if (status)
return status;
compressed = compress_dup (subset.data, subset.data_length,
&compressed_length);
if (compressed == NULL) {
_cairo_truetype_subset_fini (&subset);
return CAIRO_STATUS_NO_MEMORY;
}
stream = _cairo_pdf_surface_new_object (surface);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Filter /FlateDecode\r\n"
" /Length %lu\r\n"
" /Length1 %lu\r\n"
">>\r\n"
"stream\r\n",
stream.id,
compressed_length,
subset.data_length);
_cairo_output_stream_write (surface->output, compressed, compressed_length);
_cairo_output_stream_printf (surface->output,
"\r\n"
"endstream\r\n"
"endobj\r\n");
free (compressed);
descriptor = _cairo_pdf_surface_new_object (surface);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Type /FontDescriptor\r\n"
" /FontName /7%s\r\n"
" /Flags 4\r\n"
" /FontBBox [ %ld %ld %ld %ld ]\r\n"
" /ItalicAngle 0\r\n"
" /Ascent %ld\r\n"
" /Descent %ld\r\n"
" /CapHeight 500\r\n"
" /StemV 80\r\n"
" /StemH 80\r\n"
" /FontFile2 %u 0 R\r\n"
">>\r\n"
"endobj\r\n",
descriptor.id,
subset.base_font,
subset.x_min,
subset.y_min,
subset.x_max,
subset.y_max,
subset.ascent,
subset.descent,
stream.id);
subset_resource = _cairo_pdf_surface_new_object (surface);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Type /Font\r\n"
" /Subtype /TrueType\r\n"
" /BaseFont /%s\r\n"
" /FirstChar 0\r\n"
" /LastChar %d\r\n"
" /FontDescriptor %d 0 R\r\n"
" /Widths [",
subset_resource.id,
subset.base_font,
font_subset->num_glyphs,
descriptor.id);
for (i = 0; i < font_subset->num_glyphs; i++)
_cairo_output_stream_printf (surface->output,
" %d",
subset.widths[i]);
_cairo_output_stream_printf (surface->output,
" ]\r\n"
">>\r\n"
"endobj\r\n");
font.font_id = font_subset->font_id;
font.subset_id = font_subset->subset_id;
font.subset_resource = subset_resource;
_cairo_array_append (&surface->fonts, &font);
_cairo_truetype_subset_fini (&subset);
return CAIRO_STATUS_SUCCESS;
}
static cairo_int_status_t
_cairo_pdf_surface_emit_outline_glyph (cairo_pdf_surface_t *surface,
cairo_scaled_font_t *scaled_font,
unsigned long glyph_index,
cairo_pdf_resource_t *glyph_ret)
{
cairo_scaled_glyph_t *scaled_glyph;
cairo_status_t status;
pdf_path_info_t info;
cairo_status_t status = CAIRO_STATUS_SUCCESS;
status = _cairo_scaled_glyph_lookup (scaled_font,
scaled_font_glyph_index,
glyph_index,
CAIRO_SCALED_GLYPH_INFO_METRICS|
CAIRO_SCALED_GLYPH_INFO_PATH,
&scaled_glyph);
/*
* If that fails, try again but ask for an image instead
*/
if (status)
status = _cairo_scaled_glyph_lookup (scaled_font,
scaled_font_glyph_index,
CAIRO_SCALED_GLYPH_INFO_METRICS|
CAIRO_SCALED_GLYPH_INFO_SURFACE,
&scaled_glyph);
if (status) {
_cairo_surface_set_error (&surface->base, status);
return;
}
/* XXX: Need to actually use the image not the path if that's all
* we could get... */
return status;
*glyph_ret = _cairo_pdf_surface_open_stream (surface, NULL);
_cairo_output_stream_printf (surface->output,
"0 0 %f %f %f %f d1\r\n"
" \r\n",
"0 0 %f %f %f %f d1\r\n",
_cairo_fixed_to_double (scaled_glyph->bbox.p1.x),
-_cairo_fixed_to_double (scaled_glyph->bbox.p2.y),
_cairo_fixed_to_double (scaled_glyph->bbox.p2.x),
@ -1675,29 +1840,116 @@ _cairo_pdf_surface_emit_glyph (cairo_pdf_surface_t *surface,
_cairo_pdf_surface_close_stream (surface);
return CAIRO_STATUS_SUCCESS;
}
static cairo_int_status_t
_cairo_pdf_surface_emit_bitmap_glyph (cairo_pdf_surface_t *surface,
cairo_scaled_font_t *scaled_font,
unsigned long glyph_index,
cairo_pdf_resource_t *glyph_ret)
{
cairo_scaled_glyph_t *scaled_glyph;
cairo_status_t status;
cairo_image_surface_t *image;
unsigned char *row, *byte;
int rows, cols, bytes_per_row;
status = _cairo_scaled_glyph_lookup (scaled_font,
glyph_index,
CAIRO_SCALED_GLYPH_INFO_METRICS|
CAIRO_SCALED_GLYPH_INFO_SURFACE,
&scaled_glyph);
if (status)
return status;
image = scaled_glyph->surface;
assert (image->format == CAIRO_FORMAT_A1);
*glyph_ret = _cairo_pdf_surface_open_stream (surface, NULL);
_cairo_output_stream_printf (surface->output,
"0 0 %f %f %f %f d1\r\n",
_cairo_fixed_to_double (scaled_glyph->bbox.p1.x),
- _cairo_fixed_to_double (scaled_glyph->bbox.p2.y),
_cairo_fixed_to_double (scaled_glyph->bbox.p2.x),
- _cairo_fixed_to_double (scaled_glyph->bbox.p1.y));
_cairo_output_stream_printf (surface->output,
"%f 0.0 0.0 %f %f %f cm\r\n",
_cairo_fixed_to_double (scaled_glyph->bbox.p2.x) - _cairo_fixed_to_double (scaled_glyph->bbox.p1.x),
_cairo_fixed_to_double (scaled_glyph->bbox.p1.y) - _cairo_fixed_to_double (scaled_glyph->bbox.p2.y),
_cairo_fixed_to_double (scaled_glyph->bbox.p1.x),
_cairo_fixed_to_double (scaled_glyph->bbox.p2.y));
_cairo_output_stream_printf (surface->output,
"BI\r\n"
"/IM true\r\n"
"/W %d\r\n"
"/H %d\r\n"
"/BPC 1\r\n"
"/D [1 0]\r\n",
image->width,
image->height);
_cairo_output_stream_printf (surface->output,
"ID ");
bytes_per_row = (image->width + 7) / 8;
for (row = image->data, rows = image->height; rows; row += image->stride, rows--) {
for (byte = row, cols = (image->width + 7) / 8; cols; byte++, cols--) {
unsigned char output_byte = CAIRO_BITSWAP8_IF_LITTLE_ENDIAN (*byte);
_cairo_output_stream_write (surface->output, &output_byte, 1);
}
}
_cairo_output_stream_printf (surface->output,
"\r\nEI\r\n");
_cairo_pdf_surface_close_stream (surface);
return CAIRO_STATUS_SUCCESS;
}
static void
_cairo_pdf_surface_emit_glyph (cairo_pdf_surface_t *surface,
cairo_scaled_font_t *scaled_font,
unsigned long glyph_index,
cairo_pdf_resource_t *glyph_ret)
{
cairo_status_t status;
status = _cairo_pdf_surface_emit_outline_glyph (surface,
scaled_font,
glyph_index,
glyph_ret);
if (status == CAIRO_INT_STATUS_UNSUPPORTED)
status = _cairo_pdf_surface_emit_bitmap_glyph (surface,
scaled_font,
glyph_index,
glyph_ret);
if (status)
_cairo_surface_set_error (&surface->base, status);
}
static void
_cairo_pdf_surface_emit_font_subset (cairo_scaled_font_subset_t *font_subset,
void *closure)
static cairo_status_t
_cairo_pdf_surface_emit_type3_font_subset (cairo_pdf_surface_t *surface,
cairo_scaled_font_subset_t *font_subset)
{
cairo_pdf_surface_t *surface = closure;
cairo_pdf_resource_t *glyphs, encoding, char_procs, subset_resource;
cairo_pdf_font_t font;
cairo_matrix_t matrix;
int i;
glyphs = malloc (font_subset->num_glyphs * sizeof (cairo_pdf_resource_t));
if (glyphs == NULL) {
_cairo_surface_set_error (&surface->base, CAIRO_STATUS_NO_MEMORY);
return;
return CAIRO_STATUS_NO_MEMORY;
}
for (i = 0; i < font_subset->num_glyphs; i++) {
_cairo_pdf_surface_emit_glyph (surface,
font_subset->scaled_font,
font_subset->glyphs[i], i,
font_subset->glyphs[i],
&glyphs[i]);
}
@ -1727,17 +1979,23 @@ _cairo_pdf_surface_emit_font_subset (cairo_scaled_font_subset_t *font_subset,
"endobj\r\n");
subset_resource = _cairo_pdf_surface_new_object (surface);
matrix = font_subset->scaled_font->scale;
cairo_matrix_invert (&matrix);
_cairo_output_stream_printf (surface->output,
"%d 0 obj\r\n"
"<< /Type /Font\r\n"
" /Subtype /Type3\r\n"
" /FontBBox [0 0 0 0]\r\n"
" /FontMatrix\t[1 0 0 1 0 0]\r\n"
" /FontMatrix [ %f %f %f %f 0 0 ]\r\n"
" /Encoding %d 0 R\r\n"
" /CharProcs %d 0 R\r\n"
" /FirstChar 0\r\n"
" /LastChar %d\r\n",
subset_resource.id,
matrix.xx,
matrix.yx,
-matrix.xy,
-matrix.yy,
encoding.id,
char_procs.id,
font_subset->num_glyphs - 1);
@ -1757,6 +2015,28 @@ _cairo_pdf_surface_emit_font_subset (cairo_scaled_font_subset_t *font_subset,
font.subset_id = font_subset->subset_id;
font.subset_resource = subset_resource;
_cairo_array_append (&surface->fonts, &font);
return CAIRO_STATUS_SUCCESS;
}
static void
_cairo_pdf_surface_emit_font_subset (cairo_scaled_font_subset_t *font_subset,
void *closure)
{
cairo_pdf_surface_t *surface = closure;
cairo_status_t status;
status = _cairo_pdf_surface_emit_type1_font_subset (surface, font_subset);
if (status != CAIRO_INT_STATUS_UNSUPPORTED)
return;
status = _cairo_pdf_surface_emit_truetype_font_subset (surface, font_subset);
if (status != CAIRO_INT_STATUS_UNSUPPORTED)
return;
status = _cairo_pdf_surface_emit_type3_font_subset (surface, font_subset);
if (status != CAIRO_INT_STATUS_UNSUPPORTED)
return;
}
static cairo_status_t
@ -2027,11 +2307,11 @@ _pattern_supported (cairo_pattern_t *pattern)
static cairo_bool_t cairo_pdf_force_fallbacks = FALSE;
/**
* cairo_pdf_test_force_fallbacks
* _cairo_pdf_test_force_fallbacks
*
* Force the PDF surface backend to use image fallbacks for every
* operation.
*
*
* <note>
* This function is <emphasis>only</emphasis> intended for internal
* testing use within the cairo distribution. It is not installed in
@ -2039,7 +2319,7 @@ static cairo_bool_t cairo_pdf_force_fallbacks = FALSE;
* </note>
**/
void
cairo_pdf_test_force_fallbacks (void)
_cairo_pdf_test_force_fallbacks (void)
{
cairo_pdf_force_fallbacks = TRUE;
}
@ -2201,14 +2481,8 @@ _cairo_pdf_surface_stroke (void *abstract_surface,
pdf_path_info_t info;
cairo_status_t status;
if (surface->paginated_mode == CAIRO_PAGINATED_MODE_ANALYZE) {
/* XXX: Does PDF provide a way we can preserve this hint? For now,
* this will trigger a fallback. */
if (antialias == CAIRO_ANTIALIAS_NONE)
return CAIRO_INT_STATUS_UNSUPPORTED;
if (surface->paginated_mode == CAIRO_PAGINATED_MODE_ANALYZE)
return _analyze_operation (surface, op, source);
}
assert (_operation_supported (surface, op, source));
@ -2256,14 +2530,8 @@ _cairo_pdf_surface_fill (void *abstract_surface,
cairo_status_t status;
pdf_path_info_t info;
if (surface->paginated_mode == CAIRO_PAGINATED_MODE_ANALYZE) {
/* XXX: Does PDF provide a way we can preserve this hint? For now,
* this will trigger a fallback. */
if (antialias == CAIRO_ANTIALIAS_NONE)
return CAIRO_INT_STATUS_UNSUPPORTED;
if (surface->paginated_mode == CAIRO_PAGINATED_MODE_ANALYZE)
return _analyze_operation (surface, op, source);
}
assert (_operation_supported (surface, op, source));
@ -2300,14 +2568,6 @@ _cairo_pdf_surface_fill (void *abstract_surface,
return status;
}
static char
hex_digit (int i)
{
i &= 0xf;
if (i < 10) return '0' + i;
return 'a' + (i - 10);
}
static cairo_int_status_t
_cairo_pdf_surface_show_glyphs (void *abstract_surface,
cairo_operator_t op,
@ -2331,6 +2591,9 @@ _cairo_pdf_surface_show_glyphs (void *abstract_surface,
if (status)
return status;
_cairo_output_stream_printf (surface->output,
"BT\r\n");
for (i = 0; i < num_glyphs; i++) {
status = _cairo_scaled_font_subsets_map_glyph (surface->font_subsets,
scaled_font, glyphs[i].index,
@ -2344,13 +2607,21 @@ _cairo_pdf_surface_show_glyphs (void *abstract_surface,
font_id, subset_id);
current_subset_id = subset_id;
}
_cairo_output_stream_printf (surface->output,
"BT %f %f Td <%c%c> Tj ET\r\n",
glyphs[i].x, glyphs[i].y,
hex_digit (subset_glyph_index >> 4),
hex_digit (subset_glyph_index));
"%f %f %f %f %f %f Tm <%02x> Tj\r\n",
scaled_font->scale.xx,
scaled_font->scale.yx,
-scaled_font->scale.xy,
-scaled_font->scale.yy,
glyphs[i].x,
glyphs[i].y,
subset_glyph_index);
}
_cairo_output_stream_printf (surface->output,
"ET\r\n");
return _cairo_output_stream_get_status (surface->output);
}

Просмотреть файл

@ -1,76 +0,0 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2006 Red Hat, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is University of Southern
* California.
*
* Contributor(s):
* Carl D. Worth <cworth@cworth.org>
*/
#ifndef CAIRO_PDF_TEST_H
#define CAIRO_PDF_TEST_H
#include <cairo.h>
#if CAIRO_HAS_PDF_SURFACE
#include <cairo-pdf.h>
CAIRO_BEGIN_DECLS
struct _cairo_path_fixed;
struct _cairo_traps;
struct _cairo_trapezoid;
struct _cairo_clip;
void
cairo_pdf_test_force_fallbacks (void);
void
cairo_debug_dump_clip (struct _cairo_clip *clip,
FILE *fp);
void
cairo_debug_dump_path (struct _cairo_path_fixed *path,
FILE *fp);
void
cairo_debug_dump_traps (struct _cairo_traps *traps,
FILE *fp);
void
cairo_debug_dump_trapezoid_array (struct _cairo_trapezoid *traps,
int num_traps,
FILE *fp);
CAIRO_END_DECLS
#endif /* CAIRO_HAS_PDF_SURFACE */
#endif /* CAIRO_PDF_TEST_H */

Просмотреть файл

@ -54,11 +54,6 @@ cairo_pdf_surface_create_for_stream (cairo_write_func_t write_func,
double width_in_points,
double height_in_points);
cairo_public void
cairo_pdf_surface_set_dpi (cairo_surface_t *surface,
double x_dpi,
double y_dpi);
void
cairo_pdf_surface_set_size (cairo_surface_t *surface,
double width_in_points,

Просмотреть файл

@ -79,7 +79,7 @@ _cairo_pen_init (cairo_pen_t *pen,
pen->num_vertices = _cairo_pen_vertices_needed (tolerance,
radius,
ctm);
pen->vertices = malloc (pen->num_vertices * sizeof (cairo_pen_vertex_t));
if (pen->vertices == NULL) {
return CAIRO_STATUS_NO_MEMORY;
@ -165,7 +165,7 @@ We construct the pen by computing points along the circumference
using equally spaced angles.
We show that this approximation to the ellipse has maximum error at the
major axis of the ellipse.
major axis of the ellipse.
Set
@ -247,26 +247,26 @@ _cairo_pen_vertices_needed (double tolerance,
double radius,
cairo_matrix_t *matrix)
{
/*
/*
* the pen is a circle that gets transformed to an ellipse by matrix.
* compute major axis length for a pen with the specified radius.
* we don't need the minor axis length.
*/
double major_axis = _cairo_matrix_transformed_circle_major_axis(matrix, radius);
/*
* compute number of vertices needed
*/
int num_vertices;
/* Where tolerance / M is > 1, we use 4 points */
if (tolerance >= major_axis) {
num_vertices = 4;
} else {
double delta = acos (1 - tolerance / major_axis);
num_vertices = ceil (M_PI / delta);
/* number of vertices must be even */
if (num_vertices % 2)
num_vertices++;
@ -377,8 +377,8 @@ _cairo_pen_stroke_spline_half (cairo_pen_t *pen,
initial_slope.dx = -initial_slope.dx;
initial_slope.dy = -initial_slope.dy;
final_slope = spline->initial_slope;
final_slope.dx = -final_slope.dx;
final_slope.dy = -final_slope.dy;
final_slope.dx = -final_slope.dx;
final_slope.dy = -final_slope.dy;
}
_cairo_pen_find_active_cw_vertex_index (pen, &initial_slope, &active);
@ -443,6 +443,6 @@ _cairo_pen_stroke_spline (cairo_pen_t *pen,
_cairo_polygon_close (&polygon);
_cairo_traps_tessellate_polygon (traps, &polygon, CAIRO_FILL_RULE_WINDING);
_cairo_polygon_fini (&polygon);
return CAIRO_STATUS_SUCCESS;
}

Просмотреть файл

@ -37,6 +37,8 @@
#ifndef CAIRO_PLATFORM_H
#define CAIRO_PLATFORM_H
#include "cairo-rename.h"
#if defined(MOZ_ENABLE_LIBXUL)
#ifdef HAVE_VISIBILITY_HIDDEN_ATTRIBUTE

Просмотреть файл

@ -74,7 +74,7 @@ convert_data_to_bytes (png_structp png, png_row_infop row_info, png_bytep data)
uint32_t pixel;
memcpy (&pixel, b, sizeof (uint32_t));
b[0] = (pixel & 0xff0000) >> 16;
b[1] = (pixel & 0x00ff00) >> 8;
b[2] = (pixel & 0x0000ff) >> 0;
@ -133,7 +133,7 @@ write_png (cairo_surface_t *surface,
status = CAIRO_STATUS_NO_MEMORY;
goto BAIL3;
}
png_set_write_fn (png, closure, write_func, NULL);
switch (image->format) {
@ -179,14 +179,14 @@ write_png (cairo_surface_t *surface,
* that is needed for the write transformation functions to work.
*/
png_write_info (png, info);
if (image->format == CAIRO_FORMAT_ARGB32)
png_set_write_user_transform_fn (png, unpremultiply_data);
else if (image->format == CAIRO_FORMAT_RGB24)
png_set_write_user_transform_fn (png, convert_data_to_bytes);
if (image->format == CAIRO_FORMAT_RGB24)
png_set_filler (png, 0, PNG_FILLER_AFTER);
png_write_image (png, rows);
png_write_end (png, info);
@ -214,10 +214,10 @@ stdio_write_func (png_structp png, png_bytep data, png_size_t size)
* cairo_surface_write_to_png:
* @surface: a #cairo_surface_t with pixel contents
* @filename: the name of a file to write to
*
*
* Writes the contents of @surface to a new file @filename as a PNG
* image.
*
*
* Return value: CAIRO_STATUS_SUCCESS if the PNG file was written
* successfully. Otherwise, CAIRO_STATUS_NO_MEMORY if memory could not
* be allocated for the operation or
@ -235,7 +235,7 @@ cairo_surface_write_to_png (cairo_surface_t *surface,
fp = fopen (filename, "wb");
if (fp == NULL)
return CAIRO_STATUS_WRITE_ERROR;
status = write_png (surface, stdio_write_func, fp);
if (fclose (fp) && status == CAIRO_STATUS_SUCCESS)
@ -266,9 +266,9 @@ stream_write_func (png_structp png, png_bytep data, png_size_t size)
* @surface: a #cairo_surface_t with pixel contents
* @write_func: a #cairo_write_func_t
* @closure: closure data for the write function
*
*
* Writes the image surface to the write function.
*
*
* Return value: CAIRO_STATUS_SUCCESS if the PNG file was written
* successfully. Otherwise, CAIRO_STATUS_NO_MEMORY is returned if
* memory could not be allocated for the operation,
@ -286,7 +286,7 @@ cairo_surface_write_to_png_stream (cairo_surface_t *surface,
png_closure.closure = closure;
return write_png (surface, stream_write_func, &png_closure);
}
}
static INLINE int
multiply_alpha (int alpha, int color)
@ -447,15 +447,15 @@ stdio_read_func (png_structp png, png_bytep data, png_size_t size)
/**
* cairo_image_surface_create_from_png:
* @filename: name of PNG file to load
*
* @filename: name of PNG file to load
*
* Creates a new image surface and initializes the contents to the
* given PNG file.
*
*
* Return value: a new #cairo_surface_t initialized with the contents
* of the PNG file, or a "nil" surface if any error occurred. A nil
* surface can be checked for with cairo_surface_status(surface) which
* may return one of the following values:
* may return one of the following values:
*
* CAIRO_STATUS_NO_MEMORY
* CAIRO_STATUS_FILE_NOT_FOUND
@ -481,7 +481,7 @@ cairo_image_surface_create_from_png (const char *filename)
return (cairo_surface_t*) &_cairo_surface_nil_read_error;
}
}
surface = read_png (stdio_read_func, fp);
fclose (fp);
@ -510,10 +510,10 @@ stream_read_func (png_structp png, png_bytep data, png_size_t size)
* cairo_image_surface_create_from_png_stream:
* @read_func: function called to read the data of the file
* @closure: data to pass to @read_func.
*
*
* Creates a new image surface from PNG data read incrementally
* via the @read_func function.
*
*
* Return value: a new #cairo_surface_t initialized with the contents
* of the PNG file or %NULL if the data read is not a valid PNG image or
* memory could not be allocated for the operation.
@ -529,4 +529,3 @@ cairo_image_surface_create_from_png_stream (cairo_read_func_t read_func,
return read_png (stream_read_func, &png_closure);
}

Просмотреть файл

@ -128,7 +128,7 @@ _cairo_polygon_add_edge (cairo_polygon_t *polygon, cairo_point_t *p1, cairo_poin
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
cairo_status_t
_cairo_polygon_move_to (cairo_polygon_t *polygon, cairo_point_t *point)
{
if (! polygon->has_current_point)

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -73,11 +73,6 @@ cairo_ps_surface_dsc_begin_setup (cairo_surface_t *surface);
cairo_public void
cairo_ps_surface_dsc_begin_page_setup (cairo_surface_t *surface);
cairo_public void
cairo_ps_surface_set_dpi (cairo_surface_t *surface,
double x_dpi,
double y_dpi);
CAIRO_END_DECLS
#else /* CAIRO_HAS_PS_SURFACE */

Просмотреть файл

@ -129,10 +129,10 @@ _cairo_quartz_surface_acquire_source_image(void *abstract_surface,
static cairo_status_t
_cairo_quartz_surface_acquire_dest_image(void *abstract_surface,
cairo_rectangle_fixed_t * interest_rect,
cairo_rectangle_int16_t * interest_rect,
cairo_image_surface_t **
image_out,
cairo_rectangle_fixed_t * image_rect,
cairo_rectangle_int16_t * image_rect,
void **image_extra)
{
cairo_quartz_surface_t *surface = abstract_surface;
@ -152,10 +152,10 @@ _cairo_quartz_surface_acquire_dest_image(void *abstract_surface,
static void
_cairo_quartz_surface_release_dest_image(void *abstract_surface,
cairo_rectangle_fixed_t *
cairo_rectangle_int16_t *
intersect_rect,
cairo_image_surface_t * image,
cairo_rectangle_fixed_t * image_rect,
cairo_rectangle_int16_t * image_rect,
void *image_extra)
{
cairo_quartz_surface_t *surface = abstract_surface;
@ -204,7 +204,7 @@ _cairo_quartz_surface_set_clip_region(void *abstract_surface,
static cairo_int_status_t
_cairo_quartz_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t * rectangle)
cairo_rectangle_int16_t * rectangle)
{
cairo_quartz_surface_t *surface = abstract_surface;

Просмотреть файл

@ -58,4 +58,3 @@ CAIRO_END_DECLS
#endif /* CAIRO_HAS_QUARTZ_SURFACE */
#endif /* CAIRO_QUARTZ_H */

Просмотреть файл

@ -0,0 +1,85 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2002 University of Southern California
* Copyright © 2005 Red Hat, Inc.
* Copyright © 2006 Red Hat, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is University of Southern
* California.
*
* Contributor(s):
* Carl D. Worth <cworth@cworth.org>
*/
#include "cairoint.h"
/* XXX We currently have a confusing mix of boxes and rectangles as
* exemplified by this function. A cairo_box_t is a rectangular area
* represented by the coordinates of the upper left and lower right
* corners, expressed in fixed point numbers. A cairo_rectangle_int16_t is
* also a rectangular area, but represented by the upper left corner
* and the width and the height, as integer numbers.
*
* This function converts a cairo_box_t to a cairo_rectangle_int16_t by
* increasing the area to the nearest integer coordinates. We should
* standardize on cairo_rectangle_int16_t and cairo_rectangle_int16_t, and
* this function could be renamed to the more reasonable
* _cairo_rectangle_fixed_round.
*/
void
_cairo_box_round_to_rectangle (cairo_box_t *box, cairo_rectangle_int16_t *rectangle)
{
rectangle->x = _cairo_fixed_integer_floor (box->p1.x);
rectangle->y = _cairo_fixed_integer_floor (box->p1.y);
rectangle->width = _cairo_fixed_integer_ceil (box->p2.x) - rectangle->x;
rectangle->height = _cairo_fixed_integer_ceil (box->p2.y) - rectangle->y;
}
void
_cairo_rectangle_intersect (cairo_rectangle_int16_t *dest, cairo_rectangle_int16_t *src)
{
int x1, y1, x2, y2;
x1 = MAX (dest->x, src->x);
y1 = MAX (dest->y, src->y);
x2 = MIN (dest->x + dest->width, src->x + src->width);
y2 = MIN (dest->y + dest->height, src->y + src->height);
if (x1 >= x2 || y1 >= y2) {
dest->x = 0;
dest->y = 0;
dest->width = 0;
dest->height = 0;
} else {
dest->x = x1;
dest->y = y1;
dest->width = x2 - x1;
dest->height = y2 - y1;
}
}

Просмотреть файл

@ -37,16 +37,16 @@
/**
* _cairo_region_create_from_rectangle:
* @rect: a #cairo_rectangle_fixed_t
*
* @rect: a #cairo_rectangle_int16_t
*
* Creates a region with extents initialized from the given
* rectangle.
*
*
* Return value: a newly created #pixman_region16_t or %NULL if
* memory couldn't a allocated.
**/
pixman_region16_t *
_cairo_region_create_from_rectangle (cairo_rectangle_fixed_t *rect)
_cairo_region_create_from_rectangle (cairo_rectangle_int16_t *rect)
{
/* We can't use pixman_region_create_simple(), because it doesn't
* have an error return
@ -58,7 +58,7 @@ _cairo_region_create_from_rectangle (cairo_rectangle_fixed_t *rect)
pixman_region_destroy (region);
return NULL;
}
return region;
}
@ -66,12 +66,12 @@ _cairo_region_create_from_rectangle (cairo_rectangle_fixed_t *rect)
* _cairo_region_extents_rectangle:
* @region: a #pixman_region16_t
* @rect: rectangle into which to store the extents
*
* Gets the bounding box of a region as a cairo_rectangle_fixed_t
*
* Gets the bounding box of a region as a cairo_rectangle_int16_t
**/
void
_cairo_region_extents_rectangle (pixman_region16_t *region,
cairo_rectangle_fixed_t *rect)
cairo_rectangle_int16_t *rect)
{
pixman_box16_t *region_extents = pixman_region_extents (region);
@ -80,4 +80,3 @@ _cairo_region_extents_rectangle (pixman_region16_t *region,
rect->width = region_extents->x2 - region_extents->x1;
rect->height = region_extents->y2 - region_extents->y1;
}

Просмотреть файл

@ -78,7 +78,10 @@
#define cairo_image_surface_create_for_data _moz_cairo_image_surface_create_for_data
#define cairo_image_surface_create_from_png _moz_cairo_image_surface_create_from_png
#define cairo_image_surface_create_from_png_stream _moz_cairo_image_surface_create_from_png_stream
#define cairo_image_surface_get_data _moz_cairo_image_surface_get_data
#define cairo_image_surface_get_format _moz_cairo_image_surface_get_format
#define cairo_image_surface_get_height _moz_cairo_image_surface_get_height
#define cairo_image_surface_get_stride _moz_cairo_image_surface_get_stride
#define cairo_image_surface_get_width _moz_cairo_image_surface_get_width
#define cairo_in_fill _moz_cairo_in_fill
#define cairo_in_stroke _moz_cairo_in_stroke
@ -122,7 +125,6 @@
#define cairo_pattern_status _moz_cairo_pattern_status
#define cairo_pdf_surface_create _moz_cairo_pdf_surface_create
#define cairo_pdf_surface_create_for_stream _moz_cairo_pdf_surface_create_for_stream
#define cairo_pdf_surface_set_dpi _moz_cairo_pdf_surface_set_dpi
#define cairo_pop_group _moz_cairo_pop_group
#define cairo_pop_group_to_source _moz_cairo_pop_group_to_source
#define cairo_profile_surface_create _moz_cairo_profile_surface_create
@ -132,7 +134,6 @@
#define cairo_ps_surface_dsc_begin_page_setup _moz_cairo_ps_surface_dsc_begin_page_setup
#define cairo_ps_surface_dsc_begin_setup _moz_cairo_ps_surface_dsc_begin_setup
#define cairo_ps_surface_dsc_comment _moz_cairo_ps_surface_dsc_comment
#define cairo_ps_surface_set_dpi _moz_cairo_ps_surface_set_dpi
#define cairo_ps_surface_set_size _moz_cairo_ps_surface_set_size
#define cairo_push_group _moz_cairo_push_group
#define cairo_push_group_with_content _moz_cairo_push_group_with_content
@ -202,6 +203,7 @@
#define cairo_surface_mark_dirty_rectangle _moz_cairo_surface_mark_dirty_rectangle
#define cairo_surface_reference _moz_cairo_surface_reference
#define cairo_surface_set_device_offset _moz_cairo_surface_set_device_offset
#define cairo_surface_set_fallback_resolution _moz_cairo_surface_set_fallback_resolution
#define cairo_surface_set_user_data _moz_cairo_surface_set_user_data
#define cairo_surface_status _moz_cairo_surface_status
#define cairo_surface_write_to_png _moz_cairo_surface_write_to_png
@ -210,7 +212,6 @@
#define cairo_svg_surface_create _moz_cairo_svg_surface_create
#define cairo_svg_surface_create_for_stream _moz_cairo_svg_surface_create_for_stream
#define cairo_svg_surface_restrict_to_version _moz_cairo_svg_surface_restrict_to_version
#define cairo_svg_surface_set_dpi _moz_cairo_svg_surface_set_dpi
#define cairo_svg_version_to_string _moz_cairo_svg_version_to_string
#define cairo_text_extents _moz_cairo_text_extents
#define cairo_text_path _moz_cairo_text_path
@ -228,8 +229,10 @@
#define cairo_win32_scaled_font_get_metrics_factor _moz_cairo_win32_scaled_font_get_metrics_factor
#define cairo_win32_scaled_font_select_font _moz_cairo_win32_scaled_font_select_font
#define cairo_win32_surface_create _moz_cairo_win32_surface_create
#define cairo_win32_surface_create_with_ddb _moz_cairo_win32_surface_create_with_ddb
#define cairo_win32_surface_create_with_dib _moz_cairo_win32_surface_create_with_dib
#define cairo_win32_surface_get_dc _moz_cairo_win32_surface_get_dc
#define cairo_win32_surface_get_image _moz_cairo_win32_surface_get_image
#define cairo_xcb_surface_create _moz_cairo_xcb_surface_create
#define cairo_xcb_surface_create_for_bitmap _moz_cairo_xcb_surface_create_for_bitmap
#define cairo_xcb_surface_create_with_xrender_format _moz_cairo_xcb_surface_create_with_xrender_format
@ -240,7 +243,9 @@
#define cairo_xlib_surface_get_depth _moz_cairo_xlib_surface_get_depth
#define cairo_xlib_surface_get_display _moz_cairo_xlib_surface_get_display
#define cairo_xlib_surface_get_drawable _moz_cairo_xlib_surface_get_drawable
#define cairo_xlib_surface_get_height _moz_cairo_xlib_surface_get_height
#define cairo_xlib_surface_get_screen _moz_cairo_xlib_surface_get_screen
#define cairo_xlib_surface_get_visual _moz_cairo_xlib_surface_get_visual
#define cairo_xlib_surface_get_width _moz_cairo_xlib_surface_get_width
#define cairo_xlib_surface_set_drawable _moz_cairo_xlib_surface_set_drawable
#define cairo_xlib_surface_set_size _moz_cairo_xlib_surface_set_size

Просмотреть файл

@ -58,14 +58,14 @@ typedef struct _cairo_scaled_font_subset {
* @max_glyphs_per_subset: the maximum number of glyphs that should
* appear in any subset. A value of 0 indicates that there is no limit
* to the number of glyphs per subset.
*
*
* Create a new #cairo_scaled_font_subsets_t object which can be used
* to create subsets of any number of cairo_scaled_font_t
* objects. This allows the (arbitrarily large and sparse) glyph
* indices of a cairo_scaled_font to be mapped to one or more font
* subsets with glyph indices packed into the range
* [0 .. max_glyphs_per_subset).
*
*
* Return value: a pointer to the newly creates font subsets. The
* caller owns this object and should call
* _cairo_scaled_font_subsets_destroy() when done with it.
@ -76,7 +76,7 @@ _cairo_scaled_font_subsets_create (int max_glyphs_per_subset);
/**
* _cairo_scaled_font_subsets_destroy:
* @font_subsets: a #cairo_scaled_font_subsets_t object to be destroyed
*
*
* Destroys @font_subsets and all resources associated with it.
**/
cairo_private void
@ -90,7 +90,7 @@ _cairo_scaled_font_subsets_destroy (cairo_scaled_font_subsets_t *font_subsets);
* @font_id_ret: return value giving the font ID of the mapped glyph
* @subset_id_ret: return value giving the subset ID of the mapped glyph within the @font_id_ret
* @subset_glyph_index_ret: return value giving the index of the mapped glyph within the @subset_id_ret subset
*
*
* Map a glyph from a #cairo_scaled_font to a new index within a
* subset of that font. The mapping performed is from the tuple:
*
@ -149,7 +149,7 @@ typedef void
* @font_subsets: a #cairo_scaled_font_subsets_t
* @font_subset_callback: a function to be called for each font subset
* @closure: closure data for the callback function
*
*
* Iterate over each unique font subset as created by calls to
* _cairo_scaled_font_subsets_map_glyph(). A subset is determined by
* unique pairs of (font_id, subset_id) as returned by
@ -169,7 +169,7 @@ typedef void
* returned by _cairo_scaled_font_subsets_map_glyph() while the
* values of the array correspond to the scaled_font_glyph_index
* values passed as input to the same function.
*
*
* Return value: CAIRO_STATUS_SUCCESS if successful, or a non-zero
* value indicating an error. Possible errors include
* CAIRO_STATUS_NO_MEMORY.
@ -179,4 +179,89 @@ _cairo_scaled_font_subsets_foreach (cairo_scaled_font_subsets_t *font_subsets,
cairo_scaled_font_subset_callback_func_t font_subset_callback,
void *closure);
typedef struct _cairo_truetype_subset {
char *base_font;
int *widths;
long x_min, y_min, x_max, y_max;
long ascent, descent;
char *data;
unsigned long data_length;
} cairo_truetype_subset_t;
/**
* _cairo_truetype_subset_init:
* @truetype_subset: a #cairo_truetype_subset_t to initialize
* @font_subset: the #cairo_scaled_font_subset_t to initialize from
*
* If possible (depending on the format of the underlying
* cairo_scaled_font_t and the font backend in use) generate a
* truetype file corresponding to @font_subset and initialize
* @truetype_subset with information about the subset and the truetype
* data.
*
* Return value: CAIRO_STATUS_SUCCESS if successful,
* CAIRO_INT_STATUS_UNSUPPORTED if the font can't be subset as a
* truetype file, or an non-zero value indicating an error. Possible
* errors include CAIRO_STATUS_NO_MEMORY.
**/
cairo_private cairo_status_t
_cairo_truetype_subset_init (cairo_truetype_subset_t *truetype_subset,
cairo_scaled_font_subset_t *font_subset);
/**
* _cairo_truetype_subset_fini:
* @truetype_subset: a #cairo_truetype_subset_t
*
* Free all resources associated with @truetype_subset. After this
* call, @truetype_subset should not be used again without a
* subsequent call to _cairo_truetype_subset_init() again first.
**/
cairo_private void
_cairo_truetype_subset_fini (cairo_truetype_subset_t *truetype_subset);
typedef struct _cairo_type1_subset {
char *base_font;
int *widths;
long x_min, y_min, x_max, y_max;
long ascent, descent;
char *data;
unsigned long header_length;
unsigned long data_length;
unsigned long trailer_length;
} cairo_type1_subset_t;
/**
* _cairo_type1_subset_init:
* @type1_subset: a #cairo_type1_subset_t to initialize
* @font_subset: the #cairo_scaled_font_subset_t to initialize from
*
* If possible (depending on the format of the underlying
* cairo_scaled_font_t and the font backend in use) generate a type1
* file corresponding to @font_subset and initialize @type1_subset
* with information about the subset and the type1 data.
*
* Return value: CAIRO_STATUS_SUCCESS if successful,
* CAIRO_INT_STATUS_UNSUPPORTED if the font can't be subset as a type1
* file, or an non-zero value indicating an error. Possible errors
* include CAIRO_STATUS_NO_MEMORY.
**/
cairo_private cairo_status_t
_cairo_type1_subset_init (cairo_type1_subset_t *type_subset,
const char *name,
cairo_scaled_font_subset_t *font_subset);
/**
* _cairo_type1_subset_fini:
* @type1_subset: a #cairo_type1_subset_t
*
* Free all resources associated with @type1_subset. After this call,
* @type1_subset should not be used again without a subsequent call to
* _cairo_truetype_type1_init() again first.
**/
cairo_private void
_cairo_type1_subset_fini (cairo_type1_subset_t *subset);
#endif /* CAIRO_SCALED_FONT_SUBSETS_PRIVATE_H */

Просмотреть файл

@ -39,7 +39,6 @@
* Keith Packard <keithp@keithp.com>
*/
#include "cairoint.h"
#include "cairo-scaled-font-subsets-private.h"
@ -246,7 +245,7 @@ _cairo_sub_font_map_glyph (cairo_sub_font_t *sub_font,
sub_font->current_subset++;
sub_font->num_glyphs_in_current_subset = 0;
}
sub_font_glyph = _cairo_sub_font_glyph_create (scaled_font_glyph_index,
sub_font->current_subset,
sub_font->num_glyphs_in_current_subset++);
@ -341,7 +340,7 @@ _cairo_scaled_font_subsets_map_glyph (cairo_scaled_font_subsets_t *subsets,
_cairo_sub_font_init_key (&key, scaled_font);
if (! _cairo_hash_table_lookup (subsets->sub_fonts, &key.base,
(cairo_hash_entry_t **) &sub_font))
(cairo_hash_entry_t **) &sub_font))
{
sub_font = _cairo_sub_font_create (subsets, scaled_font,
subsets->num_sub_fonts++,

Просмотреть файл

@ -1,4 +1,4 @@
/* $Id: cairo-scaled-font.c,v 1.9 2006-06-05 23:16:24 vladimir%pobox.com Exp $
/* $Id: cairo-scaled-font.c,v 1.10 2006-07-13 20:19:37 vladimir%pobox.com Exp $
*
* Copyright © 2005 Keith Packard
*
@ -37,6 +37,7 @@
*/
#include "cairoint.h"
#include "cairo-scaled-font-test.h"
static cairo_bool_t
_cairo_scaled_glyph_keys_equal (const void *abstract_key_a, const void *abstract_key_b)
@ -61,7 +62,7 @@ _cairo_scaled_glyph_fini (cairo_scaled_glyph_t *scaled_glyph)
if (scaled_glyph->path != NULL)
_cairo_path_fixed_destroy (scaled_glyph->path);
}
static void
_cairo_scaled_glyph_destroy (void *abstract_glyph)
{
@ -94,7 +95,7 @@ static const cairo_scaled_font_t _cairo_scaled_font_nil = {
* @scaled_font: a scaled_font
* @status: a status value indicating an error, (eg. not
* CAIRO_STATUS_SUCCESS)
*
*
* Sets scaled_font->status to @status and calls _cairo_error;
*
* All assignments of an error status to scaled_font->status should happen
@ -121,8 +122,10 @@ _cairo_scaled_font_set_error (cairo_scaled_font_t *scaled_font,
/**
* cairo_scaled_font_get_type:
* @scaled_font: a #cairo_scaled_font_t
*
*
* Return value: The type of @scaled_font. See #cairo_font_type_t.
*
* Since: 1.2
**/
cairo_font_type_t
cairo_scaled_font_get_type (cairo_scaled_font_t *scaled_font)
@ -133,10 +136,10 @@ cairo_scaled_font_get_type (cairo_scaled_font_t *scaled_font)
/**
* cairo_scaled_font_status:
* @scaled_font: a #cairo_scaled_font_t
*
*
* Checks whether an error has previously occurred for this
* scaled_font.
*
*
* Return value: %CAIRO_STATUS_SUCCESS or another error such as
* %CAIRO_STATUS_NO_MEMORY.
**/
@ -168,7 +171,7 @@ cairo_scaled_font_status (cairo_scaled_font_t *scaled_font)
* of scaled fonts we keep around even when not otherwise referenced
*/
#define CAIRO_SCALED_FONT_MAX_HOLDOVERS 256
typedef struct _cairo_scaled_font_map {
cairo_hash_table_t *hash_table;
cairo_scaled_font_t *holdovers[CAIRO_SCALED_FONT_MAX_HOLDOVERS];
@ -247,7 +250,7 @@ _cairo_scaled_font_map_destroy (void)
}
/* Fowler / Noll / Vo (FNV) Hash (http://www.isthe.com/chongo/tech/comp/fnv/)
*
*
* Not necessarily better than a lot of other hashes, but should be OK, and
* well tested with binary data.
*/
@ -313,12 +316,26 @@ _cairo_scaled_font_keys_equal (const void *abstract_key_a, const void *abstract_
cairo_font_options_equal (&key_a->options, &key_b->options));
}
/* XXX: This 256 number is arbitary---we've never done any measurement
* of this. In fact, having a per-font glyph caches each managed
* separately is probably not waht we want anyway. Would probably be
* much better to have a single cache for glyphs with random
* replacement across all glyphs of all fonts. */
static int max_glyphs_cached_per_font = 256;
/* For internal testing purposes only. Not part of the supported API. */
void
_cairo_scaled_font_test_set_max_glyphs_cached_per_font (int max)
{
max_glyphs_cached_per_font = max;
}
/*
* Basic cairo_scaled_font_t object management
*/
cairo_status_t
_cairo_scaled_font_init (cairo_scaled_font_t *scaled_font,
_cairo_scaled_font_init (cairo_scaled_font_t *scaled_font,
cairo_font_face_t *font_face,
const cairo_matrix_t *font_matrix,
const cairo_matrix_t *ctm,
@ -338,31 +355,43 @@ _cairo_scaled_font_init (cairo_scaled_font_t *scaled_font,
scaled_font->glyphs = _cairo_cache_create (_cairo_scaled_glyph_keys_equal,
_cairo_scaled_glyph_destroy,
256);
max_glyphs_cached_per_font);
scaled_font->surface_backend = NULL;
scaled_font->surface_private = NULL;
scaled_font->backend = backend;
return CAIRO_STATUS_SUCCESS;
}
void
_cairo_scaled_font_freeze_cache (cairo_scaled_font_t *scaled_font)
{
_cairo_cache_freeze (scaled_font->glyphs);
}
void
_cairo_scaled_font_thaw_cache (cairo_scaled_font_t *scaled_font)
{
_cairo_cache_thaw (scaled_font->glyphs);
}
void
_cairo_scaled_font_set_metrics (cairo_scaled_font_t *scaled_font,
cairo_font_extents_t *fs_metrics)
{
double font_scale_x, font_scale_y;
_cairo_matrix_compute_scale_factors (&scaled_font->font_matrix,
&font_scale_x, &font_scale_y,
/* XXX */ 1);
/*
/*
* The font responded in unscaled units, scale by the font
* matrix scale factors to get to user space
*/
scaled_font->extents.ascent = fs_metrics->ascent * font_scale_y;
scaled_font->extents.descent = fs_metrics->descent * font_scale_y;
scaled_font->extents.height = fs_metrics->height * font_scale_y;
@ -378,7 +407,7 @@ _cairo_scaled_font_fini (cairo_scaled_font_t *scaled_font)
if (scaled_font->glyphs != NULL)
_cairo_cache_destroy (scaled_font->glyphs);
if (scaled_font->surface_backend != NULL &&
scaled_font->surface_backend->scaled_font_fini != NULL)
scaled_font->surface_backend->scaled_font_fini (scaled_font);
@ -399,11 +428,11 @@ _cairo_scaled_font_fini (cairo_scaled_font_t *scaled_font)
* be used.
* @options: options to use when getting metrics for the font and
* rendering with it.
*
*
* Creates a #cairo_scaled_font_t object from a font face and matrices that
* describe the size of the font and the environment in which it will
* be used.
*
*
* Return value: a newly created #cairo_scaled_font_t. Destroy with
* cairo_scaled_font_destroy()
**/
@ -423,7 +452,7 @@ cairo_scaled_font_create (cairo_font_face_t *font_face,
font_map = _cairo_scaled_font_map_lock ();
if (font_map == NULL)
goto UNWIND;
_cairo_scaled_font_init_key (&key, font_face,
font_matrix, ctm, options);
@ -466,7 +495,7 @@ UNWIND:
* cairo_scaled_font_reference:
* @scaled_font: a #cairo_scaled_font_t, (may be NULL in which case
* this function does nothing)
*
*
* Increases the reference count on @scaled_font by one. This prevents
* @scaled_font from being destroyed until a matching call to
* cairo_scaled_font_destroy() is made.
@ -523,7 +552,7 @@ cairo_scaled_font_reference (cairo_scaled_font_t *scaled_font)
/**
* cairo_scaled_font_destroy:
* @scaled_font: a #cairo_scaled_font_t
*
*
* Decreases the reference count on @font by one. If the result
* is zero, then @font and all associated resources are freed.
* See cairo_scaled_font_reference().
@ -561,12 +590,12 @@ cairo_scaled_font_destroy (cairo_scaled_font_t *scaled_font)
lru = font_map->holdovers[0];
assert (lru->ref_count == 0);
_cairo_hash_table_remove (font_map->hash_table, &lru->hash_entry);
_cairo_scaled_font_fini (lru);
free (lru);
font_map->num_holdovers--;
memmove (&font_map->holdovers[0],
&font_map->holdovers[1],
@ -586,8 +615,8 @@ cairo_scaled_font_destroy (cairo_scaled_font_t *scaled_font)
* cairo_scaled_font_extents:
* @scaled_font: a #cairo_scaled_font_t
* @extents: a #cairo_font_extents_t which to store the retrieved extents.
*
* Gets the metrics for a #cairo_scaled_font_t.
*
* Gets the metrics for a #cairo_scaled_font_t.
**/
void
cairo_scaled_font_extents (cairo_scaled_font_t *scaled_font,
@ -616,6 +645,8 @@ cairo_scaled_font_extents (cairo_scaled_font_t *scaled_font,
* characters. In particular, trailing whitespace characters are
* likely to not affect the size of the rectangle, though they will
* affect the x_advance and y_advance values.
*
* Since: 1.2
**/
void
cairo_scaled_font_text_extents (cairo_scaled_font_t *scaled_font,
@ -655,7 +686,7 @@ cairo_scaled_font_text_extents (cairo_scaled_font_t *scaled_font,
**/
void
cairo_scaled_font_glyph_extents (cairo_scaled_font_t *scaled_font,
cairo_glyph_t *glyphs,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_text_extents_t *extents)
{
@ -674,14 +705,14 @@ cairo_scaled_font_glyph_extents (cairo_scaled_font_t *scaled_font,
extents->height = 0.0;
extents->x_advance = 0.0;
extents->y_advance = 0.0;
return;
}
for (i = 0; i < num_glyphs; i++) {
cairo_scaled_glyph_t *scaled_glyph;
double left, top, right, bottom;
status = _cairo_scaled_glyph_lookup (scaled_font,
glyphs[i].index,
CAIRO_SCALED_GLYPH_INFO_METRICS,
@ -690,12 +721,12 @@ cairo_scaled_font_glyph_extents (cairo_scaled_font_t *scaled_font,
_cairo_scaled_font_set_error (scaled_font, status);
return;
}
left = scaled_glyph->metrics.x_bearing + glyphs[i].x;
right = left + scaled_glyph->metrics.width;
top = scaled_glyph->metrics.y_bearing + glyphs[i].y;
bottom = top + scaled_glyph->metrics.height;
if (i == 0) {
min_x = left;
max_x = right;
@ -723,8 +754,8 @@ cairo_status_t
_cairo_scaled_font_text_to_glyphs (cairo_scaled_font_t *scaled_font,
double x,
double y,
const char *utf8,
cairo_glyph_t **glyphs,
const char *utf8,
cairo_glyph_t **glyphs,
int *num_glyphs)
{
size_t i;
@ -752,12 +783,12 @@ _cairo_scaled_font_text_to_glyphs (cairo_scaled_font_t *scaled_font,
goto FAIL;
}
for (i = 0; i < *num_glyphs; i++) {
for (i = 0; i < *num_glyphs; i++) {
(*glyphs)[i].index = (*scaled_font->backend->
ucs4_to_index) (scaled_font, ucs4[i]);
(*glyphs)[i].x = x;
(*glyphs)[i].y = y;
status = _cairo_scaled_glyph_lookup (scaled_font,
(*glyphs)[i].index,
CAIRO_SCALED_GLYPH_INFO_METRICS,
@ -767,14 +798,14 @@ _cairo_scaled_font_text_to_glyphs (cairo_scaled_font_t *scaled_font,
*glyphs = NULL;
goto FAIL;
}
x += scaled_glyph->metrics.x_advance;
y += scaled_glyph->metrics.y_advance;
}
FAIL:
free (ucs4);
return status;
}
@ -785,12 +816,12 @@ cairo_status_t
_cairo_scaled_font_glyph_device_extents (cairo_scaled_font_t *scaled_font,
const cairo_glyph_t *glyphs,
int num_glyphs,
cairo_rectangle_fixed_t *extents)
cairo_rectangle_int16_t *extents)
{
cairo_status_t status = CAIRO_STATUS_SUCCESS;
int i;
int min_x = CAIRO_MAXSHORT, max_x = CAIRO_MINSHORT;
int min_y = CAIRO_MAXSHORT, max_y = CAIRO_MINSHORT;
int min_x = INT16_MAX, max_x = INT16_MIN;
int min_y = INT16_MAX, max_y = INT16_MAX;
if (scaled_font->status)
return scaled_font->status;
@ -800,7 +831,7 @@ _cairo_scaled_font_glyph_device_extents (cairo_scaled_font_t *scaled_font,
int left, top;
int right, bottom;
int x, y;
status = _cairo_scaled_glyph_lookup (scaled_font,
glyphs[i].index,
CAIRO_SCALED_GLYPH_INFO_METRICS,
@ -809,16 +840,16 @@ _cairo_scaled_font_glyph_device_extents (cairo_scaled_font_t *scaled_font,
_cairo_scaled_font_set_error (scaled_font, status);
return status;
}
/* glyph images are snapped to pixel locations */
x = (int) floor (glyphs[i].x + 0.5);
y = (int) floor (glyphs[i].y + 0.5);
left = x + _cairo_fixed_integer_floor(scaled_glyph->bbox.p1.x);
top = y + _cairo_fixed_integer_floor (scaled_glyph->bbox.p1.y);
right = x + _cairo_fixed_integer_ceil(scaled_glyph->bbox.p2.x);
bottom = y + _cairo_fixed_integer_ceil (scaled_glyph->bbox.p2.y);
if (left < min_x) min_x = left;
if (right > max_x) max_x = right;
if (top < min_y) min_y = top;
@ -858,13 +889,13 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
* they are implemented in terms of other operators in cairo-gstate.c
*/
assert (op != CAIRO_OPERATOR_SOURCE && op != CAIRO_OPERATOR_CLEAR);
if (scaled_font->status)
return scaled_font->status;
if (scaled_font->backend->show_glyphs != NULL) {
status = scaled_font->backend->show_glyphs (scaled_font,
op, pattern,
op, pattern,
surface,
source_x, source_y,
dest_x, dest_y,
@ -875,7 +906,7 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
}
/* Font display routine either does not exist or failed. */
status = CAIRO_STATUS_SUCCESS;
_cairo_cache_freeze (scaled_font->glyphs);
@ -885,7 +916,7 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
cairo_surface_pattern_t glyph_pattern;
cairo_image_surface_t *glyph_surface;
cairo_scaled_glyph_t *scaled_glyph;
status = _cairo_scaled_glyph_lookup (scaled_font,
glyphs[i].index,
CAIRO_SCALED_GLYPH_INFO_SURFACE,
@ -893,7 +924,7 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
if (status)
goto CLEANUP_MASK;
glyph_surface = scaled_glyph->surface;
/* Create the mask using the format from the first glyph */
@ -917,25 +948,26 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
pixman_image, TRUE);
}
/* round glyph locations to the nearest pixel */
x = (int) floor (glyphs[i].x +
glyph_surface->base.device_x_offset +
/* XXX: FRAGILE: We're ignoring device_transform scaling here. A bug? */
x = (int) floor (glyphs[i].x +
glyph_surface->base.device_transform.x0 +
0.5);
y = (int) floor (glyphs[i].y +
glyph_surface->base.device_y_offset +
glyph_surface->base.device_transform.y0 +
0.5);
_cairo_pattern_init_for_surface (&glyph_pattern, &glyph_surface->base);
status = _cairo_surface_composite (CAIRO_OPERATOR_ADD,
&glyph_pattern.base,
status = _cairo_surface_composite (CAIRO_OPERATOR_ADD,
&glyph_pattern.base,
NULL,
mask,
0, 0,
0, 0,
x - dest_x,
y - dest_y,
0, 0,
x - dest_x,
y - dest_y,
glyph_surface->width,
glyph_surface->height);
@ -943,25 +975,25 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
if (status)
break;
}
if (mask != NULL) {
cairo_surface_pattern_t mask_pattern;
_cairo_pattern_init_for_surface (&mask_pattern, mask);
status = _cairo_surface_composite (op, pattern, &mask_pattern.base,
surface,
source_x, source_y,
source_x, source_y,
0, 0,
dest_x, dest_y,
width, height);
_cairo_pattern_fini (&mask_pattern.base);
}
CLEANUP_MASK:
_cairo_cache_thaw (scaled_font->glyphs);
if (mask != NULL)
cairo_surface_destroy (mask);
return status;
@ -1009,7 +1041,6 @@ _scaled_glyph_path_curve_to (void *abstract_closure,
p2->y + closure->offset.y);
}
static cairo_status_t
_scaled_glyph_path_close_path (void *abstract_closure)
{
@ -1020,21 +1051,21 @@ _scaled_glyph_path_close_path (void *abstract_closure)
cairo_status_t
_cairo_scaled_font_glyph_path (cairo_scaled_font_t *scaled_font,
const cairo_glyph_t *glyphs,
const cairo_glyph_t *glyphs,
int num_glyphs,
cairo_path_fixed_t *path)
{
cairo_status_t status;
int i;
cairo_scaled_glyph_path_closure_t closure;
if (scaled_font->status)
return scaled_font->status;
closure.path = path;
for (i = 0; i < num_glyphs; i++) {
cairo_scaled_glyph_t *scaled_glyph;
status = _cairo_scaled_glyph_lookup (scaled_font,
glyphs[i].index,
CAIRO_SCALED_GLYPH_INFO_PATH,
@ -1044,7 +1075,7 @@ _cairo_scaled_font_glyph_path (cairo_scaled_font_t *scaled_font,
closure.offset.x = _cairo_fixed_from_double (glyphs[i].x);
closure.offset.y = _cairo_fixed_from_double (glyphs[i].y);
status = _cairo_path_fixed_interpret (scaled_glyph->path,
CAIRO_DIRECTION_FORWARD,
_scaled_glyph_path_move_to,
@ -1053,7 +1084,7 @@ _cairo_scaled_font_glyph_path (cairo_scaled_font_t *scaled_font,
_scaled_glyph_path_close_path,
&closure);
}
return CAIRO_STATUS_SUCCESS;
}
@ -1062,9 +1093,9 @@ _cairo_scaled_font_glyph_path (cairo_scaled_font_t *scaled_font,
* @scaled_glyph: a #cairo_scaled_glyph_t
* @scaled_font: a #cairo_scaled_font_t
* @fs_metrics: a #cairo_text_extents_t in font space
*
*
* _cairo_scaled_glyph_set_metrics() stores user space metrics
* for the specified glyph given font space metrics. It is
* for the specified glyph given font space metrics. It is
* called by the font backend when initializing a glyph with
* CAIRO_SCALED_GLYPH_INFO_METRICS.
**/
@ -1077,7 +1108,7 @@ _cairo_scaled_glyph_set_metrics (cairo_scaled_glyph_t *scaled_glyph,
double hm, wm;
double min_user_x = 0.0, max_user_x = 0.0, min_user_y = 0.0, max_user_y = 0.0;
double min_device_x = 0.0, max_device_x = 0.0, min_device_y = 0.0, max_device_y = 0.0;
for (hm = 0.0; hm <= 1.0; hm += 1.0)
for (wm = 0.0; wm <= 1.0; wm += 1.0) {
double x, y;
@ -1102,7 +1133,7 @@ _cairo_scaled_glyph_set_metrics (cairo_scaled_glyph_t *scaled_glyph,
y = fs_metrics->y_bearing + fs_metrics->height * hm;
cairo_matrix_transform_distance (&scaled_font->scale,
&x, &y);
if (first) {
min_device_x = max_device_x = x;
min_device_y = max_device_y = y;
@ -1159,7 +1190,7 @@ _cairo_scaled_glyph_set_path (cairo_scaled_glyph_t *scaled_glyph,
* the glyph should be filled in.
* @scaled_glyph_ret: a #cairo_scaled_glyph_t * where the glyph
* is returned.
*
*
* Returns a glyph with the requested portions filled in. Glyph
* lookup is cached and glyph will be automatically freed along
* with the scaled_font so no explicit free is required.
@ -1167,8 +1198,12 @@ _cairo_scaled_glyph_set_path (cairo_scaled_glyph_t *scaled_glyph,
* %CAIRO_SCALED_GLYPH_INFO_METRICS - glyph metrics and bounding box
* %CAIRO_SCALED_GLYPH_INFO_SURFACE - surface holding glyph image
* %CAIRO_SCALED_GLYPH_INFO_PATH - path holding glyph outline in device space
*
* If the desired info is not available, (for example, when trying to
* get INFO_PATH with a bitmapped font), this function will return
* CAIRO_INT_STATUS_UNSUPPORTED.
**/
cairo_status_t
cairo_int_status_t
_cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
unsigned long index,
cairo_scaled_glyph_info_t info,
@ -1178,7 +1213,7 @@ _cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
cairo_cache_entry_t key;
cairo_scaled_glyph_t *scaled_glyph;
cairo_scaled_glyph_info_t need_info;
if (scaled_font->status)
return scaled_font->status;
@ -1189,8 +1224,8 @@ _cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
* Check cache for glyph
*/
info |= CAIRO_SCALED_GLYPH_INFO_METRICS;
if (!_cairo_cache_lookup (scaled_font->glyphs, &key,
(cairo_cache_entry_t **) &scaled_glyph))
if (!_cairo_cache_lookup (scaled_font->glyphs, &key,
(cairo_cache_entry_t **) &scaled_glyph))
{
/*
* On miss, create glyph and insert into cache
@ -1200,14 +1235,14 @@ _cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
status = CAIRO_STATUS_NO_MEMORY;
goto CLEANUP;
}
_cairo_scaled_glyph_set_index(scaled_glyph, index);
scaled_glyph->cache_entry.size = 1; /* XXX */
scaled_glyph->scaled_font = scaled_font;
scaled_glyph->surface = NULL;
scaled_glyph->path = NULL;
scaled_glyph->surface_private = NULL;
/* ask backend to initialize metrics and shape fields */
status = (*scaled_font->backend->
scaled_glyph_init) (scaled_font, scaled_glyph, info);
@ -1229,14 +1264,14 @@ _cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
* already has the requested data and ammend it if not
*/
need_info = 0;
if ((info & CAIRO_SCALED_GLYPH_INFO_SURFACE) != 0 &&
if ((info & CAIRO_SCALED_GLYPH_INFO_SURFACE) != 0 &&
scaled_glyph->surface == NULL)
need_info |= CAIRO_SCALED_GLYPH_INFO_SURFACE;
if (((info & CAIRO_SCALED_GLYPH_INFO_PATH) != 0 &&
scaled_glyph->path == NULL))
need_info |= CAIRO_SCALED_GLYPH_INFO_PATH;
if (need_info) {
status = (*scaled_font->backend->
scaled_glyph_init) (scaled_font, scaled_glyph, need_info);
@ -1246,7 +1281,9 @@ _cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
CLEANUP:
if (status) {
_cairo_scaled_font_set_error (scaled_font, status);
/* It's not an error for the backend to not support the info we want. */
if (status != CAIRO_INT_STATUS_UNSUPPORTED)
_cairo_scaled_font_set_error (scaled_font, status);
*scaled_glyph_ret = NULL;
} else {
*scaled_glyph_ret = scaled_glyph;
@ -1260,9 +1297,11 @@ _cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
/**
* cairo_scaled_font_get_font_face:
* @scaled_font: a #cairo_scaled_font_t
*
*
* Return value: The #cairo_font_face_t with which @scaled_font was
* created.
*
* Since: 1.2
**/
cairo_font_face_t *
cairo_scaled_font_get_font_face (cairo_scaled_font_t *scaled_font)
@ -1277,9 +1316,11 @@ cairo_scaled_font_get_font_face (cairo_scaled_font_t *scaled_font)
* cairo_scaled_font_get_font_matrix:
* @scaled_font: a #cairo_scaled_font_t
* @font_matrix: return value for the matrix
*
*
* Stores the font matrix with which @scaled_font was created into
* @matrix.
*
* Since: 1.2
**/
void
cairo_scaled_font_get_font_matrix (cairo_scaled_font_t *scaled_font,
@ -1297,8 +1338,10 @@ cairo_scaled_font_get_font_matrix (cairo_scaled_font_t *scaled_font,
* cairo_scaled_font_get_ctm:
* @scaled_font: a #cairo_scaled_font_t
* @ctm: return value for the CTM
*
*
* Stores the CTM with which @scaled_font was created into @ctm.
*
* Since: 1.2
**/
void
cairo_scaled_font_get_ctm (cairo_scaled_font_t *scaled_font,
@ -1316,9 +1359,11 @@ cairo_scaled_font_get_ctm (cairo_scaled_font_t *scaled_font,
* cairo_scaled_font_get_font_options:
* @scaled_font: a #cairo_scaled_font_t
* @options: return value for the font options
*
*
* Stores the font options with which @scaled_font was created into
* @ctm.
* @options.
*
* Since: 1.2
**/
void
cairo_scaled_font_get_font_options (cairo_scaled_font_t *scaled_font,

Просмотреть файл

@ -59,7 +59,7 @@ _cairo_slope_compare (cairo_slope_t *a, cairo_slope_t *b)
{
cairo_fixed_48_16_t diff;
diff = ((cairo_fixed_48_16_t) a->dy * (cairo_fixed_48_16_t) b->dx
diff = ((cairo_fixed_48_16_t) a->dy * (cairo_fixed_48_16_t) b->dx
- (cairo_fixed_48_16_t) b->dy * (cairo_fixed_48_16_t) a->dx);
if (diff > 0)
@ -97,7 +97,3 @@ _cairo_slope_counter_clockwise (cairo_slope_t *a, cairo_slope_t *b)
{
return ! _cairo_slope_clockwise (a, b);
}

Просмотреть файл

@ -256,7 +256,7 @@ _cairo_spline_decompose_into (cairo_spline_t *spline, double tolerance_squared,
status = _cairo_spline_decompose_into (&s1, tolerance_squared, result);
if (status)
return status;
status = _cairo_spline_decompose_into (&s2, tolerance_squared, result);
if (status)
return status;
@ -283,4 +283,3 @@ _cairo_spline_decompose (cairo_spline_t *spline, double tolerance)
return CAIRO_STATUS_SUCCESS;
}

Просмотреть файл

@ -84,4 +84,3 @@ _cairo_stroke_style_fini (cairo_stroke_style_t *style)
}
style->num_dashes = 0;
}

Просмотреть файл

@ -99,7 +99,7 @@ cairo_private cairo_status_t
_cairo_surface_fallback_fill_rectangles (cairo_surface_t *surface,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects);
cairo_private cairo_status_t

Просмотреть файл

@ -40,18 +40,18 @@
typedef struct {
cairo_surface_t *dst;
cairo_rectangle_fixed_t extents;
cairo_rectangle_int16_t extents;
cairo_image_surface_t *image;
cairo_rectangle_fixed_t image_rect;
cairo_rectangle_int16_t image_rect;
void *image_extra;
} fallback_state_t;
/**
* _fallback_init:
*
*
* Acquire destination image surface needed for an image-based
* fallback.
*
*
* Return value: CAIRO_INT_STATUS_NOTHING_TO_DO if the extents are not
* visible, CAIRO_STATUS_SUCCESS if some portion is visible and all
* went well, or some error status otherwise.
@ -70,7 +70,7 @@ _fallback_init (fallback_state_t *state,
state->extents.y = y;
state->extents.width = width;
state->extents.height = height;
state->dst = dst;
status = _cairo_surface_acquire_dest_image (dst, &state->extents,
@ -104,7 +104,7 @@ typedef cairo_status_t (*cairo_draw_func_t) (void *clos
cairo_surface_t *dst,
int dst_x,
int dst_y,
const cairo_rectangle_fixed_t *extents);
const cairo_rectangle_int16_t *extents);
static cairo_status_t
_create_composite_mask_pattern (cairo_surface_pattern_t *mask_pattern,
@ -112,18 +112,18 @@ _create_composite_mask_pattern (cairo_surface_pattern_t *mask_pattern,
cairo_draw_func_t draw_func,
void *draw_closure,
cairo_surface_t *dst,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_surface_t *mask;
cairo_status_t status;
mask = cairo_surface_create_similar (dst,
CAIRO_CONTENT_ALPHA,
extents->width,
extents->height);
if (mask->status)
return CAIRO_STATUS_NO_MEMORY;
status = (*draw_func) (draw_closure, CAIRO_OPERATOR_ADD,
NULL, mask,
extents->x, extents->y,
@ -138,7 +138,7 @@ _create_composite_mask_pattern (cairo_surface_pattern_t *mask_pattern,
extents);
if (status)
goto CLEANUP_SURFACE;
_cairo_pattern_init_for_surface (mask_pattern, mask);
CLEANUP_SURFACE:
@ -157,7 +157,7 @@ _clip_and_composite_with_mask (cairo_clip_t *clip,
cairo_draw_func_t draw_func,
void *draw_closure,
cairo_surface_t *dst,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_surface_pattern_t mask_pattern;
cairo_status_t status;
@ -168,7 +168,7 @@ _clip_and_composite_with_mask (cairo_clip_t *clip,
dst, extents);
if (status)
return status;
status = _cairo_surface_composite (op,
src, &mask_pattern.base, dst,
extents->x, extents->y,
@ -191,7 +191,7 @@ _clip_and_composite_combine (cairo_clip_t *clip,
cairo_draw_func_t draw_func,
void *draw_closure,
cairo_surface_t *dst,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_surface_t *intermediate;
cairo_surface_pattern_t dst_pattern;
@ -237,7 +237,7 @@ _clip_and_composite_combine (cairo_clip_t *clip,
*/
status = _cairo_clip_combine_to_surface (clip, CAIRO_OPERATOR_DEST_IN,
intermediate,
extents->x, extents->y,
extents->x, extents->y,
extents);
if (status)
goto CLEANUP_SURFACE;
@ -254,7 +254,7 @@ _clip_and_composite_combine (cairo_clip_t *clip,
/* Now add the two results together
*/
_cairo_pattern_init_for_surface (&intermediate_pattern, intermediate);
status = _cairo_surface_composite (CAIRO_OPERATOR_ADD,
&intermediate_pattern.base, NULL, dst,
0, 0,
@ -263,7 +263,7 @@ _clip_and_composite_combine (cairo_clip_t *clip,
extents->width, extents->height);
_cairo_pattern_fini (&intermediate_pattern.base);
CLEANUP_SURFACE:
cairo_surface_destroy (intermediate);
@ -279,7 +279,7 @@ _clip_and_composite_source (cairo_clip_t *clip,
cairo_draw_func_t draw_func,
void *draw_closure,
cairo_surface_t *dst,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_surface_pattern_t mask_pattern;
cairo_status_t status;
@ -292,7 +292,7 @@ _clip_and_composite_source (cairo_clip_t *clip,
dst, extents);
if (status)
return status;
/* Compute dest' = dest OUT (mask IN clip)
*/
status = _cairo_surface_composite (CAIRO_OPERATOR_DEST_OUT,
@ -320,7 +320,7 @@ _clip_and_composite_source (cairo_clip_t *clip,
}
static int
_cairo_rectangle_empty (const cairo_rectangle_fixed_t *rect)
_cairo_rectangle_empty (const cairo_rectangle_int16_t *rect)
{
return rect->width == 0 || rect->height == 0;
}
@ -343,7 +343,7 @@ _cairo_rectangle_empty (const cairo_rectangle_fixed_t *rect)
*
* @draw_func is to called to draw the mask; it will be called no more
* than once.
*
*
* Return value: %CAIRO_STATUS_SUCCESS if the drawing succeeded.
**/
static cairo_status_t
@ -353,7 +353,7 @@ _clip_and_composite (cairo_clip_t *clip,
cairo_draw_func_t draw_func,
void *draw_closure,
cairo_surface_t *dst,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_pattern_union_t solid_pattern;
cairo_status_t status;
@ -408,7 +408,7 @@ _composite_trap_region (cairo_clip_t *clip,
cairo_operator_t op,
cairo_surface_t *dst,
pixman_region16_t *trap_region,
cairo_rectangle_fixed_t *extents)
cairo_rectangle_int16_t *extents)
{
cairo_status_t status;
cairo_pattern_union_t solid_pattern;
@ -425,11 +425,11 @@ _composite_trap_region (cairo_clip_t *clip,
if (num_rects == 0)
return CAIRO_STATUS_SUCCESS;
if (num_rects > 1) {
if (_cairo_surface_get_clip_mode (dst) != CAIRO_CLIP_MODE_REGION)
return CAIRO_INT_STATUS_UNSUPPORTED;
clip_serial = _cairo_surface_allocate_clip_serial (dst);
status = _cairo_surface_set_clip_region (dst,
trap_region,
@ -437,10 +437,10 @@ _composite_trap_region (cairo_clip_t *clip,
if (status)
return status;
}
if (clip_surface)
_cairo_pattern_init_for_surface (&mask.surface, clip_surface);
status = _cairo_surface_composite (op,
src,
clip_surface ? &mask.base : NULL,
@ -476,19 +476,19 @@ _composite_traps_draw_func (void *closure,
cairo_surface_t *dst,
int dst_x,
int dst_y,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_composite_traps_info_t *info = closure;
cairo_pattern_union_t pattern;
cairo_status_t status;
if (dst_x != 0 || dst_y != 0)
_cairo_traps_translate (info->traps, - dst_x, - dst_y);
_cairo_pattern_init_solid (&pattern.solid, CAIRO_COLOR_WHITE);
if (!src)
src = &pattern.base;
status = _cairo_surface_composite_trapezoids (op,
src, dst, info->antialias,
extents->x, extents->y,
@ -513,9 +513,9 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
cairo_status_t status;
pixman_region16_t *trap_region;
pixman_region16_t *clear_region = NULL;
cairo_rectangle_fixed_t extents;
cairo_rectangle_int16_t extents;
cairo_composite_traps_info_t traps_info;
if (traps->num_traps == 0)
return CAIRO_STATUS_SUCCESS;
@ -538,11 +538,11 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
else
{
cairo_surface_t *clip_surface = clip ? clip->surface : NULL;
status = _cairo_surface_get_extents (dst, &extents);
if (status)
return status;
if (trap_region && !clip_surface) {
/* If we optimize drawing with an unbounded operator to
* _cairo_surface_fill_rectangles() or to drawing with a
@ -551,7 +551,7 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
status = _cairo_surface_get_extents (dst, &extents);
if (status)
return status;
clear_region = _cairo_region_create_from_rectangle (&extents);
if (clear_region == NULL)
return CAIRO_STATUS_NO_MEMORY;
@ -559,12 +559,12 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
status = _cairo_clip_intersect_to_region (clip, clear_region);
if (status)
return status;
_cairo_region_extents_rectangle (clear_region, &extents);
if (pixman_region_subtract (clear_region, clear_region, trap_region) != PIXMAN_REGION_STATUS_SUCCESS)
return CAIRO_STATUS_NO_MEMORY;
if (!pixman_region_not_empty (clear_region)) {
pixman_region_destroy (clear_region);
clear_region = NULL;
@ -575,14 +575,14 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
return status;
}
}
if (status)
goto out;
if (trap_region)
{
cairo_surface_t *clip_surface = clip ? clip->surface : NULL;
if ((src->type == CAIRO_PATTERN_TYPE_SOLID || op == CAIRO_OPERATOR_CLEAR) &&
!clip_surface)
{
@ -592,7 +592,7 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
color = CAIRO_COLOR_TRANSPARENT;
else
color = &((cairo_solid_pattern_t *)src)->color;
/* Solid rectangles special case */
status = _cairo_surface_fill_region (dst, op, color, trap_region);
if (!status && clear_region)
@ -646,7 +646,7 @@ _clip_and_composite_trapezoids (cairo_pattern_t *src,
pixman_region_destroy (trap_region);
if (clear_region)
pixman_region_destroy (clear_region);
return status;
}
@ -656,7 +656,7 @@ _cairo_surface_fallback_paint (cairo_surface_t *surface,
cairo_pattern_t *source)
{
cairo_status_t status;
cairo_rectangle_fixed_t extents;
cairo_rectangle_int16_t extents;
cairo_box_t box;
cairo_traps_t traps;
@ -665,14 +665,14 @@ _cairo_surface_fallback_paint (cairo_surface_t *surface,
return status;
if (_cairo_operator_bounded_by_source (op)) {
cairo_rectangle_fixed_t source_extents;
cairo_rectangle_int16_t source_extents;
status = _cairo_pattern_get_extents (source, &source_extents);
if (status)
return status;
_cairo_rectangle_intersect (&extents, &source_extents);
}
status = _cairo_clip_intersect_to_rectangle (surface->clip, &extents);
if (status)
return status;
@ -685,7 +685,7 @@ _cairo_surface_fallback_paint (cairo_surface_t *surface,
status = _cairo_traps_init_box (&traps, &box);
if (status)
return status;
_clip_and_composite_trapezoids (source,
op,
surface,
@ -705,7 +705,7 @@ _cairo_surface_mask_draw_func (void *closure,
cairo_surface_t *dst,
int dst_x,
int dst_y,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_pattern_t *mask = closure;
@ -732,7 +732,7 @@ _cairo_surface_fallback_mask (cairo_surface_t *surface,
cairo_pattern_t *mask)
{
cairo_status_t status;
cairo_rectangle_fixed_t extents, source_extents, mask_extents;
cairo_rectangle_int16_t extents, source_extents, mask_extents;
status = _cairo_surface_get_extents (surface, &extents);
if (status)
@ -745,7 +745,7 @@ _cairo_surface_fallback_mask (cairo_surface_t *surface,
_cairo_rectangle_intersect (&extents, &source_extents);
}
if (_cairo_operator_bounded_by_mask (op)) {
status = _cairo_pattern_get_extents (mask, &mask_extents);
if (status)
@ -781,7 +781,7 @@ _cairo_surface_fallback_stroke (cairo_surface_t *surface,
{
cairo_status_t status;
cairo_traps_t traps;
_cairo_traps_init (&traps);
status = _cairo_path_fixed_stroke_to_traps (path,
@ -854,7 +854,7 @@ _cairo_surface_old_show_glyphs_draw_func (void *closure
cairo_surface_t *dst,
int dst_x,
int dst_y,
const cairo_rectangle_fixed_t *extents)
const cairo_rectangle_int16_t *extents)
{
cairo_show_glyphs_info_t *glyph_info = closure;
cairo_pattern_union_t pattern;
@ -866,7 +866,7 @@ _cairo_surface_old_show_glyphs_draw_func (void *closure
*/
if (dst_x != 0 || dst_y != 0) {
int i;
for (i = 0; i < glyph_info->num_glyphs; ++i)
{
((cairo_glyph_t *) glyph_info->glyphs)[i].x -= dst_x;
@ -877,8 +877,8 @@ _cairo_surface_old_show_glyphs_draw_func (void *closure
_cairo_pattern_init_solid (&pattern.solid, CAIRO_COLOR_WHITE);
if (!src)
src = &pattern.base;
status = _cairo_surface_old_show_glyphs (glyph_info->font, op, src,
status = _cairo_surface_old_show_glyphs (glyph_info->font, op, src,
dst,
extents->x, extents->y,
extents->x - dst_x,
@ -890,9 +890,9 @@ _cairo_surface_old_show_glyphs_draw_func (void *closure
if (status != CAIRO_INT_STATUS_UNSUPPORTED)
return status;
status = _cairo_scaled_font_show_glyphs (glyph_info->font,
op,
status = _cairo_scaled_font_show_glyphs (glyph_info->font,
op,
src, dst,
extents->x, extents->y,
extents->x - dst_x,
@ -916,7 +916,7 @@ _cairo_surface_fallback_show_glyphs (cairo_surface_t *surface,
cairo_scaled_font_t *scaled_font)
{
cairo_status_t status;
cairo_rectangle_fixed_t extents, glyph_extents;
cairo_rectangle_int16_t extents, glyph_extents;
cairo_show_glyphs_info_t glyph_info;
status = _cairo_surface_get_extents (surface, &extents);
@ -925,23 +925,23 @@ _cairo_surface_fallback_show_glyphs (cairo_surface_t *surface,
if (_cairo_operator_bounded_by_mask (op)) {
status = _cairo_scaled_font_glyph_device_extents (scaled_font,
glyphs,
num_glyphs,
glyphs,
num_glyphs,
&glyph_extents);
if (status)
return status;
_cairo_rectangle_intersect (&extents, &glyph_extents);
}
status = _cairo_clip_intersect_to_rectangle (surface->clip, &extents);
if (status)
return status;
glyph_info.font = scaled_font;
glyph_info.glyphs = glyphs;
glyph_info.num_glyphs = num_glyphs;
status = _clip_and_composite (surface->clip,
op,
source,
@ -949,7 +949,7 @@ _cairo_surface_fallback_show_glyphs (cairo_surface_t *surface,
&glyph_info,
surface,
&extents);
return status;
}
@ -990,8 +990,8 @@ _cairo_surface_fallback_snapshot (cairo_surface_t *surface)
_cairo_surface_release_source_image (surface,
image, &image_extra);
snapshot->device_x_offset = surface->device_x_offset;
snapshot->device_y_offset = surface->device_y_offset;
snapshot->device_transform = surface->device_transform;
snapshot->device_transform_inverse = surface->device_transform_inverse;
snapshot->is_snapshot = TRUE;
@ -1042,11 +1042,11 @@ cairo_status_t
_cairo_surface_fallback_fill_rectangles (cairo_surface_t *surface,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects)
{
fallback_state_t state;
cairo_rectangle_fixed_t *offset_rects = NULL;
cairo_rectangle_int16_t *offset_rects = NULL;
cairo_status_t status;
int x1, y1, x2, y2;
int i;
@ -1063,7 +1063,7 @@ _cairo_surface_fallback_fill_rectangles (cairo_surface_t *surface,
y1 = rects[0].y;
x2 = rects[0].x + rects[0].width;
y2 = rects[0].y + rects[0].height;
for (i = 1; i < num_rects; i++) {
if (rects[i].x < x1)
x1 = rects[i].x;
@ -1084,9 +1084,9 @@ _cairo_surface_fallback_fill_rectangles (cairo_surface_t *surface,
}
/* If the fetched image isn't at 0,0, we need to offset the rectangles */
if (state.image_rect.x != 0 || state.image_rect.y != 0) {
offset_rects = malloc (sizeof (cairo_rectangle_fixed_t) * num_rects);
offset_rects = malloc (sizeof (cairo_rectangle_int16_t) * num_rects);
if (offset_rects == NULL) {
status = CAIRO_STATUS_NO_MEMORY;
goto DONE;
@ -1140,7 +1140,7 @@ _cairo_surface_fallback_composite_trapezoids (cairo_operator_t op,
}
/* If the destination image isn't at 0,0, we need to offset the trapezoids */
if (state.image_rect.x != 0 || state.image_rect.y != 0) {
offset_traps = malloc (sizeof (cairo_trapezoid_t) * num_traps);
if (!offset_traps) {
@ -1166,6 +1166,6 @@ _cairo_surface_fallback_composite_trapezoids (cairo_operator_t op,
DONE:
_fallback_fini (&state);
return status;
}

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

Просмотреть файл

@ -1,7 +1,7 @@
/* cairo - a vector graphics library with display and print output
*
* cairo-svg.h
*
*
* Copyright © 2005 Emmanuel Pacaud <emmanuel.pacaud@univ-poitiers.fr>
*
* This library is free software; you can redistribute it and/or
@ -38,10 +38,17 @@
CAIRO_BEGIN_DECLS
/**
* cairo_svg_version_t
* @CAIRO_SVG_VERSION_1_1: The version 1.1 of the SVG specification.
* @CAIRO_SVG_VERSION_1_2: The version 1.2 of the SVG specification.
*
* #cairo_svg_version_t is used to describe the version number of the SVG
* specification that a generated SVG file will conform to.
*/
typedef enum {
CAIRO_SVG_VERSION_1_1 = 0,
CAIRO_SVG_VERSION_1_2,
CAIRO_SVG_VERSION_LAST
CAIRO_SVG_VERSION_1_1,
CAIRO_SVG_VERSION_1_2
} cairo_svg_version_t;
cairo_public cairo_surface_t *
@ -55,11 +62,6 @@ cairo_svg_surface_create_for_stream (cairo_write_func_t write_func,
double width_in_points,
double height_in_points);
cairo_public void
cairo_svg_surface_set_dpi (cairo_surface_t *surface,
double x_dpi,
double y_dpi);
cairo_public void
cairo_svg_surface_restrict_to_version (cairo_surface_t *surface,
cairo_svg_version_t version);

Просмотреть файл

@ -73,8 +73,8 @@ _cairo_traps_init (cairo_traps_t *traps)
traps->traps_size = 0;
traps->traps = NULL;
traps->extents.p1.x = traps->extents.p1.y = CAIRO_MAXSHORT << 16;
traps->extents.p2.x = traps->extents.p2.y = CAIRO_MINSHORT << 16;
traps->extents.p1.x = traps->extents.p1.y = INT16_MAX << 16;
traps->extents.p2.x = traps->extents.p2.y = INT16_MIN << 16;
}
void
@ -93,7 +93,7 @@ _cairo_traps_fini (cairo_traps_t *traps)
* @traps: a #cairo_traps_t
* @box: a box that will be converted to a single trapezoid
* to store in @traps.
*
*
* Initializes a cairo_traps_t to contain a single rectangular
* trapezoid.
**/
@ -102,13 +102,13 @@ _cairo_traps_init_box (cairo_traps_t *traps,
cairo_box_t *box)
{
cairo_status_t status;
_cairo_traps_init (traps);
status = _cairo_traps_grow_by (traps, 1);
if (status)
return status;
traps->num_traps = 1;
traps->traps[0].top = box->p1.y;
@ -165,12 +165,12 @@ _cairo_traps_add_trap (cairo_traps_t *traps, cairo_fixed_t top, cairo_fixed_t bo
traps->extents.p1.x = left->p1.x;
if (left->p2.x < traps->extents.p1.x)
traps->extents.p1.x = left->p2.x;
if (right->p1.x > traps->extents.p2.x)
traps->extents.p2.x = right->p1.x;
if (right->p2.x > traps->extents.p2.x)
traps->extents.p2.x = right->p2.x;
traps->num_traps++;
return CAIRO_STATUS_SUCCESS;
@ -540,7 +540,7 @@ _line_segs_intersect_ceil (cairo_line_t *l1, cairo_line_t *l2, cairo_fixed_t *y_
dy2 = l2->p1.y - l2->p2.y;
den_det = _det16_32 (dx1, dy1,
dx2, dy2);
if (_cairo_int64_eq (den_det, _cairo_int32_to_int64(0)))
return 0;
@ -549,26 +549,25 @@ _line_segs_intersect_ceil (cairo_line_t *l1, cairo_line_t *l2, cairo_fixed_t *y_
l2_det = _det16_32 (l2->p1.x, l2->p1.y,
l2->p2.x, l2->p2.y);
num_det = _det32_64 (l1_det, _fixed_16_16_to_fixed_32_32 (dy1),
l2_det, _fixed_16_16_to_fixed_32_32 (dy2));
/*
* Ok, this one is a bit tricky in fixed point, the denominator
* needs to be left with 32-bits of fraction so that the
* result of the divide ends up with 32-bits of fraction (64 - 32 = 32)
*/
qr = _cairo_int128_divrem (num_det, _cairo_int64_to_int128 (den_det));
intersect_32_32 = _cairo_int128_to_int64 (qr.quo);
/*
* Find the ceiling of the quotient -- divrem returns
* the quotient truncated towards zero, so if the
* quotient should be positive (num_den and den_det have same sign)
* bump the quotient up by one.
*/
if (_cairo_int128_ne (qr.rem, _cairo_int32_to_int128 (0)) &&
(_cairo_int128_ge (num_det, _cairo_int32_to_int128 (0)) ==
_cairo_int64_ge (den_det, _cairo_int32_to_int64 (0))))
@ -576,8 +575,8 @@ _line_segs_intersect_ceil (cairo_line_t *l1, cairo_line_t *l2, cairo_fixed_t *y_
intersect_32_32 = _cairo_int64_add (intersect_32_32,
_cairo_int32_to_int64 (1));
}
/*
/*
* Now convert from 32.32 to 48.16 and take the ceiling;
* this requires adding in 15 1 bits and shifting the result
*/
@ -585,12 +584,12 @@ _line_segs_intersect_ceil (cairo_line_t *l1, cairo_line_t *l2, cairo_fixed_t *y_
intersect_32_32 = _cairo_int64_add (intersect_32_32,
_cairo_int32_to_int64 ((1 << 16) - 1));
intersect_48_16 = _cairo_int64_rsa (intersect_32_32, 16);
/*
* And drop the top bits
*/
intersect_16_16 = _cairo_int64_to_int32 (intersect_48_16);
*y_intersection = intersect_16_16;
return 1;
@ -611,7 +610,7 @@ _compute_x (cairo_line_t *line, cairo_fixed_t y)
static double
_compute_inverse_slope (cairo_line_t *l)
{
return (_cairo_fixed_to_double (l->p2.x - l->p1.x) /
return (_cairo_fixed_to_double (l->p2.x - l->p1.x) /
_cairo_fixed_to_double (l->p2.y - l->p1.y));
}
@ -741,7 +740,7 @@ _cairo_traps_tessellate_polygon (cairo_traps_t *traps,
return CAIRO_STATUS_SUCCESS;
qsort (edges, num_edges, sizeof (cairo_edge_t), _compare_cairo_edge_by_top);
y = edges[0].edge.p1.y;
active = 0;
inactive = 0;
@ -809,12 +808,12 @@ static cairo_bool_t
_cairo_trap_contains (cairo_trapezoid_t *t, cairo_point_t *pt)
{
cairo_slope_t slope_left, slope_pt, slope_right;
if (t->top > pt->y)
return FALSE;
if (t->bottom < pt->y)
return FALSE;
_cairo_slope_init (&slope_left, &t->left.p1, &t->left.p2);
_cairo_slope_init (&slope_pt, &t->left.p1, pt);
@ -860,10 +859,10 @@ _cairo_traps_extents (cairo_traps_t *traps, cairo_box_t *extents)
* exactly representable as a pixman region, otherwise a
* a pointer to such a region, newly allocated.
* (free with pixman region destroy)
*
*
* Determines if a set of trapezoids are exactly representable as a
* pixman region, and if so creates such a region.
*
*
* Return value: %CAIRO_STATUS_SUCCESS or %CAIRO_STATUS_NO_MEMORY
**/
cairo_status_t
@ -882,7 +881,7 @@ _cairo_traps_extract_region (cairo_traps_t *traps,
*region = NULL;
return CAIRO_STATUS_SUCCESS;
}
*region = pixman_region_create ();
for (i = 0; i < traps->num_traps; i++) {
@ -897,7 +896,7 @@ _cairo_traps_extract_region (cairo_traps_t *traps,
*/
if (width == 0 || height == 0)
continue;
if (pixman_region_union_rect (*region, *region,
x, y, width, height) != PIXMAN_REGION_STATUS_SUCCESS) {
pixman_region_destroy (*region);

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -1,5 +1,5 @@
/* cairo_unicode.c: Unicode conversion routines
*
*
* The code in this file is derived from GLib's gutf8.c and
* ultimately from libunicode. It is relicensed under the
* dual LGPL/MPL with permission of the original authors.
@ -84,7 +84,6 @@
((Char) < 0x10000 ? 3 : \
((Char) < 0x200000 ? 4 : \
((Char) < 0x4000000 ? 5 : 6)))))
#define UTF8_GET(Result, Chars, Count, Mask, Len) \
(Result) = (Chars)[0] & (Mask); \
@ -104,8 +103,7 @@
(((Char) & 0xFFFFF800) != 0xD800) && \
((Char) < 0xFDD0 || (Char) > 0xFDEF) && \
((Char) & 0xFFFE) != 0xFFFE)
static const char utf8_skip_data[256] = {
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
@ -143,7 +141,7 @@ _utf8_get_char (const unsigned char *p)
*/
static uint32_t
_utf8_get_char_extended (const unsigned char *p,
long max_len)
long max_len)
{
int i, len;
uint32_t wc = (unsigned char) *p;
@ -170,7 +168,7 @@ _utf8_get_char_extended (const unsigned char *p,
} else {
return (uint32_t)-1;
}
if (max_len >= 0 && len > max_len) {
for (i = 1; i < max_len; i++) {
if ((((unsigned char *)p)[i] & 0xc0) != 0x80)
@ -181,7 +179,7 @@ _utf8_get_char_extended (const unsigned char *p,
for (i = 1; i < len; ++i) {
uint32_t ch = ((unsigned char *)p)[i];
if ((ch & 0xc0) != 0x80) {
if (ch)
return (uint32_t)-1;
@ -195,7 +193,7 @@ _utf8_get_char_extended (const unsigned char *p,
if (UTF8_LENGTH(wc) != len)
return (uint32_t)-1;
return wc;
}
@ -208,13 +206,13 @@ _utf8_get_char_extended (const unsigned char *p,
* @result: location to store a pointer to a newly allocated UTF-32
* string (always native endian). Free with free(). A 0
* word will be written after the last character.
* @items_written: location to store number of 32-bit words
* @items_written: location to store number of 32-bit words
* written. (Not including the trailing 0)
*
* Converts a UTF-8 string to UCS-4. UCS-4 is an encoding of Unicode
* with 1 32-bit word per character. The string is validated to
* consist entirely of valid Unicode characters.
*
*
* Return value: %CAIRO_STATUS_SUCCESS if the entire string was
* succesfully converted. %CAIRO_STATUS_INVALID_STRING if an
* an invalid sequence was found.
@ -228,7 +226,7 @@ _cairo_utf8_to_ucs4 (const unsigned char *str,
uint32_t *str32 = NULL;
int n_chars, i;
const unsigned char *in;
in = str;
n_chars = 0;
while ((len < 0 || str + len - in > 0) && *in)
@ -236,7 +234,7 @@ _cairo_utf8_to_ucs4 (const unsigned char *str,
uint32_t wc = _utf8_get_char_extended (in, str + len - in);
if (wc & 0x80000000 || !UNICODE_VALID (wc))
return CAIRO_STATUS_INVALID_STRING;
n_chars++;
if (n_chars == INT_MAX)
return CAIRO_STATUS_INVALID_STRING;
@ -247,7 +245,7 @@ _cairo_utf8_to_ucs4 (const unsigned char *str,
str32 = malloc (sizeof (uint32_t) * (n_chars + 1));
if (!str32)
return CAIRO_STATUS_NO_MEMORY;
in = str;
for (i=0; i < n_chars; i++) {
str32[i] = _utf8_get_char (in);
@ -271,14 +269,14 @@ _cairo_utf8_to_ucs4 (const unsigned char *str,
* @result: location to store a pointer to a newly allocated UTF-16
* string (always native endian). Free with free(). A 0
* word will be written after the last character.
* @items_written: location to store number of 16-bit words
* @items_written: location to store number of 16-bit words
* written. (Not including the trailing 0)
*
* Converts a UTF-8 string to UTF-16. UTF-16 is an encoding of Unicode
* where characters are represented either as a single 16-bit word, or
* as a pair of 16-bit "surrogates". The string is validated to
* consist entirely of valid Unicode characters.
*
*
* Return value: %CAIRO_STATUS_SUCCESS if the entire string was
* succesfully converted. %CAIRO_STATUS_INVALID_STRING if an
* an invalid sequence was found.
@ -299,23 +297,22 @@ _cairo_utf8_to_utf16 (const unsigned char *str,
uint32_t wc = _utf8_get_char_extended (in, str + len - in);
if (wc & 0x80000000 || !UNICODE_VALID (wc))
return CAIRO_STATUS_INVALID_STRING;
if (wc < 0x10000)
n16 += 1;
else
n16 += 2;
if (n16 == INT_MAX - 1 || n16 == INT_MAX)
return CAIRO_STATUS_INVALID_STRING;
in = UTF8_NEXT_CHAR (in);
}
str16 = malloc (sizeof (uint16_t) * (n16 + 1));
if (!str16)
return CAIRO_STATUS_NO_MEMORY;
in = str;
for (i = 0; i < n16;) {
uint32_t wc = _utf8_get_char (in);
@ -326,7 +323,7 @@ _cairo_utf8_to_utf16 (const unsigned char *str,
str16[i++] = (wc - 0x10000) / 0x400 + 0xd800;
str16[i++] = (wc - 0x10000) % 0x400 + 0xdc00;
}
in = UTF8_NEXT_CHAR (in);
}

Просмотреть файл

@ -0,0 +1,313 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2004 Keith Packard
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is Keith Packard
*
* Contributor(s):
* Keith R. Packard <keithp@keithp.com>
*
*/
#ifndef CAIRO_WIDEINT_H
#define CAIRO_WIDEINT_H
#if HAVE_STDINT_H
# include <stdint.h>
#elif HAVE_INTTYPES_H
# include <inttypes.h>
#elif HAVE_SYS_INT_TYPES_H
# include <sys/int_types.h>
#elif defined(_MSC_VER)
typedef __int8 int8_t;
typedef unsigned __int8 uint8_t;
typedef __int16 int16_t;
typedef unsigned __int16 uint16_t;
typedef __int32 int32_t;
typedef unsigned __int32 uint32_t;
typedef __int64 int64_t;
typedef unsigned __int64 uint64_t;
# ifndef HAVE_UINT64_T
# define HAVE_UINT64_T 1
# endif
# ifndef INT16_MIN
# define INT16_MIN (-32767-1)
# endif
# ifndef INT16_MAX
# define INT16_MAX (32767)
# endif
# ifndef UINT16_MAX
# define UINT16_MAX (65535)
# endif
#else
#error Cannot find definitions for fixed-width integral types (uint8_t, uint32_t, etc.)
#endif
/*
* 64-bit datatypes. Two separate implementations, one using
* built-in 64-bit signed/unsigned types another implemented
* as a pair of 32-bit ints
*/
#define I cairo_private
#if !HAVE_UINT64_T
typedef struct _cairo_uint64 {
uint32_t lo, hi;
} cairo_uint64_t, cairo_int64_t;
cairo_uint64_t I _cairo_uint32_to_uint64 (uint32_t i);
#define _cairo_uint64_to_uint32(a) ((a).lo)
cairo_uint64_t I _cairo_uint64_add (cairo_uint64_t a, cairo_uint64_t b);
cairo_uint64_t I _cairo_uint64_sub (cairo_uint64_t a, cairo_uint64_t b);
cairo_uint64_t I _cairo_uint64_mul (cairo_uint64_t a, cairo_uint64_t b);
cairo_uint64_t I _cairo_uint32x32_64_mul (uint32_t a, uint32_t b);
cairo_uint64_t I _cairo_uint64_lsl (cairo_uint64_t a, int shift);
cairo_uint64_t I _cairo_uint64_rsl (cairo_uint64_t a, int shift);
cairo_uint64_t I _cairo_uint64_rsa (cairo_uint64_t a, int shift);
int I _cairo_uint64_lt (cairo_uint64_t a, cairo_uint64_t b);
int I _cairo_uint64_eq (cairo_uint64_t a, cairo_uint64_t b);
cairo_uint64_t I _cairo_uint64_negate (cairo_uint64_t a);
#define _cairo_uint64_negative(a) (((int32_t) ((a).hi)) < 0)
cairo_uint64_t I _cairo_uint64_not (cairo_uint64_t a);
#define _cairo_uint64_to_int64(i) (i)
#define _cairo_int64_to_uint64(i) (i)
cairo_int64_t I _cairo_int32_to_int64(int32_t i);
#define _cairo_int64_to_int32(a) ((int32_t) _cairo_uint64_to_uint32(a))
#define _cairo_int64_add(a,b) _cairo_uint64_add (a,b)
#define _cairo_int64_sub(a,b) _cairo_uint64_sub (a,b)
#define _cairo_int64_mul(a,b) _cairo_uint64_mul (a,b)
cairo_int64_t I _cairo_int32x32_64_mul (int32_t a, int32_t b);
int I _cairo_int64_lt (cairo_uint64_t a, cairo_uint64_t b);
#define _cairo_int64_eq(a,b) _cairo_uint64_eq (a,b)
#define _cairo_int64_lsl(a,b) _cairo_uint64_lsl (a,b)
#define _cairo_int64_rsl(a,b) _cairo_uint64_rsl (a,b)
#define _cairo_int64_rsa(a,b) _cairo_uint64_rsa (a,b)
#define _cairo_int64_negate(a) _cairo_uint64_negate(a)
#define _cairo_int64_negative(a) (((int32_t) ((a).hi)) < 0)
#define _cairo_int64_not(a) _cairo_uint64_not(a)
#else
typedef uint64_t cairo_uint64_t;
typedef int64_t cairo_int64_t;
#define _cairo_uint32_to_uint64(i) ((uint64_t) (i))
#define _cairo_uint64_to_uint32(i) ((uint32_t) (i))
#define _cairo_uint64_add(a,b) ((a) + (b))
#define _cairo_uint64_sub(a,b) ((a) - (b))
#define _cairo_uint64_mul(a,b) ((a) * (b))
#define _cairo_uint32x32_64_mul(a,b) ((uint64_t) (a) * (b))
#define _cairo_uint64_lsl(a,b) ((a) << (b))
#define _cairo_uint64_rsl(a,b) ((uint64_t) (a) >> (b))
#define _cairo_uint64_rsa(a,b) ((uint64_t) ((int64_t) (a) >> (b)))
#define _cairo_uint64_lt(a,b) ((a) < (b))
#define _cairo_uint64_eq(a,b) ((a) == (b))
#define _cairo_uint64_negate(a) ((uint64_t) -((int64_t) (a)))
#define _cairo_uint64_negative(a) ((int64_t) (a) < 0)
#define _cairo_uint64_not(a) (~(a))
#define _cairo_uint64_to_int64(i) ((int64_t) (i))
#define _cairo_int64_to_uint64(i) ((uint64_t) (i))
#define _cairo_int32_to_int64(i) ((int64_t) (i))
#define _cairo_int64_to_int32(i) ((int32_t) (i))
#define _cairo_int64_add(a,b) ((a) + (b))
#define _cairo_int64_sub(a,b) ((a) - (b))
#define _cairo_int64_mul(a,b) ((a) * (b))
#define _cairo_int32x32_64_mul(a,b) ((int64_t) (a) * (b))
#define _cairo_int64_lt(a,b) ((a) < (b))
#define _cairo_int64_eq(a,b) ((a) == (b))
#define _cairo_int64_lsl(a,b) ((a) << (b))
#define _cairo_int64_rsl(a,b) ((int64_t) ((uint64_t) (a) >> (b)))
#define _cairo_int64_rsa(a,b) ((int64_t) (a) >> (b))
#define _cairo_int64_negate(a) (-(a))
#define _cairo_int64_negative(a) ((a) < 0)
#define _cairo_int64_not(a) (~(a))
#endif
/*
* 64-bit comparisions derived from lt or eq
*/
#define _cairo_uint64_le(a,b) (!_cairo_uint64_gt(a,b))
#define _cairo_uint64_ne(a,b) (!_cairo_uint64_eq(a,b))
#define _cairo_uint64_ge(a,b) (!_cairo_uint64_lt(a,b))
#define _cairo_uint64_gt(a,b) _cairo_uint64_lt(b,a)
#define _cairo_int64_le(a,b) (!_cairo_int64_gt(a,b))
#define _cairo_int64_ne(a,b) (!_cairo_int64_eq(a,b))
#define _cairo_int64_ge(a,b) (!_cairo_int64_lt(a,b))
#define _cairo_int64_gt(a,b) _cairo_int64_lt(b,a)
/*
* As the C implementation always computes both, create
* a function which returns both for the 'native' type as well
*/
typedef struct _cairo_uquorem64 {
cairo_uint64_t quo;
cairo_uint64_t rem;
} cairo_uquorem64_t;
typedef struct _cairo_quorem64 {
cairo_int64_t quo;
cairo_int64_t rem;
} cairo_quorem64_t;
cairo_uquorem64_t I
_cairo_uint64_divrem (cairo_uint64_t num, cairo_uint64_t den);
cairo_quorem64_t I
_cairo_int64_divrem (cairo_int64_t num, cairo_int64_t den);
/*
* 128-bit datatypes. Again, provide two implementations in
* case the machine has a native 128-bit datatype. GCC supports int128_t
* on ia64
*/
#if !HAVE_UINT128_T
typedef struct cairo_uint128 {
cairo_uint64_t lo, hi;
} cairo_uint128_t, cairo_int128_t;
cairo_uint128_t I _cairo_uint32_to_uint128 (uint32_t i);
cairo_uint128_t I _cairo_uint64_to_uint128 (cairo_uint64_t i);
#define _cairo_uint128_to_uint64(a) ((a).lo)
#define _cairo_uint128_to_uint32(a) _cairo_uint64_to_uint32(_cairo_uint128_to_uint64(a))
cairo_uint128_t I _cairo_uint128_add (cairo_uint128_t a, cairo_uint128_t b);
cairo_uint128_t I _cairo_uint128_sub (cairo_uint128_t a, cairo_uint128_t b);
cairo_uint128_t I _cairo_uint128_mul (cairo_uint128_t a, cairo_uint128_t b);
cairo_uint128_t I _cairo_uint64x64_128_mul (cairo_uint64_t a, cairo_uint64_t b);
cairo_uint128_t I _cairo_uint128_lsl (cairo_uint128_t a, int shift);
cairo_uint128_t I _cairo_uint128_rsl (cairo_uint128_t a, int shift);
cairo_uint128_t I _cairo_uint128_rsa (cairo_uint128_t a, int shift);
int I _cairo_uint128_lt (cairo_uint128_t a, cairo_uint128_t b);
int I _cairo_uint128_eq (cairo_uint128_t a, cairo_uint128_t b);
cairo_uint128_t I _cairo_uint128_negate (cairo_uint128_t a);
#define _cairo_uint128_negative(a) (_cairo_uint64_negative(a.hi))
cairo_uint128_t I _cairo_uint128_not (cairo_uint128_t a);
#define _cairo_uint128_to_int128_(i) (i)
#define _cairo_int128_to_uint128(i) (i)
cairo_int128_t I _cairo_int32_to_int128 (int32_t i);
cairo_int128_t I _cairo_int64_to_int128 (cairo_int64_t i);
#define _cairo_int128_to_int64(a) ((cairo_int64_t) (a).lo)
#define _cairo_int128_to_int32(a) _cairo_int64_to_int32(_cairo_int128_to_int64(a))
#define _cairo_int128_add(a,b) _cairo_uint128_add(a,b)
#define _cairo_int128_sub(a,b) _cairo_uint128_sub(a,b)
#define _cairo_int128_mul(a,b) _cairo_uint128_mul(a,b)
cairo_int128_t I _cairo_int64x64_128_mul (cairo_int64_t a, cairo_int64_t b);
#define _cairo_int128_lsl(a,b) _cairo_uint128_lsl(a,b)
#define _cairo_int128_rsl(a,b) _cairo_uint128_rsl(a,b)
#define _cairo_int128_rsa(a,b) _cairo_uint128_rsa(a,b)
int I _cairo_int128_lt (cairo_int128_t a, cairo_int128_t b);
#define _cairo_int128_eq(a,b) _cairo_uint128_eq (a,b)
#define _cairo_int128_negate(a) _cairo_uint128_negate(a)
#define _cairo_int128_negative(a) (_cairo_uint128_negative(a))
#define _cairo_int128_not(a) _cairo_uint128_not(a)
#else /* !HAVE_UINT128_T */
typedef uint128_t cairo_uint128_t;
typedef int128_t cairo_int128_t;
#define _cairo_uint32_to_uint128(i) ((uint128_t) (i))
#define _cairo_uint64_to_uint128(i) ((uint128_t) (i))
#define _cairo_uint128_to_uint64(i) ((uint64_t) (i))
#define _cairo_uint128_to_uint32(i) ((uint32_t) (i))
#define _cairo_uint128_add(a,b) ((a) + (b))
#define _cairo_uint128_sub(a,b) ((a) - (b))
#define _cairo_uint128_mul(a,b) ((a) * (b))
#define _cairo_uint64x64_128_mul(a,b) ((uint128_t) (a) * (b))
#define _cairo_uint128_lsl(a,b) ((a) << (b))
#define _cairo_uint128_rsl(a,b) ((uint128_t) (a) >> (b))
#define _cairo_uint128_rsa(a,b) ((uint128_t) ((int128_t) (a) >> (b)))
#define _cairo_uint128_lt(a,b) ((a) < (b))
#define _cairo_uint128_eq(a,b) ((a) == (b))
#define _cairo_uint128_negate(a) ((uint128_t) -((int128_t) (a)))
#define _cairo_uint128_negative(a) ((int128_t) (a) < 0)
#define _cairo_uint128_not(a) (~(a))
#define _cairo_uint128_to_int128(i) ((int128_t) (i))
#define _cairo_int128_to_uint128(i) ((uint128_t) (i))
#define _cairo_int32_to_int128(i) ((int128_t) (i))
#define _cairo_int64_to_int128(i) ((int128_t) (i))
#define _cairo_int128_to_int64(i) ((int64_t) (i))
#define _cairo_int128_to_int32(i) ((int32_t) (i))
#define _cairo_int128_add(a,b) ((a) + (b))
#define _cairo_int128_sub(a,b) ((a) - (b))
#define _cairo_int128_mul(a,b) ((a) * (b))
#define _cairo_int64x64_128_mul(a,b) ((int128_t) (a) * (b))
#define _cairo_int128_lt(a,b) ((a) < (b))
#define _cairo_int128_eq(a,b) ((a) == (b))
#define _cairo_int128_lsl(a,b) ((a) << (b))
#define _cairo_int128_rsl(a,b) ((int128_t) ((uint128_t) (a) >> (b)))
#define _cairo_int128_rsa(a,b) ((int128_t) (a) >> (b))
#define _cairo_int128_negate(a) (-(a))
#define _cairo_int128_negative(a) ((a) < 0)
#define _cairo_int128_not(a) (~(a))
#endif /* HAVE_UINT128_T */
typedef struct _cairo_uquorem128 {
cairo_uint128_t quo;
cairo_uint128_t rem;
} cairo_uquorem128_t;
typedef struct _cairo_quorem128 {
cairo_int128_t quo;
cairo_int128_t rem;
} cairo_quorem128_t;
cairo_uquorem128_t I
_cairo_uint128_divrem (cairo_uint128_t num, cairo_uint128_t den);
cairo_quorem128_t I
_cairo_int128_divrem (cairo_int128_t num, cairo_int128_t den);
#define _cairo_uint128_le(a,b) (!_cairo_uint128_gt(a,b))
#define _cairo_uint128_ne(a,b) (!_cairo_uint128_eq(a,b))
#define _cairo_uint128_ge(a,b) (!_cairo_uint128_lt(a,b))
#define _cairo_uint128_gt(a,b) _cairo_uint128_lt(b,a)
#define _cairo_int128_le(a,b) (!_cairo_int128_gt(a,b))
#define _cairo_int128_ne(a,b) (!_cairo_int128_eq(a,b))
#define _cairo_int128_ge(a,b) (!_cairo_int128_lt(a,b))
#define _cairo_int128_gt(a,b) _cairo_int128_lt(b,a)
#undef I
#endif /* CAIRO_WIDEINT_H */

Просмотреть файл

@ -113,7 +113,7 @@ cairo_uint64_t
_cairo_uint32x32_64_mul (uint32_t a, uint32_t b)
{
cairo_uint64_t s;
uint16_t ah, al, bh, bl;
uint32_t r0, r1, r2, r3;
@ -153,7 +153,7 @@ cairo_uint64_t
_cairo_uint64_mul (cairo_uint64_t a, cairo_uint64_t b)
{
cairo_uint64_t s;
s = _cairo_uint32x32_64_mul (a.lo, b.lo);
s.hi += a.lo * b.hi + a.hi * b.lo;
return s;
@ -262,9 +262,9 @@ _cairo_uint64_divrem (cairo_uint64_t num, cairo_uint64_t den)
cairo_uquorem64_t qr;
cairo_uint64_t bit;
cairo_uint64_t quo;
bit = _cairo_uint32_to_uint64 (1);
/* normalize to make den >= num, but not overflow */
while (_cairo_uint64_lt (den, num) && (den.hi & 0x80000000) == 0)
{
@ -272,7 +272,7 @@ _cairo_uint64_divrem (cairo_uint64_t num, cairo_uint64_t den)
den = _cairo_uint64_lsl (den, 1);
}
quo = _cairo_uint32_to_uint64 (0);
/* generate quotient, one bit at a time */
while (bit.hi | bit.lo)
{
@ -476,7 +476,7 @@ _cairo_int64x64_128_mul (cairo_int64_t a, cairo_int64_t b)
s = _cairo_uint64x64_128_mul (_cairo_int64_to_uint64(a),
_cairo_int64_to_uint64(b));
if (_cairo_int64_negative (a))
s.hi = _cairo_uint64_sub (s.hi,
s.hi = _cairo_uint64_sub (s.hi,
_cairo_int64_to_uint64 (b));
if (_cairo_int64_negative (b))
s.hi = _cairo_uint64_sub (s.hi,
@ -588,9 +588,9 @@ _cairo_uint128_divrem (cairo_uint128_t num, cairo_uint128_t den)
cairo_uquorem128_t qr;
cairo_uint128_t bit;
cairo_uint128_t quo;
bit = _cairo_uint32_to_uint128 (1);
/* normalize to make den >= num, but not overflow */
while (_cairo_uint128_lt (den, num) && !_cairo_msbset64(den.hi))
{
@ -598,7 +598,7 @@ _cairo_uint128_divrem (cairo_uint128_t num, cairo_uint128_t den)
den = _cairo_uint128_lsl (den, 1);
}
quo = _cairo_uint32_to_uint128 (0);
/* generate quotient, one bit at a time */
while (_cairo_uint128_ne (bit, _cairo_uint32_to_uint128(0)))
{

Просмотреть файл

@ -37,7 +37,7 @@
#include "cairoint.h"
#include "cairo-win32-private.h"
#ifndef SPI_GETFONTSMOOTHINGTYPE
#ifndef SPI_GETFONTSMOOTHINGTYPE
#define SPI_GETFONTSMOOTHINGTYPE 0x200a
#endif
#ifndef FE_FONTSMOOTHINGCLEARTYPE
@ -89,7 +89,7 @@ typedef struct {
cairo_bool_t swap_y;
double x_scale;
double y_scale;
/* The size of the design unit of the font
*/
int em_square;
@ -100,10 +100,10 @@ typedef struct {
cairo_bool_t delete_scaled_hfont;
} cairo_win32_scaled_font_t;
static cairo_status_t
static cairo_status_t
_cairo_win32_scaled_font_set_metrics (cairo_win32_scaled_font_t *scaled_font);
static cairo_status_t
static cairo_status_t
_cairo_win32_scaled_font_init_glyph_metrics (cairo_win32_scaled_font_t *scaled_font,
cairo_scaled_glyph_t *scaled_glyph);
@ -126,7 +126,7 @@ _compute_transform (cairo_win32_scaled_font_t *scaled_font,
scaled_font->y_scale = sc->yy;
scaled_font->swap_y = (sc->yy < 0);
scaled_font->swap_axes = FALSE;
} else if (NEARLY_ZERO (sc->xx) && NEARLY_ZERO (sc->yy)) {
scaled_font->preserve_axes = TRUE;
scaled_font->x_scale = sc->yx;
@ -145,7 +145,7 @@ _compute_transform (cairo_win32_scaled_font_t *scaled_font,
scaled_font->x_scale = - scaled_font->x_scale;
if (scaled_font->swap_y)
scaled_font->y_scale = - scaled_font->y_scale;
scaled_font->logical_scale = WIN32_FONT_LOGICAL_SCALE * scaled_font->y_scale;
scaled_font->logical_size = WIN32_FONT_LOGICAL_SCALE * floor (scaled_font->y_scale + 0.5);
}
@ -169,7 +169,7 @@ _compute_transform (cairo_win32_scaled_font_t *scaled_font,
1.0 / scaled_font->logical_scale, 1.0 / scaled_font->logical_scale);
scaled_font->device_to_logical = scaled_font->logical_to_device;
status = cairo_matrix_invert (&scaled_font->device_to_logical);
if (status)
cairo_matrix_init_identity (&scaled_font->device_to_logical);
@ -179,20 +179,19 @@ static cairo_bool_t
_have_cleartype_quality (void)
{
OSVERSIONINFO version_info;
version_info.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
if (!GetVersionEx (&version_info)) {
_cairo_win32_print_gdi_error ("_have_cleartype_quality");
return FALSE;
}
return (version_info.dwMajorVersion > 5 ||
(version_info.dwMajorVersion == 5 &&
version_info.dwMinorVersion >= 1)); /* XP or newer */
}
static BYTE
_get_system_quality (void)
{
@ -228,7 +227,7 @@ _win32_scaled_font_create (LOGFONTW *logfont,
cairo_font_face_t *font_face,
const cairo_matrix_t *font_matrix,
const cairo_matrix_t *ctm,
const cairo_font_options_t *options)
const cairo_font_options_t *options)
{
cairo_win32_scaled_font_t *f;
cairo_matrix_t scale;
@ -244,7 +243,7 @@ _win32_scaled_font_create (LOGFONTW *logfont,
* order in the Win32 font API, so we ignore those parts of
* cairo_font_options_t. We use the 'antialias' field to set
* the 'quality'.
*
*
* XXX: The other option we could pay attention to, but don't
* here is the hint_metrics options.
*/
@ -268,7 +267,7 @@ _win32_scaled_font_create (LOGFONTW *logfont,
ASSERT_NOT_REACHED;
}
}
f->em_square = 0;
f->scaled_hfont = hfont;
f->unscaled_hfont = NULL;
@ -297,7 +296,7 @@ _win32_scaled_font_set_world_transform (cairo_win32_scaled_font_t *scaled_font,
HDC hdc)
{
XFORM xform;
xform.eM11 = scaled_font->logical_to_device.xx;
xform.eM21 = scaled_font->logical_to_device.xy;
xform.eM12 = scaled_font->logical_to_device.yx;
@ -387,7 +386,7 @@ _win32_scaled_font_get_unscaled_hfont (cairo_win32_scaled_font_t *scaled_font,
_cairo_win32_print_gdi_error ("_win32_scaled_font_get_unscaled_hfont:GetOutlineTextMetrics");
return NULL;
}
otm = malloc (otm_size);
if (!otm)
return NULL;
@ -400,14 +399,14 @@ _win32_scaled_font_get_unscaled_hfont (cairo_win32_scaled_font_t *scaled_font,
scaled_font->em_square = otm->otmEMSquare;
free (otm);
logfont = scaled_font->logfont;
logfont.lfHeight = -scaled_font->em_square;
logfont.lfWidth = 0;
logfont.lfEscapement = 0;
logfont.lfOrientation = 0;
logfont.lfQuality = scaled_font->quality;
scaled_font->unscaled_hfont = CreateFontIndirectW (&logfont);
if (!scaled_font->unscaled_hfont) {
_cairo_win32_print_gdi_error ("_win32_scaled_font_get_unscaled_hfont:CreateIndirect");
@ -510,7 +509,7 @@ _cairo_win32_scaled_font_create_toy (cairo_toy_font_face_t *toy_face,
* interpretation is locale-specific, but it's not clear what
* would be a better alternative.
*/
logfont.lfCharSet = DEFAULT_CHARSET;
logfont.lfCharSet = DEFAULT_CHARSET;
logfont.lfOutPrecision = OUT_DEFAULT_PRECIS;
logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
logfont.lfQuality = DEFAULT_QUALITY; /* filled in later */
@ -518,7 +517,7 @@ _cairo_win32_scaled_font_create_toy (cairo_toy_font_face_t *toy_face,
if (!logfont.lfFaceName)
return CAIRO_STATUS_NO_MEMORY;
scaled_font = _win32_scaled_font_create (&logfont, NULL, &toy_face->base,
font_matrix, ctm, options);
if (!scaled_font)
@ -529,7 +528,7 @@ _cairo_win32_scaled_font_create_toy (cairo_toy_font_face_t *toy_face,
return CAIRO_STATUS_SUCCESS;
}
static void
static void
_cairo_win32_scaled_font_fini (void *abstract_font)
{
cairo_win32_scaled_font_t *scaled_font = abstract_font;
@ -544,12 +543,12 @@ _cairo_win32_scaled_font_fini (void *abstract_font)
DeleteObject (scaled_font->unscaled_hfont);
}
static cairo_int_status_t
static cairo_int_status_t
_cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
double x,
double y,
const char *utf8,
cairo_glyph_t **glyphs,
cairo_glyph_t **glyphs,
int *num_glyphs)
{
cairo_win32_scaled_font_t *scaled_font = abstract_font;
@ -570,7 +569,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
cairo_matrix_transform_distance (&scaled_font->base.font_matrix, &x_incr, &y_incr);
x_incr /= scaled_font->logical_scale;
y_incr /= scaled_font->logical_scale;
status = _cairo_utf8_to_utf16 (utf8, -1, &utf16, &n16);
if (status)
return status;
@ -580,13 +579,13 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
gcp_results.lpOrder = NULL;
gcp_results.lpCaretPos = NULL;
gcp_results.lpClass = NULL;
buffer_size = MAX (n16 * 1.2, 16); /* Initially guess number of chars plus a few */
if (buffer_size > INT_MAX) {
status = CAIRO_STATUS_NO_MEMORY;
goto FAIL1;
}
hdc = _get_global_font_dc ();
if (!hdc) {
status = CAIRO_STATUS_NO_MEMORY;
@ -596,7 +595,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
status = cairo_win32_scaled_font_select_font (&scaled_font->base, hdc);
if (status)
goto FAIL1;
while (TRUE) {
if (glyph_indices) {
free (glyph_indices);
@ -606,7 +605,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
free (dx);
dx = NULL;
}
glyph_indices = malloc (sizeof (WCHAR) * buffer_size);
dx = malloc (sizeof (int) * buffer_size);
if (!glyph_indices || !dx) {
@ -620,7 +619,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
if (!GetCharacterPlacementW (hdc, utf16, n16,
0,
&gcp_results,
&gcp_results,
GCP_DIACRITIC | GCP_LIGATE | GCP_GLYPHSHAPE | GCP_REORDER)) {
status = _cairo_win32_print_gdi_error ("_cairo_win32_scaled_font_text_to_glyphs");
goto FAIL2;
@ -630,7 +629,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
break;
/* Too small a buffer, try again */
buffer_size *= 1.5;
if (buffer_size > INT_MAX) {
status = CAIRO_STATUS_NO_MEMORY;
@ -647,7 +646,7 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
x_pos = x;
y_pos = y;
for (i = 0; i < gcp_results.nGlyphs; i++) {
(*glyphs)[i].index = glyph_indices[i];
(*glyphs)[i].x = x_pos ;
@ -662,16 +661,16 @@ _cairo_win32_scaled_font_text_to_glyphs (void *abstract_font,
free (glyph_indices);
if (dx)
free (dx);
cairo_win32_scaled_font_done_font (&scaled_font->base);
FAIL1:
free (utf16);
return status;
}
static cairo_status_t
static cairo_status_t
_cairo_win32_scaled_font_set_metrics (cairo_win32_scaled_font_t *scaled_font)
{
cairo_status_t status;
@ -718,7 +717,7 @@ _cairo_win32_scaled_font_set_metrics (cairo_win32_scaled_font_t *scaled_font)
extents.height = (double)(metrics.tmHeight + metrics.tmExternalLeading) / scaled_font->em_square;
extents.max_x_advance = (double)(metrics.tmMaxCharWidth) / scaled_font->em_square;
extents.max_y_advance = 0;
}
_cairo_scaled_font_set_metrics (&scaled_font->base, &extents);
@ -726,7 +725,7 @@ _cairo_win32_scaled_font_set_metrics (cairo_win32_scaled_font_t *scaled_font)
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
static cairo_status_t
_cairo_win32_scaled_font_init_glyph_metrics (cairo_win32_scaled_font_t *scaled_font,
cairo_scaled_glyph_t *scaled_glyph)
{
@ -780,7 +779,7 @@ _cairo_win32_scaled_font_init_glyph_metrics (cairo_win32_scaled_font_t *scaled_f
extents.y_bearing = (- extents.y_bearing - extents.height);
extents.y_advance = - extents.y_advance;
}
} else {
/* For all other transformations, we use the design metrics
* of the font.
@ -815,7 +814,7 @@ _cairo_win32_scaled_font_init_glyph_metrics (cairo_win32_scaled_font_t *scaled_f
* font-space metrics.
*/
#if 0
static cairo_status_t
static cairo_status_t
_cairo_win32_scaled_font_glyph_bbox (void *abstract_font,
const cairo_glyph_t *glyphs,
int num_glyphs,
@ -870,7 +869,7 @@ _cairo_win32_scaled_font_glyph_bbox (void *abstract_font,
typedef struct {
cairo_win32_scaled_font_t *scaled_font;
HDC hdc;
cairo_array_t glyphs;
cairo_array_t dx;
@ -902,7 +901,7 @@ _flush_glyphs (cairo_glyph_state_t *state)
status = _cairo_array_append (&state->dx, &dx);
if (status)
return status;
elements = _cairo_array_index (&state->glyphs, 0);
dx_elements = _cairo_array_index (&state->dx, 0);
if (!ExtTextOutW (state->hdc,
@ -914,7 +913,7 @@ _flush_glyphs (cairo_glyph_state_t *state)
dx_elements)) {
return _cairo_win32_print_gdi_error ("_flush_glyphs");
}
_cairo_array_truncate (&state->glyphs, 0);
_cairo_array_truncate (&state->dx, 0);
@ -940,14 +939,14 @@ _add_glyph (cairo_glyph_state_t *state,
if (state->glyphs.num_elements > 0) {
int dx;
if (logical_y != state->last_y) {
status = _flush_glyphs (state);
if (status)
return status;
state->start_x = logical_x;
}
dx = logical_x - state->last_x;
status = _cairo_array_append (&state->dx, &dx);
if (status)
@ -958,7 +957,7 @@ _add_glyph (cairo_glyph_state_t *state,
state->last_x = logical_x;
state->last_y = logical_y;
status = _cairo_array_append (&state->glyphs, &glyph_index);
if (status)
return status;
@ -998,7 +997,7 @@ _draw_glyphs_on_surface (cairo_win32_surface_t *surface,
SetTextColor (surface->dc, color);
SetTextAlign (surface->dc, TA_BASELINE | TA_LEFT);
SetBkMode (surface->dc, TRANSPARENT);
_start_glyphs (&state, scaled_font, surface->dc);
for (i = 0; i < num_glyphs; i++) {
@ -1013,10 +1012,10 @@ _draw_glyphs_on_surface (cairo_win32_surface_t *surface,
cairo_win32_scaled_font_done_font (&scaled_font->base);
FAIL1:
RestoreDC (surface->dc, -1);
return status;
}
/* Duplicate the green channel of a 4-channel mask in the alpha channel, then
* invert the whole mask.
*/
@ -1069,7 +1068,7 @@ _compute_a8_mask (cairo_win32_surface_t *mask_surface)
for (i = 0; i < image24->height; i++) {
uint32_t *p = (uint32_t *) (image24->data + i * image24->stride);
unsigned char *q = (unsigned char *) (image8->data + i * image8->stride);
for (j = 0; j < image24->width; j++) {
*q = 255 - ((*p & 0x0000ff00) >> 8);
p++;
@ -1080,7 +1079,6 @@ _compute_a8_mask (cairo_win32_surface_t *mask_surface)
return &image8->base;
}
static cairo_status_t
_cairo_win32_scaled_font_glyph_init (void *abstract_font,
cairo_scaled_glyph_t *scaled_glyph,
@ -1108,7 +1106,7 @@ _cairo_win32_scaled_font_glyph_init (void *abstract_font,
return CAIRO_STATUS_SUCCESS;
}
static cairo_int_status_t
static cairo_int_status_t
_cairo_win32_scaled_font_show_glyphs (void *abstract_font,
cairo_operator_t op,
cairo_pattern_t *pattern,
@ -1140,7 +1138,7 @@ _cairo_win32_scaled_font_show_glyphs (void *abstract_font,
* solid opaque color, we can just call ExtTextOut directly.
*/
COLORREF new_color;
new_color = RGB (((int)solid_pattern->color.red_short) >> 8,
((int)solid_pattern->color.green_short) >> 8,
((int)solid_pattern->color.blue_short) >> 8);
@ -1148,10 +1146,10 @@ _cairo_win32_scaled_font_show_glyphs (void *abstract_font,
status = _draw_glyphs_on_surface (surface, scaled_font, new_color,
0, 0,
glyphs, num_glyphs);
return status;
} else {
/* Otherwise, we need to draw using software fallbacks. We create a mask
/* Otherwise, we need to draw using software fallbacks. We create a mask
* surface by drawing the the glyphs onto a DIB, black-on-white then
* inverting. GDI outputs gamma-corrected images so inverted black-on-white
* is very different from white-on-black. We favor the more common
@ -1187,12 +1185,12 @@ _cairo_win32_scaled_font_show_glyphs (void *abstract_font,
_compute_argb32_mask_alpha (tmp_surface);
else
_invert_argb32_mask (tmp_surface);
mask_surface = &tmp_surface->base;
/* XXX: Hacky, should expose this in cairo_image_surface */
pixman_image_set_component_alpha (((cairo_image_surface_t *)tmp_surface->image)->pixman_image, TRUE);
} else {
mask_surface = _compute_a8_mask (tmp_surface);
cairo_surface_destroy (&tmp_surface->base);
@ -1206,7 +1204,7 @@ _cairo_win32_scaled_font_show_glyphs (void *abstract_font,
*/
_cairo_pattern_init_for_surface (&mask, mask_surface);
status = _cairo_surface_composite (op, pattern,
status = _cairo_surface_composite (op, pattern,
&mask.base,
&surface->base,
source_x, source_y,
@ -1215,7 +1213,7 @@ _cairo_win32_scaled_font_show_glyphs (void *abstract_font,
width, height);
_cairo_pattern_fini (&mask.base);
cairo_surface_destroy (mask_surface);
return status;
@ -1228,7 +1226,7 @@ _cairo_fixed_from_FIXED (FIXED f)
return *((cairo_fixed_t *)&f);
}
static cairo_status_t
static cairo_status_t
_cairo_win32_scaled_font_init_glyph_path (cairo_win32_scaled_font_t *scaled_font,
cairo_scaled_glyph_t *scaled_glyph)
{
@ -1251,18 +1249,18 @@ _cairo_win32_scaled_font_init_glyph_path (cairo_win32_scaled_font_t *scaled_font
status = cairo_win32_scaled_font_select_font (&scaled_font->base, hdc);
if (status)
goto CLEANUP_PATH;
bytesGlyph = GetGlyphOutlineW (hdc, _cairo_scaled_glyph_index (scaled_glyph),
GGO_NATIVE | GGO_GLYPH_INDEX,
&metrics, 0, NULL, &matrix);
if (bytesGlyph == GDI_ERROR) {
status = _cairo_win32_print_gdi_error ("_cairo_win32_scaled_font_glyph_path");
goto CLEANUP_FONT;
}
ptr = buffer = malloc (bytesGlyph);
if (!buffer) {
status = CAIRO_STATUS_NO_MEMORY;
goto CLEANUP_FONT;
@ -1275,13 +1273,13 @@ _cairo_win32_scaled_font_init_glyph_path (cairo_win32_scaled_font_t *scaled_font
free (buffer);
goto CLEANUP_FONT;
}
while (ptr < buffer + bytesGlyph) {
TTPOLYGONHEADER *header = (TTPOLYGONHEADER *)ptr;
unsigned char *endPoly = ptr + header->cb;
ptr += sizeof (TTPOLYGONHEADER);
_cairo_path_fixed_move_to (path,
_cairo_fixed_from_FIXED (header->pfxStart.x),
_cairo_fixed_from_FIXED (header->pfxStart.y));
@ -1304,7 +1302,7 @@ _cairo_win32_scaled_font_init_glyph_path (cairo_win32_scaled_font_t *scaled_font
_cairo_path_fixed_get_current_point (path, &p1x, &p1y);
cx = _cairo_fixed_from_FIXED (points[i].x);
cy = _cairo_fixed_from_FIXED (points[i].y);
if (i + 1 == curve->cpfx - 1) {
p2x = _cairo_fixed_from_FIXED (points[i + 1].x);
p2y = _cairo_fixed_from_FIXED (points[i + 1].y);
@ -1314,12 +1312,12 @@ _cairo_win32_scaled_font_init_glyph_path (cairo_win32_scaled_font_t *scaled_font
p2x = (cx + _cairo_fixed_from_FIXED (points[i + 1].x)) / 2;
p2y = (cy + _cairo_fixed_from_FIXED (points[i + 1].y)) / 2;
}
c1x = 2 * cx / 3 + p1x / 3;
c1y = 2 * cy / 3 + p1y / 3;
c2x = 2 * cx / 3 + p2x / 3;
c2y = 2 * cy / 3 + p2y / 3;
_cairo_path_fixed_curve_to (path, c1x, c1y, c2x, c2y, p2x, p2y);
}
break;
@ -1414,11 +1412,12 @@ static const cairo_font_face_backend_t _cairo_win32_font_face_backend = {
* @logfont: A #LOGFONTW structure specifying the font to use.
* The lfHeight, lfWidth, lfOrientation and lfEscapement
* fields of this structure are ignored.
*
*
* Creates a new font for the Win32 font backend based on a
* #LOGFONT. This font can then be used with
* cairo_set_font_face() or cairo_font_create(). The #cairo_scaled_font_t
* returned from cairo_font_create() is also for the Win32 backend
* cairo_set_font_face() or cairo_scaled_font_create().
* The #cairo_scaled_font_t
* returned from cairo_scaled_font_create() is also for the Win32 backend
* and can be used with functions such as cairo_win32_scaled_font_select_font().
*
* Return value: a newly created #cairo_font_face_t. Free with
@ -1434,16 +1433,29 @@ cairo_win32_font_face_create_for_logfontw (LOGFONTW *logfont)
_cairo_error (CAIRO_STATUS_NO_MEMORY);
return (cairo_font_face_t *)&_cairo_font_face_nil;
}
font_face->logfont = *logfont;
font_face->hfont = NULL;
_cairo_font_face_init (&font_face->base, &_cairo_win32_font_face_backend);
return &font_face->base;
}
/**
* cairo_win32_font_face_create_for_hfont:
* @font: An #HFONT structure specifying the font to use.
*
* Creates a new font for the Win32 font backend based on a
* #HFONT. This font can then be used with
* cairo_set_font_face() or cairo_scaled_font_create().
* The #cairo_scaled_font_t
* returned from cairo_scaled_font_create() is also for the Win32 backend
* and can be used with functions such as cairo_win32_scaled_font_select_font().
*
* Return value: a newly created #cairo_font_face_t. Free with
* cairo_font_face_destroy() when you are done using it.
**/
cairo_font_face_t *
cairo_win32_font_face_create_for_hfont (HFONT font)
{
@ -1454,9 +1466,9 @@ cairo_win32_font_face_create_for_hfont (HFONT font)
_cairo_error (CAIRO_STATUS_NO_MEMORY);
return (cairo_font_face_t *)&_cairo_font_face_nil;
}
font_face->hfont = font;
_cairo_font_face_init (&font_face->base, &_cairo_win32_font_face_backend);
return &font_face->base;
@ -1481,7 +1493,7 @@ cairo_win32_font_face_create_for_hfont (HFONT font)
*
* Normally, calls to SaveDC() and RestoreDC() would be made around
* the use of this function to preserve the original graphics state.
*
*
* Return value: %CAIRO_STATUS_SUCCESS if the operation succeeded.
* otherwise an error such as %CAIRO_STATUS_NO_MEMORY and
* the device context is unchanged.
@ -1528,7 +1540,7 @@ cairo_win32_scaled_font_select_font (cairo_scaled_font_t *scaled_font,
/**
* cairo_win32_scaled_font_done_font:
* @scaled_font: A #cairo_scaled_font_t from the Win32 font backend.
*
*
* Releases any resources allocated by cairo_win32_scaled_font_select_font()
**/
void
@ -1539,12 +1551,12 @@ cairo_win32_scaled_font_done_font (cairo_scaled_font_t *scaled_font)
/**
* cairo_win32_scaled_font_get_metrics_factor:
* @scaled_font: a #cairo_scaled_font_t from the Win32 font backend
*
*
* Gets a scale factor between logical coordinates in the coordinate
* space used by cairo_win32_scaled_font_select_font() (that is, the
* coordinate system used by the Windows functions to return metrics) and
* font space coordinates.
*
*
* Return value: factor to multiply logical units by to get font space
* coordinates.
**/
@ -1565,12 +1577,7 @@ cairo_win32_scaled_font_get_logical_to_device (cairo_scaled_font_t *scaled_font,
if (cairo_scaled_font_get_type (scaled_font) != CAIRO_FONT_TYPE_WIN32)
return;
logical_to_device->xx = win_font->logical_to_device.xx;
logical_to_device->yx = win_font->logical_to_device.yx;
logical_to_device->xy = win_font->logical_to_device.xy;
logical_to_device->yy = win_font->logical_to_device.yy;
logical_to_device->x0 = win_font->logical_to_device.x0;
logical_to_device->y0 = win_font->logical_to_device.y0;
*logical_to_device = win_font->logical_to_device;
}
void
@ -1581,10 +1588,5 @@ cairo_win32_scaled_font_get_device_to_logical (cairo_scaled_font_t *scaled_font,
if (cairo_scaled_font_get_type (scaled_font) != CAIRO_FONT_TYPE_WIN32)
return;
device_to_logical->xx = win_font->device_to_logical.xx;
device_to_logical->yx = win_font->device_to_logical.yx;
device_to_logical->xy = win_font->device_to_logical.xy;
device_to_logical->yy = win_font->device_to_logical.yy;
device_to_logical->x0 = win_font->device_to_logical.x0;
device_to_logical->y0 = win_font->device_to_logical.y0;
*device_to_logical = win_font->device_to_logical;
}

Просмотреть файл

@ -52,7 +52,7 @@ typedef struct _cairo_win32_surface {
cairo_surface_t base;
cairo_format_t format;
HDC dc;
/* We create off-screen surfaces as DIBs */
@ -66,34 +66,16 @@ typedef struct _cairo_win32_surface {
* on some versions of Windows.
*/
HBITMAP saved_dc_bitmap;
cairo_surface_t *image;
cairo_rectangle_fixed_t clip_rect;
cairo_rectangle_int16_t clip_rect;
HRGN saved_clip;
cairo_rectangle_fixed_t extents;
/* Surface DC flags */
uint32_t flags;
cairo_rectangle_int16_t extents;
} cairo_win32_surface_t;
/* Surface DC flag values */
enum {
/* Whether the DC is a display DC or not */
CAIRO_WIN32_SURFACE_FLAG_IS_DISPLAY = (1<<1),
/* Whether we can use BitBlt with this surface */
CAIRO_WIN32_SURFACE_CAN_BITBLT = (1<<2),
/* Whether we can use AlphaBlend with this surface */
CAIRO_WIN32_SURFACE_CAN_ALPHABLEND = (1<<3),
/* Whether we can use StretchBlt with this surface */
CAIRO_WIN32_SURFACE_CAN_STRETCHBLT = (1<<4)
};
cairo_status_t
_cairo_win32_print_gdi_error (const char *context);

Просмотреть файл

@ -54,7 +54,7 @@ static const cairo_surface_backend_t cairo_win32_surface_backend;
/**
* _cairo_win32_print_gdi_error:
* @context: context string to display along with the error
*
*
* Helper function to dump out a human readable form of the
* current error code.
*
@ -66,7 +66,7 @@ _cairo_win32_print_gdi_error (const char *context)
void *lpMsgBuf;
DWORD last_error = GetLastError ();
if (!FormatMessageA (FORMAT_MESSAGE_ALLOCATE_BUFFER |
if (!FormatMessageA (FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM,
NULL,
last_error,
@ -76,7 +76,7 @@ _cairo_win32_print_gdi_error (const char *context)
fprintf (stderr, "%s: Unknown GDI error", context);
} else {
fprintf (stderr, "%s: %s", context, (char *)lpMsgBuf);
LocalFree (lpMsgBuf);
}
@ -117,11 +117,11 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
case CAIRO_FORMAT_RGB24:
num_palette = 0;
break;
case CAIRO_FORMAT_A8:
num_palette = 256;
break;
case CAIRO_FORMAT_A1:
num_palette = 2;
break;
@ -142,7 +142,7 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
bitmap_info->bmiHeader.biXPelsPerMeter = 72. / 0.0254; /* unused here */
bitmap_info->bmiHeader.biYPelsPerMeter = 72. / 0.0254; /* unused here */
bitmap_info->bmiHeader.biPlanes = 1;
switch (format) {
/* We can't create real RGB24 bitmaps because something seems to
* break if we do, especially if we don't set up an image
@ -156,7 +156,7 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
bitmap_info->bmiHeader.biClrUsed = 0; /* unused */
bitmap_info->bmiHeader.biClrImportant = 0;
break;
case CAIRO_FORMAT_A8:
bitmap_info->bmiHeader.biBitCount = 8;
bitmap_info->bmiHeader.biCompression = BI_RGB;
@ -169,9 +169,9 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
bitmap_info->bmiColors[i].rgbRed = i;
bitmap_info->bmiColors[i].rgbReserved = 0;
}
break;
case CAIRO_FORMAT_A1:
bitmap_info->bmiHeader.biBitCount = 1;
bitmap_info->bmiHeader.biCompression = BI_RGB;
@ -205,7 +205,7 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
surface->bitmap);
if (!surface->saved_dc_bitmap)
goto FAIL;
if (bitmap_info && num_palette > 2)
free (bitmap_info);
@ -219,11 +219,11 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
case CAIRO_FORMAT_RGB24:
*rowstride_out = 4 * width;
break;
case CAIRO_FORMAT_A8:
*rowstride_out = (width + 3) & ~3;
break;
case CAIRO_FORMAT_A1:
*rowstride_out = ((width + 31) & ~31) / 8;
break;
@ -234,7 +234,7 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
FAIL:
status = _cairo_win32_print_gdi_error ("_create_dc_and_bitmap");
if (bitmap_info && num_palette > 2)
free (bitmap_info);
@ -242,17 +242,17 @@ _create_dc_and_bitmap (cairo_win32_surface_t *surface,
SelectObject (surface->dc, surface->saved_dc_bitmap);
surface->saved_dc_bitmap = NULL;
}
if (surface->bitmap) {
DeleteObject (surface->bitmap);
surface->bitmap = NULL;
}
if (surface->dc) {
DeleteDC (surface->dc);
surface->dc = NULL;
}
return status;
}
@ -285,9 +285,9 @@ _cairo_win32_surface_create_for_dc (HDC original_dc,
status = CAIRO_STATUS_NO_MEMORY;
goto FAIL;
}
surface->format = format;
surface->clip_rect.x = 0;
surface->clip_rect.y = 0;
surface->clip_rect.width = width;
@ -369,15 +369,15 @@ _cairo_win32_surface_get_subimage (cairo_win32_surface_t *surface,
cairo_status_t status;
cairo_content_t content = _cairo_content_from_format (surface->format);
local =
local =
(cairo_win32_surface_t *) _cairo_win32_surface_create_similar (surface,
content,
width,
height);
if (local->base.status)
return CAIRO_STATUS_NO_MEMORY;
if (!BitBlt (local->dc,
if (!BitBlt (local->dc,
0, 0,
width, height,
surface->dc,
@ -396,7 +396,7 @@ _cairo_win32_surface_get_subimage (cairo_win32_surface_t *surface,
}
*local_out = local;
return CAIRO_STATUS_SUCCESS;
FAIL:
@ -442,16 +442,16 @@ _cairo_win32_surface_release_source_image (void *abstract_surf
void *image_extra)
{
cairo_win32_surface_t *local = image_extra;
if (local)
cairo_surface_destroy ((cairo_surface_t *)local);
}
static cairo_status_t
_cairo_win32_surface_acquire_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void **image_extra)
{
cairo_win32_surface_t *surface = abstract_surface;
@ -490,15 +490,15 @@ _cairo_win32_surface_acquire_dest_image (void *abstract_surfa
x2 = interest_rect->x + interest_rect->width;
if (interest_rect->y + interest_rect->height < y2)
y2 = interest_rect->y + interest_rect->height;
if (x1 >= x2 || y1 >= y2) {
*image_out = NULL;
*image_extra = NULL;
return CAIRO_STATUS_SUCCESS;
}
status = _cairo_win32_surface_get_subimage (abstract_surface,
status = _cairo_win32_surface_get_subimage (abstract_surface,
x1, y1, x2 - x1, y2 - y1,
&local);
if (status)
@ -506,7 +506,7 @@ _cairo_win32_surface_acquire_dest_image (void *abstract_surfa
*image_out = (cairo_image_surface_t *)local->image;
*image_extra = local;
image_rect->x = x1;
image_rect->y = y1;
image_rect->width = x2 - x1;
@ -517,14 +517,14 @@ _cairo_win32_surface_acquire_dest_image (void *abstract_surfa
static void
_cairo_win32_surface_release_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra)
{
cairo_win32_surface_t *surface = abstract_surface;
cairo_win32_surface_t *local = image_extra;
if (!local)
return;
@ -589,22 +589,22 @@ _composite_alpha_blend (cairo_win32_surface_t *dst,
*/
if (!alpha_blend_checked) {
OSVERSIONINFO os;
os.dwOSVersionInfoSize = sizeof (os);
GetVersionEx (&os);
/* If running on Win98, disable using AlphaBlend()
* to avoid Win98 AlphaBlend() bug */
if (VER_PLATFORM_WIN32_WINDOWS != os.dwPlatformId ||
os.dwMajorVersion != 4 || os.dwMinorVersion != 10)
{
HMODULE msimg32_dll = LoadLibrary ("msimg32");
if (msimg32_dll != NULL)
alpha_blend = (cairo_alpha_blend_func_t)GetProcAddress (msimg32_dll,
"AlphaBlend");
}
alpha_blend_checked = TRUE;
}
@ -612,7 +612,7 @@ _composite_alpha_blend (cairo_win32_surface_t *dst,
return CAIRO_INT_STATUS_UNSUPPORTED;
if (GetDeviceCaps(dst->dc, SHADEBLENDCAPS) == SB_NONE)
return CAIRO_INT_STATUS_UNSUPPORTED;
blend_function.BlendOp = AC_SRC_OVER;
blend_function.BlendFlags = 0;
blend_function.SourceConstantAlpha = alpha;
@ -626,7 +626,7 @@ _composite_alpha_blend (cairo_win32_surface_t *dst,
width, height,
blend_function))
return _cairo_win32_print_gdi_error ("_cairo_win32_surface_composite");
return CAIRO_STATUS_SUCCESS;
}
@ -672,7 +672,7 @@ _cairo_win32_surface_composite (cairo_operator_t op,
if (src->base.backend != dst->base.backend)
return CAIRO_INT_STATUS_UNSUPPORTED;
integer_transform = _cairo_matrix_is_integer_translation (&pattern->matrix, &itx, &ity);
if (!integer_transform)
return CAIRO_INT_STATUS_UNSUPPORTED;
@ -711,7 +711,7 @@ _cairo_win32_surface_composite (cairo_operator_t op,
if (alpha == 255 &&
(op == CAIRO_OPERATOR_SOURCE ||
(src->format == CAIRO_FORMAT_RGB24 && op == CAIRO_OPERATOR_OVER))) {
if (!BitBlt (dst->dc,
dst_x, dst_y,
width, height,
@ -721,7 +721,7 @@ _cairo_win32_surface_composite (cairo_operator_t op,
return _cairo_win32_print_gdi_error ("_cairo_win32_surface_composite");
return CAIRO_STATUS_SUCCESS;
} else if ((src->format == CAIRO_FORMAT_RGB24 || src->format == CAIRO_FORMAT_ARGB32) &&
(dst->format == CAIRO_FORMAT_RGB24 || dst->format == CAIRO_FORMAT_ARGB32) &&
op == CAIRO_OPERATOR_OVER) {
@ -730,7 +730,7 @@ _cairo_win32_surface_composite (cairo_operator_t op,
src_x, src_y,
dst_x, dst_y, width, height);
}
return CAIRO_INT_STATUS_UNSUPPORTED;
}
@ -752,13 +752,13 @@ categorize_solid_dest_operator (cairo_operator_t op,
source = SOURCE_TRANSPARENT;
else
source = SOURCE_OTHER;
switch (op) {
case CAIRO_OPERATOR_CLEAR: /* 0 0 */
case CAIRO_OPERATOR_OUT: /* 1 - Ab 0 */
return DO_CLEAR;
break;
case CAIRO_OPERATOR_SOURCE: /* 1 0 */
case CAIRO_OPERATOR_IN: /* Ab 0 */
return DO_SOURCE;
@ -773,7 +773,7 @@ categorize_solid_dest_operator (cairo_operator_t op,
else
return DO_UNSUPPORTED;
break;
case CAIRO_OPERATOR_DEST_OUT: /* 0 1 - Aa */
case CAIRO_OPERATOR_XOR: /* 1 - Ab 1 - Aa */
if (source == SOURCE_SOLID)
@ -783,7 +783,7 @@ categorize_solid_dest_operator (cairo_operator_t op,
else
return DO_UNSUPPORTED;
break;
case CAIRO_OPERATOR_DEST: /* 0 1 */
case CAIRO_OPERATOR_DEST_OVER:/* 1 - Ab 1 */
case CAIRO_OPERATOR_SATURATE: /* min(1,(1-Ab)/Aa) 1 */
@ -799,14 +799,14 @@ categorize_solid_dest_operator (cairo_operator_t op,
else
return DO_UNSUPPORTED;
break;
case CAIRO_OPERATOR_ADD: /* 1 1 */
if (source == SOURCE_TRANSPARENT)
return DO_NOTHING;
else
return DO_UNSUPPORTED;
break;
}
}
ASSERT_NOT_REACHED;
return DO_UNSUPPORTED;
@ -816,7 +816,7 @@ static cairo_int_status_t
_cairo_win32_surface_fill_rectangles (void *abstract_surface,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects)
{
cairo_win32_surface_t *surface = abstract_surface;
@ -838,7 +838,7 @@ _cairo_win32_surface_fill_rectangles (void *abstract_surface,
switch (categorize_solid_dest_operator (op, color->alpha_short)) {
case DO_CLEAR:
new_color = RGB (0, 0, 0);
break;
break;
case DO_SOURCE:
new_color = RGB (color->red_short >> 8, color->green_short >> 8, color->blue_short >> 8);
break;
@ -848,11 +848,11 @@ _cairo_win32_surface_fill_rectangles (void *abstract_surface,
default:
return CAIRO_INT_STATUS_UNSUPPORTED;
}
new_brush = CreateSolidBrush (new_color);
if (!new_brush)
return _cairo_win32_print_gdi_error ("_cairo_win32_surface_fill_rectangles");
for (i = 0; i < num_rects; i++) {
RECT rect;
@ -866,14 +866,14 @@ _cairo_win32_surface_fill_rectangles (void *abstract_surface,
}
DeleteObject (new_brush);
return CAIRO_STATUS_SUCCESS;
FAIL:
status = _cairo_win32_print_gdi_error ("_cairo_win32_surface_fill_rectangles");
DeleteObject (new_brush);
return status;
}
@ -906,7 +906,7 @@ _cairo_win32_surface_set_clip_region (void *abstract_surface,
return _cairo_win32_print_gdi_error ("_cairo_win32_surface_set_clip_region (reset)");
return CAIRO_STATUS_SUCCESS;
} else {
pixman_box16_t *boxes = pixman_region_rects (region);
int num_boxes = pixman_region_num_rects (region);
@ -943,7 +943,7 @@ _cairo_win32_surface_set_clip_region (void *abstract_surface,
gdi_region = ExtCreateRegion (NULL, data_size, data);
free (data);
if (!gdi_region)
return CAIRO_STATUS_NO_MEMORY;
@ -969,7 +969,7 @@ _cairo_win32_surface_set_clip_region (void *abstract_surface,
static cairo_int_status_t
_cairo_win32_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_win32_surface_t *surface = abstract_surface;
@ -1021,7 +1021,7 @@ _cairo_win32_surface_show_glyphs (void *surface,
/* We can only handle operator SOURCE or OVER with the destination
* having no alpha */
if ((op != CAIRO_OPERATOR_SOURCE && op != CAIRO_OPERATOR_OVER) ||
if ((op != CAIRO_OPERATOR_SOURCE && op != CAIRO_OPERATOR_OVER) ||
(dst->format != CAIRO_FORMAT_RGB24))
return CAIRO_INT_STATUS_UNSUPPORTED;
@ -1060,7 +1060,6 @@ _cairo_win32_surface_show_glyphs (void *surface,
else
dx_buf[i] = floor(((glyphs[i+1].x - glyphs[i].x) * WIN32_FONT_LOGICAL_SCALE) + 0.5);
if (i == num_glyphs - 1 || glyphs[i].y != glyphs[i+1].y) {
const int offset = (i - output_count) + 1;
double user_x = glyphs[offset].x;
@ -1103,20 +1102,20 @@ FAIL:
free(dx_buf);
}
return (win_result) ? CAIRO_STATUS_SUCCESS : CAIRO_INT_STATUS_UNSUPPORTED;
}
}
#undef STACK_GLYPH_SIZE
/**
* cairo_win32_surface_create:
* @hdc: the DC to create a surface for
*
*
* Creates a cairo surface that targets the given DC. The DC will be
* queried for its initial clip extents, and this will be used as the
* size of the cairo surface. Also, if the DC is a raster DC, it will
* be queried for its pixel format and the cairo surface format will
* be set appropriately.
*
*
* Return value: the newly created surface
**/
cairo_surface_t *
@ -1165,11 +1164,11 @@ cairo_win32_surface_create (HDC hdc)
surface->image = NULL;
surface->format = format;
surface->dc = hdc;
surface->bitmap = NULL;
surface->saved_dc_bitmap = NULL;
surface->clip_rect.x = rect.left;
surface->clip_rect.y = rect.top;
surface->clip_rect.width = rect.right - rect.left;
@ -1197,16 +1196,17 @@ cairo_win32_surface_create (HDC hdc)
/**
* cairo_win32_surface_create_with_dib:
* @format: format of pixels in the surface to create
* @format: format of pixels in the surface to create
* @width: width of the surface, in pixels
* @height: height of the surface, in pixels
*
*
* Creates a device-independent-bitmap surface not associated with
* any particular existing surface or device context. The created
* bitmap will be unititialized.
*
*
* Return value: the newly created surface
*
* Since: 1.2
**/
cairo_surface_t *
cairo_win32_surface_create_with_dib (cairo_format_t format,
@ -1216,13 +1216,12 @@ cairo_win32_surface_create_with_dib (cairo_format_t format,
return _cairo_win32_surface_create_for_dc (NULL, format, width, height);
}
/**
* _cairo_surface_is_win32:
* @surface: a #cairo_surface_t
*
*
* Checks if a surface is an #cairo_win32_surface_t
*
*
* Return value: True if the surface is an win32 surface
**/
int
@ -1239,6 +1238,8 @@ _cairo_surface_is_win32 (cairo_surface_t *surface)
* Also returns NULL if the surface is not a win32 surface.
*
* Return value: HDC or NULL if no HDC available.
*
* Since: 1.2
**/
HDC
cairo_win32_surface_get_dc (cairo_surface_t *surface)
@ -1289,6 +1290,7 @@ static const cairo_surface_backend_t cairo_win32_surface_backend = {
NULL /* snapshot */
};
#if 0
/*
* Without pthread, on win32 we need to initialize all the 'mutex'es
* before use. It is guaranteed that DllMain will get called single
@ -1300,9 +1302,6 @@ CRITICAL_SECTION cairo_toy_font_face_hash_table_mutex;
CRITICAL_SECTION cairo_scaled_font_map_mutex;
CRITICAL_SECTION cairo_ft_unscaled_font_map_mutex;
#if 0
// Mozilla doesn't use the mutexes, and this definition of DllMain
// conflicts with libxul.
BOOL WINAPI
DllMain (HINSTANCE hinstDLL,
DWORD fdwReason,
@ -1324,6 +1323,5 @@ DllMain (HINSTANCE hinstDLL,
}
return TRUE;
}
#endif // 0
#endif
#endif

Просмотреть файл

@ -193,6 +193,8 @@ typedef struct cairo_xcb_surface {
cairo_surface_t base;
XCBConnection *dpy;
XCBSCREEN *screen;
XCBGCONTEXT gc;
XCBDRAWABLE drawable;
int owns_pixmap;
@ -277,9 +279,9 @@ _cairo_xcb_surface_create_similar (void *abstract_src,
d.pixmap, src->drawable,
width <= 0 ? 1 : width,
height <= 0 ? 1 : height);
surface = (cairo_xcb_surface_t *)
cairo_xcb_surface_create_with_xrender_format (dpy, d,
cairo_xcb_surface_create_with_xrender_format (dpy, d, src->screen,
&xrender_format,
width, height);
if (surface->base.status) {
@ -378,9 +380,9 @@ _CAIRO_MASK_FORMAT (cairo_format_masks_t *masks, cairo_format_t *format)
static cairo_status_t
_get_image_surface (cairo_xcb_surface_t *surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect)
cairo_rectangle_int16_t *image_rect)
{
cairo_image_surface_t *image;
XCBGetImageRep *imagerep;
@ -396,13 +398,13 @@ _get_image_surface (cairo_xcb_surface_t *surface,
y2 = surface->height;
if (interest_rect) {
cairo_rectangle_fixed_t rect;
cairo_rectangle_int16_t rect;
rect.x = interest_rect->x;
rect.y = interest_rect->y;
rect.width = interest_rect->width;
rect.height = interest_rect->height;
if (rect.x > x1)
x1 = rect.x;
if (rect.y > y1)
@ -530,7 +532,7 @@ _get_image_surface (cairo_xcb_surface_t *surface,
image = (cairo_image_surface_t *)
cairo_image_surface_create_for_data (data,
format,
x2 - x1,
x2 - x1,
y2 - y1,
bytes_per_line);
if (image->base.status)
@ -588,7 +590,7 @@ _draw_image_surface (cairo_xcb_surface_t *surface,
image->width,
image->height,
dst_x, dst_y,
/* left_pad */ 0, image->depth,
/* left_pad */ 0, image->depth,
data_len, image->data);
return CAIRO_STATUS_SUCCESS;
@ -623,9 +625,9 @@ _cairo_xcb_surface_release_source_image (void *abstract_surfac
static cairo_status_t
_cairo_xcb_surface_acquire_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect_out,
cairo_rectangle_int16_t *image_rect_out,
void **image_extra)
{
cairo_xcb_surface_t *surface = abstract_surface;
@ -644,9 +646,9 @@ _cairo_xcb_surface_acquire_dest_image (void *abstract_surface
static void
_cairo_xcb_surface_release_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra)
{
cairo_xcb_surface_t *surface = abstract_surface;
@ -657,6 +659,18 @@ _cairo_xcb_surface_release_dest_image (void *abstract_surface,
cairo_surface_destroy (&image->base);
}
/*
* Return whether two xcb surfaces share the same
* screen. Both core and Render drawing require this
* when using multiple drawables in an operation.
*/
static cairo_bool_t
_cairo_xcb_surface_same_screen (cairo_xcb_surface_t *dst,
cairo_xcb_surface_t *src)
{
return dst->dpy == src->dpy && dst->screen == src->screen;
}
static cairo_status_t
_cairo_xcb_surface_clone_similar (void *abstract_surface,
cairo_surface_t *src,
@ -668,9 +682,9 @@ _cairo_xcb_surface_clone_similar (void *abstract_surface,
if (src->backend == surface->base.backend ) {
cairo_xcb_surface_t *xcb_src = (cairo_xcb_surface_t *)src;
if (xcb_src->dpy == surface->dpy) {
if (_cairo_xcb_surface_same_screen(surface, xcb_src)) {
*clone_out = cairo_surface_reference (src);
return CAIRO_STATUS_SUCCESS;
}
} else if (_cairo_surface_is_image (src)) {
@ -679,20 +693,20 @@ _cairo_xcb_surface_clone_similar (void *abstract_surface,
if (surface->base.status)
return surface->base.status;
clone = (cairo_xcb_surface_t *)
_cairo_xcb_surface_create_similar (surface, content,
image_src->width, image_src->height);
if (clone->base.status)
return CAIRO_STATUS_NO_MEMORY;
_draw_image_surface (clone, image_src, 0, 0);
*clone_out = &clone->base;
return CAIRO_STATUS_SUCCESS;
}
return CAIRO_INT_STATUS_UNSUPPORTED;
}
@ -727,10 +741,10 @@ _cairo_xcb_surface_set_matrix (cairo_xcb_surface_t *surface,
if (memcmp (&xtransform, &identity, sizeof (XCBRenderTRANSFORM)) == 0)
return CAIRO_STATUS_SUCCESS;
return CAIRO_INT_STATUS_UNSUPPORTED;
}
XCBRenderSetPictureTransform (surface->dpy, surface->picture, xtransform);
return CAIRO_STATUS_SUCCESS;
@ -744,15 +758,15 @@ _cairo_xcb_surface_set_filter (cairo_xcb_surface_t *surface,
if (!surface->picture.xid)
return CAIRO_STATUS_SUCCESS;
if (!CAIRO_SURFACE_RENDER_HAS_FILTERS (surface))
{
if (filter == CAIRO_FILTER_FAST || filter == CAIRO_FILTER_NEAREST)
return CAIRO_STATUS_SUCCESS;
return CAIRO_INT_STATUS_UNSUPPORTED;
}
switch (filter) {
case CAIRO_FILTER_FAST:
render_filter = "fast";
@ -803,7 +817,7 @@ _cairo_xcb_surface_set_attributes (cairo_xcb_surface_t *surface,
status = _cairo_xcb_surface_set_matrix (surface, &attributes->matrix);
if (status)
return status;
switch (attributes->extend) {
case CAIRO_EXTEND_NONE:
_cairo_xcb_surface_set_repeat (surface, 0);
@ -894,7 +908,7 @@ _cairo_xcb_surface_composite (cairo_operator_t op,
&src_attr, &mask_attr);
if (status)
return status;
status = _cairo_xcb_surface_set_attributes (src, &src_attr);
if (status == CAIRO_STATUS_SUCCESS)
{
@ -917,7 +931,7 @@ _cairo_xcb_surface_composite (cairo_operator_t op,
else
{
static XCBRenderPICTURE maskpict = { 0 };
XCBRenderComposite (dst->dpy,
_render_operator (op),
src->picture,
@ -933,7 +947,7 @@ _cairo_xcb_surface_composite (cairo_operator_t op,
if (mask)
_cairo_pattern_release_surface (mask_pattern, &mask->base, &mask_attr);
_cairo_pattern_release_surface (src_pattern, &src->base, &src_attr);
return status;
@ -943,7 +957,7 @@ static cairo_int_status_t
_cairo_xcb_surface_fill_rectangles (void *abstract_surface,
cairo_operator_t op,
const cairo_color_t * color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects)
{
cairo_xcb_surface_t *surface = abstract_surface;
@ -990,14 +1004,14 @@ _cairo_xcb_surface_composite_trapezoids (cairo_operator_t op,
if (!CAIRO_SURFACE_RENDER_HAS_TRAPEZOIDS (dst))
return CAIRO_INT_STATUS_UNSUPPORTED;
status = _cairo_pattern_acquire_surface (pattern, &dst->base,
src_x, src_y, width, height,
(cairo_surface_t **) &src,
&attributes);
if (status)
return status;
if (traps[0].left.p1.y < traps[0].left.p2.y) {
render_reference_x = _cairo_fixed_integer_floor (traps[0].left.p1.x);
render_reference_y = _cairo_fixed_integer_floor (traps[0].left.p1.y);
@ -1026,7 +1040,7 @@ _cairo_xcb_surface_composite_trapezoids (cairo_operator_t op,
_render_operator (op),
src->picture, dst->picture,
render_format.id,
render_src_x + attributes.x_offset,
render_src_x + attributes.x_offset,
render_src_y + attributes.y_offset,
num_traps, (XCBRenderTRAP *) traps);
@ -1037,7 +1051,7 @@ _cairo_xcb_surface_composite_trapezoids (cairo_operator_t op,
static cairo_int_status_t
_cairo_xcb_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
cairo_xcb_surface_t *surface = abstract_surface;
@ -1078,9 +1092,9 @@ static const cairo_surface_backend_t cairo_xcb_surface_backend = {
/**
* _cairo_surface_is_xcb:
* @surface: a #cairo_surface_t
*
*
* Checks if a surface is a #cairo_xcb_surface_t
*
*
* Return value: True if the surface is an xcb surface
**/
static cairo_bool_t
@ -1112,6 +1126,7 @@ query_render_version (XCBConnection *c, cairo_xcb_surface_t *surface)
static cairo_surface_t *
_cairo_xcb_surface_create_internal (XCBConnection *dpy,
XCBDRAWABLE drawable,
XCBSCREEN *screen,
XCBVISUALTYPE *visual,
XCBRenderPICTFORMINFO *format,
int width,
@ -1130,6 +1145,7 @@ _cairo_xcb_surface_create_internal (XCBConnection *dpy,
_xcb_render_format_to_content (format));
surface->dpy = dpy;
surface->screen = screen;
surface->gc.xid = 0;
surface->drawable = drawable;
@ -1150,30 +1166,25 @@ _cairo_xcb_surface_create_internal (XCBConnection *dpy,
if (format) {
surface->depth = format->depth;
} else if (visual) {
XCBSCREENIter roots;
XCBDEPTHIter depths;
XCBVISUALTYPEIter visuals;
/* This is ugly, but we have to walk over all visuals
* for the display to find the depth.
* for the screen to find the depth.
*/
roots = XCBSetupRootsIter(XCBGetSetup(surface->dpy));
for(; roots.rem; XCBSCREENNext(&roots))
{
depths = XCBSCREENAllowedDepthsIter(roots.data);
for(; depths.rem; XCBDEPTHNext(&depths))
depths = XCBSCREENAllowedDepthsIter(screen);
for(; depths.rem; XCBDEPTHNext(&depths))
{
visuals = XCBDEPTHVisualsIter(depths.data);
for(; visuals.rem; XCBVISUALTYPENext(&visuals))
{
visuals = XCBDEPTHVisualsIter(depths.data);
for(; visuals.rem; XCBVISUALTYPENext(&visuals))
if(visuals.data->visual_id.id == visual->visual_id.id)
{
if(visuals.data->visual_id.id == visual->visual_id.id)
{
surface->depth = depths.data->depth;
goto found;
}
surface->depth = depths.data->depth;
goto found;
}
}
}
}
found:
;
}
@ -1207,6 +1218,29 @@ _cairo_xcb_surface_create_internal (XCBConnection *dpy,
return (cairo_surface_t *) surface;
}
static XCBSCREEN *
_cairo_xcb_screen_from_visual (XCBConnection *c, XCBVISUALTYPE *visual)
{
XCBSCREENIter s = XCBSetupRootsIter(XCBGetSetup(c));
for (; s.rem; XCBSCREENNext(&s))
{
if (s.data->root_visual.id == visual->visual_id.id)
return s.data;
XCBDEPTHIter d = XCBSCREENAllowedDepthsIter(s.data);
for (; d.rem; XCBDEPTHNext(&d))
{
XCBVISUALTYPEIter v = XCBDEPTHVisualsIter(d.data);
for (; v.rem; XCBVISUALTYPENext(&v))
{
if (v.data->visual_id.id == visual->visual_id.id)
return s.data;
}
}
}
return NULL;
}
/**
* cairo_xcb_surface_create:
* @c: an XCB connection
@ -1216,7 +1250,7 @@ _cairo_xcb_surface_create_internal (XCBConnection *dpy,
* Currently, only TrueColor visuals are fully supported.
* @width: the current width of @drawable.
* @height: the current height of @drawable.
*
*
* Creates an XCB surface that draws to the given drawable.
* The way that colors are represented in the drawable is specified
* by the provided visual.
@ -1224,7 +1258,7 @@ _cairo_xcb_surface_create_internal (XCBConnection *dpy,
* NOTE: If @drawable is a window, then the function
* cairo_xcb_surface_set_size must be called whenever the size of the
* window changes.
*
*
* Return value: the newly created surface
**/
cairo_surface_t *
@ -1234,7 +1268,14 @@ cairo_xcb_surface_create (XCBConnection *c,
int width,
int height)
{
return _cairo_xcb_surface_create_internal (c, drawable,
XCBSCREEN *screen = _cairo_xcb_screen_from_visual (c, visual);
if (screen == NULL) {
_cairo_error (CAIRO_STATUS_INVALID_VISUAL);
return (cairo_surface_t*) &_cairo_surface_nil;
}
return _cairo_xcb_surface_create_internal (c, drawable, screen,
visual, NULL,
width, height, 0);
}
@ -1243,23 +1284,25 @@ cairo_xcb_surface_create (XCBConnection *c,
* cairo_xcb_surface_create_for_bitmap:
* @c: an XCB connection
* @bitmap: an XCB Pixmap (a depth-1 pixmap)
* @screen: an XCB Screen
* @width: the current width of @bitmap
* @height: the current height of @bitmap
*
* Creates an XCB surface that draws to the given bitmap.
* This will be drawn to as a CAIRO_FORMAT_A1 object.
*
*
* Return value: the newly created surface
**/
cairo_surface_t *
cairo_xcb_surface_create_for_bitmap (XCBConnection *c,
XCBPIXMAP bitmap,
XCBSCREEN *screen,
int width,
int height)
{
XCBDRAWABLE drawable;
drawable.pixmap = bitmap;
return _cairo_xcb_surface_create_internal (c, drawable,
return _cairo_xcb_surface_create_internal (c, drawable, screen,
NULL, NULL,
width, height, 1);
}
@ -1268,29 +1311,31 @@ cairo_xcb_surface_create_for_bitmap (XCBConnection *c,
* cairo_xcb_surface_create_with_xrender_format:
* @c: an XCB connection
* @drawable: an XCB drawable
* @screen: the XCB screen associated with @drawable
* @format: the picture format to use for drawing to @drawable. The
* depth of @format mush match the depth of the drawable.
* @width: the current width of @drawable
* @height: the current height of @drawable
*
*
* Creates an XCB surface that draws to the given drawable.
* The way that colors are represented in the drawable is specified
* by the provided picture format.
*
* NOTE: If @drawable is a Window, then the function
* cairo_xlib_surface_set_size must be called whenever the size of the
* cairo_xcb_surface_set_size must be called whenever the size of the
* window changes.
*
* Return value: the newly created surface.
*
* Return value: the newly created surface.
**/
cairo_surface_t *
cairo_xcb_surface_create_with_xrender_format (XCBConnection *c,
XCBDRAWABLE drawable,
XCBSCREEN *screen,
XCBRenderPICTFORMINFO *format,
int width,
int height)
{
return _cairo_xcb_surface_create_internal (c, drawable,
return _cairo_xcb_surface_create_internal (c, drawable, screen,
NULL, format,
width, height, 0);
}
@ -1300,7 +1345,7 @@ cairo_xcb_surface_create_with_xrender_format (XCBConnection *c,
* @surface: a #cairo_surface_t for the XCB backend
* @width: the new width of the surface
* @height: the new height of the surface
*
*
* Informs cairo of the new size of the XCB drawable underlying the
* surface. For a surface created for a window (rather than a pixmap),
* this function must be called each time the size of the window
@ -1326,4 +1371,3 @@ cairo_xcb_surface_set_size (cairo_surface_t *surface,
xcb_surface->width = width;
xcb_surface->height = height;
}

Просмотреть файл

@ -49,6 +49,7 @@ CAIRO_BEGIN_DECLS
cairo_public cairo_surface_t *
cairo_xcb_surface_create_with_xrender_format (XCBConnection *c,
XCBDRAWABLE drawable,
XCBSCREEN *screen,
XCBRenderPICTFORMINFO *format,
int width,
int height);

Просмотреть файл

@ -55,6 +55,7 @@ cairo_xcb_surface_create (XCBConnection *c,
cairo_public cairo_surface_t *
cairo_xcb_surface_create_for_bitmap (XCBConnection *c,
XCBPIXMAP bitmap,
XCBSCREEN *screen,
int width,
int height);

Просмотреть файл

@ -40,11 +40,11 @@ typedef struct _cairo_xlib_screen_info cairo_xlib_screen_info_t;
struct _cairo_xlib_screen_info {
cairo_xlib_screen_info_t *next;
Display *display;
Screen *screen;
cairo_bool_t has_render;
cairo_font_options_t font_options;
};

Просмотреть файл

@ -65,7 +65,7 @@ static int
parse_boolean (const char *v)
{
char c0, c1;
c0 = *v;
if (c0 == 't' || c0 == 'T' || c0 == 'y' || c0 == 'Y' || c0 == '1')
return 1;
@ -79,7 +79,7 @@ parse_boolean (const char *v)
if (c1 == 'f' || c1 == 'F')
return 0;
}
return -1;
}
@ -90,7 +90,7 @@ get_boolean_default (Display *dpy,
{
char *v;
int i;
v = XGetDefault (dpy, "Xft", option);
if (v) {
i = parse_boolean (v);
@ -99,7 +99,7 @@ get_boolean_default (Display *dpy,
return TRUE;
}
}
return FALSE;
}
@ -110,17 +110,17 @@ get_integer_default (Display *dpy,
{
int i;
char *v, *e;
v = XGetDefault (dpy, "Xft", option);
if (v) {
if (FcNameConstant ((FcChar8 *) v, value))
return TRUE;
i = strtol (v, &e, 0);
if (e != v)
return TRUE;
}
return FALSE;
}
@ -145,23 +145,23 @@ _cairo_xlib_init_screen_font_options (cairo_xlib_screen_info_t *info)
if (!get_boolean_default (info->display, "antialias", &xft_antialias))
xft_antialias = TRUE;
if (!get_boolean_default (info->display, "hinting", &xft_hinting))
xft_hinting = TRUE;
if (!get_integer_default (info->display, "hintstyle", &xft_hintstyle))
xft_hintstyle = FC_HINT_FULL;
if (!get_integer_default (info->display, "rgba", &xft_rgba))
{
xft_rgba = FC_RGBA_UNKNOWN;
#if RENDER_MAJOR > 0 || RENDER_MINOR >= 6
if (info->has_render)
{
int render_order = XRenderQuerySubpixelOrder (info->display,
XScreenNumberOfScreen (info->screen));
switch (render_order)
{
default:
@ -208,7 +208,7 @@ _cairo_xlib_init_screen_font_options (cairo_xlib_screen_info_t *info)
} else {
hint_style = CAIRO_HINT_STYLE_NONE;
}
switch (xft_rgba) {
case FC_RGBA_RGB:
subpixel_order = CAIRO_SUBPIXEL_ORDER_RGB;
@ -352,7 +352,7 @@ _cairo_xlib_screen_info_get (Display *dpy, Screen *screen)
info = NULL;
goto out;
}
XESetCloseDisplay (dpy, codes->extension, _cairo_xlib_close_display);
}
@ -360,15 +360,15 @@ _cairo_xlib_screen_info_get (Display *dpy, Screen *screen)
info->screen = screen;
info->has_render = (XRenderQueryExtension (dpy, &event_base, &error_base) &&
(XRenderFindVisualFormat (dpy, DefaultVisual (dpy, DefaultScreen (dpy))) != 0));
_cairo_xlib_init_screen_font_options (info);
info->next = _cairo_xlib_screen_list;
_cairo_xlib_screen_list = info;
out:
CAIRO_MUTEX_UNLOCK (_xlib_screen_mutex);
return info;
}

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -1,55 +0,0 @@
/* cairo - a vector graphics library with display and print output
*
* Copyright © 2005 Red Hat, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it either under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation
* (the "LGPL") or, at your option, under the terms of the Mozilla
* Public License Version 1.1 (the "MPL"). If you do not alter this
* notice, a recipient may use your version of this file under either
* the MPL or the LGPL.
*
* You should have received a copy of the LGPL along with this library
* in the file COPYING-LGPL-2.1; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
* You should have received a copy of the MPL along with this library
* in the file COPYING-MPL-1.1
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
* OF ANY KIND, either express or implied. See the LGPL or the MPL for
* the specific language governing rights and limitations.
*
* The Original Code is the cairo graphics library.
*
* The Initial Developer of the Original Code is University of Southern
* California.
*
* Contributor(s):
* Carl D. Worth <cworth@cworth.org>
*/
#ifndef CAIRO_XLIB_TEST_H
#define CAIRO_XLIB_TEST_H
#include <cairo.h>
#if CAIRO_HAS_XLIB_SURFACE
#include <cairo-xlib.h>
CAIRO_BEGIN_DECLS
void
cairo_xlib_test_disable_render (void);
CAIRO_END_DECLS
#endif /* CAIRO_HAS_XLIB_SURFACE */
#endif /* CAIRO_XLIB_H */

Просмотреть файл

@ -53,7 +53,6 @@ cairo_xlib_surface_create_with_xrender_format (Display *dpy,
int width,
int height);
CAIRO_END_DECLS
#else /* CAIRO_HAS_XLIB_SURFACE */

Просмотреть файл

@ -85,6 +85,12 @@ cairo_xlib_surface_get_visual (cairo_surface_t *surface);
cairo_public int
cairo_xlib_surface_get_depth (cairo_surface_t *surface);
cairo_public int
cairo_xlib_surface_get_width (cairo_surface_t *surface);
cairo_public int
cairo_xlib_surface_get_height (cairo_surface_t *surface);
CAIRO_END_DECLS
#else /* CAIRO_HAS_XLIB_SURFACE */
@ -92,4 +98,3 @@ CAIRO_END_DECLS
#endif /* CAIRO_HAS_XLIB_SURFACE */
#endif /* CAIRO_XLIB_H */

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -167,7 +167,7 @@ typedef struct _cairo_user_data_key {
* @CAIRO_STATUS_INVALID_VISUAL: invalid value for an input Visual*
* @CAIRO_STATUS_FILE_NOT_FOUND: file not found
* @CAIRO_STATUS_INVALID_DASH: invalid value for a dash setting
* @CAIRO_STATUS_INVALID_DSC_COMMENT: invalid value for a DSC comment
* @CAIRO_STATUS_INVALID_DSC_COMMENT: invalid value for a DSC comment (Since 1.2)
*
* #cairo_status_t is used to indicate errors that can occur when
* using Cairo. In some cases it is returned directly by functions.
@ -204,7 +204,7 @@ typedef enum _cairo_status {
* @CAIRO_CONTENT_ALPHA: The surface will hold alpha content only.
* @CAIRO_CONTENT_COLOR_ALPHA: The surface will hold color and alpha content.
*
* @cairo_content_t is used to describe the content that a surface will
* #cairo_content_t is used to describe the content that a surface will
* contain, whether color information, alpha information (translucence
* vs. opacity), or both.
*
@ -341,7 +341,7 @@ cairo_set_tolerance (cairo_t *cr, double tolerance);
* @CAIRO_ANTIALIAS_SUBPIXEL: Perform antialiasing by taking
* advantage of the order of subpixel elements on devices
* such as LCD panels
*
*
* Specifies the type of antialiasing to do when rendering text or shapes.
**/
typedef enum _cairo_antialias {
@ -386,7 +386,6 @@ cairo_set_fill_rule (cairo_t *cr, cairo_fill_rule_t fill_rule);
cairo_public void
cairo_set_line_width (cairo_t *cr, double width);
/**
* cairo_line_cap_t
* @CAIRO_LINE_CAP_BUTT: start(stop) the line exactly at the start(end) point
@ -693,7 +692,7 @@ typedef struct {
* or <firstterm>external leading</firstterm>. When space
* is at a premium, most fonts can be set with only
* a distance of @ascent+@descent between lines.
* @max_x_advance: the maximum distance in the X direction that
* @max_x_advance: the maximum distance in the X direction that
* the the origin is advanced for any glyph in the font.
* @max_y_advance: the maximum distance in the Y direction that
* the the origin is advanced for any glyph in the font.
@ -701,7 +700,7 @@ typedef struct {
* writing. (The scripts of East Asia are sometimes written
* vertically.)
*
* The #cairo_text_extents_t structure stores metric information for
* The #cairo_font_extents_t structure stores metric information for
* a font. Values are given in the current user-space coordinate
* system.
*
@ -726,7 +725,7 @@ typedef enum _cairo_font_slant {
CAIRO_FONT_SLANT_ITALIC,
CAIRO_FONT_SLANT_OBLIQUE
} cairo_font_slant_t;
typedef enum _cairo_font_weight {
CAIRO_FONT_WEIGHT_NORMAL,
CAIRO_FONT_WEIGHT_BOLD
@ -744,7 +743,7 @@ typedef enum _cairo_font_weight {
* with red at the top
* @CAIRO_SUBPIXEL_ORDER_VBGR: Subpixel elements are arranged vertically
* with blue at the top
*
*
* The subpixel order specifies the order of color elements within
* each pixel on the display device when rendering with an
* antialiasing mode of %CAIRO_ANTIALIAS_SUBPIXEL.
@ -812,7 +811,7 @@ cairo_font_options_create (void);
cairo_public cairo_font_options_t *
cairo_font_options_copy (const cairo_font_options_t *original);
cairo_public void
cairo_public void
cairo_font_options_destroy (cairo_font_options_t *options);
cairo_public cairo_status_t
@ -839,7 +838,7 @@ cairo_font_options_set_subpixel_order (cairo_font_options_t *options,
cairo_subpixel_order_t subpixel_order);
cairo_public cairo_subpixel_order_t
cairo_font_options_get_subpixel_order (const cairo_font_options_t *options);
cairo_public void
cairo_font_options_set_hint_style (cairo_font_options_t *options,
cairo_hint_style_t hint_style);
@ -852,14 +851,13 @@ cairo_font_options_set_hint_metrics (cairo_font_options_t *options,
cairo_public cairo_hint_metrics_t
cairo_font_options_get_hint_metrics (const cairo_font_options_t *options);
/* This interface is for dealing with text as text, not caring about the
font object inside the the cairo_t. */
cairo_public void
cairo_select_font_face (cairo_t *cr,
const char *family,
cairo_font_slant_t slant,
cairo_select_font_face (cairo_t *cr,
const char *family,
cairo_font_slant_t slant,
cairo_font_weight_t weight);
cairo_public void
@ -895,7 +893,7 @@ cairo_public cairo_font_face_t *
cairo_get_font_face (cairo_t *cr);
cairo_public void
cairo_font_extents (cairo_t *cr,
cairo_font_extents (cairo_t *cr,
cairo_font_extents_t *extents);
cairo_public void
@ -908,7 +906,7 @@ cairo_text_extents (cairo_t *cr,
cairo_public void
cairo_glyph_extents (cairo_t *cr,
cairo_glyph_t *glyphs,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_text_extents_t *extents);
@ -931,17 +929,18 @@ cairo_font_face_status (cairo_font_face_t *font_face);
/**
* cairo_font_type_t
* @CAIRO_FONT_TYPE_FT: The font is of type ft
* @CAIRO_FONT_TYPE_WIN32: The font is of type win32
* @CAIRO_FONT_TYPE_ATSUI: The font is of type atsui
* @CAIRO_FONT_TYPE_TOY: The font was created using cairo's toy font api
* @CAIRO_FONT_TYPE_FT: The font is of type FreeType
* @CAIRO_FONT_TYPE_WIN32: The font is of type Win32
* @CAIRO_FONT_TYPE_ATSUI: The font is of type ATSUI
*
* @cairo_font_type_t is used to describe the type of a given font
* #cairo_font_type_t is used to describe the type of a given font
* face or scaled font. The font types are also known as "font
* backends" within cairo.
*
* The type of a font face is determined by the function used to
* create it, which will generally be of the form
* cairo_<type>_font_face_create. The font face type can be queried
* cairo_<emphasis>type</emphasis>_font_face_create. The font face type can be queried
* with cairo_font_face_get_type()
*
* The various cairo_font_face functions can be used with a font face
@ -955,10 +954,12 @@ cairo_font_face_status (cairo_font_face_t *font_face);
* fonts of any type, but some font backends also provide
* type-specific functions that must only be called with a scaled font
* of the appropriate type. These functions have names that begin with
* cairo_<type>_scaled_font such as cairo_ft_scaled_font_lock_face.
* cairo_<emphasis>type</emphasis>_scaled_font such as cairo_ft_scaled_font_lock_face.
*
* The behavior of calling a type-specific function with a scaled font
* of the wrong type is undefined.
*
* Since: 1.2
*/
typedef enum _cairo_font_type {
CAIRO_FONT_TYPE_TOY,
@ -1011,7 +1012,7 @@ cairo_scaled_font_text_extents (cairo_scaled_font_t *scaled_font,
cairo_public void
cairo_scaled_font_glyph_extents (cairo_scaled_font_t *scaled_font,
cairo_glyph_t *glyphs,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_text_extents_t *extents);
@ -1247,14 +1248,13 @@ cairo_surface_status (cairo_surface_t *surface);
* @CAIRO_SURFACE_TYPE_BEOS: The surface is of type beos
* @CAIRO_SURFACE_TYPE_DIRECTFB: The surface is of type directfb
* @CAIRO_SURFACE_TYPE_SVG: The surface is of type svg
* @CAIRO_SURFACE_TYPE_QUARTZ2: The surface is of type quartz2
*
* @cairo_surface_type_t is used to describe the type of a given
* #cairo_surface_type_t is used to describe the type of a given
* surface. The surface types are also known as "backends" or "surface
* backends" within cairo.
*
* The type of a surface is determined by the function used to create
* it, which will generally be of the form cairo_<type>_surface_create,
* it, which will generally be of the form cairo_<emphasis>type</emphasis>_surface_create,
* (though see cairo_surface_create_similar as well).
*
* The surface type can be queried with cairo_surface_get_type()
@ -1263,10 +1263,12 @@ cairo_surface_status (cairo_surface_t *surface);
* any type, but some backends also provide type-specific functions
* that must only be called with a surface of the appropriate
* type. These functions have names that begin with
* cairo_<type>_surface such as cairo_image_surface_get_width().
* cairo_<emphasis>type</emphasis>_surface such as cairo_image_surface_get_width().
*
* The behavior of calling a type-specific function with a surface of
* the wrong type is undefined.
*
* Since: 1.2
*/
typedef enum _cairo_surface_type {
CAIRO_SURFACE_TYPE_IMAGE,
@ -1279,8 +1281,7 @@ typedef enum _cairo_surface_type {
CAIRO_SURFACE_TYPE_WIN32,
CAIRO_SURFACE_TYPE_BEOS,
CAIRO_SURFACE_TYPE_DIRECTFB,
CAIRO_SURFACE_TYPE_SVG,
CAIRO_SURFACE_TYPE_QUARTZ2
CAIRO_SURFACE_TYPE_SVG
} cairo_surface_type_t;
cairo_public cairo_surface_type_t
@ -1339,6 +1340,11 @@ cairo_surface_get_device_offset (cairo_surface_t *surface,
double *x_offset,
double *y_offset);
cairo_public void
cairo_surface_set_fallback_resolution (cairo_surface_t *surface,
double x_pixels_per_inch,
double y_pixels_per_inch);
/* Image-surface functions */
/**
@ -1359,6 +1365,9 @@ cairo_surface_get_device_offset (cairo_surface_t *surface,
* endianess of the platform. On a big-endian machine, the
* first pixel is in the uppermost bit, on a little-endian
* machine the first pixel is in the least-significant bit.
* @CAIRO_FORMAT_RGB16_565: each pixel is a 16-bit quantity,
* with red in the upper 5 bits, then green in the next 6,
* then blue in the lowest 5 bits. (Since 1.2)
*
* #cairo_format_t is used to identify the memory format of
* image data.
@ -1367,7 +1376,8 @@ typedef enum _cairo_format {
CAIRO_FORMAT_ARGB32,
CAIRO_FORMAT_RGB24,
CAIRO_FORMAT_A8,
CAIRO_FORMAT_A1
CAIRO_FORMAT_A1,
CAIRO_FORMAT_RGB16_565
} cairo_format_t;
cairo_public cairo_surface_t *
@ -1382,12 +1392,21 @@ cairo_image_surface_create_for_data (unsigned char *data,
int height,
int stride);
cairo_public unsigned char *
cairo_image_surface_get_data (cairo_surface_t *surface);
cairo_public cairo_format_t
cairo_image_surface_get_format (cairo_surface_t *surface);
cairo_public int
cairo_image_surface_get_width (cairo_surface_t *surface);
cairo_public int
cairo_image_surface_get_height (cairo_surface_t *surface);
cairo_public int
cairo_image_surface_get_stride (cairo_surface_t *surface);
#if CAIRO_HAS_PNG_FUNCTIONS
cairo_public cairo_surface_t *
@ -1424,20 +1443,19 @@ cairo_pattern_reference (cairo_pattern_t *pattern);
cairo_public void
cairo_pattern_destroy (cairo_pattern_t *pattern);
cairo_public cairo_status_t
cairo_pattern_status (cairo_pattern_t *pattern);
/**
* cairo_pattern_type_t
* @CAIRO_PATTERN_TYPE_SOLID: The pattern is a solid (uniform)
* color. It may be opaque or translucent.
* @CAIRO_PATTERN_TYPE_SURFACE: The pattern is a based on a surface (an image).
* @CAIRO_PATTERN_TYPE_LINEAR: The pattern is a linear gradient.
* @CAIRO_PATTERN_TYPE_RADIAL: The pattern is a radial gradient.
*
* @cairo_pattern_type_t us used to describe the type of a given pattern.
* #cairo_pattern_type_t is used to describe the type of a given pattern.
*
* The type of a pattern is determined by the function used to create
* it. The cairo_pattern_create_rgb() and cairo_pattern_create_rgba()
@ -1454,6 +1472,8 @@ cairo_pattern_status (cairo_pattern_t *pattern);
* cairo_pattern_add_color_stop_rgba() which must only be called with
* gradient patterns (either LINEAR or RADIAL). Otherwise the pattern
* will be shutdown and put into an error state.
*
* Since: 1.2
*/
typedef enum _cairo_pattern_type {
CAIRO_PATTERN_TYPE_SOLID,
@ -1490,9 +1510,10 @@ cairo_pattern_get_matrix (cairo_pattern_t *pattern,
* are fully transparent
* @CAIRO_EXTEND_REPEAT: the pattern is tiled by repeating
* @CAIRO_EXTEND_REFLECT: the pattern is tiled by reflecting
* at the edges
* at the edges (not implemented for surface patterns currently)
* @CAIRO_EXTEND_PAD: pixels outside of the pattern copy
* the closest pixel from the source (since cairo 1.2)
* the closest pixel from the source (Since 1.2; not implemented
* for surface patterns currently)
*
* #cairo_extend_t is used to describe how the area outside
* of a pattern will be drawn.
@ -1518,7 +1539,7 @@ typedef enum _cairo_filter {
CAIRO_FILTER_BILINEAR,
CAIRO_FILTER_GAUSSIAN
} cairo_filter_t;
cairo_public void
cairo_pattern_set_filter (cairo_pattern_t *pattern, cairo_filter_t filter);
@ -1565,12 +1586,10 @@ cairo_matrix_multiply (cairo_matrix_t *result,
const cairo_matrix_t *a,
const cairo_matrix_t *b);
/* XXX: Need a new name here perhaps. */
cairo_public void
cairo_matrix_transform_distance (const cairo_matrix_t *matrix,
double *dx, double *dy);
/* XXX: Need a new name here perhaps. */
cairo_public void
cairo_matrix_transform_point (const cairo_matrix_t *matrix,
double *x, double *y);
@ -1630,7 +1649,9 @@ cairo_debug_reset_static_data (void);
#define cairo_xlib_surface_create_for_window_with_visual cairo_xlib_surface_create_for_window_with_visual_REPLACED_BY_cairo_xlib_surface_create
#define cairo_xcb_surface_create_for_pixmap_with_visual cairo_xcb_surface_create_for_pixmap_with_visual_REPLACED_BY_cairo_xcb_surface_create
#define cairo_xcb_surface_create_for_window_with_visual cairo_xcb_surface_create_for_window_with_visual_REPLACED_BY_cairo_xcb_surface_create
#define cairo_ps_surface_set_dpi cairo_ps_surface_set_dpi_REPLACED_BY_cairo_surface_set_fallback_resolution
#define cairo_pdf_surface_set_dpi cairo_pdf_surface_set_dpi_REPLACED_BY_cairo_surface_set_fallback_resolution
#define cairo_svg_surface_set_dpi cairo_svg_surface_set_dpi_REPLACED_BY_cairo_surface_set_fallback_resolution
#define cairo_current_path cairo_current_path_DEPRECATED_BY_cairo_copy_path
#define cairo_current_path_flat cairo_current_path_flat_DEPRECATED_BY_cairo_copy_path_flat

Просмотреть файл

@ -67,6 +67,10 @@
CAIRO_BEGIN_DECLS
#ifndef PACKAGE_BUGREPORT
#define PACKAGE_BUGREPORT "(unknown)"
#endif
#if __GNUC__ >= 3 && defined(__ELF__)
# define slim_hidden_proto(name) slim_hidden_proto1(name, INT_##name)
# define slim_hidden_def(name) slim_hidden_def1(name, INT_##name)
@ -144,7 +148,7 @@ CAIRO_BEGIN_DECLS
# define WIN32_LEAN_AND_MEAN
# include <windows.h>
/* the real initialization must take place in DllMain */
# define CAIRO_MUTEX_DECLARE(name) extern CRITICAL_SECTION name;
# define CAIRO_MUTEX_DECLARE(name) extern CRITICAL_SECTION name;
# define CAIRO_MUTEX_DECLARE_GLOBAL(name) extern LPCRITICAL_SECTION name;
# define CAIRO_MUTEX_LOCK(name) EnterCriticalSection (&name)
# define CAIRO_MUTEX_UNLOCK(name) LeaveCriticalSection (&name)
@ -154,12 +158,12 @@ CAIRO_BEGIN_DECLS
cairo_private void _cairo_beos_lock(void*);
cairo_private void _cairo_beos_unlock(void*);
/* the real initialization takes place in a global constructor */
# define CAIRO_MUTEX_DECLARE(name) extern void* name;
# define CAIRO_MUTEX_DECLARE(name) extern void* name;
# define CAIRO_MUTEX_DECLARE_GLOBAL(name) extern void* name;
# define CAIRO_MUTEX_LOCK(name) _cairo_beos_lock (&name)
# define CAIRO_MUTEX_UNLOCK(name) _cairo_beos_unlock (&name)
#endif
#endif /* 0 */
#endif
#ifndef CAIRO_MUTEX_DECLARE
# define CAIRO_MUTEX_DECLARE(name)
@ -192,7 +196,7 @@ do { \
assert (NOT_REACHED); \
} while (0)
#include "cairo-wideint.h"
#include "cairo-wideint-private.h"
typedef int32_t cairo_fixed_16_16_t;
typedef cairo_int64_t cairo_fixed_32_32_t;
@ -203,12 +207,21 @@ typedef cairo_int128_t cairo_fixed_96_32_t;
/* The common 16.16 format gets a shorter name */
typedef cairo_fixed_16_16_t cairo_fixed_t;
#define CAIRO_MAXSHORT SHRT_MAX
#define CAIRO_MINSHORT SHRT_MIN
#define CAIRO_ALPHA_IS_OPAQUE(alpha) ((alpha) >= ((double)0xff00 / (double)0xffff))
#define CAIRO_ALPHA_IS_ZERO(alpha) ((alpha) <= 0.0)
/* Reverse the bits in a byte with 7 operations (no 64-bit):
* Devised by Sean Anderson, July 13, 2001.
* Source: http://graphics.stanford.edu/~seander/bithacks.html#ReverseByteWith32Bits
*/
#define CAIRO_BITSWAP8(c) ((((c) * 0x0802LU & 0x22110LU) | ((c) * 0x8020LU & 0x88440LU)) * 0x10101LU >> 16)
#ifdef WORDS_BIGENDIAN
#define CAIRO_BITSWAP8_IF_LITTLE_ENDIAN(c) (c)
#else
#define CAIRO_BITSWAP8_IF_LITTLE_ENDIAN(c) CAIRO_BITSWAP8(c)
#endif
#include "cairo-hash-private.h"
#include "cairo-cache-private.h"
@ -243,10 +256,10 @@ typedef struct _cairo_trapezoid {
cairo_line_t left, right;
} cairo_trapezoid_t;
typedef struct _cairo_rectangle {
short x, y;
unsigned short width, height;
} cairo_rectangle_fixed_t, cairo_glyph_size_t;
typedef struct _cairo_rectangle_int16 {
int16_t x, y;
uint16_t width, height;
} cairo_rectangle_int16_t, cairo_glyph_size_t;
/* Sure wish C had a real enum type so that this would be distinct
from cairo_status_t. Oh well, without that, I'll use this bogus 1000
@ -332,13 +345,12 @@ typedef struct _cairo_image_surface cairo_image_surface_t;
typedef struct _cairo_surface_backend cairo_surface_backend_t;
cairo_private void
_cairo_box_round_to_rectangle (cairo_box_t *box, cairo_rectangle_fixed_t *rectangle);
_cairo_box_round_to_rectangle (cairo_box_t *box, cairo_rectangle_int16_t *rectangle);
cairo_private void
_cairo_rectangle_intersect (cairo_rectangle_fixed_t *dest, cairo_rectangle_fixed_t *src);
_cairo_rectangle_intersect (cairo_rectangle_int16_t *dest, cairo_rectangle_int16_t *src);
/* cairo_array.c structures and functions */
/* cairo_array.c structures and functions */
typedef struct _cairo_array cairo_array_t;
struct _cairo_array {
@ -450,18 +462,18 @@ struct _cairo_scaled_font {
/* useful bits for _cairo_scaled_font_nil */
cairo_status_t status;
int ref_count;
/* hash key members */
cairo_font_face_t *font_face; /* may be NULL */
cairo_matrix_t font_matrix; /* font space => user space */
cairo_matrix_t ctm; /* user space => device space */
cairo_font_options_t options;
/* "live" scaled_font members */
cairo_matrix_t scale; /* font space => device space */
cairo_font_extents_t extents; /* user space */
cairo_cache_t *glyphs; /* glyph index -> cairo_scaled_glyph_t */
/*
* One surface backend may store data in each glyph.
* Whichever surface manages to store its pointer here
@ -469,7 +481,7 @@ struct _cairo_scaled_font {
*/
const cairo_surface_backend_t *surface_backend;
void *surface_private;
/* font backend managing this scaled font */
const cairo_scaled_font_backend_t *backend;
};
@ -532,7 +544,7 @@ struct _cairo_scaled_font_backend {
void
(*fini) (void *scaled_font);
cairo_status_t
cairo_int_status_t
(*scaled_glyph_init) (void *scaled_font,
cairo_scaled_glyph_t *scaled_glyph,
cairo_scaled_glyph_info_t info);
@ -545,10 +557,10 @@ struct _cairo_scaled_font_backend {
(*text_to_glyphs) (void *scaled_font,
double x,
double y,
const char *utf8,
cairo_glyph_t **glyphs,
const char *utf8,
cairo_glyph_t **glyphs,
int *num_glyphs);
unsigned long
(*ucs4_to_index) (void *scaled_font,
uint32_t ucs4);
@ -565,7 +577,7 @@ struct _cairo_scaled_font_backend {
unsigned int height,
const cairo_glyph_t *glyphs,
int num_glyphs);
};
struct _cairo_font_face_backend {
@ -638,23 +650,23 @@ struct _cairo_surface_backend {
cairo_status_t
(*acquire_dest_image) (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void **image_extra);
void
(*release_dest_image) (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra);
cairo_status_t
(*clone_similar) (void *surface,
cairo_surface_t *src,
cairo_surface_t **clone_out);
/* XXX: dst should be the first argument for consistency */
cairo_int_status_t
(*composite) (cairo_operator_t op,
@ -674,7 +686,7 @@ struct _cairo_surface_backend {
(*fill_rectangles) (void *surface,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects);
/* XXX: dst should be the first argument for consistency */
@ -748,14 +760,14 @@ struct _cairo_surface_backend {
*/
cairo_int_status_t
(*get_extents) (void *surface,
cairo_rectangle_fixed_t *rectangle);
cairo_rectangle_int16_t *rectangle);
/*
/*
* This is an optional entry to let the surface manage its own glyph
* resources. If null, render against this surface, using image
* surfaces as glyphs.
*/
cairo_int_status_t
* surfaces as glyphs.
*/
cairo_int_status_t
(*old_show_glyphs) (cairo_scaled_font_t *font,
cairo_operator_t op,
cairo_pattern_t *pattern,
@ -859,8 +871,11 @@ struct _cairo_surface {
cairo_bool_t finished;
cairo_user_data_array_t user_data;
double device_x_offset;
double device_y_offset;
cairo_matrix_t device_transform;
cairo_matrix_t device_transform_inverse;
double x_fallback_resolution;
double y_fallback_resolution;
cairo_clip_t *clip;
@ -892,7 +907,6 @@ struct _cairo_image_surface {
unsigned char *data;
cairo_bool_t owns_data;
cairo_bool_t has_clip;
int width;
int height;
@ -950,26 +964,26 @@ extern const cairo_private cairo_solid_pattern_t cairo_pattern_nil;
typedef struct _cairo_surface_pattern {
cairo_pattern_t base;
cairo_surface_t *surface;
} cairo_surface_pattern_t;
typedef struct _cairo_gradient_pattern {
cairo_pattern_t base;
pixman_gradient_stop_t *stops;
int n_stops;
} cairo_gradient_pattern_t;
typedef struct _cairo_linear_pattern {
cairo_gradient_pattern_t base;
pixman_linear_gradient_t gradient;
} cairo_linear_pattern_t;
typedef struct _cairo_radial_pattern {
cairo_gradient_pattern_t base;
pixman_radial_gradient_t gradient;
} cairo_radial_pattern_t;
@ -982,7 +996,7 @@ typedef union {
typedef union {
cairo_pattern_t base;
cairo_solid_pattern_t solid;
cairo_surface_pattern_t surface;
cairo_gradient_pattern_union_t gradient;
@ -1038,6 +1052,8 @@ typedef struct _cairo_traps {
#define CAIRO_GSTATE_MITER_LIMIT_DEFAULT 10.0
#define CAIRO_GSTATE_DEFAULT_FONT_SIZE 10.0
#define CAIRO_SURFACE_FALLBACK_RESOLUTION_DEFAULT 300.0
typedef struct _cairo_gstate cairo_gstate_t;
typedef struct _cairo_stroke_face {
@ -1259,74 +1275,65 @@ _cairo_gstate_show_surface (cairo_gstate_t *gstate,
double height);
cairo_private cairo_status_t
_cairo_gstate_select_font_face (cairo_gstate_t *gstate,
const char *family,
cairo_font_slant_t slant,
_cairo_gstate_select_font_face (cairo_gstate_t *gstate,
const char *family,
cairo_font_slant_t slant,
cairo_font_weight_t weight);
cairo_private cairo_bool_t
_cairo_gstate_has_clip (cairo_gstate_t *gstate);
cairo_private cairo_bool_t
_cairo_gstate_extract_clip_rectangles (cairo_gstate_t *gstate,
int max_rectangles,
cairo_clip_rect_t *rectangles_out,
int *num_rectangles_out);
cairo_private cairo_status_t
_cairo_gstate_set_font_size (cairo_gstate_t *gstate,
_cairo_gstate_set_font_size (cairo_gstate_t *gstate,
double size);
cairo_private void
_cairo_gstate_get_font_matrix (cairo_gstate_t *gstate,
cairo_matrix_t *matrix);
cairo_private cairo_status_t
_cairo_gstate_set_font_matrix (cairo_gstate_t *gstate,
_cairo_gstate_set_font_matrix (cairo_gstate_t *gstate,
const cairo_matrix_t *matrix);
cairo_private void
_cairo_gstate_get_font_options (cairo_gstate_t *gstate,
cairo_font_options_t *options);
cairo_private cairo_status_t
_cairo_gstate_set_font_options (cairo_gstate_t *gstate,
_cairo_gstate_set_font_options (cairo_gstate_t *gstate,
const cairo_font_options_t *options);
cairo_private cairo_status_t
_cairo_gstate_get_font_face (cairo_gstate_t *gstate,
_cairo_gstate_get_font_face (cairo_gstate_t *gstate,
cairo_font_face_t **font_face);
cairo_private cairo_status_t
_cairo_gstate_get_font_extents (cairo_gstate_t *gstate,
_cairo_gstate_get_font_extents (cairo_gstate_t *gstate,
cairo_font_extents_t *extents);
cairo_private cairo_status_t
_cairo_gstate_set_font_face (cairo_gstate_t *gstate,
_cairo_gstate_set_font_face (cairo_gstate_t *gstate,
cairo_font_face_t *font_face);
cairo_private cairo_status_t
_cairo_gstate_text_to_glyphs (cairo_gstate_t *font,
const char *utf8,
const char *utf8,
double x,
double y,
cairo_glyph_t **glyphs,
cairo_glyph_t **glyphs,
int *num_glyphs);
cairo_private cairo_status_t
_cairo_gstate_glyph_extents (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_text_extents_t *extents);
cairo_private cairo_status_t
_cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
_cairo_gstate_show_glyphs (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
int num_glyphs);
cairo_private cairo_status_t
_cairo_gstate_glyph_path (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
_cairo_gstate_glyph_path (cairo_gstate_t *gstate,
cairo_glyph_t *glyphs,
int num_glyphs,
cairo_path_fixed_t *path);
@ -1376,6 +1383,12 @@ _cairo_color_get_rgba_premultiplied (cairo_color_t *color,
/* cairo-font.c */
cairo_private void
_cairo_scaled_font_freeze_cache (cairo_scaled_font_t *scaled_font);
cairo_private void
_cairo_scaled_font_thaw_cache (cairo_scaled_font_t *scaled_font);
cairo_private void
_cairo_scaled_font_set_error (cairo_scaled_font_t *scaled_font,
cairo_status_t status);
@ -1392,7 +1405,7 @@ _cairo_toy_font_face_create (const char *family,
cairo_font_weight_t weight);
cairo_private void
_cairo_unscaled_font_init (cairo_unscaled_font_t *font,
_cairo_unscaled_font_init (cairo_unscaled_font_t *font,
const cairo_unscaled_font_backend_t *backend);
cairo_private cairo_unscaled_font_t *
@ -1414,6 +1427,10 @@ _cairo_font_options_init_copy (cairo_font_options_t *options,
cairo_private cairo_status_t
_cairo_hull_compute (cairo_pen_vertex_t *vertices, int *num_vertices);
/* cairo-lzw.c */
cairo_private unsigned char *
_cairo_lzw_compress (unsigned char *data, unsigned long *size_in_out);
/* cairo_operator.c */
cairo_private cairo_bool_t
_cairo_operator_always_opaque (cairo_operator_t op);
@ -1513,9 +1530,8 @@ _cairo_path_fixed_bounds (cairo_path_fixed_t *path,
double *x2, double *y2);
cairo_private void
_cairo_path_fixed_offset (cairo_path_fixed_t *path,
cairo_fixed_t offx,
cairo_fixed_t offy);
_cairo_path_fixed_device_transform (cairo_path_fixed_t *path,
cairo_matrix_t *device_transform);
/* cairo_path_fill.c */
cairo_private cairo_status_t
@ -1536,7 +1552,7 @@ _cairo_path_fixed_stroke_to_traps (cairo_path_fixed_t *path,
/* cairo-scaled-font.c */
cairo_private cairo_status_t
_cairo_scaled_font_init (cairo_scaled_font_t *scaled_font,
_cairo_scaled_font_init (cairo_scaled_font_t *scaled_font,
cairo_font_face_t *font_face,
const cairo_matrix_t *font_matrix,
const cairo_matrix_t *ctm,
@ -1551,15 +1567,15 @@ cairo_private void
_cairo_scaled_font_fini (cairo_scaled_font_t *scaled_font);
cairo_private cairo_status_t
_cairo_scaled_font_font_extents (cairo_scaled_font_t *scaled_font,
_cairo_scaled_font_font_extents (cairo_scaled_font_t *scaled_font,
cairo_font_extents_t *extents);
cairo_private cairo_status_t
_cairo_scaled_font_text_to_glyphs (cairo_scaled_font_t *scaled_font,
double x,
double y,
const char *utf8,
cairo_glyph_t **glyphs,
const char *utf8,
cairo_glyph_t **glyphs,
int *num_glyphs);
cairo_private cairo_status_t
@ -1572,7 +1588,7 @@ cairo_private cairo_status_t
_cairo_scaled_font_glyph_device_extents (cairo_scaled_font_t *scaled_font,
const cairo_glyph_t *glyphs,
int num_glyphs,
cairo_rectangle_fixed_t *extents);
cairo_rectangle_int16_t *extents);
cairo_private cairo_status_t
_cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
@ -1590,7 +1606,7 @@ _cairo_scaled_font_show_glyphs (cairo_scaled_font_t *scaled_font,
cairo_private cairo_status_t
_cairo_scaled_font_glyph_path (cairo_scaled_font_t *scaled_font,
const cairo_glyph_t *glyphs,
const cairo_glyph_t *glyphs,
int num_glyphs,
cairo_path_fixed_t *path);
@ -1609,7 +1625,7 @@ _cairo_scaled_glyph_set_path (cairo_scaled_glyph_t *scaled_glyph,
cairo_scaled_font_t *scaled_font,
cairo_path_fixed_t *path);
cairo_private cairo_status_t
cairo_private cairo_int_status_t
_cairo_scaled_glyph_lookup (cairo_scaled_font_t *scaled_font,
unsigned long index,
cairo_scaled_glyph_info_t info,
@ -1694,7 +1710,7 @@ cairo_private cairo_status_t
_cairo_surface_fill_rectangles (cairo_surface_t *surface,
cairo_operator_t op,
const cairo_color_t *color,
cairo_rectangle_fixed_t *rects,
cairo_rectangle_int16_t *rects,
int num_rects);
cairo_private cairo_status_t
@ -1735,7 +1751,7 @@ _cairo_surface_show_glyphs (cairo_surface_t *surface,
const cairo_glyph_t *glyphs,
int num_glyphs,
cairo_scaled_font_t *scaled_font);
cairo_private cairo_status_t
_cairo_surface_composite_trapezoids (cairo_operator_t op,
cairo_pattern_t *pattern,
@ -1768,18 +1784,18 @@ _cairo_surface_release_source_image (cairo_surface_t *surface,
cairo_private cairo_status_t
_cairo_surface_acquire_dest_image (cairo_surface_t *surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void **image_extra);
cairo_private void
_cairo_surface_release_dest_image (cairo_surface_t *surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra);
cairo_private cairo_status_t
_cairo_surface_clone_similar (cairo_surface_t *surface,
cairo_surface_t *src,
@ -1814,7 +1830,7 @@ _cairo_surface_set_clip (cairo_surface_t *surface, cairo_clip_t *clip);
cairo_private cairo_status_t
_cairo_surface_get_extents (cairo_surface_t *surface,
cairo_rectangle_fixed_t *rectangle);
cairo_rectangle_int16_t *rectangle);
cairo_private cairo_status_t
_cairo_surface_old_show_glyphs (cairo_scaled_font_t *scaled_font,
@ -1866,8 +1882,13 @@ _cairo_surface_composite_shape_fixup_unbounded (cairo_surface_t *dst,
cairo_private cairo_bool_t
_cairo_surface_is_opaque (const cairo_surface_t *surface);
cairo_private void
_cairo_surface_set_device_scale (cairo_surface_t *surface,
double sx,
double sy);
cairo_private cairo_bool_t
_cairo_surface_has_device_offset_or_scale (cairo_surface_t *surface);
_cairo_surface_has_device_transform (cairo_surface_t *surface);
/* cairo_image_surface.c */
@ -2026,12 +2047,11 @@ _cairo_matrix_compute_scale_factors (const cairo_matrix_t *matrix,
double *sx, double *sy, int x_major);
cairo_private cairo_bool_t
_cairo_matrix_is_integer_translation(const cairo_matrix_t *matrix,
int *itx, int *ity);
_cairo_matrix_is_identity (const cairo_matrix_t *matrix);
cairo_private cairo_bool_t
_cairo_matrix_is_integer_translation_and_scale(const cairo_matrix_t *m,
int *itx, int *ity, int *sx, int *sy);
_cairo_matrix_is_integer_translation(const cairo_matrix_t *matrix,
int *itx, int *ity);
cairo_private double
_cairo_matrix_transformed_circle_major_axis(cairo_matrix_t *matrix, double radius);
@ -2128,7 +2148,7 @@ cairo_private void
_cairo_pattern_transform (cairo_pattern_t *pattern,
const cairo_matrix_t *ctm_inverse);
cairo_private cairo_bool_t
cairo_private cairo_bool_t
_cairo_pattern_is_opaque_solid (const cairo_pattern_t *pattern);
cairo_bool_t
@ -2166,7 +2186,7 @@ _cairo_pattern_acquire_surfaces (cairo_pattern_t *src,
cairo_private cairo_status_t
_cairo_pattern_get_extents (cairo_pattern_t *pattern,
cairo_rectangle_fixed_t *extents);
cairo_rectangle_int16_t *extents);
cairo_private cairo_status_t
_cairo_gstate_set_antialias (cairo_gstate_t *gstate,
@ -2178,11 +2198,11 @@ _cairo_gstate_get_antialias (cairo_gstate_t *gstate);
/* cairo-region.c */
cairo_private pixman_region16_t *
_cairo_region_create_from_rectangle (cairo_rectangle_fixed_t *rect);
_cairo_region_create_from_rectangle (cairo_rectangle_int16_t *rect);
cairo_private void
_cairo_region_extents_rectangle (pixman_region16_t *region,
cairo_rectangle_fixed_t *rect);
cairo_rectangle_int16_t *rect);
/* cairo_unicode.c */
@ -2198,91 +2218,6 @@ _cairo_utf8_to_utf16 (const unsigned char *str,
uint16_t **result,
int *items_written);
/* cairo_output_stream.c */
typedef struct _cairo_output_stream cairo_output_stream_t;
extern const cairo_private cairo_output_stream_t cairo_output_stream_nil;
/* We already have the following declared in cairo.h:
typedef cairo_status_t (*cairo_write_func_t) (void *closure,
const unsigned char *data,
unsigned int length);
*/
typedef cairo_status_t (*cairo_close_func_t) (void *closure);
/* This function never returns NULL. If an error occurs (NO_MEMORY)
* while trying to create the output stream this function returns a
* valid pointer to a nil output stream.
*
* Note that even with a nil surface, the close_func callback will be
* called by a call to _cairo_output_stream_close or
* _cairo_output_stream_destroy.
*/
cairo_private cairo_output_stream_t *
_cairo_output_stream_create (cairo_write_func_t write_func,
cairo_close_func_t close_func,
void *closure);
cairo_private void
_cairo_output_stream_close (cairo_output_stream_t *stream);
cairo_private void
_cairo_output_stream_destroy (cairo_output_stream_t *stream);
cairo_private void
_cairo_output_stream_write (cairo_output_stream_t *stream,
const void *data, size_t length);
cairo_private void
_cairo_output_stream_write_hex_string (cairo_output_stream_t *stream,
const char *data,
size_t length);
cairo_private unsigned char *
_cairo_lzw_compress (unsigned char *data, unsigned long *data_size_in_out);
cairo_private void
_cairo_output_stream_vprintf (cairo_output_stream_t *stream,
const char *fmt, va_list ap);
cairo_private void
_cairo_output_stream_printf (cairo_output_stream_t *stream,
const char *fmt, ...) CAIRO_PRINTF_FORMAT(2, 3);
cairo_private long
_cairo_output_stream_get_position (cairo_output_stream_t *status);
cairo_private cairo_status_t
_cairo_output_stream_get_status (cairo_output_stream_t *stream);
/* This function never returns NULL. If an error occurs (NO_MEMORY or
* WRITE_ERROR) while trying to create the output stream this function
* returns a valid pointer to a nil output stream.
*
* NOTE: Even if a nil surface is returned, the caller should still
* call _cairo_output_stream_destroy (or _cairo_output_stream_close at
* least) in order to ensure that everything is properly cleaned up.
*/
cairo_private cairo_output_stream_t *
_cairo_output_stream_create_for_filename (const char *filename);
/* This function never returns NULL. If an error occurs (NO_MEMORY or
* WRITE_ERROR) while trying to create the output stream this function
* returns a valid pointer to a nil output stream.
*
* The caller still "owns" file and is responsible for calling fclose
* on it when finished. The stream will not do this itself.
*/
cairo_private cairo_output_stream_t *
_cairo_output_stream_create_for_file (FILE *file);
/* cairo_base85_stream.c */
cairo_output_stream_t *
_cairo_base85_stream_create (cairo_output_stream_t *output);
cairo_private void
_cairo_error (cairo_status_t status);
@ -2311,6 +2246,7 @@ slim_hidden_proto(cairo_restore)
slim_hidden_proto(cairo_save)
slim_hidden_proto(cairo_stroke_preserve)
slim_hidden_proto(cairo_surface_destroy)
slim_hidden_proto(cairo_surface_get_content)
slim_hidden_proto(cairo_push_group)
slim_hidden_proto(cairo_push_group_with_content)
slim_hidden_proto(cairo_pop_group)

Просмотреть файл

@ -108,7 +108,7 @@ _test_fallback_surface_finish (void *abstract_surface)
test_fallback_surface_t *surface = abstract_surface;
cairo_surface_destroy (surface->backing);
return CAIRO_STATUS_SUCCESS;
}
@ -136,13 +136,13 @@ _test_fallback_surface_release_source_image (void *abstract_surface,
static cairo_status_t
_test_fallback_surface_acquire_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t **image_out,
cairo_rectangle_fixed_t *image_rect_out,
cairo_rectangle_int16_t *image_rect_out,
void **image_extra)
{
test_fallback_surface_t *surface = abstract_surface;
return _cairo_surface_acquire_dest_image (surface->backing,
interest_rect,
image_out,
@ -152,9 +152,9 @@ _test_fallback_surface_acquire_dest_image (void *abstract_surface,
static void
_test_fallback_surface_release_dest_image (void *abstract_surface,
cairo_rectangle_fixed_t *interest_rect,
cairo_rectangle_int16_t *interest_rect,
cairo_image_surface_t *image,
cairo_rectangle_fixed_t *image_rect,
cairo_rectangle_int16_t *image_rect,
void *image_extra)
{
test_fallback_surface_t *surface = abstract_surface;
@ -168,7 +168,7 @@ _test_fallback_surface_release_dest_image (void *abstract_surface,
static cairo_int_status_t
_test_fallback_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
test_fallback_surface_t *surface = abstract_surface;

Просмотреть файл

@ -110,7 +110,7 @@ _test_meta_surface_finish (void *abstract_surface)
cairo_surface_destroy (surface->meta);
cairo_surface_destroy (surface->image);
return CAIRO_STATUS_SUCCESS;
}
@ -170,7 +170,7 @@ _test_meta_surface_intersect_clip_path (void *abstract_surface,
static cairo_int_status_t
_test_meta_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
test_meta_surface_t *surface = abstract_surface;
@ -280,7 +280,7 @@ _test_meta_surface_snapshot (void *abstract_other)
#if 0
return _cairo_surface_snapshot (other->meta);
#else
cairo_rectangle_fixed_t extents;
cairo_rectangle_int16_t extents;
cairo_surface_t *surface;
_cairo_surface_get_extents (other->image, &extents);

Просмотреть файл

@ -139,7 +139,7 @@ _test_paginated_surface_set_clip_region (void *abstract_surface,
static cairo_int_status_t
_test_paginated_surface_get_extents (void *abstract_surface,
cairo_rectangle_fixed_t *rectangle)
cairo_rectangle_int16_t *rectangle)
{
test_paginated_surface_t *surface = abstract_surface;

Просмотреть файл

@ -28,7 +28,6 @@
#endif
#include "pixman-xserver-compat.h"
#include "fbpict.h"
#include "fbmmx.h"
#ifdef RENDER
@ -225,7 +224,7 @@ fbFetch_r5g6b5 (const FbBits *bits, int x, int width, CARD32 *buffer, miIndexedP
const CARD16 *end = pixel + width;
while (pixel < end) {
CARD32 p = *pixel++;
CARD32 r = (((p) << 3) & 0xf8) |
CARD32 r = (((p) << 3) & 0xf8) |
(((p) << 5) & 0xfc00) |
(((p) << 8) & 0xf80000);
r |= (r >> 5) & 0x70007;
@ -569,7 +568,6 @@ fbFetch_c4 (const FbBits *bits, int x, int width, CARD32 *buffer, miIndexedPtr i
}
}
static FASTCALL void
fbFetch_a1 (const FbBits *bits, int x, int width, CARD32 *buffer, miIndexedPtr indexed)
{
@ -1003,7 +1001,6 @@ fbFetchPixel_c4 (const FbBits *bits, int offset, miIndexedPtr indexed)
return indexed->rgba[pixel];
}
static FASTCALL CARD32
fbFetchPixel_a1 (const FbBits *bits, int offset, miIndexedPtr indexed)
{
@ -1086,8 +1083,6 @@ static fetchPixelProc fetchPixelProcForPicture (PicturePtr pict)
}
}
/*
* All the store functions
*/
@ -1471,7 +1466,6 @@ fbStore_g1 (FbBits *bits, const CARD32 *values, int x, int width, miIndexedPtr i
}
}
static storeProc storeProcForPicture (PicturePtr pict)
{
switch(pict->format_code) {
@ -1522,7 +1516,6 @@ static storeProc storeProcForPicture (PicturePtr pict)
}
}
/*
* Combine src and mask
*/
@ -1554,7 +1547,6 @@ fbCombineSrcU (CARD32 *dest, const CARD32 *src, int width)
memcpy(dest, src, width*sizeof(CARD32));
}
static FASTCALL void
fbCombineOverU (CARD32 *dest, const CARD32 *src, int width)
{
@ -1968,21 +1960,18 @@ fbCombineConjointOverU (CARD32 *dest, const CARD32 *src, int width)
fbCombineConjointGeneralU (dest, src, width, CombineAOver);
}
static FASTCALL void
fbCombineConjointOverReverseU (CARD32 *dest, const CARD32 *src, int width)
{
fbCombineConjointGeneralU (dest, src, width, CombineBOver);
}
static FASTCALL void
fbCombineConjointInU (CARD32 *dest, const CARD32 *src, int width)
{
fbCombineConjointGeneralU (dest, src, width, CombineAIn);
}
static FASTCALL void
fbCombineConjointInReverseU (CARD32 *dest, const CARD32 *src, int width)
{
@ -2123,7 +2112,6 @@ fbCombineMaskValueC (CARD32 *src, const CARD32 *mask, int width)
}
}
static FASTCALL void
fbCombineMaskAlphaC (const CARD32 *src, CARD32 *mask, int width)
{
@ -2687,14 +2675,12 @@ static CombineFuncC fbCombineFuncC[] = {
fbCombineConjointXorC,
};
FbComposeFunctions composeFunctions = {
fbCombineFuncU,
fbCombineFuncC,
fbCombineMaskU
};
static void fbFetchSolid(PicturePtr pict, int x, int y, int width, CARD32 *buffer, CARD32 *mask, CARD32 maskBits)
{
FbBits *bits;
@ -2828,8 +2814,9 @@ static void fbFetchSourcePict(PicturePtr pict, int x, int y, int width, CARD32 *
xFixed_32_32 l;
xFixed_48_16 dx, dy, a, b, off;
v.vector[0] = IntToxFixed(x);
v.vector[1] = IntToxFixed(y);
/* reference point is the center of the pixel */
v.vector[0] = IntToxFixed(x) + xFixed1/2;
v.vector[1] = IntToxFixed(y) + xFixed1/2;
v.vector[2] = xFixed1;
if (pict->transform) {
if (!PictureTransformPoint3d (pict->transform, &v))
@ -2942,8 +2929,9 @@ static void fbFetchSourcePict(PicturePtr pict, int x, int y, int width, CARD32 *
if (pict->transform) {
PictVector v;
v.vector[0] = IntToxFixed(x);
v.vector[1] = IntToxFixed(y);
/* reference point is the center of the pixel */
v.vector[0] = IntToxFixed(x) + xFixed1/2;
v.vector[1] = IntToxFixed(y) + xFixed1/2;
v.vector[2] = xFixed1;
if (!PictureTransformPoint3d (pict->transform, &v))
return;
@ -3082,8 +3070,9 @@ static void fbFetchTransformed(PicturePtr pict, int x, int y, int width, CARD32
x += xoff;
y += yoff;
v.vector[0] = IntToxFixed(x);
v.vector[1] = IntToxFixed(y);
/* reference point is the center of the pixel */
v.vector[0] = IntToxFixed(x) + xFixed1/2;
v.vector[1] = IntToxFixed(y) + xFixed1/2;
v.vector[2] = xFixed1;
/* when using convolution filters one might get here without a transform */
@ -3198,6 +3187,12 @@ static void fbFetchTransformed(PicturePtr pict, int x, int y, int width, CARD32
}
}
} else if (pict->filter == PIXMAN_FILTER_BILINEAR || pict->filter == PIXMAN_FILTER_GOOD || pict->filter == PIXMAN_FILTER_BEST) {
/* adjust vector for maximum contribution at 0.5, 0.5 of each texel. */
v.vector[0] -= v.vector[2]/2;
v.vector[1] -= v.vector[2]/2;
unit.vector[0] -= unit.vector[2]/2;
unit.vector[1] -= unit.vector[2]/2;
if (pict->repeat == RepeatNormal) {
if (PIXREGION_NUM_RECTS(pict->pCompositeClip) == 1) {
box = pict->pCompositeClip->extents;
@ -3538,7 +3533,6 @@ static void fbFetchTransformed(PicturePtr pict, int x, int y, int width, CARD32
}
}
static void fbFetchExternalAlpha(PicturePtr pict, int x, int y, int width, CARD32 *buffer, CARD32 *mask, CARD32 maskBits)
{
int i;
@ -3549,10 +3543,10 @@ static void fbFetchExternalAlpha(PicturePtr pict, int x, int y, int width, CARD3
fbFetchTransformed(pict, x, y, width, buffer, mask, maskBits);
return;
}
if (width > SCANLINE_BUFFER_LENGTH)
alpha_buffer = (CARD32 *) malloc(width*sizeof(CARD32));
fbFetchTransformed(pict, x, y, width, buffer, mask, maskBits);
fbFetchTransformed(pict->alphaMap, x - pict->alphaOrigin.x,
y - pict->alphaOrigin.y, width, alpha_buffer,
@ -3635,7 +3629,6 @@ static void fbStoreExternalAlpha(PicturePtr pict, int x, int y, int width, CARD3
bits += y*stride;
alpha_bits += (ay - pict->alphaOrigin.y)*astride;
store(bits, buffer, x, width, indexed);
astore(alpha_bits, buffer, ax - pict->alphaOrigin.x, width, aindexed);
}
@ -3653,9 +3646,9 @@ fbCompositeRect (const FbComposeData *data, CARD32 *scanline_buffer)
scanFetchProc fetchSrc = NULL, fetchMask = NULL, fetchDest = NULL;
unsigned int srcClass = SourcePictClassUnknown;
unsigned int maskClass = SourcePictClassUnknown;
FbBits *bits;
FbStride stride;
int xoff, yoff;
FbBits *bits = NULL; /* squelch bogus compiler warning */
FbStride stride = 0; /* squelch bogus compiler warning */
int xoff = 0, yoff = 0; /* squelch bogus compiler warning */
if (data->op == PIXMAN_OPERATOR_CLEAR)
fetchSrc = NULL;
@ -3762,24 +3755,6 @@ fbCompositeRect (const FbComposeData *data, CARD32 *scanline_buffer)
if (!compose)
return;
/* XXX: The non-MMX version of some of the fbCompose functions
* overwrite the source or mask data (ones that use
* fbCombineMaskC, fbCombineMaskAlphaC, or fbCombineMaskValueC
* as helpers). This causes problems with the optimization in
* this function that only fetches the source or mask once if
* possible. If we're on a non-MMX machine, disable this
* optimization as a bandaid fix.
*
* https://bugs.freedesktop.org/show_bug.cgi?id=5777
*/
#ifdef USE_MMX
if (!fbHaveMMX())
#endif
{
srcClass = SourcePictClassUnknown;
maskClass = SourcePictClassUnknown;
}
for (i = 0; i < data->height; ++i) {
/* fill first half of scanline with source */
if (fetchSrc)
@ -3839,7 +3814,8 @@ fbCompositeRect (const FbComposeData *data, CARD32 *scanline_buffer)
}
else
{
CARD32 *src_mask_buffer, *mask_buffer = 0;
CARD32 *src_mask_buffer = 0; /* squelch bogus compiler warning */
CARD32 *mask_buffer = 0;
CombineFuncU compose = composeFunctions.combineU[data->op];
if (!compose)
return;
@ -3949,7 +3925,7 @@ pixman_compositeGeneral (pixman_operator_t op,
CARD32 _scanline_buffer[SCANLINE_BUFFER_LENGTH*3];
CARD32 *scanline_buffer = _scanline_buffer;
FbComposeData compose_data;
if (pSrc->pDrawable)
srcRepeat = pSrc->repeat == RepeatNormal && !pSrc->transform
&& (pSrc->pDrawable->width != 1 || pSrc->pDrawable->height != 1);

Просмотреть файл

@ -61,7 +61,6 @@
#undef rasterizeEdges
#undef N_BITS
/*
* 1 bit alpha
*/
@ -127,7 +126,7 @@ fbRasterizeEdges8 (FbBits *buf,
CARD8 *ap = (CARD8 *) line;
xFixed lx, rx;
int lxi, rxi;
/* clip X */
lx = l->x;
if (lx < 0)
@ -135,7 +134,7 @@ fbRasterizeEdges8 (FbBits *buf,
rx = r->x;
if (xFixedToInt (rx) >= width)
rx = IntToxFixed (width);
/* Skip empty (or backwards) sections */
if (rx > lx)
{

Просмотреть файл

@ -1,136 +0,0 @@
/*
* Copyright © 2004 Keith Packard
*
* 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 Keith Packard not be used in
* advertising or publicity pertaining to distribution of the software without
* specific, written prior permission. Keith Packard makes no
* representations about the suitability of this software for any purpose. It
* is provided "as is" without express or implied warranty.
*
* KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
* INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
* EVENT SHALL KEITH PACKARD 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.
*/
#ifndef rasterizeSpan
#endif
static void
rasterizeEdges (FbBits *buf,
int width,
int stride,
RenderEdge *l,
RenderEdge *r,
xFixed t,
xFixed b)
{
xFixed y = t;
FbBits *line;
line = buf + xFixedToInt (y) * stride;
for (;;)
{
xFixed lx, rx;
int lxi, rxi;
/* clip X */
lx = l->x;
if (lx < 0)
lx = 0;
rx = r->x;
if (xFixedToInt (rx) >= width)
rx = IntToxFixed (width);
/* Skip empty (or backwards) sections */
if (rx > lx)
{
/* Find pixel bounds for span. */
lxi = xFixedToInt (lx);
rxi = xFixedToInt (rx);
#if N_BITS == 1
{
FbBits *a = line;
FbBits startmask, endmask;
int nmiddle;
int width = rxi - lxi;
int x = lxi;
a += x >> FB_SHIFT;
x &= FB_MASK;
FbMaskBits (x, width, startmask, nmiddle, endmask);
if (startmask)
*a++ |= startmask;
while (nmiddle--)
*a++ = FB_ALLONES;
if (endmask)
*a |= endmask;
}
#else
{
DefineAlpha(line,lxi);
int lxs, rxs;
/* Sample coverage for edge pixels */
lxs = RenderSamplesX (lx, N_BITS);
rxs = RenderSamplesX (rx, N_BITS);
/* Add coverage across row */
if (lxi == rxi)
{
AddAlpha (rxs - lxs);
}
else
{
int xi;
AddAlpha (N_X_FRAC(N_BITS) - lxs);
StepAlpha;
for (xi = lxi + 1; xi < rxi; xi++)
{
AddAlpha (N_X_FRAC(N_BITS));
StepAlpha;
}
/* Do not add in a 0 alpha here. This check is
* necessary to avoid a buffer overrun, (when rx
* is exactly on a pixel boundary). */
if (rxs)
AddAlpha (rxs);
}
}
#endif
}
if (y == b)
break;
#if N_BITS > 1
if (xFixedFrac (y) != Y_FRAC_LAST(N_BITS))
{
RenderEdgeStepSmall (l);
RenderEdgeStepSmall (r);
y += STEP_Y_SMALL(N_BITS);
}
else
#endif
{
RenderEdgeStepBig (l);
RenderEdgeStepBig (r);
y += STEP_Y_BIG(N_BITS);
line += stride;
}
}
}
#undef rasterizeSpan

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -23,7 +23,7 @@
*
* Author: Søren Sandmann (sandmann@redhat.com)
* Lars Knoll (lars@trolltech.com)
*
*
* Based on work by Owen Taylor
*/
#ifdef USE_MMX

Просмотреть файл

@ -72,20 +72,6 @@ fbIn (CARD32 x, CARD8 y)
return m|n|o|p;
}
static CARD32
fbIn24 (CARD32 x, CARD8 y)
{
CARD16 a = y;
CARD16 t;
CARD32 m,n,o,p;
m = FbInU(x,0,a,t);
n = FbInU(x,8,a,t);
o = FbInU(x,16,a,t);
p = (y << 24);
return m|n|o|p;
}
#define genericCombine24(a,b,c,d) (((a)*(c)+(b)*(d)))
/*
@ -750,8 +736,6 @@ fbCompositeSrc_8888x0565 (pixman_operator_t op,
}
}
static void
fbCompositeSrcAdd_8000x8000 (pixman_operator_t op,
PicturePtr pSrc,
@ -1083,8 +1067,6 @@ fbCompositeTrans_0565xnx0565(pixman_operator_t op,
}
}
/* macros for "i can't believe it's not fast" packed pixel handling */
#define alphamaskCombine24(a,b) genericCombine24(a,b,maskAlpha,maskiAlpha)
static void
@ -1376,7 +1358,7 @@ pixman_composite (pixman_operator_t op,
mmx_setup = TRUE;
}
#endif
xDst += pDst->pDrawable->x;
yDst += pDst->pDrawable->y;
if (pSrc->pDrawable) {
@ -1816,6 +1798,9 @@ pixman_composite (pixman_operator_t op,
}
}
break;
default:
/* For any operator not specifically handled above we default out to the general code. */
func = NULL;
}
if (!func) {
@ -1832,7 +1817,7 @@ pixman_composite (pixman_operator_t op,
region = pixman_region_create();
pixman_region_union_rect (region, region, xDst, yDst, width, height);
if (!FbComputeCompositeRegion (region,
pSrc,
pMask,
@ -1846,7 +1831,7 @@ pixman_composite (pixman_operator_t op,
width,
height))
return;
n = pixman_region_num_rects (region);
pbox = pixman_region_rects (region);
while (n--)
@ -1918,7 +1903,7 @@ slim_hidden_def(pixman_composite);
enum CPUFeatures {
NoFeatures = 0,
MMX = 0x1,
MMX_Extensions = 0x2,
MMX_Extensions = 0x2,
SSE = 0x6,
SSE2 = 0x8,
CMOV = 0x10
@ -1963,9 +1948,9 @@ static unsigned int detectCPUFeatures(void) {
"pop %%ebx\n"
"1:\n"
"mov %%edx, %0\n"
: "=r" (result),
"=m" (vendor[0]),
"=m" (vendor[4]),
: "=r" (result),
"=m" (vendor[0]),
"=m" (vendor[4]),
"=m" (vendor[8])
:
: "%eax", "%ecx", "%edx"
@ -1985,7 +1970,7 @@ static unsigned int detectCPUFeatures(void) {
if ((result & MMX) && !(result & SSE) && (strcmp(vendor, "AuthenticAMD") == 0)) {
/* check for AMD MMX extensions */
unsigned int result;
unsigned int result;
__asm__("push %%ebx\n"
"mov $0x80000000, %%eax\n"
"cpuid\n"
@ -2020,7 +2005,7 @@ fbHaveMMX (void)
mmx_present = (features & (MMX|MMX_Extensions)) == (MMX|MMX_Extensions);
initialized = TRUE;
}
return mmx_present;
}
#endif /* USE_MMX && !amd64 */

Некоторые файлы не были показаны из-за слишком большого количества измененных файлов Показать больше