Example #1
0
static int pdfLoadPage(PDFContext* ctx) {
	if (fullPageBuffer != NULL) {
		fz_droppixmap(fullPageBuffer);
		fullPageBuffer = NULL;
	}
	strcpy(lastPageError, "No error");

	fz_error *error;
	fz_obj *obj;

	if (ctx->page)
		pdf_droppage(ctx->page);
	ctx->page = 0;

	// empty store to save memory
	if (ctx->xref->store)
		pdf_emptystore(ctx->xref->store);
	bk_pdf_resetbufferssize();
	/*
	pdf_item *item;
	fz_obj *key;
	list<fz_obj *key> keys;
	for (item = ctx->xref->store->root; item; item = item->next) {
		if (item->kind == PDF_KIMAGE)
			keys << key;
	}
	list<fz_obj *key>::iterator it(keys.begin);
	while (it != keys.end()) {

		++it;
	}
	*/

	obj = pdf_getpageobject(ctx->pages, ctx->pageno - 1, ctx->xref);

	error = pdf_loadpage(&ctx->page, ctx->xref, obj);
	if (error) {
		printf("errLP1: %s\n", error->msg);
		strcpy(lastPageError, error->msg);
		return -1;
	}

	//printf("\n\n debug tree ------------------------------------------------\n");
	//fz_debugtree(ctx->page->tree);

	//optimizeNode(ctx->page->tree->root);

	//printf("\n\n OPT debug tree OPT ------------------------------------------------\n");
	//fz_debugtree(ctx->page->tree);

	recalcScreenMediaBox(ctx);
	if (BKUser::options.pdfFastScroll) {
		pdfRenderFullPage(ctx);
	}
	return 0;
}
Example #2
0
int
epdf_index_item_page_get(const Epdf_Document *doc, const Epdf_Index_Item *item)
{
   fz_obj *dest;
   int p;
   int n;
   int g;

   if (!item || !item->link)
     return -1;

   if (PDF_LGOTO != item->link->kind)
     return -1;

   dest = item->link->dest;
   p = 0;
   if (fz_isint(dest))
     {
        p = fz_toint(dest);
        return p;
     }
   if (fz_isdict(dest))
     {
        /* The destination is linked from a Go-To action's D array */
       fz_obj *D;

       D = fz_dictgets(dest, "D");
       if (D && fz_isarray(D))
         dest = fz_arrayget(D, 0);
     }

   n = fz_tonum(dest);
   g = fz_togen(dest);

   for (p = 1; p <= epdf_document_page_count_get(doc); p++)
     {
        fz_obj *page;
        int np;
        int gp;

        page = pdf_getpageobject(doc->xref, p);
        if (!page)
          continue;

        np = fz_tonum(page);
        gp = fz_togen(page);
        if (n == np && g == gp)
          return p-1;
    }

   return 0;
}
Example #3
0
void
drawloadpage(int pagenum, struct benchmark *loadtimes)
{
	fz_error *error;
	fz_obj *pageobj;
	long start;
	long end;
	long elapsed;

	fprintf(stderr, "draw %s page %d ", srcname, pagenum);
	if (benchmark && loadtimes)
	{
		fflush(stderr);
		gettime(&start);
	}

	pageobj = pdf_getpageobject(srcpages, pagenum - 1);
	error = pdf_loadpage(&drawpage, src, pageobj);
	if (error)
		die(error);

	if (benchmark && loadtimes)
	{
	    gettime(&end);
	    elapsed = end - start;

	    if (elapsed < loadtimes->min)
	    {
		loadtimes->min = elapsed;
		loadtimes->minpage = pagenum;
	    }
	    if (elapsed > loadtimes->max)
	    {
		loadtimes->max = elapsed;
		loadtimes->maxpage = pagenum;
	    }
	    loadtimes->avg += elapsed;
	    loadtimes->pages++;
	}

	fprintf(stderr, "mediabox [ %g %g %g %g ] rotate %d%s",
			drawpage->mediabox.x0, drawpage->mediabox.y0,
			drawpage->mediabox.x1, drawpage->mediabox.y1,
			drawpage->rotate,
			benchmark ? "" : "\n");
	if (benchmark)
		fflush(stderr);
}
Example #4
0
JNIEXPORT void JNICALL Java_com_artifex_mupdf_MuPDFCore_gotoPageInternal(
                                            JNIEnv  *env,
                                            jobject  thiz,
                                            int      page)
{
    float      zoom;
    fz_matrix  ctm;
    fz_obj    *pageobj;
    fz_bbox    bbox;
    fz_error   error;
    fz_device *dev;
    pdf_page  *currentPage;

    /* In the event of an error, ensure we give a non-empty page */
    pageWidth  = 100;
    pageHeight = 100;

    LOGE("Goto page %d...", page);
    if (currentPageList != NULL)
    {
	fz_freedisplaylist(currentPageList);
	currentPageList = NULL;
    }
    pagenum = page;
    pageobj = pdf_getpageobject(xref, pagenum);
    if (pageobj == NULL)
        return;
    error = pdf_loadpage(&currentPage, xref, pageobj);
    if (error)
        return;
    zoom = resolution / 72;
    currentMediabox = currentPage->mediabox;
    currentRotate   = currentPage->rotate;
    ctm = fz_translate(0, -currentMediabox.y1);
    ctm = fz_concat(ctm, fz_scale(zoom, -zoom));
    ctm = fz_concat(ctm, fz_rotate(currentRotate));
    bbox = fz_roundrect(fz_transformrect(ctm, currentMediabox));
    pageWidth  = bbox.x1-bbox.x0;
    pageHeight = bbox.y1-bbox.y0;
    /* Render to list */
    currentPageList = fz_newdisplaylist();
    dev = fz_newlistdevice(currentPageList);
    error = pdf_runpage(xref, currentPage, dev, fz_identity);
    pdf_freepage(currentPage);
    if (error)
        LOGE("cannot make displaylist from page %d", pagenum);
    fz_freedevice(dev);
}
Example #5
0
void
drawloadpage(int pagenum)
{
    fz_error *error;
    fz_obj *pageobj;

    pageobj = pdf_getpageobject(srcpages, pagenum - 1);
    error = pdf_loadpage(&drawpage, src, pageobj);
    if (error)
        die(error);

    fprintf(stderr, "draw %s page %d mediabox [ %g %g %g %g ] rotate %d\n",
            srcname, pagenum,
            drawpage->mediabox.x0, drawpage->mediabox.y0,
            drawpage->mediabox.x1, drawpage->mediabox.y1,
            drawpage->rotate);
}
static void drawloadpage(int pagenum, struct benchmark *loadtimes)
{
    fz_error error;
    fz_obj *pageobj;
    long start;
    long end;
    long elapsed;

    fprintf(stderr, "draw %s:%03d ", basename, pagenum);
    if (benchmark && loadtimes)
    {
	fflush(stderr);
	gettime(&start);
    }

    error = pdf_getpageobject(xref, pagenum, &pageobj);
    if (error)
	die(error);
    error = pdf_loadpage(&drawpage, xref, pageobj);
    if (error)
	die(error);

    if (benchmark && loadtimes)
    {
	gettime(&end);
	elapsed = end - start;

	if (elapsed < loadtimes->min)
	{
	    loadtimes->min = elapsed;
	    loadtimes->minpage = pagenum;
	}
	if (elapsed > loadtimes->max)
	{
	    loadtimes->max = elapsed;
	    loadtimes->maxpage = pagenum;
	}
	loadtimes->avg += elapsed;
	loadtimes->pages++;
    }

    if (benchmark)
	fflush(stderr);
}
Example #7
0
void
editcopy(int pagenum)
{
	fz_error *error;
	fz_obj *obj;
	fz_obj *ref;
	fz_obj *num;

	printf("copy %s page %d\n", srcname, pagenum);

	ref = srcpages->pref[pagenum - 1];
	obj = pdf_getpageobject(srcpages, pagenum - 1);

	fz_dictdels(obj, "Parent");
	/*
	fz_dictdels(obj, "B");
	fz_dictdels(obj, "PieceInfo");
	fz_dictdels(obj, "Metadata");
	fz_dictdels(obj, "Annots");
	fz_dictdels(obj, "Tabs");
	*/

	pdf_updateobject(src, fz_tonum(ref), fz_togen(ref), obj);

	error = fz_arraypush(editobjects, ref);
	if (error)
		die(error);

	error = fz_newint(&num, editmode);
	if (error)
		die(error);

	error = fz_arraypush(editmodelist, num);
	if (error)
		die(error);

	fz_dropobj(num);
}
Example #8
0
static void retainpages(int argc, char **argv)
{
	fz_error error;
	fz_obj *oldroot, *root, *pages, *kids, *countobj, *parent;

	/* Load the old page tree */
	error = pdf_loadpagetree(xref);
	if (error)
		die(fz_rethrow(error, "cannot load page tree"));

	/* Keep only pages/type entry to avoid references to unretained pages */
	oldroot = fz_dictgets(xref->trailer, "Root");
	pages = fz_dictgets(oldroot, "Pages");

	root = fz_newdict(2);
	fz_dictputs(root, "Type", fz_dictgets(oldroot, "Type"));
	fz_dictputs(root, "Pages", fz_dictgets(oldroot, "Pages"));

	pdf_updateobject(xref, fz_tonum(oldroot), fz_togen(oldroot), root);

	fz_dropobj(root);

	/* Create a new kids array with only the pages we want to keep */
	parent = fz_newindirect(fz_tonum(pages), fz_togen(pages), xref);
	kids = fz_newarray(1);

	/* Retain pages specified */
	while (argc - fz_optind)
	{
		int page, spage, epage;
		char *spec, *dash;
		char *pagelist = argv[fz_optind];

		spec = fz_strsep(&pagelist, ",");
		while (spec)
		{
			dash = strchr(spec, '-');

			if (dash == spec)
				spage = epage = pdf_getpagecount(xref);
			else
				spage = epage = atoi(spec);

			if (dash)
			{
				if (strlen(dash) > 1)
					epage = atoi(dash + 1);
				else
					epage = pdf_getpagecount(xref);
			}

			if (spage > epage)
				page = spage, spage = epage, epage = page;

			if (spage < 1)
				spage = 1;
			if (epage > pdf_getpagecount(xref))
				epage = pdf_getpagecount(xref);

			for (page = spage; page <= epage; page++)
			{
				fz_obj *pageobj = pdf_getpageobject(xref, page);
				fz_obj *pageref = pdf_getpageref(xref, page);

				fz_dictputs(pageobj, "Parent", parent);

				/* Store page object in new kids array */
				fz_arraypush(kids, pageref);
			}

			spec = fz_strsep(&pagelist, ",");
		}

		fz_optind++;
	}

	fz_dropobj(parent);

	/* Update page count and kids array */
	countobj = fz_newint(fz_arraylen(kids));
	fz_dictputs(pages, "Count", countobj);
	fz_dropobj(countobj);
	fz_dictputs(pages, "Kids", kids);
	fz_dropobj(kids);
}
Example #9
0
int
copyPdfFile(
    soPdfFile* inFile,
    soPdfFile* outFile
    )
{
    fz_error    *error;
    int         pageTreeNum, pageTreeGen;

    assert(inFile != NULL);
    assert(outFile != NULL);

    //
    // Process every page in the source file
    //
    {
        printf("\nProcessing input page : ");
        for (int pageNo = 0; pageNo < pdf_getpagecount(inFile->pageTree); pageNo++)
        {
            displayPageNumber(pageNo + 1, !pageNo);

            // Get the page object from the source
            fz_obj  *pageRef = inFile->pageTree->pref[pageNo];
            fz_obj  *pageObj = pdf_getpageobject(inFile->pageTree, pageNo);

            //
            // Process the page. Each page can be split into up-to 3 pages
            //
            fz_rect    bbRect[3];
            error = processPage(inFile, pageNo, bbRect, 3);
            if (error)
                return soPdfError(error);


            for (int ctr = 0; ctr < 3; ctr++)
            {
                // Check if this was a blank page
                if (fz_isemptyrect(bbRect[ctr]))
                    break;

                //
                // copy the source page dictionary entry. The way this is done is basically
                // by making a copy of the page dict object in the source file, and adding
                // the copy in the source file. Then the copied page dict object is 
                // referenced and added to the destination file.
                //
                // This convoluted procedure is done because the copy is done by pdf_transplant
                // function that accepts a source and destination. Whatever is referenced by
                // destination object is deep copied
                //
                

                // allocate an object id and generation id in source file
                //
                // There is a bug in mupdf where the object allocation returns
                // 0 oid and 0 gid when the input pdf file has iref stream
                // so to work around the issue, we wrap the pdf_allocojbect
                // in a for loop 10 times to get the number
                //
                int sNum, sGen, tries;

                for (tries = 0; tries < 10; tries++)
                {
                    error = pdf_allocobject(inFile->xref, &sNum, &sGen);
                    if (error)
                        return soPdfError(error);

                    // If sNum is non zero then the allocation was successful
                    if (sNum != 0)
                        break;  
                    pdf_updateobject(inFile->xref, sNum, sGen, pageObj);
                }

                // If we didn't succeed even after 10 tries then this file 
                // is not going to work.
                if (tries >= 10)
                    return soPdfError(fz_throw("cannot allocate object because of mupdf bug"));

                // make a deep copy of the original page dict
                fz_obj  *pageObj2;
                error = fz_deepcopydict(&pageObj2, pageObj);
                if (error)
                    return soPdfError(error);

                // update the source file with the duplicate page object
                pdf_updateobject(inFile->xref, sNum, sGen, pageObj2);

                fz_dropobj(pageObj2);

                // create an indirect reference to the page object
                fz_obj  *pageRef2;
                error = fz_newindirect(&pageRef2, sNum, sGen);
                if (error)
                    return soPdfError(error);

                // delete the parent dictionary entry
                // Do we need to delete any other dictionary entry 
                // like annot, tabs, metadata, etc
                fz_dictdels(pageObj2, "Parent");

                // Set the media box
                setPageMediaBox(inFile->xref, pageObj2, bbRect[ctr]);

                // Set the rotation based on input
                switch(p_mode)
                {
                    // no rotation if fit height
                case FitHeight:
                case Fit2xHeight:
                    break;

                    // rotate -90 deg if fit width
                case Fit2xWidth:
                case FitWidth:
                    setPageRotate(pageObj2, p_reverseLandscape ? 90 : -90);
                    break;

                case SmartFitHeight:
                case SmartFitWidth:
                default:
                    return soPdfError(fz_throw("Mode(%d) not yet implemented.", p_mode));
                    break;
                }


                // push the indirect reference to the destination list for copy by pdf_transplant
                error = fz_arraypush(outFile->editobjs, pageRef2);
                if (error)
                    return soPdfError(error);
            }
        }
    }

    // flush the objects into destination from source
    {
        fz_obj      *results;
        int         outPages;

        printf("\nCopying output page : ");
        error = pdf_transplant(outFile->xref, inFile->xref, &results, outFile->editobjs);
        if (error)
            return soPdfError(error);

        outPages = fz_arraylen(results);
        for (int ctr = 0; ctr < outPages; ctr++)
        {
            displayPageNumber(ctr + 1, !ctr);
            error = fz_arraypush(outFile->pagelist, fz_arrayget(results, 
                p_reverseLandscape ? outPages - 1 - ctr : ctr));
            if (error)
                return soPdfError(error);
        }

        fz_dropobj(results);
    }

    // flush page tree

    // Create page tree and add back-links
    {
        fz_obj  *pageTreeObj;
        fz_obj  *pageTreeRef;

        // allocate a new object in out file for pageTree object
        error = pdf_allocobject(outFile->xref, &pageTreeNum, &pageTreeGen);
        if (error)
            return soPdfError(error);

        // Create a page tree object
        error = fz_packobj(&pageTreeObj, "<</Type/Pages/Count %i/Kids %o>>",
            fz_arraylen(outFile->pagelist), outFile->pagelist);
        if (error)
            return soPdfError(error);

        // Update the xref entry with the pageTree object
        pdf_updateobject(outFile->xref, pageTreeNum, pageTreeGen, pageTreeObj);

        fz_dropobj(pageTreeObj);

        // Create a reference to the pageTree object
        error = fz_newindirect(&pageTreeRef, pageTreeNum, pageTreeGen);
        if (error)
            return soPdfError(error);

        //
        // For every page in the output file, update the parent entry
        //
        for (int ctr = 0; ctr < fz_arraylen(outFile->pagelist); ctr++)
        {
            fz_obj  *pageObj;

            int num = fz_tonum(fz_arrayget(outFile->pagelist, ctr));
            int gen = fz_togen(fz_arrayget(outFile->pagelist, ctr));

            // Get the page object from xreft
            error = pdf_loadobject(&pageObj, outFile->xref, num, gen);
            if (error)
                return soPdfError(error);

            // Update the parent entry in the page dictionary
            error = fz_dictputs(pageObj, "Parent", pageTreeRef);
            if (error)
                return soPdfError(error);

            // Update the entry with the updated page object
            pdf_updateobject(outFile->xref, num, gen, pageObj);

            fz_dropobj(pageObj);
        }
    }

    // Create catalog and root entries
    {
        fz_obj  *catObj, *infoObj;
        int     rootNum, rootGen;
        int     infoNum, infoGen;

        //
        // Copy the info catalog to the destination

        // alloc an object id and gen id in destination file
        error = pdf_allocobject(outFile->xref, &infoNum, &infoGen);
        if (error)
            return soPdfError(error);

        // make a deep copy of the original page dict
        error = fz_deepcopydict(&infoObj, inFile->xref->info);
        if (error)
            return soPdfError(error);

        // update the dest file with object
        pdf_updateobject(outFile->xref, infoNum, infoGen, infoObj);
        outFile->xref->info = infoObj;

        fz_dropobj(infoObj);

        //
        // root/catalog object creation
        error = pdf_allocobject(outFile->xref, &rootNum, &rootGen);
        if (error)
            return soPdfError(error);

        error = fz_packobj(&catObj, "<</Type/Catalog /Pages %r>>", pageTreeNum, pageTreeGen);
        if (error)
            return soPdfError(error);

        pdf_updateobject(outFile->xref, rootNum, rootGen, catObj);

        fz_dropobj(catObj);

        // Create trailer
        error = fz_packobj(&outFile->xref->trailer, "<</Root %r /Info %r>>", 
            rootNum, rootGen, infoNum, infoGen);
        if (error)
            return soPdfError(error);

    }

    // Update the info in the target file and save the xref
    printf("\nSaving.\n");
    error = setPageInfo(inFile, outFile);
    if (error)
        return soPdfError(error);

    error = pdf_savexref(outFile->xref, outFile->fileName, NULL);
    if (error)
        return soPdfError(error);

    if (g_errorCount != 0)
    {
        printf("\nFollowing issues encounted were ignored.\n\n");
        for (int ctr = g_errorCount - 1; ctr >= 0; ctr--)
            soPdfError(g_errorList[ctr]);
    }
    printf("\nSaved.\n");

    return 0;
}
Example #10
0
fz_error*
processPage(
    soPdfFile* inFile,
    int pageNo,
    fz_rect *bbRect,
    int rectCount
    )
{
    fz_error    *error;
    fz_obj      *pageRef;
    pdf_page    *pdfPage;
    fz_rect     contentBox;
    fz_rect     mediaBox;


    // Initialize 
    for (int ctr = 0; ctr < rectCount; ctr++)
        bbRect[ctr] = fz_emptyrect;

    // Get the page reference and load the page contents
    pageRef = pdf_getpageobject(inFile->pageTree, pageNo);
    error = pdf_loadpage(&pdfPage, inFile->xref, pageRef);
    if (error != NULL)
    {
        // Ideally pdf_loadpage should render all the pages
        // and this should never happen
        return processErrorPage(inFile, pageRef, pageNo, bbRect, error);
    }

    // Get the bounding box for the page
    mediaBox = pdfPage->mediabox;
    float mbHeight = mediaBox.y1 - mediaBox.y0;
    
    // calculate the bounding box for all the elements in the page
    contentBox = fz_boundnode(pdfPage->tree->root, fz_identity());
    float cbHeight = contentBox.y1 - contentBox.y0;

    // If there is nothing on the page we return nothing.
    // should we return an empty page instead ???
    if (fz_isemptyrect(contentBox))
        goto Cleanup;

    // if contentBox is bigger than mediaBox then there are some
    // elements that should not be display and hence we reset the
    // content box to media box
    if ((cbHeight > mbHeight) || ((contentBox.x1 - contentBox.x0) > (mediaBox.x1 - mediaBox.x0)))
    {
        // Calculate the new content box based on the content that is 
        // inside the the media box and recalculate cbHeight
        contentBox = getContainingRect(pdfPage->tree->root, mediaBox);
        cbHeight = contentBox.y1 - contentBox.y0;
    }


#ifdef _blahblah
    printf("-->Page %d\n", pageNo);
    bbdump(pdfPage->tree->root, 1);
#endif

    // The rotation takes place when we insert the page into destination
    // If only the mupdf renderer could give accurate values of the 
    // bounding box of all the elements in a page, the splitting would
    // be so much more easier without overlapping, cutting text, etc
    switch(p_mode)
    {
    case FitHeight:
    case FitWidth:
        bbRect[0] = contentBox;
        goto Cleanup;

    case Fit2xHeight:
    case Fit2xWidth:
        // Let the processing happen.
        break;

    case SmartFitHeight:
    case SmartFitWidth:
    default:
        return fz_throw("Mode(%d) not yet implemented.", p_mode);
        break;
    }

    // If the contentBox is 60% of mediaBox then do not split 
    if (((cbHeight / mbHeight) * 100) <= 55)
    {
        bbRect[0] = contentBox;
        goto Cleanup;
    }

    // Get the first split contents from top. The box we specify is 
    // top 55% (bottom + 45) of the contents
    bbRect[0] = contentBox;
    bbRect[0].y0 = bbRect[0].y0 + (float)(0.45 * cbHeight);
    bbRect[0] = getContainingRect(pdfPage->tree->root, bbRect[0]);

    // Check if the contents we got in first split is more than 40%
    // of the total contents
    float bbRect0Height = bbRect[0].y1 - bbRect[0].y0;
    if (((bbRect0Height / cbHeight) * 100) >= 40)
    {
        // The content is more than 40%. Put the rest of the 
        // content in the second split and exit
        bbRect[1] = contentBox;
        bbRect[1].y1 = bbRect[1].y1 - bbRect0Height;

        // Adjust the split box height by X points to make sure
        // we get everything and dont have annoying tail cuts
        bbRect[0].y0 -= 2;
        goto Cleanup;
    }

    // Since the contents we got in first split is less than 40%
    // of the total contents, split the content in half with overlap
    float overlap = (cbHeight * (float)(p_overlap / 100)) / 2;
    bbRect[0] = contentBox;
    bbRect[0].y0 = bbRect[0].y0 + (float)(0.5 * cbHeight) - overlap;
    bbRect[1] = contentBox;
    bbRect[1].y1 = bbRect[1].y1 - (float)(0.5 * cbHeight) + overlap;


Cleanup:

    // This function can overflow the stack when the pdf page
    // to be rendered is very complex. I had to increase the 
    // stack size reserved for exe using compiler option
    pdf_droppage(pdfPage);

    return error;
}
Example #11
0
void pdfmoz_open(pdfmoz_t *moz, char *filename)
{
    SCROLLINFO si;
    fz_error error;
    fz_obj *obj;
    fz_irect bbox;
    int rot;
    int i;

    strcpy(moz->error, "");

    error = fz_newrenderer(&moz->rast, pdf_devicergb, 0, 1024 * 512);
    if (error)
	pdfmoz_error(moz, error);

    /*
     * Open PDF and load xref table
     */

    moz->filename = filename;

    moz->xref = pdf_newxref();
    error = pdf_loadxref(moz->xref, filename);
    if (error)
    {
	error = pdf_repairxref(moz->xref, filename);
	if (error)
	    pdfmoz_error(moz, error);
    }

    /*
     * Handle encrypted PDF files
     */

    error = pdf_decryptxref(moz->xref);
    if (error)
	pdfmoz_error(moz, error);

    if (pdf_needspassword(moz->xref))
    {
	pdfmoz_warn(moz, "PDF file is encrypted and needs a password.");
    }

    moz->pagecount = pdf_getpagecount(moz->xref);
    moz->pages = fz_malloc(sizeof(page_t) * moz->pagecount);

    for (i = 0; i < moz->pagecount; i++)
    {
	fz_obj *pageobj;
	pageobj = pdf_getpageobject(moz->xref, i);
	moz->pages[i].obj = fz_keepobj(pageobj);
	moz->pages[i].page = nil;
	moz->pages[i].image = nil;

	obj = fz_dictgets(moz->pages[i].obj, "CropBox");
	if (!obj)
	    obj = fz_dictgets(moz->pages[i].obj, "MediaBox");
	bbox = fz_roundrect(pdf_torect(obj));
	moz->pages[i].w = bbox.x1 - bbox.x0;
	moz->pages[i].h = bbox.y1 - bbox.y0;

	rot = fz_toint(fz_dictgets(moz->pages[i].obj, "Rotate"));
	if ((rot / 90) % 2)
	{
	    int t = moz->pages[i].w;
	    moz->pages[i].w = moz->pages[i].h;
	    moz->pages[i].h = t;
	}

	moz->pages[i].px = 1 + PAD;
    }

    /*
     * Load meta information
     * TODO: move this into mupdf library
     */

    obj = fz_dictgets(moz->xref->trailer, "Root");
    moz->xref->root = fz_resolveindirect(obj);
    if (!moz->xref->root)
	pdfmoz_error(moz, fz_throw("syntaxerror: missing Root object"));
    if (moz->xref->root)
	fz_keepobj(moz->xref->root);

    obj = fz_dictgets(moz->xref->trailer, "Info");
    moz->xref->info = fz_resolveindirect(obj);
    if (moz->xref->info)
	fz_keepobj(moz->xref->info);

    moz->doctitle = filename;
    if (strrchr(moz->doctitle, '\\'))
	moz->doctitle = strrchr(moz->doctitle, '\\') + 1;
    if (strrchr(moz->doctitle, '/'))
	moz->doctitle = strrchr(moz->doctitle, '/') + 1;
    if (moz->xref->info)
    {
	obj = fz_dictgets(moz->xref->info, "Title");
	if (obj)
	    moz->doctitle = pdf_toutf8(obj);
    }

    /*
     * Start at first page
     */

    si.cbSize = sizeof(si);
    si.fMask = SIF_POS | SIF_RANGE; // XXX | SIF_PAGE;
    si.nPos = 0;
    si.nMin = 0;
    si.nMax = 1;
    si.nPage = 1;
    SetScrollInfo(moz->hwnd, SB_VERT, &si, TRUE);

    moz->scrollpage = 0;
    moz->scrollyofs = 0;

    InvalidateRect(moz->hwnd, NULL, FALSE);
}
Example #12
0
static void
gatherinfo(int show, int page)
{
	fz_error error;
	fz_obj *pageobj;
	fz_obj *rsrc;
	fz_obj *font;
	fz_obj *xobj;
	fz_obj *shade;
	fz_obj *pattern;

	pageobj = pdf_getpageobject(xref, page);

	if (!pageobj)
		die(fz_throw("cannot retrieve info from page %d", page));

	if (show & DIMENSIONS)
	{
		error = gatherdimensions(page, pageobj);
		if (error)
			die(fz_rethrow(error, "gathering dimensions at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
	}

	rsrc = fz_dictgets(pageobj, "Resources");

	if (show & FONTS)
	{
		font = fz_dictgets(rsrc, "Font");
		if (font)
		{
			error = gatherfonts(page, pageobj, font);
			if (error)
				die(fz_rethrow(error, "gathering fonts at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
		}
	}

	if (show & IMAGES || show & XOBJS)
	{
		xobj = fz_dictgets(rsrc, "XObject");
		if (xobj)
		{
			error = gatherimages(page, pageobj, xobj);
			if (error)
				die(fz_rethrow(error, "gathering images at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
			error = gatherforms(page, pageobj, xobj);
			if (error)
				die(fz_rethrow(error, "gathering forms at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
			error = gatherpsobjs(page, pageobj, xobj);
			if (error)
				die(fz_rethrow(error, "gathering postscript objects at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
		}
	}

	if (show & SHADINGS)
	{
		shade = fz_dictgets(rsrc, "Shading");
		if (shade)
		{
			error = gathershadings(page, pageobj, shade);
			if (error)
				die(fz_rethrow(error, "gathering shadings at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
		}
	}

	if (show & PATTERNS)
	{
		pattern = fz_dictgets(rsrc, "Pattern");
		if (pattern)
		{
			error = gatherpatterns(page, pageobj, pattern);
			if (error)
				die(fz_rethrow(error, "gathering shadings at page %d (%d %d R)", page, fz_tonum(pageobj), fz_togen(pageobj)));
		}
	}
}
Example #13
0
void pdfapp_showpage(pdfapp_t *app, int loadpage, int drawpage)
{
	char buf[256];
	fz_error *error;
	fz_matrix ctm;
	fz_rect bbox;
	fz_obj *obj;

	if (loadpage)
	{
		wincursor(app, WAIT);

		if (app->page)
			pdf_droppage(app->page);
		app->page = nil;

		obj = pdf_getpageobject(app->pages, app->pageno - 1);

		error = pdf_loadpage(&app->page, app->xref, obj);
		if (error)
			pdfapp_error(app, error);

		sprintf(buf, "%s - %d/%d", app->doctitle,
				app->pageno, pdf_getpagecount(app->pages));
		wintitle(app, buf);
	}

	if (drawpage)
	{
		wincursor(app, WAIT);

		if (app->image)
			fz_droppixmap(app->image);
		app->image = nil;

		ctm = pdfapp_viewctm(app);
		bbox = fz_transformaabb(ctm, app->page->mediabox);

		error = fz_rendertree(&app->image, app->rast, app->page->tree,
				ctm, fz_roundrect(bbox), 1);
		if (error)
			pdfapp_error(app, error);

		winconvert(app, app->image);
	}

	pdfapp_panview(app, app->panx, app->pany);

	if (app->shrinkwrap)
	{
		int w = app->image->w;
		int h = app->image->h;
		if (app->winw == w)
			app->panx = 0;
		if (app->winh == h)
			app->pany = 0;
		if (w > app->scrw * 90 / 100)
			w = app->scrw * 90 / 100;
		if (h > app->scrh * 90 / 100)
			h = app->scrh * 90 / 100;
		if (w != app->winw || h != app->winh)
			winresize(app, w, h);
	}

	winrepaint(app);

	wincursor(app, ARROW);
}
Example #14
0
static void pdfapp_showpage(pdfapp_t *app, int loadpage, int drawpage)
{
    char buf[256];
    fz_error error;
    fz_device *idev, *tdev, *mdev;
    fz_displaylist *list;
    fz_matrix ctm;
    fz_bbox bbox;
    fz_obj *obj;

    if (loadpage)
    {
        wincursor(app, WAIT);

        if (app->page)
            pdf_droppage(app->page);
        app->page = nil;
        //code change by kakai
        kno_clearselect(app);
        //code change by kakai
        pdf_flushxref(app->xref, 0);

        obj = pdf_getpageobject(app->xref, app->pageno);
        error = pdf_loadpage(&app->page, app->xref, obj);
        if (error)
            pdfapp_error(app, error);

        sprintf(buf, "%s - %d/%d", app->doctitle,
                app->pageno, app->pagecount);
        wintitle(app, buf);
    }

    if (drawpage)
    {
        wincursor(app, WAIT);

        ctm = pdfapp_viewctm(app);
        bbox = fz_roundrect(fz_transformrect(ctm, app->page->mediabox));

        list = fz_newdisplaylist();

        mdev = fz_newlistdevice(list);
        error = pdf_runcontentstream(mdev, fz_identity(), app->xref, app->page->resources, app->page->contents);
        if (error)
            pdfapp_error(app, error);
        fz_freedevice(mdev);

        if (app->image)
            fz_droppixmap(app->image);
        app->image = fz_newpixmapwithrect(pdf_devicergb, bbox);
        fz_clearpixmap(app->image, 0xFF);
        idev = fz_newdrawdevice(app->cache, app->image);
        fz_executedisplaylist(list, idev, ctm);
        fz_freedevice(idev);

        if (app->text)
            fz_freetextspan(app->text);
        app->text = fz_newtextspan();
        tdev = fz_newtextdevice(app->text);
        fz_executedisplaylist(list, tdev, ctm);
        fz_freedevice(tdev);

        fz_freedisplaylist(list);

        //code change by kakai
        kno_allocselection(app);
        kno_applyselect(app);
        //code change by kakai

        winconvert(app, app->image);
    }

    pdfapp_panview(app, app->panx, app->pany);

    if (app->shrinkwrap)
    {
        int w = app->image->w;
        int h = app->image->h;
        if (app->winw == w)
            app->panx = 0;
        if (app->winh == h)
            app->pany = 0;
        if (w > app->scrw * 90 / 100)
            w = app->scrw * 90 / 100;
        if (h > app->scrh * 90 / 100)
            h = app->scrh * 90 / 100;
        if (w != app->winw || h != app->winh)
            winresize(app, w, h);
    }

    winrepaint(app);

    wincursor(app, ARROW);
}