package ij.measure; import ij.plugin.filter.Analyzer; import ij.plugin.frame.Recorder; import ij.plugin.*; import ij.*; import ij.gui.*; import ij.text.*; import java.awt.*; import java.awt.event.*; /** This class implements the Apply Macro command in tables. * @author Michael Schmid */ public class ResultsTableMacros implements Runnable, DialogListener, ActionListener, KeyListener { private static String NAME = "TableMacro.ijm"; private String defaultMacro = "Sin=sin(row*0.1);\nCos=cos(row*0.1);\nSqr=Sin*Sin+Cos*Cos;"; private GenericDialog gd; private ResultsTable rt, rtBackup; private Button runButton, resetButton, openButton, saveButton; private String title; private int runCount; private TextArea ta; public ResultsTableMacros(ResultsTable rt) { this.rt = rt; title = rt!=null?rt.getTitle():null; Thread thread = new Thread(this, "ResultTableMacros"); thread.start(); } private void showDialog() { if (rt==null) rt = Analyzer.getResultsTable(); if (rt==null || rt.size()==0) { IJ.error("Results Table required"); return; } String[] temp = rt.getHeadingsAsVariableNames(); String[] variableNames = new String[temp.length+2]; variableNames[0] = "Insert..."; variableNames[1] = "row"; for (int i=2; i

Macro Equations for Results Tables

"); gd.addDialogListener(this); gd.showDialog(); if (gd.wasCanceled()) { // dialog cancelled? rt = rtBackup; updateDisplay(); return; } if (runCount==0) applyMacro(); if (Recorder.record) { String macro = getMacroCode(); macro = macro.replaceAll("\n", " "); if (Recorder.scriptMode()) { Recorder.recordCall("title = \""+title+"\";"); Recorder.recordCall("frame = WindowManager.getFrame(title);"); Recorder.recordCall("rt = frame.getResultsTable();"); Recorder.recordCall("rt.applyMacro(\""+macro+"\");"); Recorder.recordCall("rt.show(title);"); } else { if (title.equals("Results")) Recorder.record("Table.applyMacro", macro); else Recorder.record("Table.applyMacro", macro, title); } } IJ.saveString(ta.getText(), IJ.getDir("macros")+NAME); } private void applyMacro() { String code = getMacroCode(); rt.applyMacro(code); updateDisplay(); runCount++; } private String getMacroCode() { int start = ta.getSelectionStart(); int end = ta.getSelectionEnd(); return start==end?ta.getText():ta.getSelectedText(); } public boolean dialogItemChanged(GenericDialog gd, AWTEvent e) { final String variableName = gd.getNextChoice(); if (e!=null && (e.getSource() instanceof Choice) && !variableName.equals("Insert...")) { final int pos = ta.getCaretPosition(); ((Choice)e.getSource()).select(0); final TextArea textArea = ta; new Thread(new Runnable() { public void run() { IJ.wait(100); textArea.insert(variableName, pos); textArea.setCaretPosition(pos+variableName.length()); textArea.requestFocus(); }}).start(); } return true; } public void actionPerformed(ActionEvent e) { Object source = e.getSource(); if (source==runButton) { applyMacro(); } else if (source==resetButton) { rt = (ResultsTable)rtBackup.clone(); updateDisplay(); } else if (source==openButton) { String macro = IJ.openAsString(null); if (macro==null) return; if (macro.startsWith("Error: ")) { IJ.error(macro); return; } else ta.setText(macro); } else if (source==saveButton) { ta.selectAll(); String macro = ta.getText(); ta.select(0, 0); IJ.saveString(macro, null); } } public void keyPressed(KeyEvent e) { int flags = e.getModifiers(); boolean control = (flags & KeyEvent.CTRL_MASK) != 0; boolean meta = (flags & KeyEvent.META_MASK) != 0; int keyCode = e.getKeyCode(); if (keyCode==KeyEvent.VK_R && (control||meta)) applyMacro(); if (keyCode==KeyEvent.VK_Z && (control||meta)) { rt = (ResultsTable)rtBackup.clone(); updateDisplay(); } } private void updateDisplay() { if (title!=null) rt.show(title); } public void keyReleased(KeyEvent e) { } public void keyTyped(KeyEvent e) { } private String getMacro() { String macro = IJ.openAsString(IJ.getDir("macros")+NAME); if (macro==null || macro.startsWith("Error:")) return defaultMacro; else { macro = macro.replaceAll("rowNumber", "row"); macro = macro.replaceAll("rowIndex", "row"); return macro; } } public void run() { rtBackup = (ResultsTable)rt.clone(); showDialog(); } }