Am 10.11.2016 um 10:46 schrieb clifford:
This is my problem:-

PDPage page = new PDPage();
PDColorSpace cs = PDColorSpace.create(COSName.PATTERN,page.getResources());
//or even dose not matter which one you choose
//PDColorSpace cs = new PDPattern(null, PDDeviceRGB.INSTANCE);
page.getResources().put(COSName.getPDFName("R9"), cs);

If you didn't set any resources for your PDPage object, then it will indeed be null.

add this:

        page.setResources(new PDResources());

COSName cn = page.getResources().add(cs);


The above code is just to prove there is a bug, and I do not do this.

from the above code:-

cn should equal "R9" is dose not it equals "cs2". And there is another resource item added.

I get R9 with this code:

public class NewClass
{
    public static void main(String[] args) throws IOException
    {

        PDPage page = new PDPage();
        page.setResources(new PDResources());
PDColorSpace cs = PDColorSpace.create(COSName.PATTERN, page.getResources());
        page.getResources().put(COSName.getPDFName("R9"), cs);
        COSName cn = page.getResources().add(cs);
        System.out.println(cn);
    }
}


so please try that code, and with the latest PDFBox version from the snapshot site.

But you should really use the example code I created. Run it and you'll see that you'll get a PDF with patterns.

The name doesn't matter. What matters is whether it does what you need or not.


when using class PDPageContentStream and calling method public void setNonStrokingColor(PDColor color) throws IOException

with PDColor having it colour space set too cs from the above code inside setNonStrokingColor it calls getName against the colour space for PDColor and inside getName it dose the equivalent of the last line of code from above

so the code it writes to the PDF file is

q
  /cs2 cs
  0.6 0.89804 0.6 /Patten1 scn
  402.00864 419.82635 68.9668 16.31381 re
  f
Q

which is wrong as it should be
q
  /R9 cs
  0.6 0.89804 0.6 /Patten1 scn
  402.00864 419.82635 68.9668 16.31381 re
  f
Q

inside class PDResources method public COSName add(PDColorSpace colorSpace) calls private COSName add(COSName kind, String prefix, COSObjectable object) and in this method there is a line if (dict != null && dict.containsValue(object.getCOSObject()))

the object is the original cs (PDColorSpace from above code) and it dose is not find a result for getCOSObject() which is the COSArray with the COSName.PATTERN in it.

that all looks ok to me... the "put" inserts it into the dictionary with a specific name, and the "add" adds it again without specifying a key, and finds that it is already there.

Here's the latest and ultimate example, which I will commit:


import java.io.IOException;
import java.io.OutputStream;
import org.apache.pdfbox.cos.COSName;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.PDResources;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
import org.apache.pdfbox.pdmodel.graphics.color.PDColor;
import org.apache.pdfbox.pdmodel.graphics.color.PDColorSpace;
import org.apache.pdfbox.pdmodel.graphics.color.PDDeviceRGB;
import org.apache.pdfbox.pdmodel.graphics.color.PDPattern;
import org.apache.pdfbox.pdmodel.graphics.pattern.PDTilingPattern;
import org.apache.pdfbox.util.Charsets;

/**
* This is an example of how to create a page that uses patterns to paint areas.
 *
 * @author Tilman Hausherr
 */
public class CreatePatternsPDF
{
    public static void main(String[] args) throws IOException
    {
        PDDocument doc = new PDDocument();
        PDPage page = new PDPage();
        doc.addPage(page);
        page.setResources(new PDResources());

        PDPageContentStream pcs = new PDPageContentStream(doc, page);

// Colored pattern, i.e. the pattern content stream will set its own color(s) PDColorSpace patternCS1 = new PDPattern(null, PDDeviceRGB.INSTANCE);

        // Table 75 spec
        PDTilingPattern tilingPattern1 = new PDTilingPattern();
        tilingPattern1.setBBox(new PDRectangle(0, 0, 10, 10));
        tilingPattern1.setPaintType(PDTilingPattern.PAINT_COLORED);
tilingPattern1.setTilingType(PDTilingPattern.TILING_CONSTANT_SPACING);
        tilingPattern1.setXStep(10);
        tilingPattern1.setYStep(10);

        COSName patternName1 = page.getResources().add(tilingPattern1);
        //TODO
        // there's no way to create something like a PDPageContentStream,
        // so we'll do it the hard way
OutputStream os1 = tilingPattern1.getContentStream().createOutputStream(); // Set color, draw diagonal line + 2 more diagonals so that corners look good os1.write("1 0 0 RG 0 0 m 10 10 l -1 9 m 1 11 l 9 -1 m 11 1 l s".getBytes(Charsets.US_ASCII));
        os1.close();

        PDColor patternColor1 = new PDColor(patternName1, patternCS1);

        pcs.addRect(50, 500, 200, 200);
        pcs.setNonStrokingColor(patternColor1);
        pcs.fill();

        // Uncolored pattern - the color is passed later
        PDTilingPattern tilingPattern2 = new PDTilingPattern();
        tilingPattern2.setBBox(new PDRectangle(0, 0, 10, 10));
tilingPattern2.setPaintType(PDTilingPattern.PAINT_UNCOLORED);
tilingPattern2.setTilingType(PDTilingPattern.TILING_NO_DISTORTION);
        tilingPattern2.setXStep(10);
        tilingPattern2.setYStep(10);

        COSName patternName2 = page.getResources().add(tilingPattern2);
OutputStream os2 = tilingPattern2.getContentStream().createOutputStream();
        // draw a cross
os2.write("0 5 m 10 5 l 5 0 m 5 10 l s".getBytes(Charsets.US_ASCII));
        os2.close();

        // Uncolored pattern colorspace needs to know the colorspace
        // for the color values that will be passed when painting the fill
PDColorSpace patternCS2 = new PDPattern(null, PDDeviceRGB.INSTANCE);
        PDColor patternColor2green = new PDColor(
                new float[]{0,1,0},
                patternName2,
                patternCS2);

        pcs.addRect(300, 500, 100, 100);
        pcs.setNonStrokingColor(patternColor2green);
        pcs.fill();

// same pattern again but with different color + different pattern start position
        PDColor patternColor2blue = new PDColor(
                new float[]{0,0,1},
                patternName2,
                patternCS2);
        pcs.addRect(455, 505, 100, 100);
        pcs.setNonStrokingColor(patternColor2blue);
        pcs.fill();

        pcs.close();
        doc.save("patterns.pdf");
        doc.close();
    }
}


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to