Commits

Anonymous committed 49b633b

Added ptsize default size hint property to freetype.Font.
Implemented freetype.Font.copy interface.
Added CPyStreamWrapper_Clone() function for cloning stream access objects.

Comments (0)

Files changed (10)

doc/capi/base.rst

 Python stream objects in a threaded or non-threaded manner. It
 encapsules the important underlying stream methods.
 
+.. note::
+
+  The C functions provided below do **not** perform any argument
+  checks. It is up to the caller to ensure that the passed
+  CPyStreamWrapper argument is correct.
+
 Members
 ^^^^^^^
 .. cmember:: PyObject* CPyStreamWrapper.read
   Releases all resources hold by the passed :ctype:`CPyStreamWrapper`
   instance.
 
+.. cfunction:: CPyStreamWrapper_Clone (CPyStreamWrapper *wrapper)
+
+  Creates a copy of the passed :ctype:`CPyStreamWrapper` instance, which
+  uses the same bound methods for reading and writing.
+
 .. cfunction:: int CPyStreamWrapper_Read_Threaded (CPyStreamWrapper *wrapper, void *buf, pguint32 offset, pguint32 count, pguint32 *read_)
 
   Reads a maximum of *count* bytes from the passed

doc/src/freetypebase.xml

         underline, bold) used to draw this font. This style may be
         overriden on any :meth:`render` call.
     </desc>
+    <method name="copy">
+      <call>copy() -> Font</call>
+      <desc>
+        Creates a copy of the Font.
+      </desc>
+    </method>
     <attr name="name">
       <desc>Read only. Gets the name of the font face.</desc>
     </attr>
       <desc>Read only. Gets the height of the Font. This is the average
       value of all glyphs in the font.</desc>
     </attr>
+    <attr name="ptsize">
+      <desc>Gets or sets the default size of the Font in points.</desc>
+    </attr>
     <method name="render">
       <call>render(dest, text, fgcolor [, bgcolor, style, rotation, ptsize]) -> int, int[, :class:`pygame2.sdl.video.Surface`]</call>
       <desc>

src/base/pgbase.h

 
 #define PYGAME_STREAMWRAPPER_FIRSTSLOT \
     (PYGAME_BASE_FIRSTSLOT + PYGAME_BASE_NUMSLOTS)
-#define PYGAME_STREAMWRAPPER_NUMSLOTS 15
+#define PYGAME_STREAMWRAPPER_NUMSLOTS 16
 #ifndef PYGAME_STREAMWRAPPER_INTERNAL
 #define CPyStreamWrapper_New                                            \
     (*(CPyStreamWrapper*(*)(PyObject*)) PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+0])
 #define CPyStreamWrapper_Close_Threaded                                 \
     (*(int(*)(CPyStreamWrapper*)) PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+10])
 #define CPyStreamWrapper_Close                                          \
-    (*(int(*)(CPyStreamWrapper*)) PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+11)
+    (*(int(*)(CPyStreamWrapper*)) PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+11])
+#define CPyStreamWrapper_Clone                                          \
+    (*(CPyStreamWrapper*(*)(CPyStreamWrapper*)) PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+12])
 #define IsReadableStreamObj                                             \
-    (*(int(*)(PyObject*))PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+12])
+    (*(int(*)(PyObject*))PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+13])
 #define IsWriteableStreamObj                                            \
-    (*(int(*)(PyObject*))PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+13])
+    (*(int(*)(PyObject*))PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+14])
 #define IsReadWriteableStreamObj                                        \
