package com.drawbridge.dm; import java.awt.BorderLayout; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import java.awt.image.BufferedImage; import java.util.LinkedList; import javax.swing.ImageIcon; import javax.swing.JButton; import javax.swing.JOptionPane; import com.drawbridge.Activity; import com.drawbridge.dm.DMImageFactory.DMImage; import com.drawbridge.dm.DMModel.DMModelListener; import com.drawbridge.dm.animation.AnimationManager; import com.drawbridge.dm.animation.AnimationManager.AnimationListener; import com.drawbridge.dm.animation.AnimationManager.AnimationState; import com.drawbridge.jsengine.JsEngine; import com.drawbridge.jsengine.ast.DBParser; import com.drawbridge.paper.PaperPanel; import com.drawbridge.text.TextPanel; import com.drawbridge.utils.GraphicUtils; import com.drawbridge.utils.SegmentPanel; import com.drawbridge.utils.TitlePanel; import com.drawbridge.utils.Utils; import com.drawbridge.vl.VLPanel; /** * Class provides a "simple" view for the DM objects. Mouse Events are sent to * DMPanel * */ public class DMSimplePanel extends SegmentPanel implements DMModelListener, AnimationListener { private static final long serialVersionUID = 3238119688973329060L; private static DMSimplePanel mInstance = null; private TitlePanel mTitlePanel; // Canvas is just a placeholder for DMobjects private DMCanvas mCanvas; private DMModel mModel; private AnimationManager mAnimation; private BufferedImage mResetImage = null; private BufferedImage mRecordImage = null; private BufferedImage mLoopImage = null; private BufferedImage mLoopDisabledImage = null; private BufferedImage mStopImage = null; private BufferedImage mPlayImage = null; private JButton mRecordButton; private JButton mResetButton; private JButton mLoopButton; private boolean mLooping = false; public static DMSimplePanel getInstance() { if (mInstance != null) { return mInstance; } else { mInstance = new DMSimplePanel(DMPanel.getInstance().mModel); return mInstance; } } public static boolean hasInstance() { return mInstance != null; } public static void reset() { mInstance = null; } public DMCanvas getCanvas() { return mCanvas; } public DMSimplePanel(DMModel model) { mModel = model; mModel.addDMModelListener(this); this.setLayout(new BorderLayout()); mCanvas = new DMCanvas(DMCanvas.NO_BACKGROUND_SELECTOR); mTitlePanel = new TitlePanel("Animation Panel"); mTitlePanel.mHelpButton.addMouseListener(new MouseAdapter() { @Override public void mouseClicked(MouseEvent me) { JOptionPane.showMessageDialog(DMSimplePanel.this, "VLJPanel has no help associated with it."); } }); // Add Record Button mRecordButton = new JButton("Record Animation"); mLoopButton = new JButton(); mResetButton = new JButton("Remove Animation"); mRecordButton.setEnabled(false); mLoopButton.setEnabled(false); mRecordImage = GraphicUtils.loadImageFromResource("/Assets/record.png"); mLoopImage = GraphicUtils.loadImageFromResource("/Assets/loop.png"); mLoopDisabledImage = GraphicUtils.loadImageFromResource("/Assets/loop_disabled.png"); mResetImage = GraphicUtils.loadImageFromResource("/Assets/reset.png"); mStopImage = GraphicUtils.loadImageFromResource("/Assets/stop.png"); mPlayImage = GraphicUtils.loadImageFromResource("/Assets/play.png"); mRecordButton.setIcon(new ImageIcon(mRecordImage)); mResetButton.setIcon(new ImageIcon(mResetImage)); mLoopButton.setIcon(new ImageIcon(mLoopDisabledImage)); mRecordButton.addMouseListener(new MouseAdapter() { @Override public void mousePressed(MouseEvent me) { mAnimation.moveToNextState(); } }); mTitlePanel.addButton(mRecordButton); mTitlePanel.addButton(mLoopButton); mLoopButton.addMouseListener(new MouseAdapter(){ @Override public void mousePressed(MouseEvent me) { mLooping = !mLooping; //Update Icon appropriately if(mLooping) DMSimplePanel.this.mLoopButton.setIcon(new ImageIcon(mLoopImage)); else DMSimplePanel.this.mLoopButton.setIcon(new ImageIcon(mLoopDisabledImage)); } }); mResetButton.addMouseListener(new MouseAdapter() { @Override public void mousePressed(MouseEvent me) { int n = JOptionPane.showOptionDialog(Activity.getInstance(), "Are you sure? This will reset your code.", "Aer you sure?", JOptionPane.OK_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE, null, null, null); if (n == JOptionPane.OK_OPTION) { DBParser.getInstance().getEvaluators().clear(); if(VLPanel.hasInstance()){ VLPanel.getInstance().mCanvas.clear(); VLPanel.getInstance().mCanvas.removeAll(); } mAnimation.reset(); DMSimplePanel.this.mRecordButton.setIcon(new ImageIcon(mRecordImage)); DMSimplePanel.this.mRecordButton.setText("Record Animation"); DMSimplePanel.this.repaint(); // Generate static image code DMPanel.getInstance().mModel.onPaperPanelUpdate(PaperPanel.getInstance()); if(TextPanel.hasInstance()) TextPanel.getInstance().moveToTop(); if(VLPanel.hasInstance()) VLPanel.getInstance().moveToTop(); } } }); mTitlePanel.addButton(mResetButton); add(mTitlePanel, BorderLayout.NORTH); add(mCanvas, BorderLayout.CENTER); } @Override public void onDMModelUpdate(DMModel model) { mCanvas.removeAll(); LinkedList<DMImage> images = model.getModelObjects(); LinkedList<DMObject> simpleObjects = new LinkedList<DMObject>(); for (DMImage image : images) { DMSimpleObject newObject = new DMSimpleObject(image); simpleObjects.add(newObject); mCanvas.add(newObject); } // Add Animation provisions Listener added mAnimation = new AnimationManager(this, simpleObjects); mRecordButton.setEnabled(true); mLoopButton.setEnabled(true); } /** * Method to update button images in preparation for the next state ONLY */ @Override public void onAnimationStateChange() { if (mAnimation != null) { AnimationManager.AnimationState newState = mAnimation.peekAtNextState(); switch (newState) { case STATE_RECORDING: DMSimplePanel.this.mRecordButton.setIcon(new ImageIcon(mRecordImage)); DMSimplePanel.this.mRecordButton.setText("Record"); DMSimplePanel.this.repaint(); break; case STATE_PLAYING: DMSimplePanel.this.mRecordButton.setIcon(new ImageIcon(mPlayImage)); DMSimplePanel.this.mRecordButton.setText("Play"); DMSimplePanel.this.repaint(); break; case STATE_STOPPED: DMSimplePanel.this.mRecordButton.setIcon(new ImageIcon(mStopImage)); DMSimplePanel.this.mRecordButton.setText("Stop"); DMSimplePanel.this.repaint(); break; } } } /** * Allows external components to check if animation is playing. * * @return */ public boolean isPlaying() { if (mAnimation != null) { return (mAnimation.getState() == AnimationManager.AnimationState.STATE_PLAYING); } else { return false; } } public boolean isStoppedAndEmpty() { if (mAnimation != null && mAnimation.getState() == AnimationManager.AnimationState.STATE_STOPPED && mAnimation.getRawCode() != null) { return (mAnimation.getRawCode().equals("")); } else { return false; } } // Called when tweening has finished public void finishedProcessing() { if (mAnimation.getState() == AnimationState.STATE_PLAYING){ mAnimation.moveToNextState(); if(mLooping) mAnimation.moveToNextState(); // <- to repeat the animation indefinitely } } /** * Method executes current code */ public void requestAnimationStart() { if (mAnimation != null) { if (mAnimation.getState() == AnimationState.STATE_PLAYING) { mAnimation.moveToNextState(); mAnimation.moveToNextState(); } else if (mAnimation.getState() == AnimationState.STATE_STOPPED) { if (!mAnimation.getRawCode().equals("")) { mAnimation.moveToNextState(); } else { // Simply execute the text if(TextPanel.hasInstance()){ JsEngine.getInstance().executeCode(TextPanel.getInstance(), TextPanel.getInstance().getDocument().getText(), true); } else if(VLPanel.hasInstance()){ //Do something Utils.out.println(getClass(), "Attempting to executeCode!"); JsEngine.getInstance().executeCode(VLPanel.getInstance(), VLPanel.getInstance().mCanvas.getModel().generateCodeFromBlocks(VLPanel.getInstance().mCanvas.mViewGrid), true); } else{ //Do nothing, we can't execute Utils.out.println(getClass(), "Can't request any animation - neither Text or Visual is available!"); } } } else { Utils.out.println(this.getClass(),"requestAnimationStart failed:" + mAnimation.getState().name()); } } } }