2016-01-18 4 views
0

Я пытаюсь создать расширенный JPanel, который действует как способ выделения некоторой области экрана. Я взял код от this SO answer, но хотел бы расширить его, хотя я не уверен, как это сделать.Создайте исчезающий JPanel?

Я хочу, чтобы мои JPanel (MatchAreaPanel ниже) исчезли после достижения заданного таймаута. То есть JPanel устанавливает свое видимое свойство в false и впоследствии удаляет себя.

Что было бы лучшим способом сделать это?

import java.awt.BasicStroke; 
import java.awt.Color; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import javax.swing.JPanel; 

public class MatchAreaPanel extends JPanel 
{ 
    public MatchAreaPanel() 
    { 

    } 

    @Override 
    protected void paintComponent(Graphics g) 
    { 
     super.paintComponent(g); 
     Graphics2D g2d = (Graphics2D) g.create(); 
     g2d.setColor(new Color(128, 128, 128, 64)); 
     g2d.fillRect(0, 0, getWidth(), getHeight()); 

     float dash1[] = {10.0f}; 
     BasicStroke dashed = new BasicStroke(3.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 10.0f, dash1, 0.0f); 
     g2d.setColor(Color.BLACK); 
     g2d.setStroke(dashed); 
     g2d.drawRect(0, 0, getWidth() - 3, getHeight() - 3); 
     g2d.dispose(); 
    } 
} 
+1

Возможно, вы захотите использовать Swing 'Timer' – MadProgrammer

+0

Это то, что я подумал, но могу ли я получить доступ к компонентам пользовательского интерфейса из его тикаемого метода? – KDecker

+1

Это то, к чему относится Swing 'Timer',« ActionListener »уведомляется из контекста EDT – MadProgrammer

ответ

3

Вы можете использовать свинг Timer просто запланировать обратный вызов после заданной задержки и закрыть окно, связанное или скрытия компонента в зависимости от потребностей, к примеру ...

import java.awt.BasicStroke; 
import java.awt.Color; 
import java.awt.EventQueue; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import java.awt.GraphicsDevice; 
import java.awt.GraphicsEnvironment; 
import java.awt.Rectangle; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 
import java.awt.event.MouseAdapter; 
import java.awt.event.MouseEvent; 
import java.util.Random; 
import javax.swing.JPanel; 
import javax.swing.JWindow; 
import javax.swing.SwingUtilities; 
import javax.swing.Timer; 
import javax.swing.UIManager; 
import javax.swing.UnsupportedLookAndFeelException; 

public class Test { 

    public static void main(String[] args) { 
     new Test(); 
    } 

    public Test() { 
     EventQueue.invokeLater(new Runnable() { 
      @Override 
      public void run() { 
       try { 
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 
       } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { 
        ex.printStackTrace(); 
       } 

       Rectangle bounds = getVirtualBounds(); 
       Random rnd = new Random(); 
       int x = bounds.x + (rnd.nextInt(bounds.width) - 100); 
       int y = bounds.y + (rnd.nextInt(bounds.height) - 100); 

       MatchAreaPanel pane = new MatchAreaPanel(); 
       JWindow frame = new JWindow(); 
       frame.setBackground(new Color(0, 0, 0, 0)); 
       frame.add(pane); 
       frame.setBounds(x, y, 100, 100); 
       frame.setLocationRelativeTo(null); 
       frame.setVisible(true); 
       pane.start(); 
      } 
     }); 
    } 

    public static Rectangle getVirtualBounds() { 

     Rectangle bounds = new Rectangle(0, 0, 0, 0); 

     GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment(); 
     GraphicsDevice gd = ge.getDefaultScreenDevice(); 
     bounds.add(gd.getDefaultConfiguration().getBounds()); 

     return bounds; 

    } 

    public class MatchAreaPanel extends JPanel { 

     public MatchAreaPanel() { 
      setOpaque(false); 
      addMouseListener(new MouseAdapter() { 
       @Override 
       public void mouseClicked(MouseEvent e) { 
        SwingUtilities.windowForComponent(MatchAreaPanel.this).dispose(); 
       } 
      }); 
     } 

     public void start() { 
      Timer timer = new Timer(5000, new ActionListener() { 
       @Override 
       public void actionPerformed(ActionEvent e) { 
        SwingUtilities.windowForComponent(MatchAreaPanel.this).dispose(); 
       } 
      }); 
      timer.start(); 
     } 

     @Override 
     protected void paintComponent(Graphics g) { 
      super.paintComponent(g); 
      Graphics2D g2d = (Graphics2D) g.create(); 
      g2d.setColor(new Color(128, 128, 128, 64)); 
      g2d.fillRect(0, 0, getWidth(), getHeight()); 

      float dash1[] = {10.0f}; 
      BasicStroke dashed = new BasicStroke(3.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 10.0f, dash1, 0.0f); 
      g2d.setColor(Color.BLACK); 
      g2d.setStroke(dashed); 
      g2d.drawRect(0, 0, getWidth() - 3, getHeight() - 3); 
      g2d.dispose(); 
     } 
    } 

} 

How to use Swing Timers Смотреть для получения более подробной информации

