Free Support Forum - aspose.com

PageSetup PaperSize setting with HtmlFixedSaveOptions using java

Hi,
I am converting a doc file to HTML using HtmlFixedSaveOptions then printing the HTML to PDF along with few other data on HTML.
Few pages of doc file is wider than normal A4 paper size. i want to adjust those pages in A4 size without changing the layout of the orignal page. need to shrink those wider pages into A4 page.
trying below code, but no success.
Document doc = getDocument(xxxx); // getting document
DocumentBuilder builder = new DocumentBuilder(doc);
builder.getPageSetup().setPaperSize(PaperSize.A4);
HtmlFixedSaveOptions saveOptions = new HtmlFixedSaveOptions();
saveOptions.setExportEmbeddedImages(true);
saveOptions.setExportEmbeddedCss(true);
saveOptions.setExportEmbeddedFonts(true);
saveOptions.setExportEmbeddedSvg(true);
saveOptions.setPrettyFormat(true);
saveOptions.setCssClassNamesPrefix("");
saveOptions.setPageHorizontalAlignment(0);

    doc.save(outputStream, saveOptions);

Please suggest , is there any way to achieve this.
Thank you :slight_smile:

@pkr89singh

Please note that Aspose.Words mimics the behavior of MS Word. If you perform the same scenario using MS Word, you will get the same output.

Could you please ZIP and attach your input and expected output PDF here for our reference? We will then provide you more information about your query.

Is there any way to convert document table as image instead of SVG by using htmlFixedSaveOption.
I don’t want SVG components in html dom.
Please suggest the approch.

@pkr89singh

Please note that table is not converted to image when document is saved to HtmlFixed. However, you can convert table to image using Aspose.Words’ API. After conversion, please move the cursor to the table, insert the image and remove table.

Following code example shows how to convert a table to image. Hope this helps you.

Document doc = new Document("D:\\temp\\in.docx");
Table tab = doc.getFirstSection().getBody().getTables().get(0);
RenderNode(tab, "D:\\temp\\out.png", new ImageSaveOptions(SaveFormat.PNG));

public static void RenderNode(Node node, String filePath, ImageSaveOptions imageOptions) throws Exception
{
    // Run some argument checks.
    if (node == null)
        throw new IllegalArgumentException("Node cannot be null");

    // If no image options are supplied, create default options.
    if (imageOptions == null)
        imageOptions = new ImageSaveOptions(FileFormatUtil.extensionToSaveFormat((filePath.split("\\.")[filePath.split("\\.").length - 1])));

    // Store the paper color to be used on the final image and change to transparent.
    // This will cause any content around the rendered node to be removed later on.
    Color savePaperColor = imageOptions.getPaperColor();
    //imageOptions.PaperColor = Color.Transparent;
    imageOptions.setPaperColor(new Color(0, 0, 0, 0));
    // There a bug which affects the cache of a cloned node. To avoid this we instead clone the entire document including all nodes,
    // find the matching node in the cloned document and render that instead.
    Document doc = (Document)node.getDocument().deepClone(true);
    node = doc.getChild(NodeType.ANY, node.getDocument().getChildNodes(NodeType.ANY, true).indexOf(node), true);

    // Create a temporary shape to store the target node in. This shape will be rendered to retrieve
    // the rendered content of the node.
    Shape shape = new Shape(doc, ShapeType.TEXT_BOX);
    Section parentSection = (Section)node.getAncestor(NodeType.SECTION);

    // Assume that the node cannot be larger than the page in size.
    shape.setWidth(parentSection.getPageSetup().getPageWidth());
    shape.setHeight(parentSection.getPageSetup().getPageHeight());
    shape.setFillColor(new Color(0, 0, 0, 0)); // We must make the shape and paper color transparent.

    // Don't draw a surrounding line on the shape.
    shape.setStroked(false);

    // Move up through the DOM until we find node which is suitable to insert into a Shape (a node with a parent can contain paragraph, tables the same as a shape).
    // Each parent node is cloned on the way up so even a descendant node passed to this method can be rendered.
    // Since we are working with the actual nodes of the document we need to clone the target node into the temporary shape.
    Node currentNode = node;
    while (!(currentNode.getParentNode() instanceof InlineStory
            || currentNode.getParentNode() instanceof Story
            || currentNode.getParentNode() instanceof ShapeBase))
    {
        CompositeNode parent = (CompositeNode)currentNode.getParentNode().deepClone(false);
        currentNode = currentNode.getParentNode();
        parent.appendChild(node.deepClone(true));
        node = parent; // Store this new node to be inserted into the shape.
    }

    // We must add the shape to the document tree to have it rendered.
    shape.appendChild(node.deepClone(true));
    parentSection.getBody().getFirstParagraph().appendChild(shape);

    // Render the shape to stream so we can take advantage of the effects of the ImageSaveOptions class.
    // Retrieve the rendered image and remove the shape from the document.
    ByteArrayOutputStream stream = new ByteArrayOutputStream();
    shape.getShapeRenderer().save(stream, imageOptions);
    shape.remove();

    // Load the image into a new bitmap.
    BufferedImage renderedImage = ImageIO.read(new ByteArrayInputStream(stream.toByteArray()));

    // Extract the actual content of the image by cropping transparent space around
    // the rendered shape.
    Rectangle cropRectangle = FindBoundingBoxAroundNode(renderedImage);

    BufferedImage croppedImage = new BufferedImage(cropRectangle.width, cropRectangle.height, BufferedImage.TYPE_INT_RGB);

    // Create the final image with the proper background color.
    Graphics2D g = croppedImage.createGraphics();
    g.setBackground(savePaperColor);
    g.clearRect(0, 0, croppedImage.getWidth(), croppedImage.getHeight());
    g.drawImage(renderedImage,
            0, 0, croppedImage.getWidth(), croppedImage.getHeight(),
            cropRectangle.x, cropRectangle.y, cropRectangle.x + cropRectangle.width, cropRectangle.y + cropRectangle.height,
            null);

    ImageIO.write(croppedImage, "png", new File(filePath));
}

public static Rectangle FindBoundingBoxAroundNode(BufferedImage originalBitmap)
{
    Point min = new Point(Integer.MAX_VALUE, Integer.MAX_VALUE);
    Point max = new Point(Integer.MIN_VALUE, Integer.MIN_VALUE);

    for (int x = 0; x < originalBitmap.getWidth(); ++x)
    {
        for (int y = 0; y < originalBitmap.getHeight(); ++y)
        {
            // For each pixel that is not transparent calculate the bounding box around it.
            if (originalBitmap.getRGB(x, y) != 0)
            {
                min.x = Math.min(x, min.x);
                min.y = Math.min(y, min.y);
                max.x = Math.max(x, max.x);
                max.y = Math.max(y, max.y);
            }
        }
    }

    // Add one pixel to the width and height to avoid clipping.
    return new Rectangle(min.x, min.y, (max.x - min.x) + 1, (max.y - min.y) + 1);
}

Hope, this helps.