How to change background color of a JPanel when mouse enters another JPanel

时间:2015-09-14 15:55:07

标签: java swing mouselistener gridbaglayout

Im new to java Swing and this is my first question so excuse my faults..Im trying to make a JPanel (Container) that has a GridBagLayout and holds a number of smaller Jpanels which will serve as Buttons. I set to each small JPanel a mouseEntered Listener who changes the background Color to the one that enters. Is it possible to change the color also on the row and column of that Panel? For example if i enter the mouse in Cell(4,3) i want the background of cells (4,0) and (0,3) alse to be changed.

this is my Container:

public class CellPane extends JPanel{

   private List<Cell> cellList;
   private final GridBagConstraints gbc;
   private Cell cell;
   private int counter;

   public CellPane(){

     this.setLayout(new GridBagLayout()); 
     gbc = new GridBagConstraints();
     cellList = new ArrayList<>();
     counter = 0;
        for(int row=0;row<15;row++)
            for(int col=0;col<31;col++){
                gbc.gridx = col;
                gbc.gridy = row;

                cell = new Cell(col ,row);

                Border border = null;
                if (row < 14) {
                    if (col < 30) {
                        border = new MatteBorder(1, 1, 0, 0, new Color(153,204,204));
                    } else {
                        border = new MatteBorder(1, 1, 0, 1, new Color(153,204,204));
                    }
                } else {
                    if (col < 30) {
                        border = new MatteBorder(1, 1, 1, 0, new Color(153,204,204));
                    } else {
                        border = new MatteBorder(1, 1, 1, 1, new Color(153,204,204));
                    }
                }

                cell.setBorder(border);
                cellList.add(counter, cell);
                counter++;
                this.add(cell,gbc);                   
            }  
        System.out.println("Count: " + this.getComponentCount());
        for(Cell c: cellList){
            System.out.println(c.getCellCol()+" "+c.getCellRow());
        }
   }

   public List getCellList(){
       return cellList;
   }
   public int getCellCount(){
       return counter;
   }}

And here is the cell Class

class Cell extends JPanel implements MouseListener, PropertyChangeListener{

    private final Color defaultBackground = new Color(240,240,240);
    private final Color clickedColor = new Color(204,0,102);
    private final Color movingColor = new Color(153,255,153);
    private final int row ,col;
    //private CellPane cp = new CellPane();

    public Cell(int x, int y) {
      this.col = x;
      this.row = y;

      if (col>0 & row>0){
        addMouseListener(this);           
      }
      if(col==0 | row == 0){
          addPropertyChangeListener(this);
      }
      if (col == 0){
          this.setPreferredSize(new Dimension(100,35));
      }
      else{
          this.setPreferredSize(new Dimension(35,35));
      }
    }

@Override
public void mouseClicked(MouseEvent me) {
}

@Override
public void mousePressed(MouseEvent me) {
    if(col>0 & row>0 & this.getBackground().equals(movingColor)){
        this.setBackground(clickedColor);        
    }
    else if(this.getBackground().equals(clickedColor)){
        this.setBackground(defaultBackground);
    }
}

@Override
public void mouseReleased(MouseEvent me) {
}

@Override
public void mouseEntered(MouseEvent me) {
    if(col>0 & row>0 & this.getBackground().equals(defaultBackground)){
        this.setBackground(movingColor);
        System.out.println("You clicked on: " + col +" " +row);
        System.out.println("List Size:  " );
    }       
}

@Override
public void mouseExited(MouseEvent me) {
    if(col>0 & row>0 & this.getBackground().equals(movingColor)){
        this.setBackground(defaultBackground);        
    }       
}

@Override
public void propertyChange(PropertyChangeEvent pce) {

}

public int getCellCol(){
    return this.col;
}
public int getCellRow(){
    return this.row;
}}

and here is the main Class

public class ScheduleForm {

private JFrame mainFrame;
private JPanel pnlButtons;
private JPanel pnlCalendar;
private CellPane cellPane;


    public ScheduleForm(){
        initButtonPanel();
        initCalendarPane();
        initFrame();
    }                    

    private void initCalendarPane(){
       pnlCalendar = new JPanel(new BorderLayout());
       pnlCalendar.setPreferredSize(new Dimension(100,500));
       pnlCalendar.setBorder(BorderFactory.createLineBorder(Color.ORANGE));
       cellPane = new CellPane();
       pnlCalendar.add(cellPane,BorderLayout.CENTER);
    }

    private void initButtonPanel(){
       pnlButtons = new JPanel(new BorderLayout());
       pnlButtons.setPreferredSize(new Dimension(100,100));
       pnlButtons.setBorder(BorderFactory.createTitledBorder("Buttons"));  
            }

    private void initFrame(){                                            
       mainFrame = new JFrame("Schedule");
       mainFrame.setLayout(new BorderLayout());
       mainFrame.add(pnlButtons, BorderLayout.NORTH);
       mainFrame.add(pnlCalendar,BorderLayout.CENTER);
       mainFrame.pack();
       mainFrame.setLocationRelativeTo(mainFrame);
       mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
       mainFrame.setVisible(true);
       mainFrame.setExtendedState(java.awt.Frame.MAXIMIZED_BOTH);                
    }

    public static void main(String args[]) {
    /* Set the Nimbus look and feel */
    //<editor-fold defaultstate="collapsed" desc=" Look and feel setting code (optional) ">
    /* If Nimbus (introduced in Java SE 6) is not available, stay with the default look and feel.
     * For details see http://download.oracle.com/javase/tutorial/uiswing/lookandfeel/plaf.html 
     */
    try {
        for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) {
            if ("Nimbus".equals(info.getName())) {
                javax.swing.UIManager.setLookAndFeel(info.getClassName());
                break;
            }
        }
    } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | javax.swing.UnsupportedLookAndFeelException ex) {
        java.util.logging.Logger.getLogger(PopTest.class.getName()).log(java.util.logging.Level.SEVERE, null, ex);
    }
    //</editor-fold>

    /* Create and display the form */
    java.awt.EventQueue.invokeLater(new Runnable() {
        @Override
        public void run() {                                
            try {
                UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
            } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
            }
            ////EDW tha mpei to neo antikeimeno
            ScheduleForm scheduleForm = new ScheduleForm();
        }
    });
}}

1 个答案:

答案 0 :(得分:2)

Possible solution:

  1. Give Cell public methods to allow outside classes to change background color state.
  2. In the Cell's MouseListener fire a property change whenever mouse enters or mouse leaves.
  3. Have your model (if using a recommended clean MVC pattern) listen for these changes and notify the view of the changes so that row and column color can change.
  4. If not using clean MVC but rather quick and dirty GUI, then have CellPane add a PropertyChangeListener to the Cells so that it is notified of individual Cell state changes WRT mouse enter/leave, and then CellPane can change the row and column colors by calling the public methods in point 1 above.