Skip to content

Commit e611471

Browse files
committed
Reinstate FT2Image.as_rgb_str() and FT2Image.as_rgba_str(). Doesn't follow the broken model before where improperly-reference-counted copies were made. Alternative to matplotlib#575
1 parent 75c9bec commit e611471

File tree

2 files changed

+73
-4
lines changed

2 files changed

+73
-4
lines changed

src/ft2font.cpp

Lines changed: 69 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,7 +284,7 @@ FT2Image::py_draw_rect_filled(const Py::Tuple & args)
284284
PYCXX_VARARGS_METHOD_DECL(FT2Image, py_draw_rect_filled)
285285

286286
char FT2Image::as_str__doc__[] =
287-
"width, height, s = image_as_str()\n"
287+
"s = image.as_str()\n"
288288
"\n"
289289
"Return the image buffer as a string\n"
290290
"\n"
@@ -304,6 +304,70 @@ FT2Image::py_as_str(const Py::Tuple & args)
304304
}
305305
PYCXX_VARARGS_METHOD_DECL(FT2Image, py_as_str)
306306

307+
char FT2Image::as_rgba_str__doc__[] =
308+
"s = image.as_rgba_str()\n"
309+
"\n"
310+
"Return the image buffer as a RGBA string\n"
311+
"\n"
312+
;
313+
Py::Object
314+
FT2Image::py_as_rgba_str(const Py::Tuple & args)
315+
{
316+
_VERBOSE("FT2Image::as_str");
317+
args.verify_length(0);
318+
319+
Py_ssize_t size = _width*_height*4;
320+
PyObject* result = PyBytes_FromStringAndSize(NULL, size);
321+
322+
unsigned char *src = _buffer;
323+
unsigned char *src_end = src + (_width * _height);
324+
unsigned char *dst = (unsigned char *)PyBytes_AS_STRING(result);
325+
326+
while (src != src_end)
327+
{
328+
*dst++ = 0;
329+
*dst++ = 0;
330+
*dst++ = 0;
331+
*dst++ = *src++;
332+
}
333+
334+
return Py::asObject(result);
335+
}
336+
PYCXX_VARARGS_METHOD_DECL(FT2Image, py_as_rgba_str)
337+
338+
/* TODO: This could take a color as an argument, but for
339+
now it defaults to black on white background */
340+
char FT2Image::as_rgb_str__doc__[] =
341+
"s = image.as_rgb_str()\n"
342+
"\n"
343+
"Return the image buffer as a RGB string\n"
344+
"\n"
345+
;
346+
Py::Object
347+
FT2Image::py_as_rgb_str(const Py::Tuple & args)
348+
{
349+
_VERBOSE("FT2Image::as_str");
350+
args.verify_length(0);
351+
352+
Py_ssize_t size = _width*_height*3;
353+
PyObject* result = PyBytes_FromStringAndSize(NULL, size);
354+
355+
unsigned char *src = _buffer;
356+
unsigned char *src_end = src + (_width * _height);
357+
unsigned char *dst = (unsigned char *)PyBytes_AS_STRING(result);
358+
359+
while (src != src_end)
360+
{
361+
unsigned char tmp = 255 - *src++;
362+
*dst++ = tmp;
363+
*dst++ = tmp;
364+
*dst++ = tmp;
365+
}
366+
367+
return Py::asObject(result);
368+
}
369+
PYCXX_VARARGS_METHOD_DECL(FT2Image, py_as_rgb_str)
370+
307371
char FT2Image::as_array__doc__[] =
308372
"x = image.as_array()\n"
309373
"\n"
@@ -1990,6 +2054,10 @@ FT2Image::init_type(void)
19902054
FT2Image::as_array__doc__);
19912055
PYCXX_ADD_VARARGS_METHOD(as_str, py_as_str,
19922056
FT2Image::as_str__doc__);
2057+
PYCXX_ADD_VARARGS_METHOD(as_rgb_str, py_as_rgb_str,
2058+
FT2Image::as_rgb_str__doc__);
2059+
PYCXX_ADD_VARARGS_METHOD(as_rgba_str, py_as_rgba_str,
2060+
FT2Image::as_rgba_str__doc__);
19932061
PYCXX_ADD_VARARGS_METHOD(get_width, py_get_width,
19942062
"Returns the width of the image");
19952063
PYCXX_ADD_VARARGS_METHOD(get_height, py_get_height,

src/ft2font.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,10 @@ class FT2Image : public Py::PythonClass<FT2Image>
6161
Py::Object py_as_array(const Py::Tuple & args);
6262
static char as_str__doc__ [];
6363
Py::Object py_as_str(const Py::Tuple & args);
64+
static char as_rgb_str__doc__ [];
65+
Py::Object py_as_rgb_str(const Py::Tuple & args);
66+
static char as_rgba_str__doc__ [];
67+
Py::Object py_as_rgba_str(const Py::Tuple & args);
6468
Py::Object py_get_width(const Py::Tuple & args);
6569
Py::Object py_get_height(const Py::Tuple & args);
6670

@@ -70,9 +74,6 @@ class FT2Image : public Py::PythonClass<FT2Image>
7074
unsigned long _width;
7175
unsigned long _height;
7276

73-
void makeRgbCopy();
74-
void makeRgbaCopy();
75-
7677
void resize(long width, long height);
7778
};
7879

0 commit comments

Comments
 (0)