Author: ssteiner
Date: Tue Jan 17 15:00:19 2017
New Revision: 1779202

URL: http://svn.apache.org/viewvc?rev=1779202&view=rev
Log:
FOP-2680: OTF font needs format 3 FDSelect due to offset size

Modified:
    
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/cff/CFFDataReader.java
    
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java
    
xmlgraphics/fop/trunk/fop-core/src/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java

Modified: 
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/cff/CFFDataReader.java
URL: 
http://svn.apache.org/viewvc/xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/cff/CFFDataReader.java?rev=1779202&r1=1779201&r2=1779202&view=diff
==============================================================================
--- 
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/cff/CFFDataReader.java
 (original)
+++ 
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/cff/CFFDataReader.java
 Tue Jan 17 15:00:19 2017
@@ -814,7 +814,7 @@ public class CFFDataReader {
         }
     }
 
-    public class FDSelect {
+    public abstract class FDSelect {
         private int format;
 
         public void setFormat(int format) {

Modified: 
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java
URL: 
http://svn.apache.org/viewvc/xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java?rev=1779202&r1=1779201&r2=1779202&view=diff
==============================================================================
--- 
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java
 (original)
+++ 
xmlgraphics/fop/trunk/fop-core/src/main/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java
 Tue Jan 17 15:00:19 2017
@@ -415,11 +415,10 @@ public class OTFSubSetFile extends OTFFi
                 int gid = subsetGlyph.getKey();
                 int group = subsetGroups.get(gid);
                 localIndexSubr = 
cffReader.getFDFonts().get(group).getLocalSubrData();
-                localUniques = 
foundLocalUniques.get(uniqueGroups.indexOf(subsetGroups.get(gid)));
+                localUniques = 
foundLocalUniques.get(uniqueGroups.indexOf(group));
                 type2Parser = new Type2Parser();
 
-                FDIndexReference newFDReference = new FDIndexReference(
-                        uniqueGroups.indexOf(subsetGroups.get(gid)), 
subsetGroups.get(gid));
+                FDIndexReference newFDReference = new 
FDIndexReference(uniqueGroups.indexOf(group), group);
                 subsetFDSelect.put(subsetGlyph.getValue(), newFDReference);
                 byte[] data = charStringsIndex.getValue(gid);
                 preScanForSubsetIndexSize(data);
@@ -460,10 +459,40 @@ public class OTFSubSetFile extends OTFFi
     }
 
     protected void writeFDSelect() {
-        writeByte(0); //Format
+        if 
(cffReader.getTopDictEntries().get("CharStrings").getOperandLength() == 2) {
+            Map<Integer, Integer> indexs = getFormat3Index();
+            writeByte(3); //Format
+            writeCard16(indexs.size());
+            int count = 0;
+            for (Entry<Integer, Integer> x : indexs.entrySet()) {
+                writeCard16(count);
+                writeByte(x.getKey());
+                count += x.getValue();
+            }
+            writeCard16(subsetFDSelect.size());
+        } else {
+            writeByte(0); //Format
+            for (FDIndexReference e : subsetFDSelect.values()) {
+                writeByte(e.getNewFDIndex());
+            }
+        }
+    }
+
+    private Map<Integer, Integer> getFormat3Index() {
+        Map<Integer, Integer> indexs = new LinkedHashMap<Integer, Integer>();
+        int last = -1;
+        int count = 0;
         for (FDIndexReference e : subsetFDSelect.values()) {
-            writeByte(e.getNewFDIndex());
+            int i = e.getNewFDIndex();
+            count++;
+            if (i != last) {
+                indexs.put(i, count);
+                count = 1;
+            }
+            last = i;
         }
+        indexs.put(last, count);
+        return indexs;
     }
 
     protected List<Integer> getUsedFDFonts() {
@@ -534,7 +563,7 @@ public class OTFSubSetFile extends OTFFi
         return offset;
     }
 
-    private class FDIndexReference {
+    private static class FDIndexReference {
         private int newFDIndex;
         private int oldFDIndex;
 

Modified: 
xmlgraphics/fop/trunk/fop-core/src/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java
URL: 
http://svn.apache.org/viewvc/xmlgraphics/fop/trunk/fop-core/src/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java?rev=1779202&r1=1779201&r2=1779202&view=diff
==============================================================================
--- 
xmlgraphics/fop/trunk/fop-core/src/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java
 (original)
+++ 
xmlgraphics/fop/trunk/fop-core/src/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java
 Tue Jan 17 15:00:19 2017
@@ -21,15 +21,20 @@ package org.apache.fop.fonts.truetype;
 
 import java.io.IOException;
 import java.util.ArrayList;
+import java.util.Collections;
 import java.util.HashMap;
+import java.util.LinkedHashMap;
 import java.util.List;
 import java.util.Map;
 
+import org.junit.Assert;
 import org.junit.Before;
 import org.junit.Test;
 
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
 
 import org.apache.fontbox.cff.CFFFont;
 
@@ -40,9 +45,8 @@ import org.apache.fop.fonts.truetype.OTF
 
 public class OTFSubSetFileTestCase extends OTFFileTestCase {
 
-    CFFDataReader cffReaderSourceSans;
+    private CFFDataReader cffReaderSourceSans;
     private OTFSubSetFile sourceSansSubset;
-    private byte[] sourceSansData;
 
     /**
      * Initialises the test by creating the font subset. A CFFDataReader is
@@ -61,7 +65,7 @@ public class OTFSubSetFileTestCase exten
         sourceSansSubset = new OTFSubSetFile();
         String sourceSansHeader = OFFontLoader.readHeader(sourceSansReader);
         sourceSansSubset.readFont(sourceSansReader, "SourceSansProBold", 
sourceSansHeader, glyphs);
-        sourceSansData = sourceSansSubset.getFontSubset();
+        byte[] sourceSansData = sourceSansSubset.getFontSubset();
         cffReaderSourceSans = new CFFDataReader(sourceSansData);
     }
 
@@ -428,4 +432,40 @@ public class OTFSubSetFileTestCase exten
                 cffReaderSourceSans.getTopDictIndex().getData());
         assertEquals(10, topDictEntries.size());
     }
+
+    @Test
+    public void testFDSelect() throws IOException {
+        Assert.assertEquals(getSubset(1).length, 39);
+        Assert.assertEquals(getSubset(2).length, 46);
+    }
+
+    private byte[] getSubset(final int opLen) throws IOException {
+        FontFileReader reader = sourceSansReader;
+        String header = OFFontLoader.readHeader(reader);
+
+        OTFSubSetFile otfSubSetFile = new OTFSubSetFile() {
+            protected void createCFF() throws IOException {
+                cffReader = mock(CFFDataReader.class);
+                when(cffReader.getHeader()).thenReturn(new byte[0]);
+                when(cffReader.getTopDictIndex()).thenReturn(new 
CFFDataReader().new CFFIndexData() {
+                    public byte[] getByteData() throws IOException {
+                        return new byte[3];
+                    }
+                });
+
+                LinkedHashMap<String, DICTEntry> map = new 
LinkedHashMap<String, DICTEntry>();
+                DICTEntry dict = new DICTEntry();
+                dict.setOperands(Collections.<Number>singletonList(1));
+                map.put("charset", dict);
+                map.put("CharStrings", dict);
+                when((cffReader.getTopDictEntries())).thenReturn(map);
+                when(cffReader.getFDSelect()).thenReturn(new 
CFFDataReader().new Format3FDSelect());
+                
cffReader.getTopDictEntries().get("CharStrings").setOperandLength(opLen);
+                super.createCFF();
+            }
+        };
+
+        otfSubSetFile.readFont(reader, "StandardOpenType", header, new 
HashMap<Integer, Integer>());
+        return otfSubSetFile.getFontSubset();
+    }
 }



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

Reply via email to