Hello,
I finally raped your code to achieve my end!
Into PDTrueTypeFont.java I have force the mapping of width to use the
choosen encoding:
Encoding e =
EncodingManager.INSTANCE.getEncoding(COSName.WIN_ANSI_ENCODING);
for( int i=0; i<widthValues.length ; i++ )
{
if(glyphToCCode[i]-firstChar < widths.size() &&
glyphToCCode[i]-firstChar >= 0
&& widths.get( glyphToCCode[i]-firstChar) == zero )
{
try {
widths.set( e.getCode(e.getNameFromCharacter(
(new StringBuilder()).appendCodePoint(
glyphToCCode[i]).toString().toCharArray()[0])),
widthValues[i]*scaling );
} catch (IOException x) {
widths.set( glyphToCCode[i]-firstChar,
widthValues[i]*scaling );
}
}
}
Then widths seems correct now.
Just notice that firstChar is hard coded to 0 in the original code, so I
think that you can remove it from.
Regards,
Kévin
2012/4/11 Kévin Sailly <[email protected]>
> Hello,
>
> I have found the reason (maybe).
> Using the code map to characters name here:
>
> Map<String, Integer> m = e.getNameToCodeMap();
> for (int i = 0; i < mechars.length; i++) {
> char c = mechars[i];
> String name = e.getNameFromCharacter(c);
> int code = e.getCode(name);
> codesstring.appendCodePoint(
> code);
> }
>
> Makes the method "getFontWidth(int charCode)" mapping to width of another
> character.
>
> What is the best method to correct this? map the widths with encoded
> codes, or changing method the getFontWidth(char charCode) using the correct
> char, not the code?
>
> Thanks,
> Kevin
>
>
> 2012/4/10 Kévin Sailly <[email protected]>
>
>> Hello,
>>
>> I have got some problems to render the word "Cœur" (that means "heart" in
>> French) because of the "œ" character, the glyph width is not the good value.
>>
>> I am using FreeSerif truetype font downloadable from here :
>> http://packages.debian.org/squeeze/all/ttf-freefont
>> Generated PDFs can be accesed here:
>> http://www.4shared.com/office/mOkLEPGd/out2.html
>> http://www.4shared.com/office/kngqxy7X/out1.html
>>
>> I am using version 1.6 of PDFBOX
>>
>>
>> First I try :
>> String message = "Cœur";
>> PDDocument doc = null;
>> try
>> {
>> doc = new PDDocument();
>> PDPage page = new PDPage();
>> doc.addPage(page);
>> PDTrueTypeFont font = PDTrueTypeFont.loadTTF(doc,
>> "/usr/share/fonts/truetype/
>> freefont/FreeSerif.ttf");
>>
>> Encoding e = EncodingManager.INSTANCE.getEncoding(
>> COSName.WIN_ANSI_ENCODING);
>> PDPageContentStream contentStream = new
>> PDPageContentStream(doc,
>> page);
>> contentStream.beginText();
>> contentStream.setFont(font, 24);
>> contentStream.moveTextPositionByAmount(100, 700);
>> contentStream.drawString(message);
>> contentStream.endText();
>> contentStream.close();
>> doc.save("out1.pdf");
>> } catch (IOException e) {
>> e.printStackTrace();
>> } catch (COSVisitorException e) {
>> e.printStackTrace();
>> }
>> finally
>> {
>> if (doc != null)
>> {
>> try {
>> doc.close();
>> } catch (IOException e) {
>> e.printStackTrace();
>> }
>> }
>> }
>>
>> But the result out1.pdf facin the bug PDFBOX-1242 (
>> https://issues.apache.org/jira/browse/PDFBOX-1242)
>>
>> So I am using code points to render the pdf:
>>
>> String message = "Cœur";
>> PDDocument doc = null;
>> try
>> {
>> doc = new PDDocument();
>> PDPage page = new PDPage();
>> doc.addPage(page);
>> PDTrueTypeFont font = PDTrueTypeFont.loadTTF(doc,
>> "/usr/share/fonts/truetype/freefont/FreeSerif.ttf");
>>
>> Encoding e = EncodingManager.INSTANCE.getEncoding(
>> COSName.WIN_ANSI_ENCODING);
>> PDPageContentStream contentStream = new
>> PDPageContentStream(doc,
>> page);
>> contentStream.beginText();
>> contentStream.setFont(font, 24);
>> contentStream.moveTextPositionByAmount(100, 700);
>> char[] mechars = message.toCharArray();
>> StringBuilder codesstring = new StringBuilder();
>> Map<String, Integer> m = e.getNameToCodeMap();
>> for (int i = 0; i < mechars.length; i++) {
>> char c = mechars[i];
>> String name = e.getNameFromCharacter(c);
>> int code = e.getCode(name);
>> codesstring.appendCodePoint(code);
>> }
>> contentStream.drawString(codesstring.toString());
>> contentStream.endText();
>> contentStream.close();
>> doc.save("out2.pdf");
>> } catch (IOException e) {
>> e.printStackTrace();
>> } catch (COSVisitorException e) {
>> e.printStackTrace();
>> }
>> finally
>> {
>> if (doc != null)
>> {
>> try {
>> doc.close();
>> } catch (IOException e) {
>> e.printStackTrace();
>> }
>> }
>> }
>>
>> The glyph "œ" is correct now but the next letter partially recovert it
>> (see out2.pdf).
>>
>> The character "EM DASH" have the same problem.
>>
>> I looked at the PDTrueTypeFont class and the width looks correctly parsed
>> by PDFBOX:
>>
>> 339 : œ : 709 : 709.0
>>
>> (inserting this in the class:
>> for( int i=0; i<widthValues.length ; i++ )
>> {
>> if(glyphToCCode[i]-firstChar < widths.size() &&
>> glyphToCCode[i]-firstChar >= 0
>> && widths.get( glyphToCCode[i]-firstChar) == zero
>> )
>> {
>> System.out.println(glyphToCCode[i] + " : " +(new
>> StringBuilder()).appendCodePoint(glyphToCCode[i]) + " : " + widthValues[i]
>> + " : " + widthValues[i]*scaling);
>> widths.set( glyphToCCode[i]-firstChar,
>> widthValues[i]*scaling );
>> }
>> }
>> )
>>
>> I also notice that the width used to render the glyph is the "zero" value
>> :
>> float zero = 250;
>> defined in the method loadDescriptorDictionary of class PDTrueTypeFont.
>>
>> I have no more clue to investigate as the glyph have is width correctly
>> defined, so help will be greatly appreciated!
>>
>> Regards,
>> Kévin
>>
>>
>