Fixed performance issue with tables
authorFabian Stemmler <stemmler@in.tum.de>
Mon, 9 Sep 2019 15:29:19 +0000 (17:29 +0200)
committerFabian Stemmler <stemmler@in.tum.de>
Mon, 9 Sep 2019 15:29:19 +0000 (17:29 +0200)
net.mograsim.machine/src/net/mograsim/machine/mi/parameters/MnemonicFamily.java
net.mograsim.plugin.core/src/net/mograsim/plugin/tables/LazyTableViewer.java [new file with mode: 0644]
net.mograsim.plugin.core/src/net/mograsim/plugin/tables/memory/MemoryView.java
net.mograsim.plugin.core/src/net/mograsim/plugin/tables/mi/InstructionView.java
net.mograsim.plugin.core/src/net/mograsim/plugin/tables/mi/IntegerEditingSupport.java
net.mograsim.plugin.core/src/net/mograsim/plugin/tables/mi/MnemonicEditingSupport.java

index a513b60..54c275b 100644 (file)
@@ -11,14 +11,67 @@ public class MnemonicFamily implements ParameterClassification
 {
        private final Mnemonic[] values;
        private final String[] stringValues;
-       private final Map<String, Mnemonic> byText;
-       private final int vectorLength;
+       private Map<String, Mnemonic> byText;
+       private int vectorLength;
+       
+       public MnemonicFamily(String... names)
+       {
+               this.values = new Mnemonic[names.length];
+               this.stringValues = new String[names.length];
+               BitVector[] values = new BitVector[names.length];
+               int bits = (int) Math.ceil(Math.log(names.length));
+               for(int i = 0; i < names.length; i++)
+               {
+                       values[i] = BitVector.from(i, bits);
+               }
+               
+               setup(names, values);
+       }
+       
+       public MnemonicFamily(String[] names, long[] values, int bits)
+       {
+               if(names.length != values.length)
+                       throw new IllegalArgumentException();
+               this.values = new Mnemonic[values.length];
+               this.stringValues = new String[values.length];
+               BitVector[] vectors = new BitVector[values.length];
+               
+               for(int i = 0; i < vectors.length; i++)
+               {
+                       vectors[i] = BitVector.from(values[i], bits);
+               }
+               
+               setup(names, vectors);
+       }
+       
+       public MnemonicFamily(String[] names, BitVector[] values)
+       {
+               if(names.length != values.length)
+                       throw new IllegalArgumentException();
+               this.values = new Mnemonic[values.length];
+               this.stringValues = new String[values.length];
+               
+               setup(names, values);
+       }
        
        public MnemonicFamily(MnemonicPair... values)
        {
                this.values = new Mnemonic[values.length];
                this.stringValues = new String[values.length];
                
+               setup(values);
+       }
+       
+       private void setup(String[] names, BitVector[] values)
+       {
+               MnemonicPair[] mnemonics = new MnemonicPair[values.length];
+               for(int i = 0; i < values.length; i++)
+                       mnemonics[i] = new MnemonicPair(names[i], values[i]);
+               setup(mnemonics);
+       }
+       
+       private void setup(MnemonicPair[] values)
+       {
                for(int i = 0; i < values.length; i++)
                {
                        this.values[i] = createMnemonic(values[i], i);
@@ -37,7 +90,7 @@ public class MnemonicFamily implements ParameterClassification
                if(values.length != byText.keySet().size())
                        throw new IllegalArgumentException("MnemonicFamily contains multiple Mnemonics with the same name!");
        }
-       
+
        private Mnemonic createMnemonic(MnemonicPair mnemonicPair, int ordinal)
        {
                return new Mnemonic(mnemonicPair.name, mnemonicPair.value, this, ordinal);
diff --git a/net.mograsim.plugin.core/src/net/mograsim/plugin/tables/LazyTableViewer.java b/net.mograsim.plugin.core/src/net/mograsim/plugin/tables/LazyTableViewer.java
new file mode 100644 (file)
index 0000000..e00742f
--- /dev/null
@@ -0,0 +1,50 @@
+package net.mograsim.plugin.tables;
+
+import org.eclipse.jface.viewers.IContentProvider;
+import org.eclipse.jface.viewers.ILazyContentProvider;
+import org.eclipse.jface.viewers.TableViewer;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Table;
+
+public class LazyTableViewer extends TableViewer
+{
+
+       public LazyTableViewer(Composite parent, int style)
+       {
+               super(parent, style | SWT.VIRTUAL);
+       }
+
+       public LazyTableViewer(Composite parent)
+       {
+               super(parent);
+       }
+
+       public LazyTableViewer(Table table)
+       {
+               super(table);
+       }
+
+       @Override
+       public void setContentProvider(IContentProvider provider)
+       {
+               if (!(provider instanceof ILazyContentProvider))
+                       throw new IllegalArgumentException("Content provider must be an ILazyContentProvider");
+               super.setContentProvider(provider);
+       }
+
+       public void refreshLazy()
+       {
+               Table t = getTable();
+               ILazyContentProvider provider = (ILazyContentProvider) getContentProvider();
+               doClearAll();
+               int startIndex = t.getTopIndex();
+               int numRows = t.getBounds().height / t.getItemHeight();
+               int endIndex = startIndex + numRows + 5;
+
+               for (int i = startIndex; i < endIndex; i++)
+               {
+                       provider.updateElement(i);
+               }
+       }
+}
index 3227e9f..356428b 100644 (file)
@@ -3,7 +3,6 @@ package net.mograsim.plugin.tables.memory;
 import java.math.BigInteger;
 import java.util.Optional;
 
-import org.eclipse.jface.viewers.TableViewer;
 import org.eclipse.jface.viewers.TableViewerColumn;
 import org.eclipse.swt.SWT;
 import org.eclipse.swt.events.VerifyListener;
@@ -25,12 +24,13 @@ import net.mograsim.plugin.MachineContext.ContextObserver;
 import net.mograsim.plugin.asm.AsmNumberUtil;
 import net.mograsim.plugin.tables.AddressLabelProvider;
 import net.mograsim.plugin.tables.DisplaySettings;
+import net.mograsim.plugin.tables.LazyTableViewer;
 import net.mograsim.plugin.tables.NumberColumnLabelProvider;
 import net.mograsim.plugin.tables.RadixSelector;
 
 public class MemoryView extends ViewPart implements ContextObserver
 {
-       private TableViewer viewer;
+       private LazyTableViewer viewer;
        private MemoryTableContentProvider provider;
        private DisplaySettings displaySettings;
 
@@ -46,7 +46,7 @@ public class MemoryView extends ViewPart implements ContextObserver
                createHeader(parent);
                createViewer(parent);
 
-               displaySettings.addObserver(() -> viewer.refresh());
+               displaySettings.addObserver(() -> viewer.refreshLazy());
 
                setupContextBinding();
        }
@@ -97,7 +97,7 @@ public class MemoryView extends ViewPart implements ContextObserver
 
        private void createViewer(Composite parent)
        {
-               viewer = new TableViewer(parent, SWT.MULTI | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION | SWT.BORDER | SWT.VIRTUAL);
+               viewer = new LazyTableViewer(parent, SWT.MULTI | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION | SWT.BORDER | SWT.VIRTUAL);
                createColumns();
                Table table = viewer.getTable();
                table.setHeaderVisible(true);
index d864491..35b6933 100644 (file)
@@ -6,7 +6,6 @@ import java.util.Optional;
 
 import org.eclipse.jface.viewers.ColumnLabelProvider;
 import org.eclipse.jface.viewers.EditingSupport;
-import org.eclipse.jface.viewers.TableViewer;
 import org.eclipse.jface.viewers.TableViewerColumn;
 import org.eclipse.swt.SWT;
 import org.eclipse.swt.layout.GridData;
@@ -27,6 +26,7 @@ import net.mograsim.plugin.MachineContext;
 import net.mograsim.plugin.MachineContext.ContextObserver;
 import net.mograsim.plugin.tables.AddressLabelProvider;
 import net.mograsim.plugin.tables.DisplaySettings;
+import net.mograsim.plugin.tables.LazyTableViewer;
 import net.mograsim.plugin.tables.RadixSelector;
 import net.mograsim.plugin.util.DropDownMenu;
 import net.mograsim.plugin.util.DropDownMenu.DropDownEntry;
@@ -34,7 +34,7 @@ import net.mograsim.plugin.util.DropDownMenu.DropDownEntry;
 public class InstructionView extends ViewPart implements ContextObserver
 {
        private String saveLoc = null;
-       private TableViewer viewer;
+       private LazyTableViewer viewer;
        private TableViewerColumn[] columns = new TableViewerColumn[0];
        private MicroInstructionDefinition miDef;
        private MicroInstructionMemory memory;
@@ -53,7 +53,7 @@ public class InstructionView extends ViewPart implements ContextObserver
                new RadixSelector(parent, displaySettings);
 
                parent.setLayout(layout);
-               viewer = new TableViewer(parent, SWT.MULTI | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION | SWT.BORDER | SWT.VIRTUAL);
+               viewer = new LazyTableViewer(parent, SWT.MULTI | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION | SWT.BORDER | SWT.VIRTUAL);
 
                Table table = viewer.getTable();
                table.setHeaderVisible(true);
@@ -66,7 +66,7 @@ public class InstructionView extends ViewPart implements ContextObserver
                viewerData.horizontalSpan = 3;
                viewer.getTable().setLayoutData(viewerData);
 
-               displaySettings.addObserver(() -> viewer.refresh());
+               displaySettings.addObserver(() -> viewer.refreshLazy());
                MachineContext.getInstance().registerObserver(this);
        }
 
@@ -158,7 +158,7 @@ public class InstructionView extends ViewPart implements ContextObserver
                        provider = new IntegerColumnLabelProvider(displaySettings, index);
                        break;
                case MNEMONIC:
-                       support = new MnemonicEditingSupport(viewer, miDef, index);
+                       support = new MnemonicEditingSupport(viewer, miDef, index, this.provider);
                        provider = new ParameterLabelProvider(index);
                        break;
                default:
index c8f7e08..d3b48ce 100644 (file)
@@ -14,7 +14,6 @@ public class IntegerEditingSupport extends NumberCellEditingSupport
 {
        private IntegerClassification classification;
        private int index;
-       private TableViewer viewer;
        private InstructionTableContentProvider provider;
 
        public IntegerEditingSupport(TableViewer viewer, MicroInstructionDefinition miDef, int index, DisplaySettings displaySettings,
@@ -23,7 +22,6 @@ public class IntegerEditingSupport extends NumberCellEditingSupport
                super(viewer, displaySettings);
                classification = (IntegerClassification) miDef.getParameterClassifications()[index];
                this.index = index;
-               this.viewer = viewer;
                this.provider = provider;
        }
 
index 910fefa..765e434 100644 (file)
@@ -14,17 +14,18 @@ public class MnemonicEditingSupport extends EditingSupport
 {
        private final ComboBoxCellEditor editor;
        private final MnemonicFamily family;
-       private final TableViewer viewer;
        private final int index;
+       private InstructionTableContentProvider provider;
 
-       public MnemonicEditingSupport(TableViewer viewer, MicroInstructionDefinition definition, int index)
+       public MnemonicEditingSupport(TableViewer viewer, MicroInstructionDefinition definition, int index,
+                       InstructionTableContentProvider provider)
        {
                super(viewer);
-               this.viewer = viewer;
                family = (MnemonicFamily) definition.getParameterClassifications()[index];
                editor = new ComboBoxCellEditor(viewer.getTable(), family.getStringValues(), SWT.READ_ONLY);
                this.index = index;
                editor.setValidator(new MnemonicCellEditorValidator(family));
+               this.provider = provider;
        }
 
        @Override
@@ -48,8 +49,9 @@ public class MnemonicEditingSupport extends EditingSupport
        @Override
        protected void setValue(Object element, Object value)
        {
-               ((InstructionTableRow) element).data.setParameter(index, family.get((Integer) value));
-               viewer.update(element, null);
+               InstructionTableRow row = ((InstructionTableRow) element);
+               row.data.setParameter(index, family.get((Integer) value));
+               provider.update(row.address);
        }
 
 }