summaryrefslogtreecommitdiffstats
path: root/skia/ports/SkFontHost_ascender.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'skia/ports/SkFontHost_ascender.cpp')
-rw-r--r--skia/ports/SkFontHost_ascender.cpp211
1 files changed, 211 insertions, 0 deletions
diff --git a/skia/ports/SkFontHost_ascender.cpp b/skia/ports/SkFontHost_ascender.cpp
new file mode 100644
index 0000000..2148850
--- /dev/null
+++ b/skia/ports/SkFontHost_ascender.cpp
@@ -0,0 +1,211 @@
+#include "SkScalerContext.h"
+#include "SkBitmap.h"
+#include "SkCanvas.h"
+#include "SkDescriptor.h"
+#include "SkFDot6.h"
+#include "SkFontHost.h"
+#include "SkMask.h"
+#include "SkStream.h"
+#include "SkString.h"
+#include "SkThread.h"
+#include "SkTemplates.h"
+
+#include <acaapi.h>
+
+//////////////////////////////////////////////////////////////////////////
+
+#include "SkMMapStream.h"
+
+class SkScalerContext_Ascender : public SkScalerContext {
+public:
+ SkScalerContext_Ascender(const SkDescriptor* desc);
+ virtual ~SkScalerContext_Ascender();
+
+protected:
+ virtual unsigned generateGlyphCount() const;
+ virtual uint16_t generateCharToGlyph(SkUnichar uni);
+ virtual void generateMetrics(SkGlyph* glyph);
+ virtual void generateImage(const SkGlyph& glyph);
+ virtual void generatePath(const SkGlyph& glyph, SkPath* path);
+ virtual void generateFontMetrics(SkPaint::FontMetrics* mx, SkPaint::FontMetrics* my);
+
+private:
+ aca_FontHandle fHandle;
+ void* fWorkspace;
+ void* fGlyphWorkspace;
+ SkStream* fFontStream;
+ SkStream* fHintStream;
+};
+
+///////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////
+
+SkScalerContext_Ascender::SkScalerContext_Ascender(const SkDescriptor* desc)
+ : SkScalerContext(desc)
+{
+ int size = aca_Get_FontHandleRec_Size();
+ fHandle = (aca_FontHandle)sk_malloc_throw(size);
+
+ // get the pointer to the font
+
+ fFontStream = new SkMMAPStream("/UcsGB2312-Hei-H.FDL");
+ fHintStream = new SkMMAPStream("/genv6-23.bin");
+
+ void* hints = sk_malloc_throw(fHintStream->getLength());
+ memcpy(hints, fHintStream->getMemoryBase(), fHintStream->getLength());
+
+ aca_Create_Font_Handle(fHandle,
+ (void*)fFontStream->getMemoryBase(), fFontStream->getLength(),
+ "fred",
+ hints, fHintStream->getLength());
+
+ // compute our factors from the record
+
+ SkMatrix m;
+
+ fRec.getSingleMatrix(&m);
+
+ // now compute our scale factors
+ SkScalar sx = m.getScaleX();
+ SkScalar sy = m.getScaleY();
+
+ int ppemX = SkScalarRound(sx);
+ int ppemY = SkScalarRound(sy);
+
+ size = aca_Find_Font_Memory_Required(fHandle, ppemX, ppemY);
+ size *= 8; // Jeff suggests this :)
+ fWorkspace = sk_malloc_throw(size);
+ aca_Set_Font_Memory(fHandle, (uint8_t*)fWorkspace, size);
+
+ aca_GlyphAttribsRec rec;
+
+ memset(&rec, 0, sizeof(rec));
+ rec.xSize = ppemX;
+ rec.ySize = ppemY;
+ rec.doAdjust = true;
+ rec.doExceptions = true;
+ rec.doGlyphHints = true;
+ rec.doInterpolate = true;
+ rec.grayMode = 2;
+ aca_Set_Font_Attributes(fHandle, &rec, &size);
+
+ fGlyphWorkspace = sk_malloc_throw(size);
+ aca_Set_Glyph_Memory(fHandle, fGlyphWorkspace);
+}
+
+SkScalerContext_Ascender::~SkScalerContext_Ascender()
+{
+ delete fHintStream;
+ delete fFontStream;
+ sk_free(fGlyphWorkspace);
+ sk_free(fWorkspace);
+ sk_free(fHandle);
+}
+
+unsigned SkScalerContext_Ascender::generateGlyphCount() const
+{
+ return 1000;
+}
+
+uint16_t SkScalerContext_Ascender::generateCharToGlyph(SkUnichar uni)
+{
+ return (uint16_t)(uni & 0xFFFF);
+}
+
+void SkScalerContext_Ascender::generateMetrics(SkGlyph* glyph)
+{
+ glyph->fRsbDelta = 0;
+ glyph->fLsbDelta = 0;
+
+ aca_GlyphImageRec rec;
+ aca_Vector topLeft;
+
+ int adv = aca_Get_Adv_Width(fHandle, glyph->getGlyphID());
+ if (aca_GLYPH_NOT_PRESENT == adv)
+ goto ERROR;
+
+ aca_Rasterize(glyph->getGlyphID(), fHandle, &rec, &topLeft);
+
+ if (false) // error
+ {
+ERROR:
+ glyph->fWidth = 0;
+ glyph->fHeight = 0;
+ glyph->fTop = 0;
+ glyph->fLeft = 0;
+ glyph->fAdvanceX = 0;
+ glyph->fAdvanceY = 0;
+ return;
+ }
+
+ glyph->fWidth = rec.width;
+ glyph->fHeight = rec.rows;
+ glyph->fRowBytes = rec.width;
+ glyph->fTop = -topLeft.y;
+ glyph->fLeft = topLeft.x;
+ glyph->fAdvanceX = SkIntToFixed(adv);
+ glyph->fAdvanceY = SkIntToFixed(0);
+}
+
+void SkScalerContext_Ascender::generateImage(const SkGlyph& glyph)
+{
+ aca_GlyphImageRec rec;
+ aca_Vector topLeft;
+
+ aca_Rasterize(glyph.getGlyphID(), fHandle, &rec, &topLeft);
+
+ const uint8_t* src = (const uint8_t*)rec.buffer;
+ uint8_t* dst = (uint8_t*)glyph.fImage;
+ int height = glyph.fHeight;
+
+ src += rec.y0 * rec.pitch + rec.x0;
+ while (--height >= 0)
+ {
+ memcpy(dst, src, glyph.fWidth);
+ src += rec.pitch;
+ dst += glyph.fRowBytes;
+ }
+}
+
+///////////////////////////////////////////////////////////////////////////////////////////
+
+void SkScalerContext_Ascender::generatePath(const SkGlyph& glyph, SkPath* path)
+{
+ SkRect r;
+
+ r.set(0, 0, SkIntToScalar(4), SkIntToScalar(4));
+ path->reset();
+ path->addRect(r);
+}
+
+void SkScalerContext_Ascender::generateFontMetrics(SkPaint::FontMetrics* mx, SkPaint::FontMetrics* my)
+{
+ if (NULL == mx && NULL == my)
+ return;
+
+ if (mx)
+ {
+ mx->fTop = SkIntToScalar(-16);
+ mx->fAscent = SkIntToScalar(-16);
+ mx->fDescent = SkIntToScalar(4);
+ mx->fBottom = SkIntToScalar(4);
+ mx->fLeading = 0;
+ }
+ if (my)
+ {
+ my->fTop = SkIntToScalar(-16);
+ my->fAscent = SkIntToScalar(-16);
+ my->fDescent = SkIntToScalar(4);
+ my->fBottom = SkIntToScalar(4);
+ my->fLeading = 0;
+ }
+}
+
+////////////////////////////////////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////
+
+SkScalerContext* SkFontHost::CreateScalerContext(const SkDescriptor* desc)
+{
+ return SkNEW_ARGS(SkScalerContext_Ascender, (desc));
+}
+