Обновлено ...

Теперь, просто "прячется" панель, скучная, также возможно, чтобы пользователь пропустил панель, так как внезапное появление не гарантирует, что пользователь ее увидит, поэтому вместо этого вы можете добавить эффект постепенного уменьшения.

В этом примере, вы можете исчезать панели, щелкнув его (но я сделал это как часть моего тестирования, так что вам не нужно) или по истечении заданного времени ожидания ...

import java.awt.AlphaComposite; 
import java.awt.BasicStroke; 
import java.awt.Color; 
import java.awt.EventQueue; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import java.awt.GraphicsDevice; 
import java.awt.GraphicsEnvironment; 
import java.awt.Rectangle; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 
import java.awt.event.MouseAdapter; 
import java.awt.event.MouseEvent; 
import java.util.Random; 
import javax.swing.JPanel; 
import javax.swing.JWindow; 
import javax.swing.SwingUtilities; 
import javax.swing.Timer; 
import javax.swing.UIManager; 
import javax.swing.UnsupportedLookAndFeelException; 

public class Test { 

    public static void main(String[] args) { 
     new Test(); 
    } 

    public Test() { 
     EventQueue.invokeLater(new Runnable() { 
      @Override 
      public void run() { 
       try { 
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 
       } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { 
        ex.printStackTrace(); 
       } 

       Rectangle bounds = getVirtualBounds(); 
       Random rnd = new Random(); 
       int x = bounds.x + (rnd.nextInt(bounds.width) - 100); 
       int y = bounds.y + (rnd.nextInt(bounds.height) - 100); 

       MatchAreaPanel pane = new MatchAreaPanel(); 
       JWindow frame = new JWindow(); 
       frame.setBackground(new Color(0, 0, 0, 0)); 
       frame.add(pane); 
       frame.setBounds(x, y, 100, 100); 
       frame.setLocationRelativeTo(null); 
       frame.setVisible(true); 
       pane.start(); 
      } 
     }); 
    } 

    public static Rectangle getVirtualBounds() { 

     Rectangle bounds = new Rectangle(0, 0, 0, 0); 

     GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment(); 
     GraphicsDevice gd = ge.getDefaultScreenDevice(); 
     bounds.add(gd.getDefaultConfiguration().getBounds()); 

     return bounds; 

    } 

    public static class MatchAreaPanel extends JPanel { 

     protected static final long FADE_OUT_TIME = 2500; 

     private float alpha = 1f; 
     private long fadeStartAt; 
     private Timer fadeTimer; 
     private Timer waitTimer; 

     public MatchAreaPanel() { 
      setOpaque(false); 
      addMouseListener(new MouseAdapter() { 
       @Override 
       public void mouseClicked(MouseEvent e) { 
        fadeOut(); 
       } 
      }); 
      fadeTimer = new Timer(40, new ActionListener() { 
       @Override 
       public void actionPerformed(ActionEvent e) { 
        long runTime = System.currentTimeMillis() - fadeStartAt; 
        float progress = 0f; 
        if (runTime >= FADE_OUT_TIME) { 
         progress = 1f; 
        } else { 
         progress = (float) runTime/(float) FADE_OUT_TIME; 
         if (progress > 1f) { 
          progress = 1f; 
         } 
        } 
        alpha = 1f - progress; 

        if (progress >= 1f) { 
         ((Timer) e.getSource()).stop(); 
         SwingUtilities.windowForComponent(MatchAreaPanel.this).dispose(); 
        } 
        repaint(); 
       } 
      }); 
      waitTimer = new Timer(5000, new ActionListener() { 
       @Override 
       public void actionPerformed(ActionEvent e) { 
        ((Timer) e.getSource()).stop(); 
        fadeOut(); 
       } 
      }); 
     } 

     protected void fadeOut() { 
      waitTimer.stop(); 
      fadeStartAt = System.currentTimeMillis(); 
      fadeTimer.start(); 
     } 

     public void start() { 
      if (!waitTimer.isRunning() && !fadeTimer.isRunning()) { 
       waitTimer.start(); 
      } 
     } 

     @Override 
     protected void paintComponent(Graphics g) { 
      super.paintComponent(g); 
      Graphics2D g2d = (Graphics2D) g.create(); 
      g2d.setComposite(AlphaComposite.SrcOver.derive(alpha)); 
      g2d.setColor(new Color(128, 128, 128, 64)); 
      g2d.fillRect(0, 0, getWidth(), getHeight()); 

      float dash1[] = {10.0f}; 
      BasicStroke dashed = new BasicStroke(3.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 10.0f, dash1, 0.0f); 
      g2d.setColor(Color.BLACK); 
      g2d.setStroke(dashed); 
      g2d.drawRect(0, 0, getWidth() - 3, getHeight() - 3); 
      g2d.dispose(); 
     } 
    } 

} 
+0

. Я полагаю, что« MouseListener », добавленный вами в конструктор, закроет панель, если она нажата? Это никак не связано с таймером? – KDecker

+0

Нет, это просто, поэтому я могу закрыть окно, пока я его тестировал, вам это не нужно, но это может обеспечить хороший способ для пользователя очистить окно – MadProgrammer