Edit

kc3-lang/ftgl/src/FTGlyph/FTGlyphGlue.cpp

Branch :

  • Show log

    Commit

  • Author : brlcad
    Date : 2010-09-28 19:01:23
    Hash : 9a13e4f8
    Message : implement a quick check for __FUNCTION__ and __func__ based on whether the compiler can actually use one or the other at runtime. cache the checks and provide __FUNC__ for use via FTGL_CPP_FUNC.

  • src/FTGlyph/FTGlyphGlue.cpp
  • /*
     * FTGL - OpenGL font library
     *
     * Copyright (c) 2001-2004 Henry Maddocks <ftgl@opengl.geek.nz>
     * Copyright (c) 2008 Sam Hocevar <sam@hocevar.net>
     *
     * Permission is hereby granted, free of charge, to any person obtaining
     * a copy of this software and associated documentation files (the
     * "Software"), to deal in the Software without restriction, including
     * without limitation the rights to use, copy, modify, merge, publish,
     * distribute, sublicense, and/or sell copies of the Software, and to
     * permit persons to whom the Software is furnished to do so, subject to
     * the following conditions:
     *
     * The above copyright notice and this permission notice shall be
     * included in all copies or substantial portions of the Software.
     *
     * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
     * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
     * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
     * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
     * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
     * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
     * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
     */
    
    #include "config.h"
    
    #include "FTGL/ftgl.h"
    
    #include "FTInternals.h"
    
    static const FTPoint static_ftpoint;
    static const FTBBox static_ftbbox;
    
    FTGL_BEGIN_C_DECLS
    
    #define C_TOR(cname, cargs, cxxname, cxxarg, cxxtype) \
        FTGLglyph* cname cargs \
        { \
            cxxname *g = new cxxname cxxarg; \
            if(g->Error()) \
            { \
                delete g; \
                return NULL; \
            } \
            FTGLglyph *ftgl = (FTGLglyph *)malloc(sizeof(FTGLglyph)); \
            ftgl->ptr = g; \
            ftgl->type = cxxtype; \
            return ftgl; \
        }
    
    // FTBitmapGlyph::FTBitmapGlyph();
    C_TOR(ftglCreateBitmapGlyph, (FT_GlyphSlot glyph),
          FTBitmapGlyph, (glyph), GLYPH_BITMAP);
    
    // FTBufferGlyph::FTBufferGlyph();
    // FIXME: not implemented
    
    // FTExtrudeGlyph::FTExtrudeGlyph();
    C_TOR(ftglCreateExtrudeGlyph, (FT_GlyphSlot glyph, float depth,
                       float frontOutset, float backOutset, int useDisplayList),
          FTExtrudeGlyph, (glyph, depth, frontOutset, backOutset, (useDisplayList != 0)),
          GLYPH_EXTRUDE);
    
    // FTOutlineGlyph::FTOutlineGlyph();
    C_TOR(ftglCreateOutlineGlyph, (FT_GlyphSlot glyph, float outset,
                                   int useDisplayList),
          FTOutlineGlyph, (glyph, outset, (useDisplayList != 0)), GLYPH_OUTLINE);
    
    // FTPixmapGlyph::FTPixmapGlyph();
    C_TOR(ftglCreatePixmapGlyph, (FT_GlyphSlot glyph),
          FTPixmapGlyph, (glyph), GLYPH_PIXMAP);
    
    // FTPolygonGlyph::FTPolygonGlyph();
    C_TOR(ftglCreatePolygonGlyph, (FT_GlyphSlot glyph, float outset,
                                   int useDisplayList),
          FTPolygonGlyph, (glyph, outset, (useDisplayList != 0)), GLYPH_POLYGON);
    
    // FTTextureGlyph::FTTextureGlyph();
    C_TOR(ftglCreateTextureGlyph, (FT_GlyphSlot glyph, int id, int xOffset,
                                   int yOffset, int width, int height),
          FTTextureGlyph, (glyph, id, xOffset, yOffset, width, height),
          GLYPH_TEXTURE);
    
    // FTCustomGlyph::FTCustomGlyph();
    class FTCustomGlyph : public FTGlyph
    {
    public:
        FTCustomGlyph(FTGLglyph *base, void *p,
                      void (*render) (FTGLglyph *, void *, FTGL_DOUBLE, FTGL_DOUBLE,
                                      int, FTGL_DOUBLE *, FTGL_DOUBLE *),
                      void (*destroy) (FTGLglyph *, void *))
         : FTGlyph((FT_GlyphSlot)0),
           baseGlyph(base),
           data(p),
           renderCallback(render),
           destroyCallback(destroy)
        {}
    
        ~FTCustomGlyph()
        {
            destroyCallback(baseGlyph, data);
        }
    
        float Advance() const { return baseGlyph->ptr->Advance(); }
    
        const FTPoint& Render(const FTPoint& pen, int renderMode)
        {
            FTGL_DOUBLE advancex, advancey;
            renderCallback(baseGlyph, data, pen.X(), pen.Y(), renderMode,
                           &advancex, &advancey);
            advance = FTPoint(advancex, advancey);
            return advance;
        }
    
        const FTBBox& BBox() const { return baseGlyph->ptr->BBox(); }
    
        FT_Error Error() const { return baseGlyph->ptr->Error(); }
    
    private:
        FTPoint advance;
        FTGLglyph *baseGlyph;
        void *data;
        void (*renderCallback) (FTGLglyph *, void *, FTGL_DOUBLE, FTGL_DOUBLE,
                                int, FTGL_DOUBLE *, FTGL_DOUBLE *);
        void (*destroyCallback) (FTGLglyph *, void *);
    };
    
    C_TOR(ftglCreateCustomGlyph, (FTGLglyph *base, void *data,
             void (*renderCallback) (FTGLglyph *, void *, FTGL_DOUBLE, FTGL_DOUBLE,
                                     int, FTGL_DOUBLE *, FTGL_DOUBLE *),
             void (*destroyCallback) (FTGLglyph *, void *)),
          FTCustomGlyph, (base, data, renderCallback, destroyCallback),
          GLYPH_CUSTOM);
    
    #define C_FUN(cret, cname, cargs, cxxerr, cxxname, cxxarg) \
        cret cname cargs \
        { \
            if(!g || !g->ptr) \
            { \
                fprintf(stderr, "FTGL warning: NULL pointer in %s\n", #cname); \
                cxxerr; \
            } \
            return g->ptr->cxxname cxxarg; \
        }
    
    // FTGlyph::~FTGlyph();
    void ftglDestroyGlyph(FTGLglyph *g)
    {
        if(!g || !g->ptr)
        {
            fprintf(stderr, "FTGL warning: NULL pointer in %s\n", __FUNC__);
            return;
        }
        delete g->ptr;
        free(g);
    }
    
    // const FTPoint& FTGlyph::Render(const FTPoint& pen, int renderMode);
    extern "C++" {
    C_FUN(static const FTPoint&, _ftglRenderGlyph, (FTGLglyph *g,
                                       const FTPoint& pen, int renderMode),
          return static_ftpoint, Render, (pen, renderMode));
    }
    
    void ftglRenderGlyph(FTGLglyph *g, FTGL_DOUBLE penx, FTGL_DOUBLE peny,
                         int renderMode, FTGL_DOUBLE *advancex,
                         FTGL_DOUBLE *advancey)
    {
        FTPoint pen(penx, peny);
        FTPoint ret = _ftglRenderGlyph(g, pen, renderMode);
        *advancex = ret.X();
        *advancey = ret.Y();
    }
    
    // float FTGlyph::Advance() const;
    C_FUN(float, ftglGetGlyphAdvance, (FTGLglyph *g), return 0.0, Advance, ());
    
    // const FTBBox& FTGlyph::BBox() const;
    extern "C++" {
    C_FUN(static const FTBBox&, _ftglGetGlyphBBox, (FTGLglyph *g),
          return static_ftbbox, BBox, ());
    }
    
    void ftglGetGlyphBBox(FTGLglyph *g, float bounds[6])
    {
        FTBBox ret = _ftglGetGlyphBBox(g);
        FTPoint lower = ret.Lower(), upper = ret.Upper();
        bounds[0] = lower.Xf(); bounds[1] = lower.Yf(); bounds[2] = lower.Zf();
        bounds[3] = upper.Xf(); bounds[4] = upper.Yf(); bounds[5] = upper.Zf();
    }
    
    // FT_Error FTGlyph::Error() const;
    C_FUN(FT_Error, ftglGetGlyphError, (FTGLglyph *g), return -1, Error, ());
    
    FTGL_END_C_DECLS