-    (*(int(*)(PyObject*))PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+14])
+    (*(int(*)(PyObject*))PyGameBase_C_API[PYGAME_STREAMWRAPPER_FIRSTSLOT+15])
 #endif /* PYGAME_STREAMWRAPPER_INTERNAL */
 
 /**

src/base/streamwrapper.c

 static pgint32 CPyStreamWrapper_Tell (CPyStreamWrapper *wrapper);
 static int CPyStreamWrapper_Close_Threaded (CPyStreamWrapper *wrapper);
 static int CPyStreamWrapper_Close (CPyStreamWrapper *wrapper);
+static CPyStreamWrapper* CPyStreamWrapper_Clone (CPyStreamWrapper *wrapper);
 
 static int IsReadableStreamObj (PyObject *obj);
 static int IsWriteableStreamObj (PyObject *obj);
         PyErr_SetString (PyExc_ValueError, "wrapper must not be NULL");
         return;
     }
+
 #ifdef WITH_THREAD
     PyThreadState_Clear (wrapper->thread);
     PyThreadState_Delete (wrapper->thread);
 {
     PyObject *result;
     int retval = 1;
-    
+
     if (!wrapper->close)
         return -1;
 
     return retval;
 }
 
+static CPyStreamWrapper*
+CPyStreamWrapper_Clone (CPyStreamWrapper *wrapper)
+{
+    CPyStreamWrapper *clone;
+
+#ifdef WITH_THREAD
+    PyInterpreterState* interp;
+    PyThreadState* thread;
+#endif
+
+    clone = PyMem_New (CPyStreamWrapper, 1);
+    if (!clone)
+        return NULL;
+
+#ifdef WITH_THREAD    
+    PyEval_InitThreads ();
+    thread = PyThreadState_Get ();
+    interp = thread->interp;
+    clone->thread = PyThreadState_New (interp);
+#endif
+
+    clone->read = wrapper->read;
+    clone->write = wrapper->write;
+    clone->seek = wrapper->seek;
+    clone->tell = wrapper->tell;
+    clone->close = wrapper->close;
+
+    Py_XINCREF (clone->seek);
+    Py_XINCREF (clone->tell);
+    Py_XINCREF (clone->write);
+    Py_XINCREF (clone->read);
+    Py_XINCREF (clone->close);
+    
+    return clone;
+}
+
 static int
 IsReadableStreamObj (PyObject *obj)
 {
     capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+10] =
         (void *)CPyStreamWrapper_Close_Threaded;
     capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+11] = (void *)CPyStreamWrapper_Close;
-    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+12] = (void *)IsReadableStreamObj;
-    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+13] = (void *)IsWriteableStreamObj;
-    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+14] = (void *)IsReadWriteableStreamObj;
+    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+12] = (void *)CPyStreamWrapper_Clone;
+    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+13] = (void *)IsReadableStreamObj;
+    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+14] = (void *)IsWriteableStreamObj;
+    capi[PYGAME_STREAMWRAPPER_FIRSTSLOT+15] = (void *)IsReadWriteableStreamObj;
 }

src/freetype/ft_font.c

 static PyObject* _ftfont_getmetrics(PyObject *self, PyObject* args, PyObject *kwds);
 static PyObject* _ftfont_render(PyObject *self, PyObject* args, PyObject *kwds);
 static PyObject* _ftfont_render_raw(PyObject *self, PyObject* args, PyObject *kwds);
-/*static PyObject* _ftfont_copy (PyObject *self);*/
+static PyObject* _ftfont_copy (PyObject *self);
 
 /*
  * Getters/setters
 static PyObject* _ftfont_getstyle(PyObject *self, void *closure);
 static int _ftfont_setstyle(PyObject *self, PyObject *value, void *closure);
 static PyObject* _ftfont_getheight(PyObject *self, void *closure);
+static PyObject* _ftfont_getptsize(PyObject *self, void *closure);
+static int _ftfont_setptsize(PyObject *self, PyObject *value, void *closure);
 static PyObject* _ftfont_getname(PyObject *self, void *closure);
 static PyObject* _ftfont_getfixedwidth(PyObject *self, void *closure);
 
       DOC_BASE_FONT_RENDER },
     { "render_raw", (PyCFunction)_ftfont_render_raw,
       METH_VARARGS | METH_KEYWORDS, DOC_BASE_FONT_RENDER_RAW },
+    { "copy", (PyCFunction)_ftfont_copy, METH_NOARGS, DOC_BASE_FONT_COPY },
     { NULL, NULL, 0, NULL }
 };
 
     { "style",  _ftfont_getstyle, _ftfont_setstyle,  DOC_BASE_FONT_STYLE,
       NULL },
     { "height", _ftfont_getheight, NULL, DOC_BASE_FONT_HEIGHT, NULL },
+    { "ptsize", _ftfont_getptsize, _ftfont_setptsize, DOC_BASE_FONT_PTSIZE,
+      NULL },
     { "name", _ftfont_getname, NULL, DOC_BASE_FONT_NAME, NULL },
     { "fixed_width", _ftfont_getfixedwidth, NULL, DOC_BASE_FONT_FIXED_WIDTH,
       NULL },
     font->pyfont.set_style = _ftfont_setstyle;
     font->pyfont.get_size = _ftfont_getsize;
     font->pyfont.render = _ftfont_render;
-    /*font->pyfont.copy = _ftfont_copy;*/
-    /* TODO: font->pyfont.copy  */
+    font->pyfont.copy = _ftfont_copy;
 
     return (PyObject*)font;
 }
     return 0;
 }
 
-
 /** Antialias attribute */
 static PyObject*
 _ftfont_getantialias(PyObject *self, void *closure)
     return 0;
 }
 
-
 /** Generic style attributes */
 static PyObject*
 _ftfont_getstyle_flag(PyObject *self, void *closure)
     return 0;
 }
 
