Lossless Images added.
[swftools.git] / pdf2swf / swfoutput.cc
index 31b57ef..5a634b5 100644 (file)
@@ -31,34 +31,34 @@ extern "C" {
 int ignoredraworder=0;
 int drawonlyshapes=0;
 int jpegquality=85;
+static int flag_protected = 0;
 
 typedef unsigned char u8;
 typedef unsigned short int u16;
 typedef unsigned long int u32;
 
-static int drawmode;
 static int fi;
-static int flag_protected;
+static char* filename = 0;
 static SWF swf;
 static TAG *tag;
 static int currentswfid = 0;
+static int depth = 1;
+static int startdepth = 1;
 
 static SHAPE* shape;
 static int shapeid = -1;
 static int textid = -1;
 
+static int drawmode = -1;
+static char storefont = 0;
 static int fillstyleid;
 static int linestyleid;
 static int swflastx=0;
 static int swflasty=0;
 static int lastwasfill = 0;
-static char* filename = 0;
+static char fill = 0;
 static int sizex;
 static int sizey;
-static char fill = 0;
-static char storefont = 0;
-static int depth = 1;
-static int startdepth = 1;
 TAG* cliptags[128];
 int clipshapes[128];
 u32 clipdepths[128];
@@ -168,7 +168,6 @@ void drawpath(TAG*tag, T1_OUTLINE*outline, struct swfmatrix*m)
     double lastx=0,lasty=0;
     double firstx=0,firsty=0;
     int init=1;
-    if(log) printf("shape-start %d\n", fill);
 
     while (outline)
     {
@@ -178,7 +177,7 @@ void drawpath(TAG*tag, T1_OUTLINE*outline, struct swfmatrix*m)
        {
            if(((int)(lastx*20) != (int)(firstx*20) ||
                (int)(lasty*20) != (int)(firsty*20)) &&
-                    fill)
+                    fill && !init)
            {
                plotxy p0;
                plotxy p1;
@@ -191,6 +190,7 @@ void drawpath(TAG*tag, T1_OUTLINE*outline, struct swfmatrix*m)
            }
            firstx=x;
            firsty=y;
+           init = 0;
        }
        else if(outline->type == T1_PATHTYPE_LINE) 
        {
@@ -241,7 +241,6 @@ void drawpath(TAG*tag, T1_OUTLINE*outline, struct swfmatrix*m)
        if(log) printf("fix: %f,%f -> %f,%f\n",p0.x,p0.y,p1.x,p1.y);
        line(tag, p0, p1, m);
     }
-    if(log) printf("shape-end\n");
 }
 
 int colorcompare(RGBA*a,RGBA*b)
@@ -267,7 +266,6 @@ struct chardata {
 } chardata[CHARDATAMAX];
 int chardatapos = 0;
 
-int once=0;
 void putcharacters(TAG*tag)
 {
     int t;
@@ -293,6 +291,9 @@ void putcharacters(TAG*tag)
        logf("<error> internal error: putcharacters needs an text tag, not %d\n",tag->id);
        exit(1);
     }
