mirror of
https://git.huckle.dev/Huckles-Minecraft-Archive/jpexs-decompiler.git
synced 2026-09-25 07:50:47 +00:00
#676: extended logging for text import, imorpt logic moved to separated class, allow to ignore errors duting import
This commit is contained in:
@@ -78,7 +78,7 @@ public class FolderPreviewPanel extends JPanel {
|
||||
|
||||
public FolderPreviewPanel(final MainPanel mainPanel, List<TreeItem> items) {
|
||||
this.items = items;
|
||||
cachedPreviews = Cache.getInstance(false,"preview");
|
||||
cachedPreviews = Cache.getInstance(false, "preview");
|
||||
|
||||
addMouseListener(new MouseAdapter() {
|
||||
|
||||
|
||||
@@ -736,7 +736,7 @@ public final class ImagePanel extends JPanel implements ActionListener, MediaDis
|
||||
if (frame >= timeline.getFrameCount()) {
|
||||
return;
|
||||
}
|
||||
if(frame<0){
|
||||
if (frame < 0) {
|
||||
return;
|
||||
}
|
||||
this.frame = frame;
|
||||
|
||||
@@ -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.configuration.ConfigurationItem;
|
||||
import com.jpexs.decompiler.flash.dumpview.DumpInfo;
|
||||
import com.jpexs.decompiler.flash.dumpview.DumpInfoSwfNode;
|
||||
import com.jpexs.decompiler.flash.exporters.BinaryDataExporter;
|
||||
@@ -71,6 +72,7 @@ import com.jpexs.decompiler.flash.helpers.Freed;
|
||||
import com.jpexs.decompiler.flash.importers.BinaryDataImporter;
|
||||
import com.jpexs.decompiler.flash.importers.ImageImporter;
|
||||
import com.jpexs.decompiler.flash.importers.ShapeImporter;
|
||||
import com.jpexs.decompiler.flash.importers.TextImporter;
|
||||
import com.jpexs.decompiler.flash.tags.ABCContainerTag;
|
||||
import com.jpexs.decompiler.flash.tags.DefineBinaryDataTag;
|
||||
import com.jpexs.decompiler.flash.tags.DefineSoundTag;
|
||||
@@ -90,6 +92,7 @@ import com.jpexs.decompiler.flash.tags.base.MorphShapeTag;
|
||||
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.TextImportErrorHandler;
|
||||
import com.jpexs.decompiler.flash.tags.base.TextTag;
|
||||
import com.jpexs.decompiler.flash.tags.text.TextParseException;
|
||||
import com.jpexs.decompiler.flash.timeline.DepthState;
|
||||
@@ -141,7 +144,6 @@ import java.beans.PropertyChangeListener;
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FilenameFilter;
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
@@ -1372,125 +1374,6 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
|
||||
}
|
||||
}
|
||||
|
||||
private Map<Integer, String[]> splitTextRecords(String texts) {
|
||||
String[] textsArr = texts.split(Helper.newLine + Configuration.textExportSingleFileSeparator.get() + Helper.newLine);
|
||||
String recordSeparator = Helper.newLine + Configuration.textExportSingleFileRecordSeparator.get() + Helper.newLine;
|
||||
Map<Integer, String[]> 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 {
|
||||
if (View.showConfirmDialog(this, translate("error.text.import"), translate("error"), JOptionPane.OK_CANCEL_OPTION) == JOptionPane.CANCEL_OPTION) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private void importTextsSingleFile(File textsFile, SWF swf) {
|
||||
String texts = Helper.readTextFile(textsFile.getPath());
|
||||
Map<Integer, String[]> records = splitTextRecords(texts);
|
||||
if (records != null) {
|
||||
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();
|
||||
if (!saveText(textTag, text, currentRecords)) {
|
||||
if (View.showConfirmDialog(this, translate("error.text.import"), translate("error"), JOptionPane.OK_CANCEL_OPTION) == JOptionPane.CANCEL_OPTION) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void importTextsSingleFileFormatted(File textsFile, SWF swf) {
|
||||
String texts = Helper.readTextFile(textsFile.getPath());
|
||||
Map<Integer, String[]> records = splitTextRecords(texts);
|
||||
if (records != null) {
|
||||
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);
|
||||
if (!saveText(textTag, currentRecords[0], null)) {
|
||||
if (View.showConfirmDialog(this, translate("error.text.import"), translate("error"), JOptionPane.OK_CANCEL_OPTION) == JOptionPane.CANCEL_OPTION) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void importTextsMultipleFiles(String folder, SWF swf) {
|
||||
File textsFolder = new File(Path.combine(folder, TextExporter.TEXT_EXPORT_FOLDER));
|
||||
String[] files = textsFolder.list(new FilenameFilter() {
|
||||
|
||||
private final 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(textsFolder.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();
|
||||
if (!saveText(textTag, text, records)) {
|
||||
if (View.showConfirmDialog(this, translate("error.text.import"), translate("error"), JOptionPane.OK_CANCEL_OPTION) == JOptionPane.CANCEL_OPTION) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (Tag tag : swf.tags) {
|
||||
if (tag instanceof TextTag) {
|
||||
TextTag textTag = (TextTag) tag;
|
||||
if (textTag.getCharacterId() == characterId) {
|
||||
if (!saveText(textTag, texts, null)) {
|
||||
if (View.showConfirmDialog(this, translate("error.text.import"), translate("error"), JOptionPane.OK_CANCEL_OPTION) == JOptionPane.CANCEL_OPTION) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void importText(final SWF swf) {
|
||||
JFileChooser chooser = new JFileChooser();
|
||||
chooser.setCurrentDirectory(new File(Configuration.lastExportDir.get()));
|
||||
@@ -1500,16 +1383,38 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
|
||||
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));
|
||||
final MainPanel diz = this;
|
||||
TextImporter textImporter = new TextImporter(getMissingCharacterHandler(), new TextImportErrorHandler() {
|
||||
|
||||
// "configuration items" for the current replace only
|
||||
private final ConfigurationItem<Boolean> doNotShowImportError = new ConfigurationItem<>("doNotShowImportError", true, true);
|
||||
private final ConfigurationItem<Boolean> doNotShowInvalidText = new ConfigurationItem<>("doNotShowInvalidText", true, true);
|
||||
|
||||
@Override
|
||||
public boolean handle() {
|
||||
String msg = translate("error.text.import");
|
||||
logger.log(Level.SEVERE, msg);
|
||||
return View.showConfirmDialog(diz, msg, translate("error"), JOptionPane.OK_CANCEL_OPTION, doNotShowImportError, JOptionPane.OK_OPTION) == JOptionPane.CANCEL_OPTION;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean handle(String message, long line) {
|
||||
String msg = translate("error.text.invalid.continue").replace("%text%", message).replace("%line%", Long.toString(line));
|
||||
logger.log(Level.SEVERE, msg);
|
||||
return View.showConfirmDialog(diz, msg, translate("error"), JOptionPane.OK_CANCEL_OPTION, doNotShowInvalidText, JOptionPane.OK_OPTION) == JOptionPane.CANCEL_OPTION;
|
||||
}
|
||||
});
|
||||
|
||||
// try to import formatted texts
|
||||
if (textsFile.exists()) {
|
||||
importTextsSingleFileFormatted(textsFile, swf);
|
||||
textImporter.importTextsSingleFileFormatted(textsFile, swf);
|
||||
} else {
|
||||
textsFile = new File(Path.combine(selFile, TextExporter.TEXT_EXPORT_FOLDER, TextExporter.TEXT_EXPORT_FILENAME_PLAIN));
|
||||
// try to import plain texts
|
||||
if (textsFile.exists()) {
|
||||
importTextsSingleFile(textsFile, swf);
|
||||
textImporter.importTextsSingleFile(textsFile, swf);
|
||||
} else {
|
||||
importTextsMultipleFiles(selFile, swf);
|
||||
textImporter.importTextsMultipleFiles(selFile, swf);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1806,31 +1711,35 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
|
||||
updateClassesList();
|
||||
}
|
||||
|
||||
private MissingCharacterHandler getMissingCharacterHandler() {
|
||||
return new MissingCharacterHandler() {
|
||||
@Override
|
||||
public boolean handle(FontTag font, char character) {
|
||||
String fontName = font.getSwf().sourceFontNamesMap.get(font.getFontId());
|
||||
if (fontName == null) {
|
||||
fontName = font.getFontName();
|
||||
}
|
||||
Font f = FontTag.installedFontsByName.get(fontName);
|
||||
if (f == null || !f.canDisplay(character)) {
|
||||
View.showMessageDialog(null, translate("error.font.nocharacter").replace("%char%", "" + character), translate("error"), JOptionPane.ERROR_MESSAGE);
|
||||
return false;
|
||||
}
|
||||
font.addCharacter(character, f);
|
||||
return true;
|
||||
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
public boolean saveText(TextTag textTag, String formattedText, String[] texts) {
|
||||
try {
|
||||
if (textTag.setFormattedText(new MissingCharacterHandler() {
|
||||
@Override
|
||||
public boolean handle(FontTag font, char character) {
|
||||
String fontName = font.getSwf().sourceFontNamesMap.get(font.getFontId());
|
||||
if (fontName == null) {
|
||||
fontName = font.getFontName();
|
||||
}
|
||||
Font f = FontTag.installedFontsByName.get(fontName);
|
||||
if (f == null || !f.canDisplay(character)) {
|
||||
View.showMessageDialog(null, translate("error.font.nocharacter").replace("%char%", "" + character), translate("error"), JOptionPane.ERROR_MESSAGE);
|
||||
return false;
|
||||
}
|
||||
font.addCharacter(character, f);
|
||||
return true;
|
||||
|
||||
}
|
||||
}, formattedText, texts)) {
|
||||
textTag.setModified(true);
|
||||
if (textTag.setFormattedText(getMissingCharacterHandler(), formattedText, texts)) {
|
||||
return true;
|
||||
}
|
||||
} catch (TextParseException ex) {
|
||||
View.showMessageDialog(null, translate("error.text.invalid").replace("%text%", ex.text).replace("%line%", Long.toString(ex.line)), translate("error"), JOptionPane.ERROR_MESSAGE);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
@@ -155,20 +155,20 @@ public class PreviewPanel extends JSplitPane implements ActionListener {
|
||||
super(JSplitPane.HORIZONTAL_SPLIT);
|
||||
this.mainPanel = mainPanel;
|
||||
this.flashPanel = flashPanel;
|
||||
|
||||
Runtime.getRuntime().addShutdownHook(new Thread(){
|
||||
|
||||
Runtime.getRuntime().addShutdownHook(new Thread() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
if(tempFile!=null){
|
||||
try{
|
||||
if (tempFile != null) {
|
||||
try {
|
||||
tempFile.delete();
|
||||
}catch(Exception ex){
|
||||
|
||||
} catch (Exception ex) {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
});
|
||||
|
||||
addPropertyChangeListener(JSplitPane.DIVIDER_LOCATION_PROPERTY, new PropertyChangeListener() {
|
||||
@@ -952,7 +952,7 @@ public class PreviewPanel extends JSplitPane implements ActionListener {
|
||||
tempFile.delete();
|
||||
}
|
||||
try {
|
||||
tempFile = File.createTempFile("ffdec_view_", ".swf");
|
||||
tempFile = File.createTempFile("ffdec_view_", ".swf");
|
||||
swf.saveTo(new BufferedOutputStream(new FileOutputStream(tempFile)));
|
||||
flashPanel.displaySWF(tempFile.getAbsolutePath(), backgroundColor, swf.frameRate);
|
||||
} catch (IOException iex) {
|
||||
|
||||
@@ -382,6 +382,10 @@ public class View {
|
||||
return ret[0];
|
||||
}
|
||||
|
||||
public static int showConfirmDialog(final Component parentComponent, String message, final String title, final int optionType, ConfigurationItem<Boolean> showAgainConfig, int defaultOption) {
|
||||
return showConfirmDialog(parentComponent, message, title, optionType, JOptionPane.PLAIN_MESSAGE, showAgainConfig, defaultOption);
|
||||
}
|
||||
|
||||
public static int showConfirmDialog(final Component parentComponent, String message, final String title, final int optionType, final int messageTyp, ConfigurationItem<Boolean> showAgainConfig, int defaultOption) {
|
||||
|
||||
JLabel warLabel = new JLabel("<html>" + message.replace("\r\n", "<br>") + "</html>");
|
||||
|
||||
@@ -535,4 +535,6 @@ preview.gotoframe = Goto frame...
|
||||
|
||||
preview.gotoframe.dialog.title = Goto frame
|
||||
preview.gotoframe.dialog.message = Enter frame number (%min% - %max%)
|
||||
preview.gotoframe.dialog.frame.error = Invalid frame number. It must be number between %min% and %max%.
|
||||
preview.gotoframe.dialog.frame.error = Invalid frame number. It must be number between %min% and %max%.
|
||||
|
||||
error.text.invalid.continue = Invalid text: %text% on line %line%. Do you want to continue?
|
||||
|
||||
@@ -137,7 +137,7 @@ public class FlashPlayerPanel extends Panel implements Closeable, MediaDisplay {
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
public synchronized void stopSWF() {
|
||||
@@ -193,16 +193,16 @@ public class FlashPlayerPanel extends Panel implements Closeable, MediaDisplay {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isPlaying() {
|
||||
public boolean isPlaying() {
|
||||
return flash.IsPlaying();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void gotoFrame(int frame) {
|
||||
if(frame<0){
|
||||
if (frame < 0) {
|
||||
return;
|
||||
}
|
||||
if(frame>=getTotalFrames()){
|
||||
if (frame >= getTotalFrames()) {
|
||||
return;
|
||||
}
|
||||
flash.GotoFrame(frame);
|
||||
|
||||
@@ -35,8 +35,6 @@ import java.awt.datatransfer.Transferable;
|
||||
import java.awt.datatransfer.UnsupportedFlavorException;
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.awt.event.ComponentAdapter;
|
||||
import java.awt.event.ComponentEvent;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.awt.event.MouseMotionAdapter;
|
||||
@@ -48,7 +46,6 @@ import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Timer;
|
||||
import java.util.TimerTask;
|
||||
import javax.swing.Box;
|
||||
import javax.swing.BoxLayout;
|
||||
import javax.swing.Icon;
|
||||
import javax.swing.JButton;
|
||||
@@ -169,7 +166,6 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
|
||||
add(graphicControls);
|
||||
graphicControls.setVisible(display.screenAvailable());
|
||||
|
||||
|
||||
playbackControls = new JPanel();
|
||||
this.display = display;
|
||||
@@ -186,7 +182,7 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
});
|
||||
|
||||
frameLabel.setVisible(display.screenAvailable());
|
||||
|
||||
|
||||
Dimension min = new Dimension(frameLabel.getFontMetrics(notUnderlinedFont).stringWidth("000"), frameLabel.getPreferredSize().height);
|
||||
frameLabel.setMinimumSize(min);
|
||||
frameLabel.setPreferredSize(min);
|
||||
@@ -215,12 +211,11 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
timeLabel = new JLabel("(00:00.00)");
|
||||
totalTimeLabel = new JLabel("(00:00.00)");
|
||||
totalFrameLabel = new JLabel("0");
|
||||
|
||||
|
||||
totalFrameLabel.setVisible(display.screenAvailable());
|
||||
|
||||
|
||||
frameControls = new JPanel(new FlowLayout());
|
||||
|
||||
frameControls = new JPanel(new FlowLayout());
|
||||
|
||||
JButton prevFrameButton = new JButton(View.getIcon("prevframe16"));
|
||||
prevFrameButton.setToolTipText(AppStrings.translate("preview.prevframe"));
|
||||
prevFrameButton.setMargin(new Insets(4, 2, 2, 2));
|
||||
@@ -229,16 +224,15 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
frameControls.add(prevFrameButton);
|
||||
frameControls.setVisible(display.screenAvailable());
|
||||
|
||||
|
||||
frameControls.add(frameLabel);
|
||||
|
||||
|
||||
JButton nextFrameButton = new JButton(View.getIcon("nextframe16"));
|
||||
nextFrameButton.setToolTipText(AppStrings.translate("preview.nextframe"));
|
||||
nextFrameButton.setMargin(new Insets(4, 2, 2, 2));
|
||||
nextFrameButton.setActionCommand(ACTION_NEXTFRAME);
|
||||
nextFrameButton.addActionListener(this);
|
||||
frameControls.add(nextFrameButton);
|
||||
|
||||
|
||||
JButton gotoFrameButton = new JButton(View.getIcon("gotoframe16"));
|
||||
gotoFrameButton.setToolTipText(AppStrings.translate("preview.gotoframe"));
|
||||
gotoFrameButton.setMargin(new Insets(4, 2, 2, 2));
|
||||
@@ -246,7 +240,6 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
gotoFrameButton.addActionListener(this);
|
||||
frameControls.add(gotoFrameButton);
|
||||
|
||||
|
||||
JPanel currentPanel = new JPanel(new FlowLayout());
|
||||
currentPanel.add(frameControls);
|
||||
currentPanel.add(timeLabel);
|
||||
@@ -259,7 +252,6 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
playbackControls.setLayout(new BoxLayout(playbackControls, BoxLayout.Y_AXIS));
|
||||
JPanel buttonsPanel = new JPanel(new FlowLayout());
|
||||
|
||||
|
||||
pauseButton = new JButton(pauseIcon);
|
||||
pauseButton.setToolTipText(AppStrings.translate("preview.pause"));
|
||||
pauseButton.setMargin(new Insets(4, 2, 2, 2));
|
||||
@@ -271,7 +263,7 @@ public class PlayerControls extends JPanel implements ActionListener {
|
||||
stopButton.setActionCommand(ACTION_STOP);
|
||||
stopButton.addActionListener(this);
|
||||
buttonsPanel.add(pauseButton);
|
||||
buttonsPanel.add(stopButton);
|
||||
buttonsPanel.add(stopButton);
|
||||
controlPanel.add(buttonsPanel, BorderLayout.CENTER);
|
||||
|
||||
progress = new JProgressBar();
|
||||
|
||||
Reference in New Issue
Block a user