001package framebuffer;
002
003import java.awt.*;
004import java.awt.event.*;
005import java.awt.image.MemoryImageSource;
006import javax.swing.JFrame;
007import javax.swing.JPanel;
008
009/**
010   This class allows our renderer to be interactive. This class is
011   an interface between our renderer and the Java GUI system.
012
013   This class is meant to be sub classed by classes that implement
014   event listeners. The event listeners provide the interactivity.
015
016   Each instance of InteractiveFrame has a reference to a FrameBuffer
017   object (with the same dimensions as the JFrame). When a GUI event
018   happens, one of the implemented event listeners will update the
019   framebuffer by having the renderer render the scene into the
020   framebuffer. When the renderer is done updating the framebuffer,
021   this class will pass the framebufer's pixel data to the Graphics
022   context of this JFrame. This will display the framebuffer's contents
023   in the JFrame's window.
024
025   This is a resizeable window. When the window resizes, the FrameBuffer
026   object needs to also resize. But FrameBuffer objects cannot be resized.
027   So this class instantiates a new FrameBuffer object each time the window
028   is resized.
029*/
030@SuppressWarnings("serial")
031public class InteractiveFrame extends JFrame implements
032   FocusListener,  ComponentListener, WindowListener,
033   ActionListener, ItemListener,      AdjustmentListener,
034   TextListener,   MouseListener,     MouseMotionListener,
035   KeyListener
036{
037   private FrameBuffer fb;
038   private MemoryImageSource source;
039   private Image img;
040
041   /**
042      @param title  title for the JFrame window
043      @param width  width of the JFrame window
044      @param height height of the JFrame window
045   */
046   public InteractiveFrame(String title, int width, int height)
047   {
048      super(title);
049      setLocationByPlatform(true);
050      setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
051
052      setSize(width, height);
053      setVisible(true);
054      java.awt.Insets insets = getInsets();
055      //System.err.println(""+insets.left+" "+insets.right+" "+insets.top+" "+insets.bottom);
056      setSize(width+insets.left+insets.right, height+insets.top+insets.bottom);
057
058      this.createFrameBuffer(width, height);
059
060      // Give this JFrame a JPanel.
061      setContentPane(new JPanel()
062      {
063         @Override
064         protected void paintComponent(Graphics g)
065         {
066            // Send the new pixel data to the ImageProducer.
067            source.newPixels(0, 0, fb.getWidthFB(), fb.getHeightFB());
068
069            Graphics2D g2 = (Graphics2D)g.create();
070            g2.drawImage(img, 0, 0, this);
071            g2.dispose();
072         }
073      });
074   }
075
076
077   /**
078      @return a reference to the FrameBuffer owned by this window
079   */
080   public FrameBuffer getFrameBuffer()
081   {
082      return this.fb;
083   }
084
085
086   /**
087      Change the FrameBuffer being used as the source for the Image painted on this JFrame's JPanel.
088
089      This will usually be in response to a call to the componentResized() event listener.
090
091      @param width  new width for this JFrame window
092      @param height new height for this JFrame window
093   */
094   public void createFrameBuffer(int width, int height)
095   {
096      this.fb = new FrameBuffer(width, height);
097
098      // Use the framebuffer as the source for an Image.
099      this.source = new MemoryImageSource(this.fb.getWidthFB(), this.fb.getHeightFB(),
100                                          this.fb.pixel_buffer, 0, this.fb.getWidthFB());
101      this.source.setAnimated(true);
102      this.img = createImage(this.source);
103   }
104
105
106   // implement the ActionListener interface
107   @Override public void actionPerformed(ActionEvent e){}
108   // implement the ItemListener interface
109   @Override public void itemStateChanged(ItemEvent e){}
110   // implement the AdjustmentListener interface
111   @Override public void adjustmentValueChanged(AdjustmentEvent e){}
112   // implement the TextListener interface
113   @Override public void textValueChanged(TextEvent e){}
114   // implement the KeyListener interface (three methods)
115   @Override public void keyPressed(KeyEvent e){}
116   @Override public void keyReleased(KeyEvent e){}
117   @Override public void keyTyped(KeyEvent e){}
118   // implement the MouseListener interface (five methods)
119   @Override public void mouseClicked(MouseEvent e){}
120   @Override public void mousePressed(MouseEvent e){}
121   @Override public void mouseReleased(MouseEvent e){}
122   @Override public void mouseEntered(MouseEvent e){}
123   @Override public void mouseExited(MouseEvent e){}
124   // implement the MouseMotionListener interface
125   @Override public void mouseDragged(MouseEvent e){}
126   @Override public void mouseMoved(MouseEvent e){}
127   // implement the ComponentListener interface (four methods)
128   @Override public void componentMoved(ComponentEvent e){}
129   @Override public void componentHidden(ComponentEvent e){}
130   @Override public void componentResized(ComponentEvent e){}
131   @Override public void componentShown(ComponentEvent e){}
132   // implement the FocusListener interface
133   @Override public void focusGained(FocusEvent e){}
134   @Override public void focusLost(FocusEvent e){}
135   // implement the WindowListener interface (seven methods)
136   @Override public void windowClosed(WindowEvent e){}
137   @Override public void windowDeiconified(WindowEvent e){}
138   @Override public void windowIconified(WindowEvent e){}
139   @Override public void windowActivated(WindowEvent e){}
140   @Override public void windowDeactivated(WindowEvent e){}
141   @Override public void windowOpened(WindowEvent e){}
142   @Override public void windowClosing(WindowEvent e){}
143}