是否仍然可以看到不可见的组件?

时间:2014-03-05 17:48:06

标签: java swing paint

似乎明显的答案是否定的,但无论如何我想知道。

如果我的面板中有许多复杂的组件需要一段时间来加载,然后在顶部有另一个非常基本的面板,完全覆盖它,背景面板是否仍然会在绘制方法中绘制?

3 个答案:

答案 0 :(得分:3)

(编辑:camickr的答案是真正正确的答案)

Java确实有一个重绘管理器,可以确保只重新绘制组件的“脏”区域。更多信息:http://www.oracle.com/technetwork/java/painting-140037.html#mgr

但是,重绘管理器是否可以正常工作可能取决于您的代码(甚至可能取决于系统?)。

测试此方法的最佳方法是扩展组件并覆盖其paintComponent()方法,以便在重新绘制组件时打印消息。将该组件添加到正在覆盖的JPanel中,并查看是否正在触发该组件的paintComponent()方法。

答案 1 :(得分:3)

是的,您可以将组件涂在彼此之上。顶部面板下方显示的内容取决于顶部面板的不透明度。

请参阅Glass Pane示例。另请参阅How to Use Layered Panes示例的目录。

编辑:

  

似乎明显的答案是没有

我现在更好地理解这个问题了。您要问的是,即使在复杂面板的顶部涂有不透明面板,是否仍会对复杂组件的绘制进行绘制。答案是肯定的,在顶部组件涂漆之前,底部组件将被涂漆。

每个Swing组件负责绘制其子组件。通常,组件以二维方式布局,但像OverlayLayout这样的布局允许您将组件绘制在彼此之上。在这种情况下,除非您使组件不可见,否则所有组件都会被绘制。简单的例子:

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.border.*;

public class OverlayPanel extends JPanel
{
    private static int ctr = 1;

    public OverlayPanel(String name)
    {
        setName( name );
        add( new JLabel("Label " + ctr++) );
    }

    @Override
    protected void paintComponent(Graphics g)
    {
        System.out.println("Painting: " + getName());
        super.paintComponent(g);
    }

    private static void createAndShowUI()
    {
        JPanel panel = new JPanel();
        panel.setLayout( new OverlayLayout(panel) );

        panel.add( new OverlayPanel("first") );
        panel.add( new OverlayPanel("second") );

        JPanel third = new OverlayPanel("third");
        third.setVisible(false);
        panel.add(third);

        JFrame frame = new JFrame("OverlayPanel");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add( panel );
        frame.pack();
        frame.setLocationByPlatform( true );
        frame.setVisible( true );
    }

    public static void main(String[] args)
    {
        EventQueue.invokeLater(new Runnable()
        {
            public void run()
            {
                createAndShowUI();
            }
        });
    }
}

答案 2 :(得分:0)

我认为您可以在System.out.println("painting..")中的public void paintComponent(Graphics g)中尝试JPanel,看看会发生什么。