Package com.kylin.jgroups.demo

Source Code of com.kylin.jgroups.demo.DrawDemo

package com.kylin.jgroups.demo;

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ComponentAdapter;
import java.awt.event.ComponentEvent;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.io.BufferedOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;

import javax.management.MBeanServer;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;

import org.apache.log4j.Logger;
import org.jgroups.Address;
import org.jgroups.Channel;
import org.jgroups.ChannelListener;
import org.jgroups.JChannel;
import org.jgroups.MergeView;
import org.jgroups.Message;
import org.jgroups.View;
import org.jgroups.jmx.JmxConfigurator;
import org.jgroups.util.Util;

import com.kylin.jgroups.DemoBase;

public class DrawDemo extends DemoBase implements ActionListener, ChannelListener{

  /**
   * DrawDemo cluster name
   */
  private String clusterName = "DrawCluster";
 
  private boolean no_channel = false;
 
  private boolean jmx = true;
 
  private boolean use_state = false;
 
  private long state_timeout = 5000;
 
  /**
   * Whether use unicast, default false emans use multicast
   */
  private boolean use_unicasts = false;
 
  /**
   * DrawDemo main Channel
   */
  private Channel channel = null;
 
  /**
   * DrawDemo main Frame
   */
  private JFrame mainFrame = null;
 
  /**
   * DrawDemo main panel
   */
  private DrawPanel panel = null;
 
  /**
   * DrawDemo button panel
   */
  private JPanel sub_panel = null;
 
  /**
   * DrawDemo clear and leave button
   */
  private JButton clear_button, leave_button;
 
  private final Font default_font = new Font("Helvetica", Font.PLAIN, 12);
 
  private static final Color background_color = Color.white;
 
  private int member_size = 1;
 
  private final Random random = new Random(System.currentTimeMillis());
 
  private final Color draw_color = selectColor();
 
  private final List<Address> members = new ArrayList<Address>();
 
  private static final Logger logger = Logger.getLogger(DrawDemo.class);
 
  public DrawDemo() {
   
  }
 
  public DrawDemo(Channel channel) throws Exception{
    this.channel = channel;
    channel.setReceiver(this);
    channel.addChannelListener(this);
  }
 
 
  public void init(String[] args) throws Exception {
   
    String props = "udp.xml";
    String name = null;
   
     for(int i=0; i < args.length; i++) {
      
      if ("-help".equals(args[i]) || "-h".equals(args[i])) {
        help();
        return;
      }
     
      if ("-c".equals(args[i])) {
        clusterName = args[++i];
        continue;
      }
             
      if ("-p".equals(args[i])) {
        props = args[++i];
        continue;
      }
     
      if ("-n".equals(args[i])) {
        name = args[++i];
        continue;
      }
     
      if ("-t".equals(args[i])) {
        state_timeout = Long.parseLong(args[++i]);
        continue;
      }
     
      if("-b".equals(args[i])) {
                System.setProperty("jgroups.bind_addr", args[++i]);
                continue;
            }
     
      if ("-no_channel".equals(args[i])) {
        no_channel = true;
        continue;
      }
     
      if ("-jmx".equals(args[i])) {
        jmx = true;
        continue;
      }

      if ("-state".equals(args[i])) {
        use_state = true;
        continue;
      }

      if ("-use_unicasts".equals(args[i])) {
        use_unicasts = true;
        continue;
      }
            
      help();
    }


    logger.info("Create Channel with name " + name);
    channel=new JChannel(props);
   
    if(name != null){
      channel.setName(name);
    }
   
    channel.setReceiver(this);
        channel.addChannelListener(this);
       
        if (!no_channel && !use_state) {
      logger.info("connect to " + clusterName);
      channel.connect(clusterName);
    }
   
    if(!no_channel && use_state) {
      logger.info("connect to " + clusterName + ", use_state = " + use_state);
            channel.connect(clusterName, null, state_timeout);
        }
   
  }

  private void help() {
   
    System.out.println("Run Application with [-p <props>] [-n <name>] [-c <clusterName>] [-b <bind_address>] [-t <state_timeout>]");
    System.out.println("                     [-no_channel] [-jmx] [-state] [-use_unicasts]");
    Runtime.getRuntime().exit(1);
  }

  public static void main(String[] args) throws Exception {

    DrawDemo demo = new DrawDemo();
    demo.start(args);
   
//    demo.help();
  }
 
  public void start(String[] args) throws Exception {
   
    init(args);
   
    launchFrame();
  }
 
