From 1233dfe1f22d9f14584e3811d480a97c6a89d4ff Mon Sep 17 00:00:00 2001 From: Matthias Kramm Date: Tue, 6 Oct 2009 17:28:23 -0700 Subject: [PATCH] added fontalign support in swfdump --- lib/modules/swftext.c | 21 +++++------ lib/modules/swftools.c | 1 + lib/rfxswf.c | 35 ++++++++++++++++-- lib/rfxswf.h | 2 ++ src/swfdump.c | 93 ++++++++++++++++++++++++++++++++++++++---------- 5 files changed, 121 insertions(+), 31 deletions(-) diff --git a/lib/modules/swftext.c b/lib/modules/swftext.c index d2b8989..6bd59f0 100644 --- a/lib/modules/swftext.c +++ b/lib/modules/swftext.c @@ -253,7 +253,7 @@ int swf_FontExtract_DefineFont2(int id, SWFFONT * font, TAG * tag) int fid; U32 offset_start; U32 *offset; - U8 flags1, flags2, namelen; + U8 flags1, langcode, namelen; swf_SetTagPos(tag, 0); font->version = 2; fid = swf_GetU16(tag); @@ -261,7 +261,7 @@ int swf_FontExtract_DefineFont2(int id, SWFFONT * font, TAG * tag) return id; font->id = fid; flags1 = swf_GetU8(tag); - flags2 = swf_GetU8(tag); //reserved flags + langcode = swf_GetU8(tag); //reserved flags if (flags1 & 1) font->style |= FONT_STYLE_BOLD; @@ -318,7 +318,7 @@ int swf_FontExtract_DefineFont2(int id, SWFFONT * font, TAG * tag) maxcode = 0; for (t = 0; t < glyphcount; t++) { int code; - if (flags1 & 4) // wide codes + if (flags1 & 4) // wide codes (always on for definefont3) code = swf_GetU16(tag); else code = swf_GetU8(tag); @@ -498,6 +498,7 @@ int swf_FontExtract(SWF * swf, int id, SWFFONT * *font) break; case ST_DEFINEFONT2: + case ST_DEFINEFONT3: nid = swf_FontExtract_DefineFont2(id, f, t); break; @@ -1393,13 +1394,13 @@ void swf_WriteFont(SWFFONT * font, char *filename) if(font->name) { t = swf_InsertTag(t, ST_NAMECHARACTER); swf_SetU16(t, WRITEFONTID); - swf_SetString(t, font->name); + swf_SetString(t, (char*)font->name); t = swf_InsertTag(t, ST_EXPORTASSETS); swf_SetU16(t, 1); swf_SetU16(t, WRITEFONTID); - swf_SetString(t, font->name); + swf_SetString(t, (char*)font->name); - t = swf_AddAS3FontDefine(t, WRITEFONTID, font->name); + t = swf_AddAS3FontDefine(t, WRITEFONTID, (char*)font->name); } if (storeGlyphNames && font->glyphnames) { @@ -1409,9 +1410,9 @@ void swf_WriteFont(SWFFONT * font, char *filename) swf_SetU16(t, font->numchars); for (c = 0; c < font->numchars; c++) { if (font->glyphnames[c]) - swf_SetString(t, (U8*)font->glyphnames[c]); + swf_SetString(t, font->glyphnames[c]); else - swf_SetString(t, (U8*)""); + swf_SetString(t, ""); } } @@ -1560,9 +1561,9 @@ void swf_SetEditText(TAG * tag, U16 flags, SRECT r, const char *text, RGBA * col swf_SetU16(tag, layout->indent); //indent swf_SetU16(tag, layout->leading); //leading } - swf_SetString(tag, (U8*)variable); + swf_SetString(tag, variable); if (flags & ET_HASTEXT) - swf_SetString(tag, (U8*)text); + swf_SetString(tag, text); } SRECT swf_SetDefineText(TAG * tag, SWFFONT * font, RGBA * rgb, const char *text, int scale) diff --git a/lib/modules/swftools.c b/lib/modules/swftools.c index 42279bb..7b1cae1 100644 --- a/lib/modules/swftools.c +++ b/lib/modules/swftools.c @@ -1166,6 +1166,7 @@ U8 swf_isFontTag(TAG*tag) { if(tag->id == ST_DEFINEFONT || tag->id == ST_DEFINEFONT2 || + tag->id == ST_DEFINEFONT3 || tag->id == ST_DEFINEFONTINFO) return 1; return 0; diff --git a/lib/rfxswf.c b/lib/rfxswf.c index d601a15..c4f42e8 100644 --- a/lib/rfxswf.c +++ b/lib/rfxswf.c @@ -406,6 +406,35 @@ int swf_SetU30String(TAG*tag, const char*str, int l) swf_SetBlock(tag, (void*)str, l); return len; } +float swf_GetF16(TAG * t) +{ + // D16 is 1-5-10 + // D32 is 1-8-23 + U16 f1 = swf_GetU16(t); + if(!f1) return 0; + U32 f2 = (f1&0x8000)<<16; //sign + f2 |= ((f1&0x7c00)<<13)+(0x40000000-(0x4000<<13)); //exp + f2 |= (f1&0x03ff)<<13; //mantissa + fprintf(stderr, "%f = %d-%d-%x\n", *(float*)&f2, f1>>15, (f1>>10)&31, f1&0x3ff); + return *(float*)&f2; +} +void swf_SetF16(TAG * t, float f) +{ + U32 f1 = *(U32*)&f; + U16 f2 = (f1>>16)&0x8000; + int exp = ((f1>>23)&0xff)-0x80+0x10; + if(exp<0) { + exp = 0; + fprintf(stderr, "Exponent underflow in FLOAT16 encoding\n"); + } else if(exp>=32) { + exp = 31; + fprintf(stderr, "Exponent overflow in FLOAT16 encoding\n"); + } + f2 |= exp<<10; + f2 |= (f1>>13)&0x3ff; + swf_SetU16(t, f2); +} + double swf_GetD64(TAG*tag) { /* FIXME: this is not big-endian compatible */ @@ -949,7 +978,7 @@ void swf_SetPassword(TAG * t, const char * password) md5string = crypt_md5(password, salt); swf_SetU16(t,0); - swf_SetString(t, (U8*)md5string); + swf_SetString(t, md5string); } void swf_SetString(TAG*t, const char* s) @@ -957,7 +986,7 @@ void swf_SetString(TAG*t, const char* s) if(!s) { swf_SetU8(t, 0); } else { - swf_SetBlock(t,s,strlen(s)+1); + swf_SetBlock(t,(U8*)s,strlen(s)+1); } } @@ -1578,7 +1607,7 @@ int WriteExtraTags(SWF*swf, writer_t*writer) if(0 && !has_scenedescription) { TAG*scene = swf_InsertTag(0, ST_SCENEDESCRIPTION); swf_SetU16(scene, 1); - swf_SetString(scene, (U8*)"Scene 1"); + swf_SetString(scene, "Scene 1"); swf_SetU8(scene, 0); if(writer) { if(swf_WriteTag2(writer, scene)<0) diff --git a/lib/rfxswf.h b/lib/rfxswf.h index 326c45a..862d492 100644 --- a/lib/rfxswf.h +++ b/lib/rfxswf.h @@ -231,6 +231,7 @@ U8 swf_GetU8(TAG * t); // resets Bitcount U16 swf_GetU16(TAG * t); #define swf_GetS16(tag) ((S16)swf_GetU16(tag)) U32 swf_GetU32(TAG * t); +float swf_GetF16(TAG * t); void swf_GetRGB(TAG * t, RGBA * col); void swf_GetRGBA(TAG * t, RGBA * col); void swf_GetGradient(TAG * t, GRADIENT * gradient, char alpha); @@ -241,6 +242,7 @@ int swf_SetU8(TAG * t,U8 v); // resets Bitcount int swf_SetU16(TAG * t,U16 v); void swf_SetS16(TAG * t,int v); int swf_SetU32(TAG * t,U32 v); +void swf_SetF16(TAG * t,float f); void swf_SetString(TAG*t,const char*s); /* abc datatypes */ diff --git a/src/swfdump.c b/src/swfdump.c index 12c653d..3df34df 100644 --- a/src/swfdump.c +++ b/src/swfdump.c @@ -298,7 +298,7 @@ void dumpFont(TAG*tag, char*prefix) { SWFFONT* font = malloc(sizeof(SWFFONT)); memset(font, 0, sizeof(SWFFONT)); - if(tag->id == ST_DEFINEFONT2) { + if(tag->id == ST_DEFINEFONT2 || tag->id == ST_DEFINEFONT3) { swf_FontExtract_DefineFont2(0, font, tag); } else if(tag->id == ST_DEFINEFONT) { swf_FontExtract_DefineFont(0, font, tag); @@ -962,6 +962,57 @@ void handleExportAssets(TAG*tag, char* prefix) } } +static void handleFontAlign1(TAG*tag) +{ + swf_SetTagPos(tag, 0); + U16 id = swf_GetU16(tag); + U8 flags = swf_GetU8(tag); + printf(" for font %04d, ", id); + if((flags&3)==0) printf("thin, "); + else if((flags&3)==1) printf("medium, "); + else if((flags&3)==2) printf("thick, "); + else printf("?, "); + int num=0; + while(tag->pos < tag->len) { + int nr = swf_GetU8(tag); // should be 2 + int t; + if(nr>2) { + printf("*** unsupported multiboxes ***, "); + break; + } + for(t=0;tpos < tag->len) { + printf("%sglyph %d) ", prefix, num++); + int nr = swf_GetU8(tag); // should be 2 + int t; + for(t=0;tid, tag->len, prefix, swf_TagGetName(tag)); } - if(swf_isDefiningTag(tag)) { - U16 id = swf_GetDefineID(tag); - printf(" defines id %04d", id); - if(idtab[id]) - dumperror("Id %04d is defined more than once.", id); - idtab[id] = 1; - } - else if(swf_isPseudoDefiningTag(tag)) { - U16 id = swf_GetDefineID(tag); - printf(" adds information to id %04d", id); - if(!idtab[id]) - dumperror("Id %04d is not yet defined.\n", id); - } - else if(tag->id == ST_PLACEOBJECT) { + if(tag->id == ST_PLACEOBJECT) { printf(" places id %04d at depth %04x", swf_GetPlaceID(tag), swf_GetDepth(tag)); if(swf_GetName(tag)) printf(" name \"%s\"",swf_GetName(tag)); @@ -1279,7 +1317,7 @@ int main (int argc,char ** argv) } } else if(tag->id == ST_FRAMELABEL) { - int l = strlen(tag->data); + int l = strlen((char*)tag->data); printf(" \"%s\"", tag->data); if((l+1) < tag->len) { printf(" has %d extra bytes", tag->len-1-l); @@ -1291,8 +1329,8 @@ int main (int argc,char ** argv) dumperror("Frame %d has more than one label", issprite?spriteframe:mainframe); } - if(issprite) spriteframelabel = tag->data; - else framelabel = tag->data; + if(issprite) spriteframelabel = (char*)tag->data; + else framelabel = (char*)tag->data; } else if(tag->id == ST_SHOWFRAME) { char*label = issprite?spriteframelabel:framelabel; @@ -1329,6 +1367,9 @@ int main (int argc,char ** argv) printf(" %s", swf_GetString(tag)); } } + else if(tag->id == ST_DEFINEFONTALIGNZONES) { + handleFontAlign1(tag); + } else if(tag->id == ST_CSMTEXTSETTINGS) { U16 id = swf_GetU16(tag); U8 flags = swf_GetU8(tag); @@ -1349,6 +1390,19 @@ int main (int argc,char ** argv) printf("s=%.2f,t=%.2f)", thickness, sharpness); swf_GetU8(tag); } + else if(swf_isDefiningTag(tag)) { + U16 id = swf_GetDefineID(tag); + printf(" defines id %04d", id); + if(idtab[id]) + dumperror("Id %04d is defined more than once.", id); + idtab[id] = 1; + } + else if(swf_isPseudoDefiningTag(tag)) { + U16 id = swf_GetDefineID(tag); + printf(" adds information to id %04d", id); + if(!idtab[id]) + dumperror("Id %04d is not yet defined.\n", id); + } if(tag->id == ST_DEFINEBITSLOSSLESS || tag->id == ST_DEFINEBITSLOSSLESS2) { @@ -1463,6 +1517,9 @@ int main (int argc,char ** argv) else if(tag->id == ST_PLACEOBJECT2 || tag->id == ST_PLACEOBJECT3) { handlePlaceObject23(tag, myprefix); } + else if(tag->id == ST_DEFINEFONTALIGNZONES) { + handleFontAlign2(tag, myprefix); + } else if(tag->id == ST_DEFINEFONTNAME) { swf_SetTagPos(tag, 0); swf_GetU16(tag); //id -- 1.7.10.4