-
 /** Style attribute */
 static PyObject*
 _ftfont_getstyle(PyObject *self, void *closure)
     return 0;
 }
 
+static PyObject*
+_ftfont_getptsize (PyObject *self, void *closure)
+{
+    PyFreeTypeFont *font = (PyFreeTypeFont *)self;
+    return PyInt_FromLong (font->ptsize);
+}
+static int
+_ftfont_setptsize (PyObject *self, PyObject *value, void *closure)
+{
+    int ptsize;
+
+    if (!IntFromObj (value, &ptsize))
+        return -1;
+    ((PyFreeTypeFont*)self)->ptsize = (FT_Int16)((ptsize <= 0) ? -1 : ptsize);
+    return 0;
+}
 
 /** Height attribute */
 static PyObject*
     return PyBool_FromLong(PGFT_Face_IsFixedWidth(ft, (PyFreeTypeFont *)self));
 }
 
-
-
 /****************************************************
  * MAIN METHODS
  ****************************************************/
 #endif // HAVE_PYGAME_SDL_VIDEO
 }
 
+static PyObject*
+_ftfont_copy (PyObject *self)
+{
+    PyFreeTypeFont *font;
+    FreeTypeInstance *ft;
+
+    ASSERT_GRAB_FREETYPE(ft, NULL);
+
+    font = (PyFreeTypeFont *)PyFreeTypeFont_Type.tp_new
+        (&PyFreeTypeFont_Type, NULL, NULL);
+
+    if (!font)
+        return NULL;
+
+    if (PGFT_TryClone_Font (ft, font, (PyFreeTypeFont*)self) == -1)
+    {
+        PyErr_SetString (PyExc_PyGameError, PGFT_GetError (ft));
+        return NULL;
+    }
+
+    return (PyObject*) font;
+}
+
 /****************************************************
  * C API CALLS
  ****************************************************/
         return NULL;
     }
 
-    font = (PyFreeTypeFont *)PyFreeTypeFont_Type.tp_new(
-            &PyFreeTypeFont_Type, NULL, NULL);
+    font = (PyFreeTypeFont *)PyFreeTypeFont_Type.tp_new
+        (&PyFreeTypeFont_Type, NULL, NULL);
 
     if (!font)
         return NULL;

src/freetype/ft_wrap.c

     return _PGFT_Init_INTERNAL(ft, font);
 }
 