  private void launchFrame() throws Exception {

    logger.info("launch Frame Start");
   
   
   
    mainFrame = new JFrame();
    mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
   
    panel = new DrawPanel(use_state);
    panel.setBackground(background_color);
   
    mainFrame.getContentPane().add("Center", panel);
   
    clear_button = new JButton("Clear");
    clear_button.setFont(default_font);
    clear_button.addActionListener(this);
    clear_button.setForeground(Color.blue);
   
    leave_button = new JButton("Leave");
    leave_button.setFont(default_font);
    leave_button.addActionListener(this);
    leave_button.setForeground(Color.blue);

    sub_panel = new JPanel();
    sub_panel.add("South", clear_button);
        sub_panel.add("South", leave_button);
       
        mainFrame.getContentPane().add("South", sub_panel);
        mainFrame.setBackground(background_color);
       
        mainFrame.pack();
        mainFrame.setLocation(100, 100);
        mainFrame.setBounds(new Rectangle(500, 350));
        mainFrame.setVisible(true);
        setTitle(null);
  }

  private void setTitle(String title) {

    String tmp = " Draw Demo ";
   
    if (no_channel) {
      mainFrame.setTitle(tmp);
      return;
    }
   
    if (title != null) {
      mainFrame.setTitle(title);
    } else {
      mainFrame.setTitle(tmp + channel.getName());
    }
  }

  public void channelConnected(Channel channel) {
   
    logger.info("Channel Connected");
   
    logChannel(channel);
   
    if(jmx) {
      logger.info("Register " + channel.getName() + " to JGroups JMX MBean Server");
            Util.registerChannel((JChannel)channel, "jgroups");
        }
  }

  public void channelDisconnected(Channel channel) {
   
    logger.info("Channel Disconnected");
   
    logChannel(channel);
   
    if(jmx) {
            MBeanServer server=Util.getMBeanServer();
            if(server != null) {
                try {
                    JmxConfigurator.unregisterChannel((JChannel)channel,server, clusterName);
                }
                catch(Exception e) {
                    logger.error(e);
                }
            }
        }
  }

  public void channelClosed(Channel channel) {
   
    logger.info("Channel Closed");
   
    logChannel(channel);
  }

  private void logChannel(Channel channel) {
   
    try {
      logger.debug("----------");
      logger.debug("Channel Name: " + channel.getName());
      logger.debug("Channel Address: " + channel.getAddress());
      logger.debug("Channel ClusterName: " + channel.getClusterName());
      logger.debug("Channel View: " + channel.getView());
      logger.debug("  -> View Id: " + channel.getView().getViewId());
      logger.debug("  -> View Creater: " + channel.getView().getCreator());
      logger.debug("  -> View Coordinator: " + channel.getView().getMembers().get(0));
      logger.debug("  -> View Memembers: " + channel.getView().getMembers());
      logger.debug("-----------");
    } catch (Exception e) {
     
    }
  }

  public void actionPerformed(ActionEvent e) {

    String command = e.getActionCommand();
        if("Clear".equals(command)) {
            if(no_channel) {
                clearPanel();
                return;
            }
            sendClearPanelMsg();
    } else if ("Leave".equals(command)) {
            stop();
    } else {
      System.out.println("Unknown action");
    }
  }
 
 
  private void clearPanel() {
   
    if(panel != null){
      panel.clear();
    }
  }

  private void sendClearPanelMsg() {

    DrawDemoCommand comm = new DrawDemoCommand(DrawDemoCommand.CLEAR);

        try {
            byte[] buf=Util.streamableToByteBuffer(comm);
            if(use_unicasts)
                sendToAll(buf);
            else
                channel.send(new Message(null, null, buf));
        }
        catch(Exception ex) {
            System.err.println(ex);
        }
  }
 
  private void sendToAll(byte[] buf) throws Exception {
   
    for (Address mbr : members) {
      Message msg = new Message(mbr, null, buf);
      channel.send(msg);
    }
  }

  private void stop() {

    if (!no_channel) {
      try {
        channel.close();
      } catch (Exception ex) {
        logger.error(ex);
      }
    }
    mainFrame.setVisible(false);
    mainFrame.dispose();
  }

  private Color selectColor() {
   
    int red=Math.abs(random.nextInt()) % 255;
        int green=Math.abs(random.nextInt()) % 255;
        int blue=Math.abs(random.nextInt()) % 255;
        return new Color(red, green, blue);
  }

  public void viewAccepted(View view) {
   
    logger.info("View Acceepted");
   
    member_size = view.size();
   
        if(mainFrame != null){
          setTitle(null);
        }
       
        members.clear();
        members.addAll(view.getMembers());

        if(view instanceof MergeView) {
            System.out.println("** MergeView = " + view);

      if (use_state && !members.isEmpty()) {
        Address coord = members.get(0);
        Address local_addr = channel.getAddress();
        if (local_addr != null && !local_addr.equals(coord)) {
          try {
            System.out.println("fetching state from " + coord);
            channel.getState(coord, 5000);
          } catch (Exception e) {
            logger.error(e);
          }
        }
      }
    } else {
      System.out.println("** View = " + view);
    }
  }

