From ecae3cdbb0feca01ebced18a44464506f56cee28 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jindra=20Pet=C5=99=C3=ADk?= Date: Wed, 14 May 2025 21:29:49 +0200 Subject: [PATCH] Added: Link blur X and blur Y --- .../flash/easygui/FiltersTreeTable.java | 83 +++++++++++- .../gui/generictageditors/ChangeListener.java | 3 +- .../gui/generictageditors/FloatEditor.java | 127 ++++++++++++++---- .../gui/generictageditors/NumberEditor.java | 1 - .../flash/gui/graphics/linkbreak16.png | Bin 0 -> 804 bytes .../flash/gui/locales/EasyPanel.properties | 4 +- 6 files changed, 184 insertions(+), 34 deletions(-) create mode 100644 src/com/jpexs/decompiler/flash/gui/graphics/linkbreak16.png diff --git a/src/com/jpexs/decompiler/flash/easygui/FiltersTreeTable.java b/src/com/jpexs/decompiler/flash/easygui/FiltersTreeTable.java index 22a3b60df..28d814a5c 100644 --- a/src/com/jpexs/decompiler/flash/easygui/FiltersTreeTable.java +++ b/src/com/jpexs/decompiler/flash/easygui/FiltersTreeTable.java @@ -24,6 +24,7 @@ import com.jpexs.decompiler.flash.ecma.EcmaScript; import com.jpexs.decompiler.flash.gui.AppStrings; import com.jpexs.decompiler.flash.gui.View; import com.jpexs.decompiler.flash.gui.generictageditors.BooleanEditor; +import com.jpexs.decompiler.flash.gui.generictageditors.ChangeListener; import com.jpexs.decompiler.flash.gui.generictageditors.ColorEditor; import com.jpexs.decompiler.flash.gui.generictageditors.FloatEditor; import com.jpexs.decompiler.flash.gui.generictageditors.NumberEditor; @@ -42,6 +43,8 @@ import de.javagl.treetable.TreeTableModel; import java.awt.BorderLayout; import java.awt.Color; import java.awt.Component; +import java.awt.Dimension; +import java.awt.FlowLayout; import java.awt.datatransfer.DataFlavor; import java.awt.datatransfer.Transferable; import java.awt.datatransfer.UnsupportedFlavorException; @@ -60,6 +63,8 @@ import java.util.List; import java.util.Objects; import java.util.Timer; import java.util.TimerTask; +import java.util.logging.Level; +import java.util.logging.Logger; import javax.swing.DropMode; import javax.swing.JCheckBox; import javax.swing.JComponent; @@ -89,6 +94,7 @@ import javax.swing.tree.TreePath; public class FiltersTreeTable extends JTreeTable { private List filterChangedListeners = new ArrayList<>(); + private boolean linkEnabled = true; public FiltersTreeTable() { super(new FiltersTreeTableModel(null)); @@ -556,7 +562,6 @@ public class FiltersTreeTable extends JTreeTable { //((BooleanEditor) editor).setRequestFocusEnabled(false); } else if (realValue.getClass() == Double.class || realValue.getClass() == Float.class) { editor = new FloatEditor(filterField.toString(), filterField.filter, filterField.field, -1, realValue.getClass()); - //editor = new NumberEditor(filterField.toString(), filterField.filter, filterField.field, -1, realValue.getClass(), filterField.field.getAnnotation(SWFType.class)); if ("angle".equals(filterField.field.getName())) { ((FloatEditor) editor).setValueNormalizer(new ValueNormalizer() { @Override @@ -570,6 +575,22 @@ public class FiltersTreeTable extends JTreeTable { } }); } + if ("blurX".equals(filterField.field.getName())) { + try { + ((FloatEditor) editor).setLinkedField(filterField.filter.getClass().getField("blurY")); + ((FloatEditor) editor).setLinkEnabled(filtersTable.linkEnabled); + } catch (NoSuchFieldException | SecurityException ex) { + //ignore + } + } + if ("blurY".equals(filterField.field.getName())) { + try { + ((FloatEditor) editor).setLinkedField(filterField.filter.getClass().getField("blurX")); + ((FloatEditor) editor).setLinkEnabled(filtersTable.linkEnabled); + } catch (NoSuchFieldException | SecurityException ex) { + //ignore + } + } } else if (realValue.getClass() == int.class || realValue.getClass() == Integer.class) { editor = new NumberEditor(filterField.toString(), filterField.filter, filterField.field, -1, realValue.getClass(), filterField.field.getAnnotation(SWFType.class)); } else if (realValue.getClass() == RGBA.class) { @@ -578,12 +599,18 @@ public class FiltersTreeTable extends JTreeTable { if (editor != null) { - /*editor.addChangeListener(new ChangeListener() { + editor.addChangeListener(new ChangeListener() { @Override public void change(PropertyEditor editor) { - editor.save(); } - });*/ + + @Override + public void linkChanged(boolean newValue) { + filtersTable.linkEnabled = newValue; + stopCellEditing(); + filtersTable.repaint(); + } + }); if (table instanceof JTreeTable) { JTreeTable treeTable = (JTreeTable) table; if (treeTable.isRowSelected(row)) { @@ -672,7 +699,7 @@ public class FiltersTreeTable extends JTreeTable { private static class FiltersTableCellRenderer extends DefaultTableCellRenderer { JLabel label = new JLabel(); - + @Override public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) { label.setText(value.toString()); @@ -740,6 +767,17 @@ public class FiltersTreeTable extends JTreeTable { component = new ColorEditor(filterValue.filterField.toString(), filterValue.filterField.filter, filterValue.filterField.field, -1, RGBA.class); component.setToolTipText(AppStrings.translate("button.selectcolor.hint")); } + if ("blurX".equals(filterValue.filterField.field.getName()) + || "blurY".equals(filterValue.filterField.field.getName())) { + JPanel panel = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, 0)); + JLabel blurLabel = new JLabel(label.getText()); + panel.add(blurLabel); + blurLabel.setPreferredSize(new Dimension(50, blurLabel.getPreferredSize().height)); + blurLabel.setMaximumSize(blurLabel.getPreferredSize()); + JLabel linkLabel = new JLabel(View.getIcon(((FiltersTreeTable) table).linkEnabled ? "link16" : "linkbreak16")); + panel.add(linkLabel); + component = panel; + } } } @@ -953,6 +991,7 @@ public class FiltersTreeTable extends JTreeTable { DefaultMutableTreeNode filterNode = new DefaultMutableTreeNode(new FilterName(filter)); root.insert(filterNode, index); Field[] fields = filter.getClass().getFields(); + LinkedDefaultMutableTreeNode lastLinkedNode = null; for (Field field : fields) { if ("id".equals(field.getName())) { continue; @@ -996,7 +1035,19 @@ public class FiltersTreeTable extends JTreeTable { continue; } FilterField filterField = new FilterField(filter, field); - DefaultMutableTreeNode fieldNode = new DefaultMutableTreeNode(filterField); + DefaultMutableTreeNode fieldNode; + if ("blurX".equals(field.getName())) { + LinkedDefaultMutableTreeNode linkedNode = new LinkedDefaultMutableTreeNode(filterField); + fieldNode = linkedNode; + lastLinkedNode = linkedNode; + } else if ("blurY".equals(field.getName())) { + LinkedDefaultMutableTreeNode linkedNode = new LinkedDefaultMutableTreeNode(filterField); + fieldNode = linkedNode; + linkedNode.setLinkedNode(lastLinkedNode); + lastLinkedNode.setLinkedNode(linkedNode); + } else { + fieldNode = new DefaultMutableTreeNode(filterField); + } filterNode.add(fieldNode); } this.filters.add(index, filter); @@ -1130,5 +1181,23 @@ public class FiltersTreeTable extends JTreeTable { public void removeTreeModelListener(TreeModelListener l) { listeners.remove(l); } - } + } + + private static class LinkedDefaultMutableTreeNode extends DefaultMutableTreeNode { + private LinkedDefaultMutableTreeNode linkedNode; + + public LinkedDefaultMutableTreeNode(Object userObject) { + super(userObject); + } + + + + public void setLinkedNode(LinkedDefaultMutableTreeNode linkedNode) { + this.linkedNode = linkedNode; + } + + public LinkedDefaultMutableTreeNode getLinkedNode() { + return linkedNode; + } + } } diff --git a/src/com/jpexs/decompiler/flash/gui/generictageditors/ChangeListener.java b/src/com/jpexs/decompiler/flash/gui/generictageditors/ChangeListener.java index 5ec0e471a..da5e7d24f 100644 --- a/src/com/jpexs/decompiler/flash/gui/generictageditors/ChangeListener.java +++ b/src/com/jpexs/decompiler/flash/gui/generictageditors/ChangeListener.java @@ -21,8 +21,9 @@ import com.jpexs.decompiler.flash.easygui.properties.PropertyEditor; /** * @author JPEXS */ -@FunctionalInterface public interface ChangeListener { public void change(PropertyEditor editor); + + public void linkChanged(boolean newValue); } diff --git a/src/com/jpexs/decompiler/flash/gui/generictageditors/FloatEditor.java b/src/com/jpexs/decompiler/flash/gui/generictageditors/FloatEditor.java index b38836f09..92e967332 100644 --- a/src/com/jpexs/decompiler/flash/gui/generictageditors/FloatEditor.java +++ b/src/com/jpexs/decompiler/flash/gui/generictageditors/FloatEditor.java @@ -18,20 +18,30 @@ package com.jpexs.decompiler.flash.gui.generictageditors; import com.jpexs.decompiler.flash.easygui.properties.PropertyEditor; import com.jpexs.decompiler.flash.ecma.EcmaScript; +import com.jpexs.decompiler.flash.gui.View; import com.jpexs.helpers.Helper; import com.jpexs.helpers.ReflectionTools; +import java.awt.BorderLayout; import java.awt.Component; import java.awt.Dimension; +import java.awt.FlowLayout; import java.awt.event.FocusAdapter; import java.awt.event.FocusEvent; +import java.awt.event.MouseAdapter; +import java.awt.event.MouseEvent; import java.lang.reflect.Field; +import java.util.ArrayList; +import java.util.List; import java.util.Objects; +import javax.swing.BorderFactory; +import javax.swing.JLabel; +import javax.swing.JPanel; import javax.swing.JTextField; /** * @author JPEXS */ -public class FloatEditor extends JTextField implements GenericTagEditor { +public class FloatEditor extends JPanel implements GenericTagEditor { private final Object obj; @@ -42,13 +52,17 @@ public class FloatEditor extends JTextField implements GenericTagEditor { private final Class type; private String fieldName; - + private ValueNormalizer normalizer; - - @Override - public boolean getScrollableTracksViewportWidth() { - return true; - } + + private Field linkedField; + + private boolean linkEnabled; + + private List listeners = new ArrayList<>(); + + private JTextField textField; + private JLabel linkLabel; @Override public Dimension getPreferredSize() { @@ -73,7 +87,48 @@ public class FloatEditor extends JTextField implements GenericTagEditor { this.index = index; this.type = type; this.fieldName = fieldName; - reset(); + + addFocusListener(new FocusAdapter() { + @Override + public void focusLost(FocusEvent e) { + for (ChangeListener l : listeners) { + l.change(FloatEditor.this); + } + } + }); + + textField = new JTextField() { + @Override + public boolean getScrollableTracksViewportWidth() { + return true; + } + }; + + textField.setBorder(BorderFactory.createEmptyBorder()); + + setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); + textField.setPreferredSize(new Dimension(50, textField.getPreferredSize().height)); + textField.setMaximumSize(textField.getPreferredSize()); + + add(textField); + linkLabel = new JLabel(View.getIcon("link16")); + add(linkLabel); + + linkLabel.addMouseListener(new MouseAdapter() { + @Override + public void mouseReleased(MouseEvent e) { + boolean newValue = !linkEnabled; + setLinkEnabled(newValue); + for (ChangeListener l : listeners) { + l.linkChanged(newValue); + } + repaint(); + } + }); + + linkLabel.setVisible(false); + + reset(); } @Override @@ -83,7 +138,7 @@ public class FloatEditor extends JTextField implements GenericTagEditor { if (normalizer != null) { val = normalizer.toViewValue(val); } - setText(val == null ? "" : EcmaScript.toString(val)); + textField.setText(val == null ? "" : EcmaScript.toString(val)); } catch (IllegalArgumentException | IllegalAccessException ex) { // ignore } @@ -97,20 +152,38 @@ public class FloatEditor extends JTextField implements GenericTagEditor { oldFieldValue = normalizer.toViewValue(oldFieldValue); } String oldValue = (String) EcmaScript.toString(oldFieldValue); - String newValue = getText(); + String newValue = textField.getText(); if (Objects.equals(oldValue, newValue)) { return false; } Object val; if (type.equals(double.class) || type.equals(Double.class)) { - val = Double.valueOf(getText()); + val = Double.valueOf(textField.getText()); } else { - val = Float.valueOf(getText()); + val = Float.valueOf(textField.getText()); } if (normalizer != null) { val = normalizer.toFieldValue(val); } + ReflectionTools.setValue(obj, field, index, val); + + if (linkedField != null && linkEnabled) { + Object linkedFieldValue = ReflectionTools.getValue(obj, linkedField); + Object newLinkefFieldValue = null; + if (oldFieldValue instanceof Double) { + Double v = (Double) oldFieldValue; + Double v2 = (Double) val; + Double vL = (Double) linkedFieldValue; + newLinkefFieldValue = v == 0.0 ? v2 : v2 * vL / v; + } else if (oldFieldValue instanceof Float) { + Float v = (Float) oldFieldValue; + Float v2 = (Float) val; + Float vL = (Float) linkedFieldValue; + newLinkefFieldValue = v == 0f ? v2 : v2 * vL / v; + } + ReflectionTools.setValue(obj, linkedField, -1, newLinkefFieldValue); + } } catch (IllegalArgumentException | IllegalAccessException ex) { // ignore } @@ -119,20 +192,12 @@ public class FloatEditor extends JTextField implements GenericTagEditor { @Override public void addChangeListener(final ChangeListener l) { - final PropertyEditor t = this; - addFocusListener(new FocusAdapter() { - - @Override - public void focusLost(FocusEvent e) { - l.change(t); - } - - }); + listeners.add(l); } @Override public Object getChangedValue() { - return getText(); + return textField.getText(); } @Override @@ -163,10 +228,24 @@ public class FloatEditor extends JTextField implements GenericTagEditor { public Object getObject() { return obj; } - + @Override public void setValueNormalizer(ValueNormalizer normalizer) { this.normalizer = normalizer; reset(); - } + } + + public void setLinkedField(Field linkedField) { + this.linkedField = linkedField; + linkLabel.setVisible(true); + } + + public void setLinkEnabled(boolean enabled) { + this.linkEnabled = enabled; + linkLabel.setIcon(View.getIcon(enabled ? "link16" : "linkbreak16")); + } + + public boolean isLinkEnabled() { + return linkEnabled; + } } diff --git a/src/com/jpexs/decompiler/flash/gui/generictageditors/NumberEditor.java b/src/com/jpexs/decompiler/flash/gui/generictageditors/NumberEditor.java index 984703449..1bc3eaa26 100644 --- a/src/com/jpexs/decompiler/flash/gui/generictageditors/NumberEditor.java +++ b/src/com/jpexs/decompiler/flash/gui/generictageditors/NumberEditor.java @@ -30,7 +30,6 @@ import javax.swing.JPanel; import javax.swing.JSpinner; import javax.swing.SpinnerModel; import javax.swing.SpinnerNumberModel; -import javax.swing.event.ChangeEvent; import javax.swing.text.DefaultFormatter; /** diff --git a/src/com/jpexs/decompiler/flash/gui/graphics/linkbreak16.png b/src/com/jpexs/decompiler/flash/gui/graphics/linkbreak16.png new file mode 100644 index 0000000000000000000000000000000000000000..57bafcfc30fc38bc4275e03d85c0b01f02daba6e GIT binary patch literal 804 zcmV+<1Ka$GP)IyWavh={P~!Zwc2GHJGGq_Q%!{#Zrxj0NAkHDaOUCaNAcsr~^#(;43h#lXm> znYl;BC30Nf*uc`V3Y5uY_wq#rs5cCw=$aUJSHQ!L2(N}mKBX0vOlEnx0=IP`N~Kc$ ztp5dG6^IxBmLGtL%KE~`8$ra`L=+TyU}0eqoDK&F3kt_+)yl+_Ip67YgWKg|f>=0v z)`%k~5UT^3K&sBp_aeHSPH1Uu14X$UtV>Ifb14r~Q_sQRpdJpfk7&Jq-0kvsyPMhG z*`=}BY?yjJ9S8IV?Cu-D?A*&(^H4QRo5RT!0%&25I8T^A)%W)Hjn3`|T)+M%{8@HF$UWh1J?5Vdhe z27pjRGAnLZF;odeV$8_MMBPgR3JN4U0Cx}iQ%p9Oq0vK+=KTBu*nh7-AS|dG>iJq@JC=jy*t%+kfPFzF9UbjO;_H&}=$IJL>vRxtJhq3) zu4MnESn!>X#*}}?kHzEhv`;nNkdTl7`-9oFiAl-u&S-?V`1n@}si>Io3O=wiY{{d1 ze*lVfwW+zaZfxvB8Z$ifgdGhHeO+_E`U-vgN_4iC$jQTbpHKex=;$6$+cKdh#LxEA i8|*i1b9({&5nuopO>d#a9tOPt0000