+    if(!chardatapos) {
+       logf("<warning> putcharacters called with zero characters");
+    }
 
     for(pass = 0; pass < 2; pass++)
     {
@@ -304,7 +305,7 @@ void putcharacters(TAG*tag)
 
        if(pass==1)
        {
-           advancebits++;
+           advancebits++; // add sign bit
            SetU8(tag, glyphbits);
            SetU8(tag, advancebits);
         }
@@ -334,7 +335,7 @@ void putcharacters(TAG*tag)
                {
                    tag->bitcount = 0;
                    SetBits(tag, 0, 1); // GLYPH Record
-                   SetBits(tag, charstorepos, 7); // one glyph
+                   SetBits(tag, charstorepos, 7); // number of glyphs
                    int s;
                    for(s=0;s<charstorepos;s++)
                    {
@@ -397,7 +398,8 @@ void putcharacters(TAG*tag)
     chardatapos = 0;
 }
 
-void putcharacter(struct swfoutput*obj, int fontid, int charid, int x,int y, int size)
+void putcharacter(struct swfoutput*obj, int fontid, int charid, 
+                   int x,int y, int size)
 {
     if(chardatapos == CHARDATAMAX)
     {
@@ -430,7 +432,7 @@ void drawchar(struct swfoutput*obj, SWFFont*font, char*character, swfmatrix*m)
            endshape();
        if(textid<0)
            starttext(obj);
-       putcharacter(obj, font->swfid, charid, (int)(m->m13*20),(int)(m->m23*20),
+       putcharacter(obj, font->swfid, charid,(int)(m->m13*20),(int)(m->m23*20),
                (int)(m->m11*20/2+0.5)); //where does the /2 come from?
     }
     else
@@ -439,7 +441,8 @@ void drawchar(struct swfoutput*obj, SWFFont*font, char*character, swfmatrix*m)
        char* charname = character;
 
        if(!outline) {
-        logf("Didn't find %s in current charset (%s)", character,font->getName());
+        logf("Didn't find %s in current charset (%s)", 
+                character,font->getName());
         return;
        }
        
@@ -466,7 +469,8 @@ void drawchar(struct swfoutput*obj, SWFFont*font, char*character, swfmatrix*m)
 }
 
 /* draw a curved polygon. */
-void swfoutput_drawpath(swfoutput*output, T1_OUTLINE*outline, struct swfmatrix*m)
+void swfoutput_drawpath(swfoutput*output, T1_OUTLINE*outline, 
+                           struct swfmatrix*m)
 {
     if(textid>=0)
        endtext();
@@ -613,7 +617,6 @@ T1_OUTLINE*SWFFont::getOutline(char*name)
     int t;
     for(t=0;t<this->charnum;t++) {
        if(!strcmp(this->charname[t],name)) {
-
            if(!used[t])
            {
                swfcharid2char[swfcharpos] = t;
@@ -632,7 +635,6 @@ int SWFFont::getSWFCharID(char*name)
     int t;
     for(t=0;t<this->charnum;t++) {
        if(!strcmp(this->charname[t],name)) {
-          
            if(!used[t])
            {
                swfcharid2char[swfcharpos] = t;
@@ -642,6 +644,7 @@ int SWFFont::getSWFCharID(char*name)
            return char2swfcharid[t];
        }
     }
+    logf("<warning> Didn't find character '%s' in font '%s'", name, this->name);
     return 0;
 }
 
@@ -752,7 +755,6 @@ void swfoutput_init(struct swfoutput* obj, char*_filename, int _sizex, int _size
   memset(&swf,0x00,sizeof(SWF));
 
   swf.FileVersion    = 4;
-//  swf.FrameRate      = 0x1900;
   swf.FrameRate      = 0x0040; // 1 frame per 4 seconds
   swf.MovieSize.xmax = 20*sizex;
   swf.MovieSize.ymax = 20*sizey;
@@ -987,11 +989,13 @@ void swfoutput_startclip(swfoutput*obj, T1_OUTLINE*outline, struct swfmatrix*m)
        logf("<warning> Too many clip levels.");
        clippos --;
     } 
-
+    
     startshape(obj);
+    int olddrawmode = drawmode;
     swfoutput_setdrawmode(obj, DRAWMODE_CLIP);
     swfoutput_drawpath(obj, outline, m);
     ShapeSetEnd(tag);
+    swfoutput_setdrawmode(obj, olddrawmode);
 
     tag = InsertTag(tag,ST_PLACEOBJECT2);
     cliptags[clippos] = tag;
@@ -1016,22 +1020,17 @@ void swfoutput_endclip(swfoutput*obj)
     PlaceObject(cliptags[clippos],clipshapes[clippos],clipdepths[clippos],NULL,NULL,NULL,depth++);
 }
 
-void swfoutput_drawimagefile(struct swfoutput*, char*filename, int sizex,int sizey, 
+
+void drawimage(struct swfoutput*obj, int bitid, int sizex,int sizey, 
        double x1,double y1,
        double x2,double y2,
        double x3,double y3,
        double x4,double y4)
 {
-    if(shapeid>=0)
-     endshape();
-    if(textid>=0)
-     endtext();
-
     RGBA rgb;
     SRECT r;
     int lsid=0;
     int fsid;
-    int bitid;
     struct plotxy p1,p2,p3,p4;
     int myshapeid;
     double xmax=x1,ymax=y1,xmin=x1,ymin=y1;
@@ -1064,14 +1063,7 @@ void swfoutput_drawimagefile(struct swfoutput*, char*filename, int sizex,int siz
 
     m.tx = (int)(x1*20);
     m.ty = (int)(y1*20);
-
-    bitid = ++currentswfid;
   
-    /* bitmap */
-    tag = InsertTag(tag,ST_DEFINEBITSJPEG2);
-    SetU16(tag, bitid);
-    SetJPEGBits(tag, filename, jpegquality);
-
     /* shape */
     myshapeid = ++currentswfid;
     tag = InsertTag(tag,ST_DEFINESHAPE);
@@ -1108,3 +1100,60 @@ void swfoutput_drawimagefile(struct swfoutput*, char*filename, int sizex,int siz
     ObjectPlace(tag,myshapeid,/*depth*/depth++,NULL,NULL,NULL);
 }
 
+void swfoutput_drawimagejpeg(struct swfoutput*obj, char*filename, int sizex,int sizey, 
+       double x1,double y1,
+       double x2,double y2,
+       double x3,double y3,
+       double x4,double y4)
+{
+    if(shapeid>=0)
+     endshape();
+    if(textid>=0)
+     endtext();
+
+    int bitid = ++currentswfid;
+    tag = InsertTag(tag,ST_DEFINEBITSJPEG2);
+    SetU16(tag, bitid);
+    SetJPEGBits(tag, filename, jpegquality);
+
+    drawimage(obj, bitid, sizex, sizey, x1,y1,x2,y2,x3,y3,x4,y4);
+}
+
+void swfoutput_drawimagelossless(struct swfoutput*obj, RGBA*mem, int sizex,int sizey, 
+       double x1,double y1,
+       double x2,double y2,
+       double x3,double y3,
+       double x4,double y4)
+{
+    if(shapeid>=0)
+     endshape();
+    if(textid>=0)
+     endtext();
+
+    int bitid = ++currentswfid;
+    tag = InsertTag(tag,ST_DEFINEBITSLOSSLESS);
+    SetU16(tag, bitid);
+    SetLosslessBits(tag,sizex,sizey,mem, BMF_32BIT);
+    
+    drawimage(obj, bitid, sizex, sizey, x1,y1,x2,y2,x3,y3,x4,y4);
+}
+
+void swfoutput_drawimagelossless256(struct swfoutput*obj, U8*mem, RGBA*pal, int sizex,int sizey, 
+       double x1,double y1,
+       double x2,double y2,
+       double x3,double y3,
+       double x4,double y4)
+{
+    if(shapeid>=0)
+     endshape();
+    if(textid>=0)
+     endtext();
+
+    int bitid = ++currentswfid;
+    tag = InsertTag(tag,ST_DEFINEBITSLOSSLESS2);
+    SetU16(tag, bitid);
+    SetLosslessBitsIndexed(tag,sizex,sizey,mem, pal, 256);
+  
+    drawimage(obj, bitid, sizex, sizey, x1,y1,x2,y2,x3,y3,x4,y4);
+}
+