/**
  *
  * OnlyAnImage
  * for ProVisu
  * programming sample
  *
  * showing only an image
  *
  * @author Peter Beck
  */

package de.p_b_e.provisu.components.onlyanimage;


import de.p_b_e.provisu.interfaces.ProVisuComponent;
import de.p_b_e.provisu.interfaces.ProVisuDevice;
import de.p_b_e.provisu.components.*; //JMenueItemXxx...
import de.p_b_e.provisu.components.grouppanel.GroupPanel;
import de.p_b_e.utilities.config.Settings;

import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;
import java.util.*;
import java.io.*;
import javax.swing.*;


public class OnlyAnImage extends JComponent
   implements ProVisuComponent, MouseListener {

  private static final String[] settingsValue = {
       "Is",
       "Visible",
       "Image",
       "Transparent",
       "ShowImage",
       "Width",
       "Height",
       "X",
       "Y"};
  private String address;
  private String name;
  private Paint painter;
  private Image image;

  private Settings settings;
  private JFrame propertyFrame;


  /* ********************************************************************* */
  /* **************      Constructors   ********************************** */
  /* ********************************************************************* */
  /**
   *  constructor for first component generatet at startup,
   *  this first instance generates additional new instances
   */
  public OnlyAnImage(Settings sets){
     super();
     settings = sets;
  } // end constructor
  
  /**
   *  constructor for instances
   */
  public OnlyAnImage(ArrayList <ProVisuDevice>dev, String adr, Settings sets)
  {
    super();
    address = adr;
    settings=sets;
    name = settings.getProperty(address,address);
    propertyFrame=null;

  } // end constructor
  

  /* ********************************************************************* */
  /* **************      getInstance   *********************************** */
  /* ********************************************************************* */
  /**
   *  return new instance of this component
   */
   public ProVisuComponent getInstance(ArrayList <ProVisuDevice>devices, String adr, Settings sets){
      return new OnlyAnImage(devices, adr, sets);
   } // end getInstance()
   
  /* ********************************************************************* */
  /* **************      getMenuName   *********************************** */
  /* ********************************************************************* */
  /**
   *  return menu name for component
   */
   public String getMenuName(){
      return "OnlyAnImage";
   } // end getMenuName()


  /* ********************************************************************* */
  /* **************      init OnlyAnImage   ******************************* */
  /* ********************************************************************* */
  /**
   *  intit and show component
   */
  public void init(){
    
    addMouseListener(this);

    // ***  Size and Position *********************
    int x = settings.getPropertyInt(address+"X","100");
    int y = settings.getPropertyInt(address+"Y","100");
    int width = settings.getPropertyInt(address+"Width","200");
    int height = settings.getPropertyInt(address+"Height","150");
    setSize(width,height);
    setLocation(x,y);


    // ***  set transparent *********************
    String isTransparent = settings.getProperty(address+"Transparent","FALSE");
    if (isTransparent.equals("TRUE")) {
      setOpaque(false);
    }
    else{
      setOpaque(true);
    }

    // ***  background *********************
    String isImage = settings.getProperty(address+"Image","");
    if (!isImage.equals("") ){
       try{
//         setImage(ImageIO.read(new File(isImage)));    // returns bufferedImage no animated GIF
         setImage(new ImageIcon(isImage).getImage());    // Image
       }
       catch (Exception e) { }
    }

    setPaint(Color.RED);


  }  // end init()
  
  
  /* ********************************************************************* */
  /* **************      disposePropertyFrame     ************************ */
  /* ********************************************************************* */
  /**
   *  dispose the Property Frame
   */
   public void disposePropertyFrame(){
      propertyFrame=null;
      
   } // end disposePropertyFrame()



  /* ********************************************************************* */
  /* **************      getAddress     ********************************** */
  /* ********************************************************************* */
  /**
   *  get the address of component
   */
  public String getAddress(){
    return address;
    
  } // end getAddress
  

  /* ********************************************************************* */
  /* **************      getName     ************************************* */
  /* ********************************************************************* */
  /**
   *  get the name of component
   */
  public String getName(){
    return name;
    
  } // end getName()
  

  /* ********************************************************************* */
  /* **************      setName     ************************************* */
  /* ********************************************************************* */
  /**
   *  set the name of component
   */
  public void setName(String var){
    firePropertyChange("name",name,var);
    name = var;
    settings.setProperty(address,name);
    
  } // end setName()
  

  /* ********************************************************************* */
  /* **************      clone     *************************************** */
  /* ********************************************************************* */
  /**
   *  clone component
   */
  public void clone(String parent){
  
    String value = settings.getProperty(parent,"NULL");
    if (!value.equals("NULL")) {
      name=value;
      settings.setProperty(address,value);
    }
    for (String setValue : settingsValue) {
      value = settings.getProperty(parent+setValue,"NULL");
      if (!value.equals("NULL")) settings.setProperty(address+setValue,value);
    }
    init();

  } // end clone()


  /* ********************************************************************* */
  /* **************      delete     ************************************** */
  /* ********************************************************************* */
  /**
   *  delete component
   */
  public void delete(){

       settings.remove(address);
       for (String setValue : settingsValue) settings.remove(address+setValue);
       ((GroupPanel)this.getParent()).deleteComponent(this);
       
  } // end delete()
  
  
  /* ********************************************************************* */
  /* **************      export     ************************************** */
  /* ********************************************************************* */
  /**
   *  export the settings to export file
   */
  public boolean export(BufferedWriter bw){

       try{
          String value = settings.getProperty(address,"NULL");
          if (!value.equals("NULL")) {
            bw.write("Ex"+address+"="+value);
            bw.newLine();
          }
          for (String setValue : settingsValue) {
            value = settings.getProperty(address+setValue,"NULL");
            if (!value.equals("NULL")) {bw.write("Ex"+address+setValue+"="+value);bw.newLine();}
          }
       }
       catch(Exception e){
         return false;
       }

       return true;
       
  } // end export()



  
  /* ********************************************************************* */
  /* **************      MouseListener Events    ************************* */
  /* ********************************************************************* */
  /**
   *  verify if mouse event is popup trigger an show popup
   */
  private void verifyPopupTrigger( MouseEvent evt ){

    String configMode = settings.getProperty("configMode");
    if (configMode.equals("TRUE")) {    // config mode ? show popup
    
      Object source = evt.getSource();

      if ( (source==this) && evt.isPopupTrigger() && !evt.isControlDown() && !evt.isShiftDown() ){


      // *** generate PopUp Menue ************************************************
        final ResourceBundle messages = settings.getMessages();
        final JPopupMenu popup = new JPopupMenu();

        JMenuItem popupProperties =  new JMenuItem(messages.getString("Popup.Properties"));
        JMenuItem popupExport =  new JMenuItemExport(this,settings);
        JMenuItem popupForeGround = new JMenuItemInToForeground(this, settings);
        JMenuItem popupCopy =  new JMenuItemCopy(this, settings);
        JMenuItem popupInvisible = new JMenuItemInvisible(this, settings);
        JMenuItem popupDelete = new JMenuItemDelete(this, settings);


     // *** add Actions  ********************************************************

        popupProperties.addActionListener(new ActionListener() {
           public void actionPerformed(ActionEvent e) {
              if (propertyFrame == null)  propertyFrame = new PropertyFrame(OnlyAnImage.this, settings);
              else  {
                propertyFrame.setVisible(true);
                propertyFrame.setExtendedState(Frame.NORMAL);
                propertyFrame.toFront();
              }
           }
        });

        // insert popup elements
        popup.add(popupProperties);
        popup.addSeparator();
        popup.add(popupExport);
        popup.add(popupForeGround);
        popup.add(popupCopy);
        popup.add(popupInvisible);
        popup.add(popupDelete);

        popup.show(evt.getComponent(),evt.getX(),evt.getY());
        
      }
    }
  } // end verifyPopupTrigger()
  
  public void mouseReleased(MouseEvent evt){verifyPopupTrigger( evt );}
  public void mouseExited(MouseEvent evt){}
  public void mouseEntered(MouseEvent evt){}
  public void mousePressed(MouseEvent evt){verifyPopupTrigger( evt );}
  public void mouseClicked(MouseEvent evt){}
  

  /* ********************************************************************* */
  /* **************      setVisible    *********************************** */
  /* ********************************************************************* */
  /**
   *  Set the component visible and save to settings
   */
  public void setVisible(boolean isVisible ){

    super.setVisible(isVisible);

      if (isVisible) {
        if (settings.getProperty(address+"Visible","NULL").equals("FALSE")) settings.remove(address+"Visible");
      }
      else {
        if (!settings.getProperty(address+"Visible","NULL").equals("FALSE")) settings.setProperty(address+"Visible","FALSE");
      }

  } // end setVisible()



  /* ********************************************************************* */
  /* **************      setImage    ************************************* */
  /* ********************************************************************* */
  /**
   *  Set the image used as the background
   */
  public void setImage(Image image)
  {
    this.image = image;
    repaint();
    
  } // ens setImage()


  /* ********************************************************************* */
  /* **************      setPaint    ************************************* */
  /* ********************************************************************* */
  /**
   *  Set the Paint object used to paint the background
   */
  public void setPaint(Paint painter)
  {
    this.painter = painter;
    repaint();
    
  } // end setPaint
  

  /* ********************************************************************* */
  /* **************      paintComponent    ******************************* */
  /* ********************************************************************* */
  /**
   *  Add background painting
   */
  protected void paintComponent(Graphics g)
  {
    super.paintComponent(g);

    String isShowImage = settings.getProperty(address+"ShowImage","FALSE");

    if (!isOpaque() && isShowImage.equals("FALSE") ) return; // do nothing if transparence

    // Draw background Color
    if (painter != null && isOpaque() ) {
      Dimension d = getSize();
      Graphics2D g2 = (Graphics2D) g;
      g2.setPaint(painter);
      g2.fill( new Rectangle(0, 0, d.width, d.height) );
    }

    //  Draw the image
    if (image != null ) {
    //***** draw image scaled  *****
//      Dimension d = getSize();
//      g.drawImage(image, 0, 0, d.width, d.height, null);

    //***** draw image actual and centered  *****
      Dimension d = getSize();
      Insets insets = getInsets();
      int width = d.width - insets.left - insets.right;
      int height = d.height - insets.top - insets.bottom;
      float x = (width - image.getWidth(null)) * 0.5f;
      float y = (height - image.getHeight(null)) * 0.5f;
      g.drawImage(image, (int)x + insets.left, (int)y + insets.top, this);
    }
  }  // end paintComponent


}  // end class OnlyAnImage



