From b3d3ea7b6cf9768e756920cecb986e262af01c07 Mon Sep 17 00:00:00 2001 From: Simon Ebner Date: Mon, 15 Apr 2013 12:59:13 +0200 Subject: [PATCH] Changed connection direction Added gui elements to be able to select method and server --- ch.psi.imagej.zeromq/pom.xml | 2 +- .../ch/psi/imagej/zeromq/ZeroMQViewer.java | 218 ++++++++++++++---- 2 files changed, 176 insertions(+), 44 deletions(-) diff --git a/ch.psi.imagej.zeromq/pom.xml b/ch.psi.imagej.zeromq/pom.xml index a766865..0647484 100644 --- a/ch.psi.imagej.zeromq/pom.xml +++ b/ch.psi.imagej.zeromq/pom.xml @@ -3,7 +3,7 @@ 4.0.0 ch.psi ch.psi.imagej.zeromq - 0.0.1-SNAPSHOT + 0.0.3-SNAPSHOT diff --git a/ch.psi.imagej.zeromq/src/main/java/ch/psi/imagej/zeromq/ZeroMQViewer.java b/ch.psi.imagej.zeromq/src/main/java/ch/psi/imagej/zeromq/ZeroMQViewer.java index e069bb1..652953a 100644 --- a/ch.psi.imagej.zeromq/src/main/java/ch/psi/imagej/zeromq/ZeroMQViewer.java +++ b/ch.psi.imagej.zeromq/src/main/java/ch/psi/imagej/zeromq/ZeroMQViewer.java @@ -1,4 +1,5 @@ package ch.psi.imagej.zeromq; + // EPICS_AD_Viewer.java // Original authors // Tim Madden, APS @@ -11,12 +12,12 @@ import ij.plugin.*; import java.nio.ByteBuffer; import java.nio.ByteOrder; import java.awt.event.*; +import java.util.concurrent.Semaphore; import java.util.logging.Level; import java.util.logging.Logger; import javax.swing.*; import javax.swing.Timer; -import javax.swing.border.*; import org.jeromq.ZMQ; @@ -34,48 +35,92 @@ public class ZeroMQViewer implements PlugIn { private int numImageUpdates; private JFrame frame; - private JTextField fpsText; + // private JLabel fpsText; - private boolean isPluginRunning; + private volatile boolean isPluginRunning; + private volatile boolean collect; private Timer timer; private ZMQ.Context context; private ZMQ.Socket socket; + private JPanel panel_1; + private JLabel lblNewLabel; + private JLabel labelFrameRate; + private JTextField textHostname; + private JLabel lblHostname; + private JLabel lblPort; + private JTextField textPort; + private JButton btnStart; + + private Semaphore semaphore = new Semaphore(1); + private JLabel lblMethod; + private JComboBox comboBoxMethod; + public void run(String arg) { IJ.showStatus("Running ZeroMQ Viewer"); try { isPluginRunning = true; - + prevTime = System.currentTimeMillis(); numImageUpdates = 0; - + semaphore.acquire(); // block semaphore + javax.swing.SwingUtilities.invokeLater(new Runnable() { public void run() { createAndShowGUI(); } }); - context = ZMQ.context(1); - socket = context.socket(ZMQ.PULL); - socket.bind("tcp://*:8080"); - + while (isPluginRunning) { - byte[] message = socket.recv(); - byte[] content = null; - if (socket.hasReceiveMore()) { - content = socket.recv(); + semaphore.acquire(); + collect=true; + try{ + if(img!=null){ + img.close(); + img=null; + } + String hostname = textHostname.getText(); + int port = Integer.parseInt(textPort.getText()); + String method = (String) comboBoxMethod.getSelectedItem(); + + + context = ZMQ.context(1); + if(method.equals("PULL")){ + socket = context.socket(ZMQ.PULL); + } + else if(method.equals("SUB")){ + socket = context.socket(ZMQ.SUB); + } + else{ + logger.severe("Method not supported"); + collect=false; + } + socket.connect("tcp://"+hostname+":"+port); + + while(collect){ + byte[] message = socket.recv(); + byte[] content = null; + if (socket.hasReceiveMore()) { + content = socket.recv(); + } + logger.info(new String(message)); + updateImage(content); + } + + socket.close(); + context.term(); + } + catch(Exception e){ + logger.log(Level.SEVERE, "",e); + btnStart.setText("Start"); } - logger.info(new String(message)); - updateImage(content); } timer.stop(); - socket.close(); - context.term(); - img.close(); frame.setVisible(false); @@ -89,14 +134,14 @@ public class ZeroMQViewer implements PlugIn { public void updateImage(byte[] content) { try { - if(img==null){ + if (img == null) { // TODO eventually use ByteProcessor or BinaryProcessor // BinaryProcessor p = new ij.process.BinaryProcessor(new // ByteProcessor(imageSizeX, imageSizeY)); img = new ImagePlus("", new ShortProcessor(imageSizeX, imageSizeY)); img.show(); } - + // TODO Check whether this is needed short[] shorts = new short[content.length / 2]; ByteBuffer.wrap(content).order(ByteOrder.LITTLE_ENDIAN).asShortBuffer().get(shorts); @@ -112,46 +157,133 @@ public class ZeroMQViewer implements PlugIn { /** * Create the GUI and show it. For thread safety, this method should be * invoked from the event-dispatching thread. + * + * @wbp.parser.entryPoint */ public void createAndShowGUI() { - fpsText = new JTextField(6); - fpsText.setEditable(false); - fpsText.setHorizontalAlignment(JTextField.CENTER); frame = new JFrame("ZeroMQ_Viewer Plugin"); - JPanel panel = new JPanel(new BorderLayout()); - panel.setLayout(new GridBagLayout()); - panel.setBorder(new EmptyBorder(new Insets(5, 5, 5, 5))); - frame.getContentPane().add(BorderLayout.CENTER, panel); - GridBagConstraints c = new GridBagConstraints(); - // Add extra space around each component to avoid clutter - c.insets = new Insets(2, 2, 2, 2); + panel_1 = new JPanel(); + GridBagConstraints gbc_panel_1 = new GridBagConstraints(); + gbc_panel_1.fill = GridBagConstraints.BOTH; + gbc_panel_1.gridx = 0; + gbc_panel_1.gridy = 1; + frame.getContentPane().add(panel_1, BorderLayout.CENTER); + GridBagLayout gbl_panel_1 = new GridBagLayout(); + gbl_panel_1.columnWidths = new int[] { 0, 0, 0 }; + gbl_panel_1.rowHeights = new int[] { 0, 0, 0, 0, 0, 0 }; + gbl_panel_1.columnWeights = new double[] { 0.0, 1.0, Double.MIN_VALUE }; + gbl_panel_1.rowWeights = new double[] { 0.0, 0.0, 0.0, 0.0, 0.0, Double.MIN_VALUE }; + panel_1.setLayout(gbl_panel_1); - // Top row - // Anchor all components CENTER - c.anchor = GridBagConstraints.CENTER; - c.gridx = 0; - c.gridy = 0; - panel.add(new JLabel("Frames/s"), c); + lblHostname = new JLabel("Hostname"); + GridBagConstraints gbc_lblHostname = new GridBagConstraints(); + gbc_lblHostname.insets = new Insets(0, 0, 5, 5); + gbc_lblHostname.anchor = GridBagConstraints.EAST; + gbc_lblHostname.gridx = 0; + gbc_lblHostname.gridy = 0; + panel_1.add(lblHostname, gbc_lblHostname); - // Middle row - // These widgets should be centered - c.anchor = GridBagConstraints.CENTER; - c.gridy = 1; - c.gridx = 0; - panel.add(fpsText, c); + textHostname = new JTextField(); + GridBagConstraints gbc_textHostname = new GridBagConstraints(); + gbc_textHostname.insets = new Insets(0, 0, 5, 0); + gbc_textHostname.fill = GridBagConstraints.HORIZONTAL; + gbc_textHostname.gridx = 1; + gbc_textHostname.gridy = 0; + panel_1.add(textHostname, gbc_textHostname); + textHostname.setColumns(10); + + lblPort = new JLabel("Port"); + GridBagConstraints gbc_lblPort = new GridBagConstraints(); + gbc_lblPort.anchor = GridBagConstraints.EAST; + gbc_lblPort.insets = new Insets(0, 0, 5, 5); + gbc_lblPort.gridx = 0; + gbc_lblPort.gridy = 1; + panel_1.add(lblPort, gbc_lblPort); + + textPort = new JTextField(); + GridBagConstraints gbc_textPort = new GridBagConstraints(); + gbc_textPort.insets = new Insets(0, 0, 5, 0); + gbc_textPort.fill = GridBagConstraints.HORIZONTAL; + gbc_textPort.gridx = 1; + gbc_textPort.gridy = 1; + panel_1.add(textPort, gbc_textPort); + textPort.setColumns(10); + + lblMethod = new JLabel("Method"); + GridBagConstraints gbc_lblMethod = new GridBagConstraints(); + gbc_lblMethod.anchor = GridBagConstraints.EAST; + gbc_lblMethod.insets = new Insets(0, 0, 5, 5); + gbc_lblMethod.gridx = 0; + gbc_lblMethod.gridy = 2; + panel_1.add(lblMethod, gbc_lblMethod); + + comboBoxMethod = new JComboBox(); + comboBoxMethod.setModel(new DefaultComboBoxModel(new String[] {"PULL", "SUB"})); + comboBoxMethod.setSelectedIndex(0); + GridBagConstraints gbc_comboBoxMethod = new GridBagConstraints(); + gbc_comboBoxMethod.insets = new Insets(0, 0, 5, 0); + gbc_comboBoxMethod.fill = GridBagConstraints.HORIZONTAL; + gbc_comboBoxMethod.gridx = 1; + gbc_comboBoxMethod.gridy = 2; + panel_1.add(comboBoxMethod, gbc_comboBoxMethod); + + lblNewLabel = new JLabel("Frame/s"); + GridBagConstraints gbc_lblNewLabel = new GridBagConstraints(); + gbc_lblNewLabel.anchor = GridBagConstraints.EAST; + gbc_lblNewLabel.insets = new Insets(0, 0, 5, 5); + gbc_lblNewLabel.gridx = 0; + gbc_lblNewLabel.gridy = 3; + panel_1.add(lblNewLabel, gbc_lblNewLabel); + + labelFrameRate = new JLabel("0.0"); + GridBagConstraints gbc_labelFrameRate = new GridBagConstraints(); + gbc_labelFrameRate.anchor = GridBagConstraints.EAST; + gbc_labelFrameRate.insets = new Insets(0, 0, 5, 0); + gbc_labelFrameRate.gridx = 1; + gbc_labelFrameRate.gridy = 3; + panel_1.add(labelFrameRate, gbc_labelFrameRate); + + btnStart = new JButton("Start"); + btnStart.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + if(btnStart.getText().equals("Start")){ + // Start data acquisition + semaphore.release(); + btnStart.setText("Stop"); + } + else{ + // Stop data acquisition + collect = false; + try{ + socket.notifyAll(); + } + catch(Exception ex){ + // This exception can savely be ignored (somewhat most of the time an exception is expected) + } + btnStart.setText("Start"); + } + } + }); + GridBagConstraints gbc_btnStart = new GridBagConstraints(); + gbc_btnStart.anchor = GridBagConstraints.WEST; + gbc_btnStart.gridx = 1; + gbc_btnStart.gridy = 4; + panel_1.add(btnStart, gbc_btnStart); // Display the window. frame.pack(); frame.addWindowListener(new FrameExitListener()); frame.setVisible(true); + + // Update frame rate int timerDelay = 2000; // 2 seconds timer = new Timer(timerDelay, new ActionListener() { public void actionPerformed(ActionEvent event) { long time = System.currentTimeMillis(); double fps = 1000. * numImageUpdates / (double) (time - prevTime); - fpsText.setText(String.format("%.1f", fps)); + labelFrameRate.setText(String.format("%.1f", fps)); prevTime = time; numImageUpdates = 0; }