001/** 002 * 003 */ 004package plugins.tutorial.undo; 005 006import icy.math.ArrayMath; 007import icy.plugin.abstract_.PluginActionable; 008import icy.sequence.Sequence; 009import icy.sequence.edit.AbstractSequenceEdit; 010import icy.type.collection.array.Array1DUtil; 011 012import javax.swing.undo.CannotRedoException; 013import javax.swing.undo.CannotUndoException; 014 015/** 016 * This plugin demonstrate how to use the Undo framework with 'redo' operation support. 017 * 018 * @author Stephane 019 */ 020public class AdvancedUndo extends PluginActionable 021{ 022 /** 023 * Create the Undoable operation class 024 * 025 * @author Stephane 026 */ 027 class DivideOperation extends AbstractSequenceEdit 028 { 029 final double divisor; 030 031 public DivideOperation(Sequence sequence, double divisor) 032 { 033 super(sequence, "Divide intensity"); 034 035 this.divisor = divisor; 036 // consider the operation as "not done" by default 037 hasBeenDone = false; 038 } 039 040 @Override 041 public void undo() throws CannotUndoException 042 { 043 super.undo(); 044 045 final Sequence seq = getSequence(); 046 final Object data = seq.getDataXY(0, 0, 0); 047 048 // convert to double 049 final double[] doubleArray = Array1DUtil.arrayToDoubleArray(data, seq.isSignedDataType()); 050 // multiply intensity by 2 051 ArrayMath.multiply(doubleArray, 2d, doubleArray); 052 // copy data back to image 053 Array1DUtil.doubleArrayToArray(doubleArray, data); 054 // notify sequence we changed its data 055 seq.dataChanged(); 056 } 057 058 @Override 059 public void redo() throws CannotRedoException 060 { 061 super.redo(); 062 063 final Sequence seq = getSequence(); 064 final Object data = seq.getDataXY(0, 0, 0); 065 066 // convert to double 067 final double[] doubleArray = Array1DUtil.arrayToDoubleArray(data, seq.isSignedDataType()); 068 // divide intensity by 2 069 ArrayMath.divide(doubleArray, 2d, doubleArray); 070 // copy data back to image, note that here we can loss information (double --> whatever 071 // type conversion) so the redo operation won't correctly restore original data 072 Array1DUtil.doubleArrayToArray(doubleArray, data); 073 // notify sequence we changed its data 074 seq.dataChanged(); 075 } 076 } 077 078 @Override 079 public void run() 080 { 081 final Sequence seq = getActiveSequence(); 082 083 if (seq != null) 084 { 085 final Object data = seq.getDataXY(0, 0, 0); 086 087 // have some data here ? 088 if (data != null) 089 { 090 final DivideOperation op = new DivideOperation(seq, 2d); 091 092 // execute operation 093 op.redo(); 094 // add as undoable edit 095 seq.addUndoableEdit(op); 096 } 097 } 098 } 099}