【问题标题】:How to change the color of an individual ellipse when clicking a jButton?单击jButton时如何更改单个椭圆的颜色?
【发布时间】:2014-08-04 00:16:29
【问题描述】:

我希望能够单击 JButton 并将我制作的下一个单独的椭圆从默认的蓝色更改为各自的颜色,红色或黑色。到目前为止,我已经能够更改所有椭圆的颜色。

public class MainClient {

private JFrame frame;

/**
 * Launch the application.
 */
public static void main(String[] args) {
    EventQueue.invokeLater(new Runnable() {
        public void run() {
            try {
                MainClient window = new MainClient();
                window.frame.setVisible(true);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    });
}

/**
 * Create the application.
 */
public MainClient() {
    initialize();
}

/**
 * Initialize the contents of the frame.
 */
    private void initialize() {
    frame = new JFrame();
    frame.setBounds(100, 100, 800, 600);
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

    final SpriteField panel = new SpriteField();
    panel.setBounds(0, 110, 782, 331);
    panel.addMouseListener(new MouseAdapter() {
        @Override
        public void mouseClicked(MouseEvent e) {
            int tX = e.getX();
            int tY = e.getY();
            panel.CreateObjectAt(tX,tY);
        }
    });
    frame.getContentPane().setLayout(null);
    panel.setBackground(Color.LIGHT_GRAY);
    frame.getContentPane().add(panel);

    final JButton btnRed = new JButton("black");
    btnRed.addMouseListener(new MouseAdapter() {
        @Override
        public void mouseClicked(MouseEvent e) {
            panel.setColor(Color.BLACK);
        }
    });
    btnRed.setBounds(229, 500, 97, 25);
    frame.getContentPane().add(btnRed);

    JButton btnRed_1 = new JButton("red");
    btnRed_1.addMouseListener(new MouseAdapter() {
        @Override
        public void mouseClicked(MouseEvent e) {
            panel.setColor(Color.RED);
        }
    });
    btnRed_1.setBounds(342, 500, 97, 25);
    frame.getContentPane().add(btnRed_1);

}

}

我有一个 SriteField 类

public class SpriteField extends JPanel
{
    ArrayList<RoundSprite>mSprites = new ArrayList<RoundSprite>();

    private Color color = Color.BLUE;
    @Override
    protected void paintComponent(Graphics g)
    {
        super.paintComponent(g);
        Graphics2D g2 = (Graphics2D)g;
        AffineTransform tOldTransform = g2.getTransform();

        for(RoundSprite tOne:mSprites)
        {
            tOne.DrawSprite(g2, color);
        }
        g2.setTransform(tOldTransform);
    }
    public void CreateObjectAt(int tX, int tY)
    {
        //make sprite
        RoundSprite mLonely = new RoundSprite();
        //set position
        mLonely.SetPosition(tX, tY);
        //add to array
        mSprites.add(mLonely);
        repaint();
    }
    public void setColor(Color color)
    {
        this.color = color;
        repaint();
    }

}

我有一个 RoundSprite 类

public class RoundSprite 
{
int mX;
int mY;
private Color color;
void DrawSprite(Graphics2D g2, Color color)
{

    AffineTransform tOldTransform = g2.getTransform();
    g2.setColor(color);
    g2.translate(mX, mY); //got it out from the corner

    g2.draw(new Ellipse2D.Double(-15, -22, 30, 50));

    g2.setTransform(tOldTransform);

}
public void SetPosition(int tX, int tY) //g2.translate
{
    mX = tX;
    mY = tY;        
}

【问题讨论】:

  • 避免使用null 布局,像素完美的布局是现代用户界面设计中的一种错觉。影响组件单个尺寸的因素太多,您无法控制。 Swing 旨在与核心布局管理器一起工作,丢弃这些将导致无穷无尽的问题和问题,您将花费越来越多的时间来尝试纠正

标签: java swing jbutton mouselistener ellipse


【解决方案1】:

存在三个核心问题...

一个

为了使panel_1 MouseListener 更改panel 内的精灵颜色,MouseListener 需要引用panel

您可以在initialize 方法中将panel 声明为final,但我更喜欢将panel 设为privateprivate 实例字段MainClient

两个

为了更改颜色,SpriteField 需要提供一种方式,让相关方可以请求更改。

这将要求SpriteField 提供某种方法,相关方可以在需要时调用,例如setColor 方法...

public class SpriteField extends JPanel {

    private Color color = Color.BLACK;
    //...
    public void setColor(Color color) {
        this.color = color;
        repaint();
    }

那么panel_1MouseListener 现在可以引用SpriteField 并调用可以产生变化的方法...

panel_1.addMouseListener(new MouseAdapter() {
    @Override
    public void mouseClicked(MouseEvent e) {
        System.out.println("Click");
        panel.setColor(Color.BLUE);
    }
});

三个

你需要一些方法来告诉精灵它应该是什么颜色...

这取决于你想要实现什么......

如果你想为所有的精灵绘制相同的颜色,那么你需要一些方法来告诉精灵他们应该使用哪种颜色,例如,你可以更改DrawSprite 方法以接受Color 参数。 .

public class RoundSprite {
    //...
    void DrawSprite(Graphics2D g2, Color color) {

SpriteFieldpaintComponent内,将颜色传递给精灵

public class SpriteField extends JPanel {
    //...
    private Color color = Color.BLACK;

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2 = (Graphics2D) g;
        AffineTransform tOldTransform = g2.getTransform();


        for (RoundSprite tOne : mSprites) {
            tOne.DrawSprite(g2, color);
        }
        g2.setTransform(tOldTransform);
    }

现在,这会将场内的所有精灵涂成相同的颜色,如果你想改变单个精灵的颜色,这会变得无限复杂......

让我们暂时先把选择精灵的问题放在一边……

基本上,您需要将相同的原则从第二点应用到RoundSprite 类。

您需要提供一种可以set/get 所需颜色的方法。您需要将此值存储在 RoundSprite 类的实例字段中,并在调用 DrawSprite 时,将 Color 应用于 Graphics 上下文。

这意味着SpriteField 不需要执行任何颜色管理,除了将更改请求从调用者传递给选定的精灵,因此它仍然需要setColor 方法...

旁注...

您可能想通读一下Code Conventions for the Java TM Programming Language,它将使人们更容易阅读您的代码并让您更轻松地阅读其他人

避免使用null 布局,像素完美的布局是现代用户界面设计中的一种错觉。影响组件单个尺寸的因素太多,您无法控制。 Swing 旨在与核心的布局管理器一起工作,丢弃这些将导致无穷无尽的问题和问题,您将花费越来越多的时间来尝试纠正

哦,你意识到已经有一个 JButton 类可能应该使用而不是 JPanelMouseListener....?

【讨论】:

  • 感谢您的帮助。这是我的第一篇文章,所以我尽可能地编写我的代码。我已经切换到 Jbutton,一切都解决了。我确定我需要更改每个椭圆的颜色,因为稍后我需要调整每个椭圆的大小和旋转以及撤消一个。
  • 然后您需要定义一种方法,您可以通过该方法选择单个精灵,可能通过SpriteField 上的MouseListener 循环遍历mSprites 列表并确定鼠标是否“击中”任何精灵...
猜你喜欢
  • 1970-01-01
  • 2014-05-18
  • 1970-01-01
  • 2020-12-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-04-25
  • 2015-05-29
相关资源
最近更新 更多