From 3e58bccc7e8aa5ca59a2b3c2605a8bba5cf2e780 Mon Sep 17 00:00:00 2001 From: Honfika Date: Sun, 20 Apr 2014 22:10:59 +0200 Subject: [PATCH] #563 Import DefineTexts (formatted [and plain if possible]) from exported .txt files --- trunk/src/com/jpexs/decompiler/flash/SWF.java | 67 +--------- .../flash/configuration/Configuration.java | 3 + .../flash/exporters/TextExporter.java | 105 +++++++++++++++ .../jpexs/decompiler/flash/gui/FontPanel.java | 2 +- .../flash/gui/MainFrameRibbonMenu.java | 15 ++- .../jpexs/decompiler/flash/gui/MainPanel.java | 124 +++++++++++++++++- .../jpexs/decompiler/flash/gui/TextPanel.java | 2 +- .../flash/gui/graphics/import16.png | Bin 0 -> 621 bytes .../flash/gui/graphics/import32.png | Bin 0 -> 1052 bytes .../flash/gui/locales/MainFrame.properties | 5 + .../flash/gui/locales/MainFrame_hu.properties | 8 ++ .../flash/tags/DefineEditTextTag.java | 15 ++- .../decompiler/flash/tags/DefineText2Tag.java | 18 ++- .../decompiler/flash/tags/DefineTextTag.java | 18 ++- .../decompiler/flash/tags/base/TextTag.java | 5 +- trunk/src/com/jpexs/helpers/Helper.java | 12 +- 16 files changed, 299 insertions(+), 100 deletions(-) create mode 100644 trunk/src/com/jpexs/decompiler/flash/exporters/TextExporter.java create mode 100644 trunk/src/com/jpexs/decompiler/flash/gui/graphics/import16.png create mode 100644 trunk/src/com/jpexs/decompiler/flash/gui/graphics/import32.png diff --git a/trunk/src/com/jpexs/decompiler/flash/SWF.java b/trunk/src/com/jpexs/decompiler/flash/SWF.java index b3f39c289..56aa3f488 100644 --- a/trunk/src/com/jpexs/decompiler/flash/SWF.java +++ b/trunk/src/com/jpexs/decompiler/flash/SWF.java @@ -57,6 +57,7 @@ import com.jpexs.decompiler.flash.exporters.Matrix; import com.jpexs.decompiler.flash.exporters.PathExporter; import com.jpexs.decompiler.flash.exporters.SVGExporter; import com.jpexs.decompiler.flash.exporters.SVGExporterContext; +import com.jpexs.decompiler.flash.exporters.TextExporter; import com.jpexs.decompiler.flash.exporters.modes.FontExportMode; import com.jpexs.decompiler.flash.exporters.modes.FramesExportMode; import com.jpexs.decompiler.flash.exporters.modes.ImageExportMode; @@ -64,7 +65,6 @@ import com.jpexs.decompiler.flash.exporters.modes.MovieExportMode; import com.jpexs.decompiler.flash.exporters.modes.ScriptExportMode; import com.jpexs.decompiler.flash.exporters.modes.ShapeExportMode; import com.jpexs.decompiler.flash.exporters.modes.SoundExportMode; -import com.jpexs.decompiler.flash.exporters.modes.TextExportMode; import com.jpexs.decompiler.flash.exporters.settings.BinaryDataExportSettings; import com.jpexs.decompiler.flash.exporters.settings.FontExportSettings; import com.jpexs.decompiler.flash.exporters.settings.FramesExportSettings; @@ -114,7 +114,6 @@ import com.jpexs.decompiler.flash.tags.base.RemoveTag; import com.jpexs.decompiler.flash.tags.base.ShapeTag; import com.jpexs.decompiler.flash.tags.base.SoundStreamHeadTypeTag; import com.jpexs.decompiler.flash.tags.base.SoundTag; -import com.jpexs.decompiler.flash.tags.base.TextTag; import com.jpexs.decompiler.flash.timeline.Clip; import com.jpexs.decompiler.flash.timeline.DepthState; import com.jpexs.decompiler.flash.timeline.Frame; @@ -1807,70 +1806,8 @@ public final class SWF implements TreeItem, Timelined { return ret; } - public List exportTexts(AbortRetryIgnoreHandler handler, String outdir, List tags, final TextExportSettings settings) throws IOException { - List ret = new ArrayList<>(); - if (tags.isEmpty()) { - return ret; - } - File foutdir = new File(outdir); - if (!foutdir.exists()) { - if (!foutdir.mkdirs()) { - if (!foutdir.exists()) { - throw new IOException("Cannot create directory " + outdir); - } - } - } - - if (settings.singleFile) { - final File file = new File(outdir + File.separator + - (settings.mode == TextExportMode.FORMATTED ? "textsformatted.txt" : "textsplain.txt")); - final String nl = System.getProperty("line.separator"); - try (FileOutputStream fos = new FileOutputStream(file)) { - for (final Tag t : tags) { - if (t instanceof TextTag) { - final TextTag textTag = (TextTag) t; - new RetryTask(new RunnableIOEx() { - @Override - public void run() throws IOException { - fos.write(Utf8Helper.getBytes("ID: " + textTag.getCharacterId() + nl)); - if (settings.mode == TextExportMode.FORMATTED) { - fos.write(Utf8Helper.getBytes(textTag.getFormattedText())); - } else { - fos.write(Utf8Helper.getBytes(textTag.getText())); - } - fos.write(Utf8Helper.getBytes(nl + Configuration.textExportSingleFileSeparator.get() + nl)); - } - }, handler).run(); - } - } - } - ret.add(file); - } else { - for (Tag t : tags) { - if (t instanceof TextTag) { - final TextTag textTag = (TextTag) t; - final File file = new File(outdir + File.separator + textTag.getCharacterId() + ".txt"); - new RetryTask(new RunnableIOEx() { - @Override - public void run() throws IOException { - try (FileOutputStream fos = new FileOutputStream(file)) { - if (settings.mode == TextExportMode.FORMATTED) { - fos.write(Utf8Helper.getBytes(textTag.getFormattedText())); - } else { - fos.write(Utf8Helper.getBytes(textTag.getText())); - } - } - } - }, handler).run(); - ret.add(file); - } - } - } - return ret; - } - public void exportTexts(AbortRetryIgnoreHandler handler, String outdir, TextExportSettings settings) throws IOException { - exportTexts(handler, outdir, tags, settings); + new TextExporter().exportTexts(handler, outdir, tags, settings); } public static List exportShapes(AbortRetryIgnoreHandler handler, final String outdir, List tags, final ShapeExportSettings settings) throws IOException { diff --git a/trunk/src/com/jpexs/decompiler/flash/configuration/Configuration.java b/trunk/src/com/jpexs/decompiler/flash/configuration/Configuration.java index eb1001812..6862febac 100644 --- a/trunk/src/com/jpexs/decompiler/flash/configuration/Configuration.java +++ b/trunk/src/com/jpexs/decompiler/flash/configuration/Configuration.java @@ -259,6 +259,9 @@ public class Configuration { @ConfigurationDefaultString("--- SEPARATOR ---") public static final ConfigurationItem textExportSingleFileSeparator = null; + @ConfigurationDefaultString("--- RECORDSEPARATOR ---") + public static final ConfigurationItem textExportSingleFileRecordSeparator = null; + @ConfigurationDefaultBoolean(true) @ConfigurationName("warning.experimental.as12edit") public static final ConfigurationItem warningExperimentalAS12Edit = null; diff --git a/trunk/src/com/jpexs/decompiler/flash/exporters/TextExporter.java b/trunk/src/com/jpexs/decompiler/flash/exporters/TextExporter.java new file mode 100644 index 000000000..3b100fc4f --- /dev/null +++ b/trunk/src/com/jpexs/decompiler/flash/exporters/TextExporter.java @@ -0,0 +1,105 @@ +/* + * Copyright (C) 2014 JPEXS + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ +package com.jpexs.decompiler.flash.exporters; + +import com.jpexs.decompiler.flash.AbortRetryIgnoreHandler; +import com.jpexs.decompiler.flash.RetryTask; +import com.jpexs.decompiler.flash.RunnableIOEx; +import com.jpexs.decompiler.flash.configuration.Configuration; +import com.jpexs.decompiler.flash.exporters.modes.TextExportMode; +import com.jpexs.decompiler.flash.exporters.settings.TextExportSettings; +import com.jpexs.decompiler.flash.tags.Tag; +import com.jpexs.decompiler.flash.tags.base.TextTag; +import com.jpexs.helpers.Helper; +import com.jpexs.helpers.utf8.Utf8Helper; +import java.io.File; +import java.io.FileOutputStream; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +/** + * + * @author JPEXS + */ +public class TextExporter { + + public static final String TEXT_EXPORT_FOLDER = "texts"; + public static final String TEXT_EXPORT_FILENAME_FORMATTED = "textsformatted.txt"; + public static final String TEXT_EXPORT_FILENAME_PLAIN = "textsplain.txt"; + + public List exportTexts(AbortRetryIgnoreHandler handler, String outdir, List tags, final TextExportSettings settings) throws IOException { + List ret = new ArrayList<>(); + if (tags.isEmpty()) { + return ret; + } + File foutdir = new File(outdir); + if (!foutdir.exists()) { + if (!foutdir.mkdirs()) { + if (!foutdir.exists()) { + throw new IOException("Cannot create directory " + outdir); + } + } + } + + if (settings.singleFile) { + final File file = new File(outdir + File.separator + + (settings.mode == TextExportMode.FORMATTED ? TEXT_EXPORT_FILENAME_FORMATTED : TEXT_EXPORT_FILENAME_PLAIN)); + try (FileOutputStream fos = new FileOutputStream(file)) { + for (final Tag t : tags) { + if (t instanceof TextTag) { + final TextTag textTag = (TextTag) t; + new RetryTask(new RunnableIOEx() { + @Override + public void run() throws IOException { + fos.write(Utf8Helper.getBytes("ID: " + textTag.getCharacterId() + Helper.newLine)); + if (settings.mode == TextExportMode.FORMATTED) { + fos.write(Utf8Helper.getBytes(textTag.getFormattedText())); + } else { + fos.write(Utf8Helper.getBytes(textTag.getText(Configuration.textExportSingleFileRecordSeparator.get()))); + } + fos.write(Utf8Helper.getBytes(Helper.newLine + Configuration.textExportSingleFileSeparator.get() + Helper.newLine)); + } + }, handler).run(); + } + } + } + ret.add(file); + } else { + for (Tag t : tags) { + if (t instanceof TextTag) { + final TextTag textTag = (TextTag) t; + final File file = new File(outdir + File.separator + textTag.getCharacterId() + ".txt"); + new RetryTask(new RunnableIOEx() { + @Override + public void run() throws IOException { + try (FileOutputStream fos = new FileOutputStream(file)) { + if (settings.mode == TextExportMode.FORMATTED) { + fos.write(Utf8Helper.getBytes(textTag.getFormattedText())); + } else { + fos.write(Utf8Helper.getBytes(textTag.getText(Configuration.textExportSingleFileRecordSeparator.get()))); + } + } + } + }, handler).run(); + ret.add(file); + } + } + } + return ret; + } +} diff --git a/trunk/src/com/jpexs/decompiler/flash/gui/FontPanel.java b/trunk/src/com/jpexs/decompiler/flash/gui/FontPanel.java index aa2510406..5f772e548 100644 --- a/trunk/src/com/jpexs/decompiler/flash/gui/FontPanel.java +++ b/trunk/src/com/jpexs/decompiler/flash/gui/FontPanel.java @@ -140,7 +140,7 @@ public class FontPanel extends javax.swing.JPanel { TextTag textTag = (TextTag) tag; if (textTag.getFontIds().contains(fontId)) { String text = textTag.getFormattedText(); - mainPanel.saveText(textTag, text); + mainPanel.saveText(textTag, text, null); } } } diff --git a/trunk/src/com/jpexs/decompiler/flash/gui/MainFrameRibbonMenu.java b/trunk/src/com/jpexs/decompiler/flash/gui/MainFrameRibbonMenu.java index 4ddd03365..f35b6e7ef 100644 --- a/trunk/src/com/jpexs/decompiler/flash/gui/MainFrameRibbonMenu.java +++ b/trunk/src/com/jpexs/decompiler/flash/gui/MainFrameRibbonMenu.java @@ -104,6 +104,7 @@ public class MainFrameRibbonMenu implements MainFrameMenu, ActionListener { static final String ACTION_EXPORT_FLA = "EXPORTFLA"; public static final String ACTION_EXPORT_SEL = "EXPORTSEL"; static final String ACTION_EXPORT = "EXPORT"; + static final String ACTION_IMPORT_TEXT = "IMPORTTEXT"; static final String ACTION_CHECK_UPDATES = "CHECKUPDATES"; static final String ACTION_HELP_US = "HELPUS"; static final String ACTION_HOMEPAGE = "HOMEPAGE"; @@ -133,6 +134,7 @@ public class MainFrameRibbonMenu implements MainFrameMenu, ActionListener { private JCommandButton exportAllCommandButton; private JCommandButton exportFlaCommandButton; private JCommandButton exportSelectionCommandButton; + private JCommandButton importTextCommandButton; private JCommandButton reloadCommandButton; private JCommandButton renameinvalidCommandButton; @@ -312,7 +314,14 @@ public class MainFrameRibbonMenu implements MainFrameMenu, ActionListener { exportBand.addCommandButton(exportSelectionCommandButton, RibbonElementPriority.MEDIUM); exportBand.addCommandButton(saveasexeCommandButton, RibbonElementPriority.MEDIUM); - return new RibbonTask(translate("menu.file"), editBand, exportBand); + JRibbonBand importBand = new JRibbonBand(translate("menu.import"), null); + importBand.setResizePolicies(getResizePolicies(importBand)); + importTextCommandButton = new JCommandButton(fixCommandTitle(translate("menu.file.import.text")), View.getResizableIcon("import32")); + assignListener(importTextCommandButton, ACTION_IMPORT_TEXT); + + importBand.addCommandButton(importTextCommandButton, RibbonElementPriority.TOP); + + return new RibbonTask(translate("menu.file"), editBand, exportBand, importBand); } private RibbonTask createToolsRibbonTask() { @@ -508,6 +517,7 @@ public class MainFrameRibbonMenu implements MainFrameMenu, ActionListener { exportAllCommandButton.setEnabled(swfLoaded); exportFlaCommandButton.setEnabled(swfLoaded); exportSelectionCommandButton.setEnabled(swfLoaded); + importTextCommandButton.setEnabled(swfLoaded); reloadCommandButton.setEnabled(swfLoaded); renameinvalidCommandButton.setEnabled(swfLoaded); @@ -694,6 +704,9 @@ public class MainFrameRibbonMenu implements MainFrameMenu, ActionListener { case ACTION_EXPORT_FLA: mainFrame.panel.exportFla(mainFrame.panel.getCurrentSwf()); break; + case ACTION_IMPORT_TEXT: + mainFrame.panel.importText(mainFrame.panel.getCurrentSwf()); + break; case ACTION_EXPORT_SEL: case ACTION_EXPORT: boolean onlySel = e.getActionCommand().endsWith("SEL"); diff --git a/trunk/src/com/jpexs/decompiler/flash/gui/MainPanel.java b/trunk/src/com/jpexs/decompiler/flash/gui/MainPanel.java index e75a54548..261914386 100644 --- a/trunk/src/com/jpexs/decompiler/flash/gui/MainPanel.java +++ b/trunk/src/com/jpexs/decompiler/flash/gui/MainPanel.java @@ -26,6 +26,7 @@ import com.jpexs.decompiler.flash.abc.ScriptPack; import com.jpexs.decompiler.flash.abc.types.traits.Trait; import com.jpexs.decompiler.flash.abc.types.traits.TraitClass; import com.jpexs.decompiler.flash.configuration.Configuration; +import com.jpexs.decompiler.flash.exporters.TextExporter; import com.jpexs.decompiler.flash.exporters.modes.BinaryDataExportMode; import com.jpexs.decompiler.flash.exporters.modes.FontExportMode; import com.jpexs.decompiler.flash.exporters.modes.FramesExportMode; @@ -117,6 +118,7 @@ import com.jpexs.decompiler.flash.types.sound.SoundFormat; import com.jpexs.decompiler.flash.xfl.FLAVersion; import com.jpexs.helpers.CancellableWorker; import com.jpexs.helpers.Helper; +import com.jpexs.helpers.Path; import com.jpexs.helpers.SerializableImage; import java.awt.BorderLayout; import java.awt.CardLayout; @@ -148,6 +150,7 @@ import java.beans.PropertyChangeEvent; import java.beans.PropertyChangeListener; import java.io.File; import java.io.FileInputStream; +import java.io.FilenameFilter; import java.io.IOException; import java.util.ArrayList; import java.util.Arrays; @@ -1277,7 +1280,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec new ShapeExportSettings(export.getValue(ShapeExportMode.class)))); ret.addAll(SWF.exportMorphShapes(handler, selFile + File.separator + "morphshapes", morphshapes, new MorphShapeExportSettings(export.getValue(MorphShapeExportMode.class)))); - ret.addAll(swf.exportTexts(handler, selFile + File.separator + "texts", texts, + ret.addAll(new TextExporter().exportTexts(handler, selFile + File.separator + "texts", texts, new TextExportSettings(export.getValue(TextExportMode.class), Configuration.textExportSingleFile.get()))); ret.addAll(swf.exportMovies(handler, selFile + File.separator + "movies", movies, new MovieExportSettings(export.getValue(MovieExportMode.class)))); @@ -1547,7 +1550,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec if (!selDir.endsWith(File.separator)) { selDir += File.separator; } - String fileName = (new File(swf.file).getName()); + String fileName = new File(swf.file).getName(); fileName = fileName.substring(0, fileName.length() - 4) + ".fla"; fc.setSelectedFile(new File(selDir + fileName)); List flaFilters = new ArrayList<>(); @@ -1645,6 +1648,118 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec }.execute(); } } + + private Map splitTextRecords(String texts) { + String[] textsArr = texts.split(Helper.newLine + Configuration.textExportSingleFileSeparator.get() + Helper.newLine); + String recordSeparator = Helper.newLine + Configuration.textExportSingleFileRecordSeparator.get() + Helper.newLine; + Map result = new HashMap<>(); + for (String text : textsArr) { + String[] textArr = text.split(Helper.newLine, 2); + String idLine = textArr[0]; + if (idLine.startsWith("ID:")) { + int id = Integer.parseInt(idLine.substring(3).trim()); + String[] records = textArr[1].split(recordSeparator); + result.put(id, records); + } else { + View.showMessageDialog(null, translate("error.text.import"), translate("error"), JOptionPane.ERROR_MESSAGE); + } + } + return result; + } + + public void importText(final SWF swf) { + JFileChooser chooser = new JFileChooser(); + chooser.setCurrentDirectory(new File(Configuration.lastExportDir.get())); + chooser.setDialogTitle(translate("import.select.directory")); + chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY); + chooser.setAcceptAllFileFilterUsed(false); + if (chooser.showOpenDialog(this) == JFileChooser.APPROVE_OPTION) { + String selFile = Helper.fixDialogFile(chooser.getSelectedFile()).getAbsolutePath(); + File textsFile = new File(Path.combine(selFile, TextExporter.TEXT_EXPORT_FOLDER, TextExporter.TEXT_EXPORT_FILENAME_FORMATTED)); + // try to import formatted texts + if (textsFile.exists()) { + String texts = Helper.readTextFile(textsFile.getPath()); + Map records = splitTextRecords(texts); + for (int characterId : records.keySet()) { + for (Tag tag : swf.tags) { + if (tag instanceof TextTag) { + TextTag textTag = (TextTag) tag; + if (textTag.getCharacterId() == characterId) { + String[] currentRecords = records.get(characterId); + saveText(textTag, currentRecords[0], null); + break; + } + } + } + } + } else { + textsFile = new File(Path.combine(selFile, TextExporter.TEXT_EXPORT_FOLDER, TextExporter.TEXT_EXPORT_FILENAME_PLAIN)); + // try to import plain texts + if (textsFile.exists()) { + String texts = Helper.readTextFile(textsFile.getPath()); + Map records = splitTextRecords(texts); + for (int characterId : records.keySet()) { + for (Tag tag : swf.tags) { + if (tag instanceof TextTag) { + TextTag textTag = (TextTag) tag; + if (textTag.getCharacterId() == characterId) { + String[] currentRecords = records.get(characterId); + String text = textTag.getFormattedText(); + saveText(textTag, text, currentRecords); + break; + } + } + } + } + } else { + textsFile = new File(Path.combine(selFile, TextExporter.TEXT_EXPORT_FOLDER)); + String[] files = textsFile.list(new FilenameFilter() { + + private Pattern pat = Pattern.compile("\\d+\\.txt", Pattern.CASE_INSENSITIVE); + + @Override + public boolean accept(File dir, String name) { + + return pat.matcher(name).matches(); + } + }); + + for (String fileName : files) { + String texts = Helper.readTextFile(Path.combine(textsFile.getPath(), fileName)); + int characterId = Integer.parseInt(fileName.split("\\.")[0]); + String recordSeparator = Helper.newLine + Configuration.textExportSingleFileRecordSeparator.get() + Helper.newLine; + boolean formatted = !texts.contains(recordSeparator) && texts.startsWith("[" + Helper.newLine); + if (!formatted) { + String[] records = texts.split(recordSeparator); + for (Tag tag : swf.tags) { + if (tag instanceof TextTag) { + TextTag textTag = (TextTag) tag; + if (textTag.getCharacterId() == characterId) { + String text = textTag.getFormattedText(); + saveText(textTag, text, records); + break; + } + } + } + } else { + for (Tag tag : swf.tags) { + if (tag instanceof TextTag) { + TextTag textTag = (TextTag) tag; + if (textTag.getCharacterId() == characterId) { + saveText(textTag, texts, null); + break; + } + } + } + } + } + } + } + + SWF.clearImageCache(); + reload(true); + } + } private String selectExportDir() { JFileChooser chooser = new JFileChooser(); @@ -1653,7 +1768,6 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY); chooser.setAcceptAllFileFilterUsed(false); if (chooser.showOpenDialog(this) == JFileChooser.APPROVE_OPTION) { - final long timeBefore = System.currentTimeMillis(); Main.startWork(translate("work.exporting") + "..."); final String selFile = Helper.fixDialogFile(chooser.getSelectedFile()).getAbsolutePath(); Configuration.lastExportDir.set(Helper.fixDialogFile(chooser.getSelectedFile()).getAbsolutePath()); @@ -1920,7 +2034,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec updateClassesList(); } - public boolean saveText(TextTag textTag, String text) { + public boolean saveText(TextTag textTag, String formattedText, String[] texts) { try { if (textTag.setFormattedText(new MissingCharacterHandler() { @Override @@ -1939,7 +2053,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec return true; } - }, text)) { + }, formattedText, texts)) { textTag.setModified(true); return true; } diff --git a/trunk/src/com/jpexs/decompiler/flash/gui/TextPanel.java b/trunk/src/com/jpexs/decompiler/flash/gui/TextPanel.java index ad1853a42..1fdc928b1 100644 --- a/trunk/src/com/jpexs/decompiler/flash/gui/TextPanel.java +++ b/trunk/src/com/jpexs/decompiler/flash/gui/TextPanel.java @@ -121,7 +121,7 @@ public class TextPanel extends JPanel implements ActionListener { TreeItem item = mainPanel.tagTree.getCurrentTreeItem(); if (item instanceof TextTag) { TextTag textTag = (TextTag) item; - if (mainPanel.saveText(textTag, textValue.getText())) { + if (mainPanel.saveText(textTag, textValue.getText(), null)) { setEditText(false); mainPanel.reload(true); } diff --git a/trunk/src/com/jpexs/decompiler/flash/gui/graphics/import16.png b/trunk/src/com/jpexs/decompiler/flash/gui/graphics/import16.png new file mode 100644 index 0000000000000000000000000000000000000000..7c6ed41cb2aa643e16ef9a6219b5bd3d68d73217 GIT binary patch literal 621 zcmV-z0+RiSP)j9@fsA?_k60~>7N)}2BGnVXV`7K*EOEn;{Y6d2MbgoF^<1hr^05Tin2Ge$y% z6TbIu-*?CPd6Oo7aCrCL$2s5me#FbAr5}C}ByAYNqA~a;AccSsqNJ2cNh#4B+V}nB z)xkmhFN(!t``gu3&lrfPHV}{s#_y(KY#zixt<<}ny`(wTGt6GBEV7J`GXw-C*gnX$J-#miIkg8M4(#p zenEqTR&jT3)k(zY{Eq-T*q1CM3=vvm8fT{jj*(8>5K%hix`0yh0CEdrae*_F0#8O~ zVRRhh3uD$$B}}QY6pgD9njE$03b~uek8e)n!{>3l&yV5J&Wpm=sEkq7pp=0! z0;lf?%#BPSzj+skQ9sH4r>_%uFm#_L0;{pt3|<~IjEL=Xjl<_Jah>lI)J9>R7F;5un_h^M*SN+OZC=oX}DN!W#! z#+5W*7{&MUCKOqqh24I23n#A3qRfsu2uU0*e8NXQ{1spTvgpS2%W?K800000NkvXX Hu0mjfKw1*x literal 0 HcmV?d00001 diff --git a/trunk/src/com/jpexs/decompiler/flash/gui/graphics/import32.png b/trunk/src/com/jpexs/decompiler/flash/gui/graphics/import32.png new file mode 100644 index 0000000000000000000000000000000000000000..d31b964172e06ef00ff7c282fc9c04f0a123f123 GIT binary patch literal 1052 zcmV+%1mpXOP)0+38}<|x716+u{nu5^TpAHjr`kF?I@DW!e?6@y*|jh0y-O#8mewyqk%Ts|YUK*l z+`f&H;$r0G=6Y-V{yQc6_U)yghvU7^^`05BbIvtLk`x!lTx|jBJAeH~dU`tYJf7Wm z1A#UgR_qcmo7lZrRP^y+%+uZzGCH03_WcJkGBV)K%F4J?SJxVkge8GQVKk>xL6Xa5 zlE}%eVakwA^aYnfawCB5CNKv-kvZvWoBxyYLV#X91|-rDh6yT zKy$STu^`L85?DhyZms9V|lEKoDhHtMK$A z87DPF+zE*1#^wV!xTPBIb?_FP9Z6!+F3^fm^6{C_PJ|-?lonLr(LJ>gei8l>`eO+U?(%v) z)GwIAU99As#p40F4UW{9R6?u$QQ9a&YX1r2->ec*SZCKhg-c-GP%mCxyV>Q|jK>h* ztP?DPuT~k3>0igwaj~TlmJ=3QWY`FylOR4)x@L-itVg!X!i{3*gCZVv|C{Zf00RKs WZ%;#=EAS`)0000= texts.length) ? (String) s.values[0] : texts[textIdx++]; break; } } this.bounds = bounds; - if (text.length() > 0) { - initialText = text; + if (formattedText.length() > 0) { + initialText = formattedText; this.hasText = true; } else { this.hasText = false; diff --git a/trunk/src/com/jpexs/decompiler/flash/tags/DefineText2Tag.java b/trunk/src/com/jpexs/decompiler/flash/tags/DefineText2Tag.java index eed6504df..1955f6c39 100644 --- a/trunk/src/com/jpexs/decompiler/flash/tags/DefineText2Tag.java +++ b/trunk/src/com/jpexs/decompiler/flash/tags/DefineText2Tag.java @@ -80,10 +80,15 @@ public class DefineText2Tag extends TextTag { } @Override - public String getText() { + public String getText(String separator) { FontTag fnt = null; String ret = ""; + boolean first = true; for (TEXTRECORD rec : textRecords) { + if (!first) { + ret += Helper.newLine + separator + Helper.newLine; + } + first = false; if (rec.styleFlagsHasFont) { for (Tag t : swf.tags) { if (t instanceof FontTag) { @@ -95,9 +100,9 @@ public class DefineText2Tag extends TextTag { } } if (rec.styleFlagsHasXOffset || rec.styleFlagsHasYOffset) { - if (!ret.isEmpty()) { + /*if (!ret.isEmpty()) { ret += "\r\n"; - } + }*/ } ret += rec.getText(fnt); } @@ -166,10 +171,10 @@ public class DefineText2Tag extends TextTag { } @Override - public boolean setFormattedText(MissingCharacterHandler missingCharHandler, String text) throws ParseException { + public boolean setFormattedText(MissingCharacterHandler missingCharHandler, String formattedText, String[] texts) throws ParseException { List oldTextRecords = textRecords; try { - TextLexer lexer = new TextLexer(new StringReader(text)); + TextLexer lexer = new TextLexer(new StringReader(formattedText)); ParsedSymbol s = null; textRecords = new ArrayList<>(); RGBA colorA = null; @@ -187,6 +192,7 @@ public class DefineText2Tag extends TextTag { textMatrix.hasRotate = false; textMatrix.hasScale = false; RECT textBounds = new RECT(); + int textIdx = 0; while ((s = lexer.yylex()) != null) { switch (s.type) { case PARAMETER: @@ -347,7 +353,7 @@ public class DefineText2Tag extends TextTag { tr.styleFlagsHasYOffset = true; y = null; } - String txt = (String) s.values[0]; + String txt = (texts == null || textIdx >= texts.length) ? (String) s.values[0] : texts[textIdx++]; tr.glyphEntries = new GLYPHENTRY[txt.length()]; for (int i = 0; i < txt.length(); i++) { char c = txt.charAt(i); diff --git a/trunk/src/com/jpexs/decompiler/flash/tags/DefineTextTag.java b/trunk/src/com/jpexs/decompiler/flash/tags/DefineTextTag.java index 44ae0c635..e6fdcfa00 100644 --- a/trunk/src/com/jpexs/decompiler/flash/tags/DefineTextTag.java +++ b/trunk/src/com/jpexs/decompiler/flash/tags/DefineTextTag.java @@ -81,10 +81,15 @@ public class DefineTextTag extends TextTag { } @Override - public String getText() { + public String getText(String separator) { FontTag fnt = null; String ret = ""; + boolean first = true; for (TEXTRECORD rec : textRecords) { + if (!first) { + ret += Helper.newLine + separator + Helper.newLine; + } + first = false; if (rec.styleFlagsHasFont) { for (Tag t : swf.tags) { if (t instanceof FontTag) { @@ -96,9 +101,9 @@ public class DefineTextTag extends TextTag { } } if (rec.styleFlagsHasXOffset || rec.styleFlagsHasYOffset) { - if (!ret.isEmpty()) { + /*if (!ret.isEmpty()) { ret += "\r\n"; - } + }*/ } ret += rec.getText(fnt); } @@ -172,10 +177,10 @@ public class DefineTextTag extends TextTag { } @Override - public boolean setFormattedText(MissingCharacterHandler missingCharHandler, String text) throws ParseException { + public boolean setFormattedText(MissingCharacterHandler missingCharHandler, String formattedText, String[] texts) throws ParseException { List oldTextRecords = textRecords; try { - TextLexer lexer = new TextLexer(new StringReader(text)); + TextLexer lexer = new TextLexer(new StringReader(formattedText)); ParsedSymbol s = null; textRecords = new ArrayList<>(); RGB color = null; @@ -193,6 +198,7 @@ public class DefineTextTag extends TextTag { textMatrix.hasRotate = false; textMatrix.hasScale = false; RECT textBounds = new RECT(); + int textIdx = 0; while ((s = lexer.yylex()) != null) { switch (s.type) { case PARAMETER: @@ -353,7 +359,7 @@ public class DefineTextTag extends TextTag { tr.styleFlagsHasYOffset = true; y = null; } - String txt = (String) s.values[0]; + String txt = (texts == null || textIdx >= texts.length) ? (String) s.values[0] : texts[textIdx++]; tr.glyphEntries = new GLYPHENTRY[txt.length()]; for (int i = 0; i < txt.length(); i++) { char c = txt.charAt(i); diff --git a/trunk/src/com/jpexs/decompiler/flash/tags/base/TextTag.java b/trunk/src/com/jpexs/decompiler/flash/tags/base/TextTag.java index 4313122ee..91a3ba830 100644 --- a/trunk/src/com/jpexs/decompiler/flash/tags/base/TextTag.java +++ b/trunk/src/com/jpexs/decompiler/flash/tags/base/TextTag.java @@ -67,13 +67,14 @@ public abstract class TextTag extends CharacterTag implements BoundedTag, Drawab public abstract MATRIX getTextMatrix(); - public abstract String getText(); + public abstract String getText(String separator); public abstract List getFontIds(); public abstract String getFormattedText(); - public abstract boolean setFormattedText(MissingCharacterHandler missingCharHandler, String text) throws ParseException; + // use the texts from the "texts" argument when it is not null + public abstract boolean setFormattedText(MissingCharacterHandler missingCharHandler, String formattedText, String[] texts) throws ParseException; @Override public abstract int getCharacterId(); diff --git a/trunk/src/com/jpexs/helpers/Helper.java b/trunk/src/com/jpexs/helpers/Helper.java index af975b8a0..a2a44513c 100644 --- a/trunk/src/com/jpexs/helpers/Helper.java +++ b/trunk/src/com/jpexs/helpers/Helper.java @@ -59,6 +59,8 @@ import java.util.regex.Pattern; */ public class Helper { + public static String newLine = System.getProperty("line.separator"); + /** * Converts array of int values to string * @@ -417,6 +419,10 @@ public class Helper { return baos.toByteArray(); } + public static String readTextFile(String... file) { + return new String(readFile(file), Utf8Helper.charset); + } + public static byte[] readStream(InputStream is) { if (is instanceof MemoryInputStream) { return ((MemoryInputStream) is).getAllRead(); @@ -446,12 +452,6 @@ public class Helper { } } - //public static String stripComments(String str) { - // return str.replaceAll("[^\r\n]*\r?\n", ""); - //} - //public static String hexToComments(String str) { - // return str.replaceAll("([^\r\n]*)(\r?\n)", "; $1$2"); - //} public static String stackToString(Stack stack, LocalData localData) throws InterruptedException { String ret = "["; for (int i = stack.size() - 1; i >= 0; i--) {