2 * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3 * Copyright (C) 2009 - DIGITEO - Vincent COUVERT
4 * Copyright (C) 2009 - DIGITEO - Clement DAVID
5 * Copyright (C) 2011-2015 - Scilab Enterprises - Clement DAVID
7 * Copyright (C) 2012 - 2016 - Scilab Enterprises
9 * This file is hereby licensed under the terms of the GNU GPL v2.0,
10 * pursuant to article 5.3.4 of the CeCILL v.2.1.
11 * This file was originally licensed under the terms of the CeCILL v2.1,
12 * and continues to be available under such terms.
13 * For more information, see the COPYING file which you should have received
14 * along with this program.
18 package org.scilab.modules.xcos.block.actions;
20 import java.awt.event.ActionEvent;
21 import java.awt.event.ActionListener;
22 import java.util.Arrays;
23 import java.util.Iterator;
24 import java.util.List;
27 import java.util.logging.Level;
28 import java.util.logging.Logger;
30 import javax.swing.BorderFactory;
31 import javax.swing.DefaultCellEditor;
32 import javax.swing.JComboBox;
33 import javax.swing.JFrame;
34 import javax.swing.WindowConstants;
35 import javax.swing.event.ChangeEvent;
36 import javax.swing.event.ChangeListener;
37 import javax.swing.event.ListSelectionEvent;
38 import javax.swing.event.ListSelectionListener;
39 import javax.swing.event.TableModelEvent;
40 import javax.swing.event.TableModelListener;
41 import javax.swing.table.DefaultTableModel;
42 import javax.swing.table.TableColumn;
44 import org.scilab.modules.graph.ScilabComponent;
45 import org.scilab.modules.graph.ScilabGraph;
46 import org.scilab.modules.graph.actions.base.DefaultAction;
47 import org.scilab.modules.gui.menuitem.MenuItem;
48 import org.scilab.modules.types.ScilabDouble;
49 import org.scilab.modules.types.ScilabList;
50 import org.scilab.modules.types.ScilabString;
51 import org.scilab.modules.types.ScilabType;
52 import org.scilab.modules.xcos.JavaController;
53 import org.scilab.modules.xcos.ObjectProperties;
54 import org.scilab.modules.xcos.VectorOfDouble;
55 import org.scilab.modules.xcos.block.SuperBlock;
56 import org.scilab.modules.xcos.graph.XcosDiagram;
57 import org.scilab.modules.xcos.io.ScilabTypeCoder;
58 import org.scilab.modules.xcos.utils.XcosMessages;
61 * Customize the mask of the {@link SuperBlock}.
63 @SuppressWarnings(value = { "serial" })
64 public final class SuperblockMaskCustomizeAction extends DefaultAction {
65 /** Name of the action */
66 public static final String NAME = XcosMessages.CUSTOMIZE;
67 /** Icon name of the action */
68 public static final String SMALL_ICON = "";
69 /** Mnemonic key of the action */
70 public static final int MNEMONIC_KEY = 0;
71 /** Accelerator key for the action */
72 public static final int ACCELERATOR_KEY = 0;
74 private static final String TERMINATE_EDIT_ON_FOCUS_LOST = "terminateEditOnFocusLost";
80 * the associated graph
82 public SuperblockMaskCustomizeAction(ScilabGraph scilabGraph) {
87 * Create the menu associated with this action
90 * the associated graph
91 * @return the newly created menu
93 public static MenuItem createMenu(ScilabGraph scilabGraph) {
94 return createMenu(scilabGraph, SuperblockMaskCustomizeAction.class);
98 * Function to be performed by this action.
101 * The associated event
104 public void actionPerformed(ActionEvent e) {
105 final XcosDiagram graph = (XcosDiagram) getGraph(e);
107 // action disabled when the cell is edited
108 final ScilabComponent comp = ((ScilabComponent) graph.getAsComponent());
109 if (comp.isEditing()) {
113 SuperBlock block = (SuperBlock) graph.getSelectionCell();
115 CustomizeFrame frame = new CustomizeFrame(graph);
116 CustomizeFrame.CustomizeFrameModel model = frame.getController().getModel();
117 model.setBlock(block);
118 model.importFromBlock();
119 frame.setVisible(true);
123 * Frame used to customize fields and variables default values. DAC: this
124 * class is tightly coupled to Swing
126 // CSOFF: ClassDataAbstractionCoupling
127 @SuppressWarnings(value = { "serial" })
128 private static class CustomizeFrame extends JFrame {
130 private final CustomizeFrameControler controler;
132 private javax.swing.JPanel buttonBlob;
133 private javax.swing.JButton cancelButton;
134 private javax.swing.JPanel customizeMainPanel;
135 private javax.swing.JScrollPane customizeScrollPane;
136 private javax.swing.JTabbedPane tabbedPane;
137 private javax.swing.JTable defaultValueTable;
138 private javax.swing.JPanel defaultValues;
139 private javax.swing.JScrollPane defaultValuesScrollPane;
140 private javax.swing.JButton delete;
141 private javax.swing.JButton insert;
142 private javax.swing.JPanel mainPanel;
143 private javax.swing.JButton moveDown;
144 private javax.swing.JButton moveUp;
145 private javax.swing.JButton okButton;
146 private javax.swing.JLabel rowLabel;
147 private javax.swing.JPanel rowManagement;
148 private javax.swing.JSpinner rowSpinner;
149 private javax.swing.JPanel tableManagement;
150 private javax.swing.JPanel validationPanel;
151 private javax.swing.JTable varCustomizeTable;
152 private javax.swing.JPanel varSettings;
158 * the container diagram
160 public CustomizeFrame(XcosDiagram diagram) {
161 setTitle(XcosMessages.MASK_TITLE);
162 setDefaultCloseOperation(WindowConstants.HIDE_ON_CLOSE);
163 controler = new CustomizeFrameControler(diagram);
168 * @return The associated controller
170 public CustomizeFrameControler getController() {
175 * Construct the UI and install the listeners.
178 // CSOFF: MagicNumber
179 private void initComponents() {
181 /* Construct the components */
182 mainPanel = new javax.swing.JPanel();
183 tabbedPane = new javax.swing.JTabbedPane();
184 varSettings = new javax.swing.JPanel();
185 customizeMainPanel = new javax.swing.JPanel();
186 customizeScrollPane = new javax.swing.JScrollPane();
187 varCustomizeTable = new javax.swing.JTable();
188 tableManagement = new javax.swing.JPanel();
189 insert = new javax.swing.JButton();
190 delete = new javax.swing.JButton();
191 buttonBlob = new javax.swing.JPanel();
192 moveUp = new javax.swing.JButton();
193 moveDown = new javax.swing.JButton();
194 rowManagement = new javax.swing.JPanel();
195 rowLabel = new javax.swing.JLabel();
196 rowSpinner = new javax.swing.JSpinner();
197 defaultValues = new javax.swing.JPanel();
198 defaultValuesScrollPane = new javax.swing.JScrollPane();
199 defaultValueTable = new javax.swing.JTable();
200 validationPanel = new javax.swing.JPanel();
201 okButton = new javax.swing.JButton();
202 cancelButton = new javax.swing.JButton();
204 setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
206 /* Initialize the components */
207 mainPanel.setLayout(new java.awt.BorderLayout());
208 mainPanel.setBorder(BorderFactory.createEmptyBorder(2, 2, 2, 2));
210 varSettings.setLayout(new javax.swing.BoxLayout(varSettings, javax.swing.BoxLayout.PAGE_AXIS));
212 varCustomizeTable.setModel(controler.getModel().customizeTableModel);
213 varCustomizeTable.putClientProperty(TERMINATE_EDIT_ON_FOCUS_LOST, Boolean.TRUE);
214 customizeScrollPane.setViewportView(varCustomizeTable);
215 // setAutoCreateRowSorter is java 1.6
216 // varCustomizeTable.setAutoCreateRowSorter(true);
218 /* Update the default value table */
219 varCustomizeTable.getModel().addTableModelListener(controler.updateValuesTable);
222 * Activate and deactivate insertion/deletion sensible
225 varCustomizeTable.getModel().addTableModelListener(controler.updateButtonsSensibleForModifications);
227 /* Activate and deactivate selection sensible buttons */
228 varCustomizeTable.getSelectionModel().addListSelectionListener(controler.updateButtonsSensibleForSelectionChange);
230 customizeMainPanel.add(customizeScrollPane);
232 tableManagement.setBorder(javax.swing.BorderFactory.createEmptyBorder(2, 2, 2, 2));
233 tableManagement.setLayout(new java.awt.GridLayout(5, 1));
235 /* Install the insert action */
236 insert.setMnemonic('n');
237 insert.setText(XcosMessages.MASK_INSERT);
238 tableManagement.add(insert);
239 insert.addActionListener(controler.insertActionListener);
241 /* Install the delete action */
242 delete.setMnemonic('l');
243 delete.setText(XcosMessages.MASK_DELETE);
244 tableManagement.add(delete);
245 delete.addActionListener(controler.deleteActionListener);
247 /* Install empty area */
248 tableManagement.add(buttonBlob);
250 /* Install the move-up action */
251 moveUp.setMnemonic('u');
252 moveUp.setText(XcosMessages.MASK_MOVEUP);
253 tableManagement.add(moveUp);
254 moveUp.addActionListener(controler.moveUpActionListener);
256 /* Install the move-down action */
257 moveDown.setMnemonic('w');
258 moveDown.setText(XcosMessages.MASK_MOVEDOWN);
259 tableManagement.add(moveDown);
260 moveDown.addActionListener(controler.moveDownActionListener);
262 /* add the table management */
263 customizeMainPanel.add(tableManagement);
265 varSettings.add(customizeMainPanel);
267 rowLabel.setText(XcosMessages.MASK_ROWS + " :");
268 rowManagement.add(rowLabel);
270 rowSpinner.setModel(new javax.swing.SpinnerNumberModel(1, 1, Integer.MAX_VALUE, 1));
271 rowSpinner.setEditor(new javax.swing.JSpinner.NumberEditor(rowSpinner, "######0"));
272 rowSpinner.setValue(varCustomizeTable.getModel().getRowCount());
273 rowManagement.add(rowSpinner);
274 rowSpinner.addChangeListener(controler.rowSpinnerChangeListener);
276 varSettings.add(rowManagement);
278 tabbedPane.addTab(XcosMessages.MASK_VARSETTINGS, varSettings);
280 defaultValueTable.setModel(controler.getModel().valuesTableModel);
281 defaultValueTable.putClientProperty(TERMINATE_EDIT_ON_FOCUS_LOST, Boolean.TRUE);
282 defaultValuesScrollPane.setViewportView(defaultValueTable);
284 // setAutoCreateRowSorter is java 1.6
285 // defaultValueTable.setAutoCreateRowSorter(false);
287 defaultValues.add(defaultValuesScrollPane);
289 tabbedPane.addTab(XcosMessages.MASK_DEFAULTVALUES, defaultValues);
291 mainPanel.add(tabbedPane, java.awt.BorderLayout.CENTER);
293 okButton.setText(XcosMessages.OK);
294 validationPanel.add(okButton);
295 okButton.addActionListener(controler.okActionListener);
297 cancelButton.setText(XcosMessages.CANCEL);
298 validationPanel.add(cancelButton);
299 cancelButton.addActionListener(controler.cancelActionListener);
301 mainPanel.add(validationPanel, java.awt.BorderLayout.PAGE_END);
306 cancelButton.requestFocusInWindow();
308 /* Evaluate the context and set up the variable name selection */
309 TableColumn vars = varCustomizeTable.getColumnModel().getColumn(0);
310 JComboBox validVars = new JComboBox();
311 final Set<String> keys = controler.context.keySet();
312 for (String key : keys) {
313 validVars.addItem(key);
315 vars.setCellEditor(new DefaultCellEditor(validVars));
317 insert.setEnabled(validVars.getModel().getSize() != 0);
324 * Implements the models used on the frame.
326 private class CustomizeFrameModel {
327 private SuperBlock block;
330 * Model used on the customize table.
332 private final DefaultTableModel customizeTableModel = new DefaultTableModel(new Object[][] { new Object[] { XcosMessages.MASK_WINTITLEVAR,
333 XcosMessages.MASK_WINTITLE, false
335 }, new String[] { XcosMessages.MASK_VARNAME, XcosMessages.MASK_VARDESC, XcosMessages.MASK_EDITABLE }) {
336 private final Class<?>[] types = new Class[] { java.lang.String.class, java.lang.String.class, java.lang.Boolean.class };
337 private final boolean[] canEdit = new boolean[] { true, true, true };
340 public Class<?> getColumnClass(int columnIndex) {
341 return types[columnIndex];
345 public boolean isCellEditable(int rowIndex, int columnIndex) {
347 return canEdit[columnIndex];
354 * Model used for the values table
356 private final DefaultTableModel valuesTableModel = new javax.swing.table.DefaultTableModel(new Object[][] { new Object[] {
357 XcosMessages.MASK_WINTITLE, ""
359 }, new String[] { XcosMessages.MASK_VARDESC, XcosMessages.MASK_VARVALUES }) {
360 private final Class<?>[] types = new Class[] { java.lang.String.class, java.lang.String.class };
361 private final boolean[] canEdit = new boolean[] { false, true };
364 public Class<?> getColumnClass(int columnIndex) {
365 return types[columnIndex];
369 public boolean isCellEditable(int rowIndex, int columnIndex) {
370 return canEdit[columnIndex];
375 * Default constructor
377 protected CustomizeFrameModel() {
378 // Does nothing as the fields are final.
383 * This model associated block.
385 public void setBlock(SuperBlock block) {
390 * @return This model associated block.
392 public SuperBlock getBlock() {
397 * Export the table models to the block exprs.
399 public void exportToBlock() {
400 /** Data vectors are typed when parsing */
401 final List<?> customModel = customizeTableModel.getDataVector();
402 final List<?> valuesModel = valuesTableModel.getDataVector();
404 /* We have one content that is not a variable : Window Title */
405 final int nbOfVar = valuesModel.size() - 1;
407 final String[][] values = new String[nbOfVar][1];
408 final String[][] varNames = new String[nbOfVar][1];
409 final String[][] varDesc = new String[nbOfVar + 1][1];
410 final ScilabList polFields = new ScilabList();
413 varDesc[0][0] = (String) ((List<?>) valuesModel.get(0)).get(1);
416 for (int i = 0; i < nbOfVar; i++) {
417 values[i][0] = (String) ((List<?>) valuesModel.get(i + 1)).get(1);
418 varNames[i][0] = (String) ((List<?>) customModel.get(i + 1)).get(0);
419 varDesc[i + 1][0] = (String) ((List<?>) customModel.get(i + 1)).get(1);
422 * reconstruct pol fields. The default types of the values.
424 * This field indicate the dimension of each entry (-1.0 is
425 * automatic). TODO: type the data there instead of using
428 polFields.add(new ScilabString("pol"));
429 polFields.add(new ScilabDouble(-1.0));
432 /* Construct fields from data */
433 final ScilabList exprs;
435 /* Set default values */
436 exprs = new ScilabList(Arrays.asList(
438 new ScilabList(Arrays.asList(new ScilabDouble(), new ScilabString(XcosMessages.MASK_DEFAULTWINDOWNAME),
439 new ScilabList(Arrays.asList(new ScilabDouble()))))));
442 exprs = new ScilabList(Arrays.asList(new ScilabString(values),
443 new ScilabList(Arrays.asList(new ScilabString(varNames), new ScilabString(varDesc), polFields))));
446 JavaController controller = new JavaController();
447 VectorOfDouble vec = new ScilabTypeCoder().var2vec(exprs);
448 controller.setObjectProperty(block.getUID(), block.getKind(), ObjectProperties.EXPRS, vec);
451 * Trace the exprs update.
453 if (Logger.getLogger(SuperblockMaskCustomizeAction.class.getName()).isLoggable(Level.FINEST)) {
454 Logger.getLogger(SuperblockMaskCustomizeAction.class.getName()).finest("exprs=" + exprs);
459 * Import the model exprs to the table models.
461 public void importFromBlock() {
463 ScilabString varNames;
464 ScilabString varDesc;
466 JavaController controller = new JavaController();
467 VectorOfDouble vec = new VectorOfDouble();
468 controller.getObjectProperty(block.getUID(), block.getKind(), ObjectProperties.EXPRS, vec);
469 ScilabType rawExprs = new ScilabTypeCoder().vec2var(vec);
471 // Xcos from Scilab 5.2.0 version
472 // so set default values
473 if (rawExprs instanceof ScilabDouble) {
474 rawExprs = new ScilabList(Arrays.asList(
476 new ScilabList(Arrays.asList(new ScilabDouble(), new ScilabString(XcosMessages.MASK_DEFAULTWINDOWNAME),
477 new ScilabList(Arrays.asList(new ScilabDouble()))))));
479 DefaultTableModel customModel = customizeTableModel;
480 DefaultTableModel valuesModel = valuesTableModel;
483 * rawExprs have to be typed as
484 * list([],list([],"Set block parameters",list())) or as
485 * list([""],list([""],"Set block parameters",list([""])))
487 assert rawExprs instanceof ScilabList;
488 ScilabList exprs = (ScilabList) rawExprs;
490 assert (exprs.get(0) instanceof ScilabDouble) || (exprs.get(0) instanceof ScilabString);
491 if (exprs.get(0) instanceof ScilabDouble) {
492 values = new ScilabString("");
493 } else { /* exprs.get(0) instanceof ScilabString) */
494 values = (ScilabString) exprs.get(0);
497 assert exprs.get(1) instanceof ScilabList;
498 ScilabList lvalues = (ScilabList) exprs.get(1);
500 assert (lvalues.get(0) instanceof ScilabDouble) || (lvalues.get(0) instanceof ScilabString);
501 if (lvalues.get(0) instanceof ScilabDouble) {
502 varNames = new ScilabString();
503 } else { /* exprs.get(0) instanceof ScilabString) */
504 varNames = (ScilabString) lvalues.get(0);
507 assert lvalues.get(1) instanceof ScilabString;
508 varDesc = (ScilabString) lvalues.get(1);
511 * Check if the data are stored as columns or as row.
513 if (varDesc.getHeight() >= varDesc.getWidth()) {
516 valuesModel.setValueAt(varDesc.getData()[0][0], 0, 1);
518 /* Loop all over the data */
519 for (int i = 1; i < varDesc.getHeight(); i++) {
520 customModel.addRow(new Object[] { varNames.getData()[i - 1][0], varDesc.getData()[i][0], true });
521 valuesModel.setValueAt(values.getData()[i - 1][0], i, 1);
525 valuesModel.setValueAt(varDesc.getData()[0][0], 0, 1);
527 /* Loop all over the data */
528 for (int i = 1; i < varDesc.getHeight(); i++) {
529 customModel.addRow(new Object[] { varNames.getData()[0][i - 1], varDesc.getData()[0][i], true });
530 valuesModel.setValueAt(values.getData()[0][i - 1], i, 1);
537 * Implement the action listeners for the frame
539 private class CustomizeFrameControler {
540 private final CustomizeFrameModel model;
542 private final ActionListener cancelActionListener = new ActionListener() {
544 public void actionPerformed(ActionEvent e) {
549 private final ActionListener okActionListener = new ActionListener() {
551 public void actionPerformed(ActionEvent arg0) {
552 model.exportToBlock();
557 private final ChangeListener rowSpinnerChangeListener = new ChangeListener() {
559 public void stateChanged(ChangeEvent e) {
560 int rowCount = varCustomizeTable.getRowCount();
561 int value = (Integer) rowSpinner.getModel().getValue();
563 for (; rowCount < value; rowCount++) {
564 insertActionListener.actionPerformed(new ActionEvent(this, -1, ACTION_COMMAND_KEY));
567 for (; rowCount > value; rowCount--) {
568 deleteActionListener.actionPerformed(new ActionEvent(this, -1, ACTION_COMMAND_KEY));
573 private final ActionListener moveDownActionListener = new ActionListener() {
575 public void actionPerformed(ActionEvent arg0) {
576 int selectedRow = varCustomizeTable.getSelectedRow();
578 swapTableRow(model.customizeTableModel, selectedRow, selectedRow + 1);
579 swapTableRow(model.valuesTableModel, selectedRow, selectedRow + 1);
581 /* Keep the same row selected */
582 varCustomizeTable.changeSelection(selectedRow + 1, varCustomizeTable.getSelectedColumn(), false, false);
586 private final ActionListener moveUpActionListener = new ActionListener() {
588 public void actionPerformed(ActionEvent arg0) {
589 int selectedRow = varCustomizeTable.getSelectedRow();
591 swapTableRow(model.customizeTableModel, selectedRow, selectedRow - 1);
592 swapTableRow(model.valuesTableModel, selectedRow, selectedRow - 1);
594 /* Keep the same row selected */
595 varCustomizeTable.changeSelection(selectedRow - 1, varCustomizeTable.getSelectedColumn(), false, false);
599 private final ActionListener deleteActionListener = new ActionListener() {
601 public void actionPerformed(ActionEvent e) {
602 int selected = varCustomizeTable.getSelectedRow();
603 int nbOfRows = varCustomizeTable.getRowCount();
606 model.customizeTableModel.removeRow(selected);
607 varCustomizeTable.changeSelection(selected - 1, 1, false, false);
608 } else if (nbOfRows > 1) {
609 model.customizeTableModel.removeRow(nbOfRows - 1);
610 varCustomizeTable.changeSelection(nbOfRows - 2, 1, false, false);
615 private final ActionListener insertActionListener = new ActionListener() {
617 public void actionPerformed(ActionEvent e) {
618 final String nextKey;
619 if (keyIterator.hasNext()) {
620 nextKey = keyIterator.next();
622 // at the end of the iteration loop again
623 keyIterator = context.keySet().iterator();
625 if (keyIterator.hasNext()) {
626 nextKey = keyIterator.next();
628 nextKey = ""; // no defined vars.
632 model.customizeTableModel.addRow(new Object[] { nextKey, nextKey, true });
633 varCustomizeTable.changeSelection(model.customizeTableModel.getRowCount() - 1, 1, false, false);
638 * Update the buttons on selection change.
640 private final ListSelectionListener updateButtonsSensibleForSelectionChange = new ListSelectionListener() {
642 public void valueChanged(ListSelectionEvent e) {
643 /* We cannot move up anymore */
644 final boolean isFirst;
645 /* We cannot move down anymore */
646 final boolean isLast;
647 /* The second row is selected */
648 final boolean isSecond;
650 int selectedRow = varCustomizeTable.getSelectedRow();
651 int rowCount = varCustomizeTable.getRowCount();
653 isFirst = selectedRow < 1;
654 isSecond = selectedRow == 1;
655 isLast = selectedRow == rowCount - 1;
657 moveUp.setEnabled(!isFirst && !isSecond);
658 moveDown.setEnabled(!isFirst && !isLast);
660 delete.setEnabled(!isFirst);
665 * Update the buttons/spinner on modifications
667 private final TableModelListener updateButtonsSensibleForModifications = new TableModelListener() {
669 public void tableChanged(TableModelEvent e) {
670 int rowCount = model.customizeTableModel.getRowCount();
671 rowSpinner.setValue(rowCount);
676 * Update the values table on change on the customize table.
678 private final TableModelListener updateValuesTable = new TableModelListener() {
680 public void tableChanged(TableModelEvent e) {
681 final DefaultTableModel valuesModel = model.valuesTableModel;
682 final DefaultTableModel customModel = model.customizeTableModel;
683 int row = e.getFirstRow();
684 int column = e.getColumn();
686 switch (e.getType()) {
687 case TableModelEvent.INSERT:
688 String key = (String) customModel.getValueAt(row, 0);
689 String value = context.get(key);
690 valuesModel.addRow(new Object[] { key, value });
693 case TableModelEvent.DELETE:
694 valuesModel.removeRow(row);
697 case TableModelEvent.UPDATE:
699 // update the description when it was set to a var
700 // name and the variable change
701 // the description should not change when it is not
703 String varName = (String) customModel.getValueAt(row, 0);
704 String varDesc = (String) customModel.getValueAt(row, 1);
705 if (context.containsKey(varDesc)) {
706 customModel.setValueAt(varName, row, 1);
708 } else if (column == 1) {
709 // update the description on the default value table
710 valuesModel.setValueAt(customModel.getValueAt(row, 1), row, 0);
720 private final Map<String, String> context;
721 private Iterator<String> keyIterator;
727 * the calling diagram
729 public CustomizeFrameControler(XcosDiagram diagram) {
730 model = new CustomizeFrameModel();
731 context = diagram.evaluateContext();
732 keyIterator = context.keySet().iterator();
738 public CustomizeFrameModel getModel() {
743 * Swap two table rows
752 private void swapTableRow(DefaultTableModel model, int row1, int row2) {
754 * doesn't need to be checked as the operation doesn't depend on
757 @SuppressWarnings("unchecked")
758 final List < List<? >> data = model.getDataVector();
761 List<?> tmp = data.get(row2);
762 data.set(row2, data.get(row1));
767 // CSON: ClassDataAbstractionCoupling