Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
# Don't replace unknown characters as '?' is forbidden in Windows filenames
errors = 'ignore' if os.name == 'nt' else 'replace'
if not isinstance(filename, bytes):
if os.name == 'nt' and cairo.cairo_version() >= 11510:
# Since 1.15.10, cairo uses utf-8 filenames on Windows
filename = filename.encode('utf-8', errors=errors)
else:
try:
filename = filename.encode(sys.getfilesystemencoding())
except UnicodeEncodeError:
# Use plain ASCII filenames as fallback
filename = filename.encode('ascii', errors=errors)
# TODO: avoid characters forbidden in filenames?
return ffi.new('char[]', filename)
def get_fallback_resolution(self):
"""Returns the previous fallback resolution
set by :meth:`set_fallback_resolution`,
or default fallback resolution if never set.
:returns: ``(x_pixels_per_inch, y_pixels_per_inch)``
"""
ppi = ffi.new('double[2]')
cairo.cairo_surface_get_fallback_resolution(
self._pointer, ppi + 0, ppi + 1)
return tuple(ppi)
dy2 = dx1 * yx + dy1 * yy
Affine transformations are position invariant,
so the same vector always transforms to the same vector.
If ``(x1, y1)`` transforms to ``(x2, y2)``
then ``(x1 + dx1, y1 + dy1)`` will transform
to ``(x1 + dx2, y1 + dy2)`` for all values of ``x1`` and ``x2``.
:param dx: X component of a distance vector.
:param dy: Y component of a distance vector.
:type dx: float
:type dy: float
:returns: A ``(new_dx, new_dy)`` tuple of floats.
"""
xy = ffi.new('double[2]', [dx, dy])
cairo.cairo_matrix_transform_distance(self._pointer, xy + 0, xy + 1)
return tuple(xy)
def supports_mime_type(self, mime_type):
""" Return whether surface supports :obj:`mime_type`.
:param mime_type: The MIME type of the image data.
:type mime_type: ASCII string
*New in cairo 1.12.*
"""
mime_type = ffi.new('char[]', mime_type.encode('utf8'))
return bool(cairo.cairo_surface_supports_mime_type(
self._pointer, mime_type))
:param mime_type: The MIME type of the image data.
:type mime_type: ASCII string
:param data: The image data to attach to the surface.
:type data: bytes
*New in cairo 1.10.*
"""
mime_type = ffi.new('char[]', mime_type.encode('utf8'))
if data is None:
_check_status(cairo.cairo_surface_set_mime_data(
self._pointer, mime_type, ffi.NULL, 0, ffi.NULL, ffi.NULL))
else:
# TODO: avoid making a copy here if possible.
length = len(data)
data = ffi.new('unsigned char[]', data)
keep_alive = KeepAlive(data, mime_type)
_check_status(cairo.cairo_surface_set_mime_data(
self._pointer, mime_type, data, length,
*keep_alive.closure))
keep_alive.save() # Only on success
This method is part of
what the cairo designers call the "toy" text API.
It is convenient for short demos and simple programs,
but it is not expected to be adequate
for serious text-using applications.
See :ref:`fonts` for details
and :meth:`Context.show_glyphs`
for the "real" text display API in cairo.
"""
glyphs = ffi.new('cairo_glyph_t **', ffi.NULL)
num_glyphs = ffi.new('int *')
if with_clusters:
clusters = ffi.new('cairo_text_cluster_t **', ffi.NULL)
num_clusters = ffi.new('int *')
cluster_flags = ffi.new('cairo_text_cluster_flags_t *')
else:
clusters = ffi.NULL
num_clusters = ffi.NULL
cluster_flags = ffi.NULL
# TODO: Pass len_utf8 explicitly to support NULL bytes?
status = cairo.cairo_scaled_font_text_to_glyphs(
self._pointer, x, y, _encode_string(text), -1,
glyphs, num_glyphs, clusters, num_clusters, cluster_flags)
glyphs = ffi.gc(glyphs[0], _keepref(cairo, cairo.cairo_glyph_free))
if with_clusters:
clusters = ffi.gc(
clusters[0], _keepref(cairo, cairo.cairo_text_cluster_free))
_check_status(status)
glyphs = [
(glyph.index, glyph.x, glyph.y)
def append_spline(cr, spline, closed=False):
points = cairocffi.ffi.new("cairou_point_t[%d]" % len(spline))
for i, p in enumerate(spline):
points[i].x = p[0]
points[i].y = p[1]
_lib.cairou_append_spline(cr._pointer, points, len(spline), closed)