From bbe2c95f0a39d7dff0a4011bde439507897fa8ef Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jindra=20Pet=C5=99=C3=ADk?= Date: Mon, 18 Jan 2016 10:48:16 +0100 Subject: [PATCH] Corrected read only tags handling in GUI (allow edit only after pressing Edit button outside of Editor mode) Font wideOffsets,wideCodes fixed in DefineFont2/3 --- .../decompiler/flash/SWFOutputStream.java | 10 ++-- .../decompiler/flash/tags/DefineFont2Tag.java | 44 ++++++++++++++++ .../decompiler/flash/tags/DefineFont3Tag.java | 52 ++++++++++++++++--- .../jpexs/decompiler/flash/gui/FontPanel.java | 6 ++- .../jpexs/decompiler/flash/gui/TextPanel.java | 4 +- 5 files changed, 100 insertions(+), 16 deletions(-) diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/SWFOutputStream.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/SWFOutputStream.java index 5f55aa8d9..8c7931bee 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/SWFOutputStream.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/SWFOutputStream.java @@ -161,7 +161,7 @@ public class SWFOutputStream extends OutputStream { */ public void writeUI8(int value) throws IOException { if (value > 0xff) { - throw new Error("Value is too large for UI8: " + value); + throw new IllegalArgumentException("Value is too large for UI8: " + value); } write(value); @@ -218,7 +218,7 @@ public class SWFOutputStream extends OutputStream { */ public void writeUI32(long value) throws IOException { if (value > 0xffffffffL) { - throw new Error("Value is too large for UI32: " + value); + throw new IllegalArgumentException("Value is too large for UI32: " + value); } write((int) (value & 0xff)); @@ -235,7 +235,7 @@ public class SWFOutputStream extends OutputStream { */ public void writeUI16(int value) throws IOException { if (value > 0xffff) { - throw new Error("Value is too large for UI16: " + value); + throw new IllegalArgumentException("Value is too large for UI16: " + value); } write((int) (value & 0xff)); @@ -250,7 +250,7 @@ public class SWFOutputStream extends OutputStream { */ public void writeSI32(long value) throws IOException { if (value > 0x7fffffffL) { - throw new Error("Value is too large for SI32: " + value); + throw new IllegalArgumentException("Value is too large for SI32: " + value); } writeUI32(value); @@ -280,7 +280,7 @@ public class SWFOutputStream extends OutputStream { */ public void writeSI8(int value) throws IOException { if (value > 0x7ff) { - throw new Error("Value is too large for SI8: " + value); + throw new IllegalArgumentException("Value is too large for SI8: " + value); } writeUI8(value); diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont2Tag.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont2Tag.java index 9e4567cd5..b74d3679f 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont2Tag.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont2Tag.java @@ -195,6 +195,48 @@ public class DefineFont2Tag extends FontTag { } } + private void checkWideParameters() { + int numGlyphs = glyphShapeTable.size(); + + if (!fontFlagsWideOffsets) { + ByteArrayOutputStream baosGlyphShapes = new ByteArrayOutputStream(); + SWFOutputStream sos3 = new SWFOutputStream(baosGlyphShapes, getVersion()); + for (int i = 0; i < numGlyphs; i++) { + long offset = ((glyphShapeTable.size() + 1/*CodeTableOffset*/) * (fontFlagsWideOffsets ? 4 : 2) + sos3.getPos()); + if (offset > 0xffff) { + fontFlagsWideOffsets = true; + checkWideParameters(); + return; + } + try { + sos3.writeSHAPE(glyphShapeTable.get(i), 1); + } catch (IOException ex) { + //should not happen + return; + } + } + byte[] baGlyphShapes = baosGlyphShapes.toByteArray(); + + if (numGlyphs > 0) { + long offset = (glyphShapeTable.size() + 1/*CodeTableOffset*/) * (fontFlagsWideOffsets ? 4 : 2) + baGlyphShapes.length; + if (offset > 0xffff) { + fontFlagsWideOffsets = true; + checkWideParameters(); + return; + } + } + } + + if (!fontFlagsWideCodes) { + for (int i = 0; i < numGlyphs; i++) { + long code = codeTable.get(i); + if (code > 0xffff) { + fontFlagsWideCodes = true; + } + } + } + } + /** * Gets data bytes * @@ -203,6 +245,7 @@ public class DefineFont2Tag extends FontTag { */ @Override public void getData(SWFOutputStream sos) throws IOException { + checkWideParameters(); sos.writeUI16(fontId); sos.writeUB(1, fontFlagsHasLayout ? 1 : 0); sos.writeUB(1, fontFlagsShiftJIS ? 1 : 0); @@ -442,6 +485,7 @@ public class DefineFont2Tag extends FontTag { } } + checkWideParameters(); setModified(true); } diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont3Tag.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont3Tag.java index 0abe6bf47..6ce6a01d6 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont3Tag.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/tags/DefineFont3Tag.java @@ -185,6 +185,48 @@ public class DefineFont3Tag extends FontTag { } } + private void checkWideParameters() { + int numGlyphs = glyphShapeTable.size(); + + if (!fontFlagsWideOffsets) { + ByteArrayOutputStream baosGlyphShapes = new ByteArrayOutputStream(); + SWFOutputStream sos3 = new SWFOutputStream(baosGlyphShapes, getVersion()); + for (int i = 0; i < numGlyphs; i++) { + long offset = (glyphShapeTable.size()) * 2 + sos3.getPos(); + if (offset > 0xffff) { + fontFlagsWideOffsets = true; + checkWideParameters(); + return; + } + try { + sos3.writeSHAPE(glyphShapeTable.get(i), 1); + } catch (IOException ex) { + //should not happen + return; + } + } + byte[] baGlyphShapes = baosGlyphShapes.toByteArray(); + + if (numGlyphs > 0) { + long maxOffset = (glyphShapeTable.size() + 1/*CodeTableOffset*/) * 2 + baGlyphShapes.length; + if (maxOffset > 0xffff) { + fontFlagsWideOffsets = true; + checkWideParameters(); + return; + } + } + } + + if (!fontFlagsWideCodes) { + for (int i = 0; i < numGlyphs; i++) { + long code = codeTable.get(i); + if (code > 0xffff) { + fontFlagsWideCodes = true; + } + } + } + } + /** * Gets data bytes * @@ -193,6 +235,7 @@ public class DefineFont3Tag extends FontTag { */ @Override public void getData(SWFOutputStream sos) throws IOException { + checkWideParameters(); List offsetTable = new ArrayList<>(); ByteArrayOutputStream baosGlyphShapes = new ByteArrayOutputStream(); SWFOutputStream sos3 = new SWFOutputStream(baosGlyphShapes, getVersion()); @@ -203,14 +246,6 @@ public class DefineFont3Tag extends FontTag { } byte[] baGlyphShapes = baosGlyphShapes.toByteArray(); - if (!fontFlagsWideOffsets && numGlyphs > 0) { - // Set wide offsets when necessary - long maxOffset = (glyphShapeTable.size() + 1/*CodeTableOffset*/) * 2 + baGlyphShapes.length; - if (maxOffset > 65535) { - fontFlagsWideOffsets = true; - } - } - sos.writeUI16(fontId); sos.writeUB(1, fontFlagsHasLayout ? 1 : 0); sos.writeUB(1, fontFlagsShiftJIS ? 1 : 0); @@ -443,6 +478,7 @@ public class DefineFont3Tag extends FontTag { } } + checkWideParameters(); setModified(true); } diff --git a/src/com/jpexs/decompiler/flash/gui/FontPanel.java b/src/com/jpexs/decompiler/flash/gui/FontPanel.java index ca2b8b5b0..f9bbcc219 100644 --- a/src/com/jpexs/decompiler/flash/gui/FontPanel.java +++ b/src/com/jpexs/decompiler/flash/gui/FontPanel.java @@ -227,8 +227,10 @@ public class FontPanel extends JPanel { setAllowSave(true); setEditable(false); boolean readOnly = ((Tag) ft).isReadOnly(); - addCharsPanel.setVisible(!readOnly); - buttonEdit.setVisible(!readOnly); + if (readOnly) { + addCharsPanel.setVisible(false); + buttonEdit.setVisible(false); + } } private void initComponents() { diff --git a/src/com/jpexs/decompiler/flash/gui/TextPanel.java b/src/com/jpexs/decompiler/flash/gui/TextPanel.java index 7625cac24..47ebfcfac 100644 --- a/src/com/jpexs/decompiler/flash/gui/TextPanel.java +++ b/src/com/jpexs/decompiler/flash/gui/TextPanel.java @@ -178,7 +178,9 @@ public class TextPanel extends JPanel implements TagEditorPanel { setModified(false); setEditText(false); boolean readOnly = ((Tag) textTag).isReadOnly(); - textValue.setEditable(!readOnly); + if (readOnly) { + textValue.setEditable(false); + } buttonsPanel.setVisible(!readOnly); textAlignLeftButton.setVisible(!readOnly); textAlignCenterButton.setVisible(!readOnly);