+int
+PGFT_TryClone_Font (FreeTypeInstance *ft, PyFreeTypeFont *font,
+    PyFreeTypeFont *source)
+{
+    font->ptsize = source->ptsize;
+    font->style = source->style;
+    font->antialias = source->antialias;
+    font->vertical = source->vertical;
+
+    if ((source->id.open_args.flags == FT_OPEN_PATHNAME))
+    {
+        return PGFT_TryLoadFont_Filename (ft, font,
+            source->id.open_args.pathname, source->id.face_index);
+    }
+    else if ((source->id.open_args.flags == FT_OPEN_STREAM))
+    {
+        CPyStreamWrapper *clone = CPyStreamWrapper_Clone ((CPyStreamWrapper*)
+            (source->id.open_args.stream->descriptor.pointer));
+        if (!clone)
+        {
+            _PGFT_SetError(ft, "Failed to clone font stream", 0);
+            return -1;
+        }
+        return PGFT_TryLoadFont_Stream (ft, font, clone, source->id.face_index);
+    }
+
+    _PGFT_SetError (ft, "Unsupported font type for cloning", 0);
+    return -1;
+}
+
 void
 PGFT_UnloadFont(FreeTypeInstance *ft, PyFreeTypeFont *font)
 {

src/freetype/ft_wrap.h

  * Internal API
  **********************************************************/
 
-/********************************************************* General functions ****/
+/**** General functions ****/
 const char *PGFT_GetError(FreeTypeInstance *);
-void        PGFT_Quit(FreeTypeInstance *);
-int         PGFT_Init(FreeTypeInstance **, int cache_size);
+void PGFT_Quit(FreeTypeInstance *);
+int PGFT_Init(FreeTypeInstance **, int cache_size);
 
-int         PGFT_Face_GetHeight(FreeTypeInstance *ft, PyFreeTypeFont *);
-int         PGFT_Face_IsFixedWidth(FreeTypeInstance *ft, PyFreeTypeFont *);
+int PGFT_Face_GetHeight(FreeTypeInstance *ft, PyFreeTypeFont *);
+int PGFT_Face_IsFixedWidth(FreeTypeInstance *ft, PyFreeTypeFont *);
 const char *PGFT_Face_GetName(FreeTypeInstance *ft, PyFreeTypeFont *);
 
-int         PGFT_TryLoadFont_Filename(FreeTypeInstance *, 
-                PyFreeTypeFont *, const char *, int);
+int PGFT_TryLoadFont_Filename(FreeTypeInstance *, PyFreeTypeFont *,
+    const char *, int);
+int PGFT_TryLoadFont_Stream (FreeTypeInstance *ft, PyFreeTypeFont *font,
+    CPyStreamWrapper *wrapper, int face_index);
+int PGFT_TryClone_Font (FreeTypeInstance *ft, PyFreeTypeFont *font,
+    PyFreeTypeFont *source);
+void PGFT_UnloadFont(FreeTypeInstance *, PyFreeTypeFont *);
 
-int         PGFT_TryLoadFont_Stream (FreeTypeInstance *ft, 
-    PyFreeTypeFont *font, CPyStreamWrapper *wrapper, int face_index);
 
-void        PGFT_UnloadFont(FreeTypeInstance *, PyFreeTypeFont *);
 
-
-
-/********************************************************* Metrics management ****/
+/**** Metrics management ****/
 int         PGFT_GetTextSize(FreeTypeInstance *ft, PyFreeTypeFont *font,
                 const FontRenderMode *render, PyObject *text, int *w, int *h);
 
 
 
 
-/******************************************************************* Rendering ****/
+/**** Rendering ****/
 PyObject *  PGFT_Render_PixelArray(FreeTypeInstance *ft, PyFreeTypeFont *font,
                 const FontRenderMode *render, PyObject *text, int *_width, int *_height);
 
 int PGFT_CheckStyle(FT_UInt32 style);
 
 
-/******************************************************************* Render callbacks ****/
-
+/**** Render callbacks ****/
 void __fill_glyph_RGB1(int x, int y, int w, int h, FontSurface *surface, FontColor *color);
 void __fill_glyph_RGB2(int x, int y, int w, int h, FontSurface *surface, FontColor *color);
 void __fill_glyph_RGB3(int x, int y, int w, int h, FontSurface *surface, FontColor *color);
 
 void __render_glyph_ByteArray(int x, int y, FontSurface *surface, FT_Bitmap *bitmap, FontColor *color);
 
-/******************************************************** Font text management ****/
+/**** Font text management ****/
 FontText *  PGFT_LoadFontText(FreeTypeInstance *ft, PyFreeTypeFont *font, 
                 const FontRenderMode *render, PyObject *text);
 
 FT_UInt16 * PGFT_BuildUnicodeString(FreeTypeInstance *ft, PyObject *text);
 
 
-/******************************************************** Glyph cache management ****/
+/**** Glyph cache management ****/
 int        PGFT_Cache_Init(FreeTypeInstance *ft, FontCache *cache, PyFreeTypeFont *parent);
 void        PGFT_Cache_Destroy(FontCache *cache);
 void        PGFT_Cache_Cleanup(FontCache *cache);
                 const FontRenderMode *render);
 
 
-/******************************************************************* Internals ****/
+/**** Internals ****/
 void        _PGFT_SetError(FreeTypeInstance *, const char *, FT_Error);
 FT_Face     _PGFT_GetFace(FreeTypeInstance *, PyFreeTypeFont *);
 FT_Face     _PGFT_GetFaceSized(FreeTypeInstance *, PyFreeTypeFont *, int);

src/freetype/pgfreetype.h

 
 /* Render styles */
 #define FT_STYLE_NORMAL     0x00
-#define FT_STYLE_BOLD		0x01
+#define FT_STYLE_BOLD       0x01
 #define FT_STYLE_ITALIC     0x02
 #define FT_STYLE_UNDERLINE  0x04
 #define FT_STYLE_DEFAULT    0xFF

src/sdl/pixelformat.c

 {
     PyPixelFormat *format;
     if (!fmt)
+    {
+        PyErr_SetString (PyExc_ValueError, "fmt must not be NULL");
         return NULL;
-        
+    }
+   
     format = (PyPixelFormat*) PyPixelFormat_Type.tp_new (&PyPixelFormat_Type,
         NULL, NULL);
     if (!format)

test/freetype_font_test.py

         font.style = ft_const.STYLE_NORMAL
         self.assertEqual(ft_const.STYLE_NORMAL, font.style)
         ft.quit ()
+
+    def todo_test_pygame2_freetype_Font_copy (self):
+
+        # __doc__ (as of 2010-04-07) for pygame2.freetype.Font.copy:
+
+        # Creates a copy of the Font.
         
+        ft.init ()
+        font = self.get_sans_font ()
+        fontcopy = font.copy ()
+        ft.quit ()
+    
     def todo_test_pygame2_freetype_Font_antialiased(self):
 
         # __doc__ (as of 2009-12-14) for pygame2.freetype.Font.antialiased:
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.