  public void receive(Message msg) {
   
    logger.info("Recieve Message");
   
    byte[] buf = msg.getRawBuffer();
        if(buf == null) {
            logger.warn("[" + channel.getAddress() + "] received null buffer from " + msg.getSrc() + ", headers: " + msg.printHeaders());
            return;
        }

        try {
      DrawDemoCommand comm = (DrawDemoCommand)Util.streamableFromByteBuffer(DrawDemoCommand.class, buf, msg.getOffset(), msg.getLength());
            switch(comm.mode) {
                case DrawDemoCommand.DRAW:
                    if(panel != null)
                        panel.drawPoint(comm);
                    break;
                case DrawDemoCommand.CLEAR:
                    clearPanel();
                    break;
                default:
                  logger.warn("***** received invalid draw command " + comm.mode);
                    break;
            }
        }
        catch(Exception e) {
           logger.error(e);
        }
  }

  public void getState(OutputStream output) throws Exception {
    panel.writeState(output);
  }

  public void setState(InputStream input) throws Exception {
    panel.readState(input);
  }


  private class DrawPanel extends JPanel implements MouseMotionListener {
   
    private Dimension d;
    private Dimension imgsize = null;
    private Image img = null;
    private Graphics gr = null;
   
    final Map<Point,Color>  state;
   
    public DrawPanel(boolean use_state) {
     
            if(use_state){
              state=new LinkedHashMap<Point,Color>();
      } else {
        state=null;
      }
               
            createOffscreenImage(false);
            addMouseMotionListener(this);
            addComponentListener(new ComponentAdapter() {
                public void componentResized(ComponentEvent e) {
                    if(getWidth() <= 0 || getHeight() <= 0) return;
                    createOffscreenImage(false);
                }
            });
        }

    public void readState(InputStream input) throws IOException {

      DataInputStream in = new DataInputStream(input);
      Map<Point, Color> new_state = new HashMap<Point, Color>();
      int num = in.readInt();
      for (int i = 0; i < num; i++) {
        Point point = new Point(in.readInt(), in.readInt());
        Color col = new Color(in.readInt());
        new_state.put(point, col);
      }

      synchronized (state) {
        state.clear();
        state.putAll(new_state);
        logger.info("read state: " + state.size() + " entries");
        createOffscreenImage(true);
      }
    }

    public void writeState(OutputStream output) throws IOException {

       if(state == null){
         return;
       }
      
      synchronized (state) {
        DataOutputStream dos = new DataOutputStream(new BufferedOutputStream(output, 4096));
        dos.writeInt(state.size());
        for (Map.Entry<Point, Color> entry : state.entrySet()) {
          Point point = entry.getKey();
          Color col = entry.getValue();
          dos.writeInt(point.x);
          dos.writeInt(point.y);
          dos.writeInt(col.getRGB());
        }
        dos.flush();
      }
    }

    public void drawPoint(DrawDemoCommand c) {

      if (c == null || gr == null) {
        return;
      }
     
      Color col = new Color(c.r, c.g, c.b);
      gr.setColor(col);
      gr.fillOval(c.x, c.y, 10, 10);
      repaint();
     
      if (state != null) {
        synchronized (state) {
          state.put(new Point(c.x, c.y), col);
        }
      }
    }

    public void clear() {

      if (gr == null) {
        return;
      }
     
      gr.clearRect(0, 0, getSize().width, getSize().height);
      repaint();
     
      if (state != null) {
        synchronized (state) {
          state.clear();
        }
      }
    }

    private void createOffscreenImage(boolean discard_image) {

      d = getSize();
     
      if (discard_image) {
        img = null;
        imgsize = null;
      }
     
            if(img == null || imgsize == null || imgsize.width != d.width || imgsize.height != d.height) {
        img = createImage(d.width, d.height);
        if (img != null) {
          gr = img.getGraphics();
          if (gr != null && state != null) {
            drawState();
          }
        }
        imgsize = d;
      }
      repaint();
    }

    private void drawState() {

      Map.Entry entry;
      Point pt;
      Color col;
      synchronized (state) {
        for (Iterator it = state.entrySet().iterator(); it.hasNext();) {
          entry = (Map.Entry) it.next();
          pt = (Point) entry.getKey();
          col = (Color) entry.getValue();
          gr.setColor(col);
          gr.fillOval(pt.x, pt.y, 10, 10);

        }
      }
      repaint();
    }

    public void mouseDragged(MouseEvent e) {
     
      logger.debug("Mouse Dragged");
     
      int x = e.getX();
      int y = e.getY();
     
      DrawDemoCommand comm = new DrawDemoCommand(DrawDemoCommand.DRAW, x, y, draw_color.getRed(), draw_color.getGreen(), draw_color.getBlue());

      if (no_channel) {
        drawPoint(comm);
        return;
      }

          try {
        byte[] buf = Util.streamableToByteBuffer(comm);
             
              if(use_unicasts){
                sendToAll(buf);
        } else {
          channel.send(new Message(null, null, buf));
        }
                 
      } catch (Exception ex) {
        logger.error(ex);
      }
    }

    public void mouseMoved(MouseEvent e) {
     
    }
   
  }
 
}
TOP

Related Classes of com.kylin.jgroups.demo.DrawDemo

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.