如何在JAVA中在运行时设置笔画颜色? [英] How can I set the stroke color at runtime in JAVA?

查看:250
本文介绍了如何在JAVA中在运行时设置笔画颜色?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想创建一个界面,用户可以更改线条的颜色来标记什么是背景或什么是图像的前景。到目前为止我已经编码了这个:

  private class ImageLine extends JComponent 
{

java .awt.Point p1,p2;
BufferedImage show;
ArrayList< Shape> shapes = new ArrayList< Shape>();
int flag = 0;
颜色color = Color.ORANGE;


public ImageLine(BufferedImage img)
{
show = img;
setPreferredSize(new Dimension(img.getWidth(),img.getHeight()));
this.addMouseListener

new MouseAdapter()
{
@Override
public void mousePressed(MouseEvent e)
{
p1 = e.getPoint();

}

@Override
public void mouseReleased(MouseEvent e)
{
p2 = e.getPoint();
Shape r = createLine(p1.x,p1.y,e.getX(),e.​​getY());

shapes.add ;
repaint();


}

@Override
public void mouseDragged(MouseEvent e)
{

mouseReleased(e);
repaint();

}


}

b $ b);

this.addKeyListener(

new KeyAdapter()
{


@Override
public void keyPressed (KeyEvent e)
{

if(e.getKeyChar()=='b')
{

color = Color.GREEN;
System.out.println(bck);

}
if(e.getKeyChar()=='f')
{

color = Color.RED;
System.out.println(fgr);


}


}





}







);

this.setFocusable(true);


}


private Line2D.Float createLine(int x1,int y1,int x2,int y2)
{
return new Line2D.Float(x1,y1,x2,y2);
}

直到这个部分一切正常,我真正的问题来了, paintComponent()方法,这里实际上我不知道如何设置颜色作为keylistener指示,在这种情况下如果用户按b键的颜色的行已经改变为绿色,另一方面if用户按f键,线的颜色必须更改为红色,如果用户绘制不同的线,这些线必须保持显示。我试过这个代码没有成功:

  public void paintComponent(Graphics g){
Graphics2D g2 = ) G;
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,RenderingHints.VALUE_ANTIALIAS_ON);
g2.setStroke(new BasicStroke(10));
g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER,0.50f));

(Shape s:shapes){
//g2.setPaint(Color.BLACK);
g2.draw(s);
g2.setPaint(color);
//g2.fill(s);
}

if(p1!= null& p2!= null){
g2.setPaint(Color.CYAN);
Shape r = createLine(p1.x,p1.y,p2.x,p2.y);
g2.draw(r);
}
}

但结果不是我想要的,线条和颜色改变,但是当这种情况发生时,我画的线条在改变颜色之前自动变为所选颜色,并且不保持原来的颜色。任何建议?先感谢。

解决方案

有几种方法可以实现这一点,我喜欢结婚的想法将 Shape Color 组合到一个对象中,但是当您添加更多形状时,这可能会提供更多的工作。另一个解决方案可能是使用 Map 将行简单地映射为颜色,例如



  import java.awt.Color; 
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.Shape;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.Line2D;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.swing.AbstractAction;
import javax.swing.ActionMap;
import javax.swing.InputMap;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.KeyStroke;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class DrawLines {

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

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

JFrame frame = new JFrame(Testing);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}

public class TestPane extends JPanel {

private Line2D currentLine;
private Map< Shape,Color> mapColors;

private color currentColor;

私人列表< Shape>形状;

public TestPane(){

mapColors = new HashMap<>(25);
shapes = new ArrayList<>(25);

InputMap inputMap = getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
ActionMap actionMap = getActionMap();

inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_F,0),foreground);
inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_B,0),background);

actionMap.put(foreground,new AbstractAction(){
@Override
public void actionPerformed(ActionEvent e){
currentColor = Color.GREEN;
if(currentLine!= null){
mapColors.put(currentLine,currentColor);
repaint();
}
}
}
actionMap.put(background,new AbstractAction(){
@Override
public void actionPerformed(ActionEvent e){
currentColor = Color.RED;
if (currentLine!= null){
mapColors.put(currentLine,currentColor);
repaint();
}
}
}

MouseAdapter ma = new MouseAdapter(){

private Point p1,p2;

@Override
public void mousePressed(MouseEvent e){
p1 = e.getPoint();
currentLine = null;
}

@Override
public void mouseReleased(MouseEvent e){
p2 = e.getPoint();
if(currentLine == null){
currentLine = createLine(p1.x,p1.y,e.getX(),e.​​getY());
} else {
currentLine.setLine(p1,p2);
}

mapColors.put(currentLine,currentColor);
shapes.add(currentLine);
repaint();
}

@Override
public void mouseDragged(MouseEvent e){
p2 = e.getPoint();
if(currentLine == null){
currentLine = createLine(p1.x,p1.y,e.getX(),e.​​getY());
} else {
currentLine.setLine(p1,p2);
}

repaint();
}

private Line2D.Float createLine(int x1,int y1,int x2,int y2){
return new Line2D.Float(x1,y1,x2,y2) ;
}
};

addMouseListener(ma);
addMouseMotionListener(ma);
}

@Override
public Dimension getPreferredSize(){
return new Dimension(200,200);
}

protected void paintComponent(Graphics g){
super.paintComponent(g);
Graphics2D g2d =(Graphics2D)g.create();
for(Shape shape:shapes){
color color = mapColors.get(shape);
if(color == null){
color = Color.BLACK;
}
g2d.setColor(color);
g2d.draw(shape);
}

if(currentLine!= null){
color color = mapColors.get(currentLine);
if(color == null){
color = currentColor;
}
g2d.setColor(color);
g2d.draw(currentLine);
}
g2d.dispose();
}

}

}

另外,我避免使用 KeyListener ,而是使用键绑定API,而不是麻烦。



href =http://docs.oracle.com/javase/tutorial/uiswing/misc/keybinding.html =nofollow noreferrer>如何使用键绑定了解更多详情


I'm trying to create an interface where the user can change the color of a line to mark what is background or what is foreground of an image. So far I have coded this:

private class ImageLine extends JComponent 
{

    java.awt.Point p1,p2;
    BufferedImage show;
    ArrayList <Shape> shapes = new ArrayList<Shape>();
    int flag = 0;
    Color color = Color.ORANGE;


    public ImageLine(BufferedImage img)
    {
        show = img;
        setPreferredSize(new Dimension(img.getWidth(), img.getHeight()));
        this.addMouseListener
        (
                new MouseAdapter()
                {
                    @Override
                    public void mousePressed(MouseEvent e)
                    {
                        p1 = e.getPoint();

                    }

                    @Override
                    public void mouseReleased(MouseEvent e)
                    {
                       p2 = e.getPoint();
                       Shape r = createLine(p1.x,p1.y,e.getX(),e.getY());

                       shapes.add(r);
                       repaint();


                    }

                    @Override
                    public void mouseDragged(MouseEvent e)
                    {

                        mouseReleased(e);
                        repaint();

                    }


                }


        );

        this.addKeyListener(

                new KeyAdapter()
                        {


                            @Override
                            public void keyPressed(KeyEvent e)
                            {

                                if(e.getKeyChar() == 'b')
                                {

                                    color = Color.GREEN;
                                    System.out.println("bck");

                                }
                                if(e.getKeyChar() == 'f')
                                {

                                    color = Color.RED;
                                    System.out.println("fgr");


                                }


                            }





                        }







        );

       this.setFocusable(true);


    }


    private Line2D.Float createLine(int x1, int y1, int x2, int y2) 
    {
          return new Line2D.Float(x1,y1 ,x2, y2);
    }    

Until this part everything works fine , my real problem comes when I try to override the paintComponent() method, here actually I dont know exactly how to set the color as the keylistener indicates, in this case if the user press the "b" key the color of the line has to change to green, in the other hand if the user press the "f" key the color of the line has to change to red, also if the user draws differents lines , these lines have to remain shown. I have tried with this code without sucess:

public void paintComponent(Graphics g) {
      Graphics2D g2 = (Graphics2D) g;
      g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
      g2.setStroke(new BasicStroke(10));
      g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.50f));

      for (Shape s : shapes) {
        //g2.setPaint(Color.BLACK);
        g2.draw(s);
        g2.setPaint(color);
        //g2.fill(s);
      }

      if (p1 != null && p2 != null) {
        g2.setPaint(Color.CYAN);
        Shape r = createLine(p1.x, p1.y, p2.x, p2.y);
        g2.draw(r);
      }
    }

But the result is not what I want, I paint the lines and change the color, but when this happen , the lines I drew before change it´s color automatically to the color selected, and they dont keep it's "original color". Any sugestions? Thanks in advance.

解决方案

There are a few ways you might be able to achieve this, I kind of like the idea of marrying the Shape and Color together into a single object, but this might present more work as you add more shapes.

Another solution might be to use a Map to simply map the line to a color, for example

import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.Shape;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.Line2D;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.swing.AbstractAction;
import javax.swing.ActionMap;
import javax.swing.InputMap;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.KeyStroke;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class DrawLines {

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

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

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new TestPane());
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class TestPane extends JPanel {

        private Line2D currentLine;
        private Map<Shape, Color> mapColors;

        private Color currentColor;

        private List<Shape> shapes;

        public TestPane() {

            mapColors = new HashMap<>(25);
            shapes = new ArrayList<>(25);

            InputMap inputMap = getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
            ActionMap actionMap = getActionMap();

            inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_F, 0), "foreground");
            inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_B, 0), "background");

            actionMap.put("foreground", new AbstractAction() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    currentColor = Color.GREEN;
                    if (currentLine != null) {
                        mapColors.put(currentLine, currentColor);
                        repaint();
                    }
                }
            });
            actionMap.put("background", new AbstractAction() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    currentColor = Color.RED;
                    if (currentLine != null) {
                        mapColors.put(currentLine, currentColor);
                        repaint();
                    }
                }
            });

            MouseAdapter ma = new MouseAdapter() {

                private Point p1, p2;

                @Override
                public void mousePressed(MouseEvent e) {
                    p1 = e.getPoint();
                    currentLine = null;
                }

                @Override
                public void mouseReleased(MouseEvent e) {
                    p2 = e.getPoint();
                    if (currentLine == null) {
                        currentLine = createLine(p1.x, p1.y, e.getX(), e.getY());
                    } else {
                        currentLine.setLine(p1, p2);
                    }

                    mapColors.put(currentLine, currentColor);
                    shapes.add(currentLine);
                    repaint();                  
                }

                @Override
                public void mouseDragged(MouseEvent e) {
                    p2 = e.getPoint();
                    if (currentLine == null) {
                        currentLine = createLine(p1.x, p1.y, e.getX(), e.getY());
                    } else {
                        currentLine.setLine(p1, p2);
                    }

                    repaint();
                }

                private Line2D.Float createLine(int x1, int y1, int x2, int y2) {
                    return new Line2D.Float(x1, y1, x2, y2);
                }
            };

            addMouseListener(ma);
            addMouseMotionListener(ma);
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
            Graphics2D g2d = (Graphics2D) g.create();
            for (Shape shape : shapes) {
                Color color = mapColors.get(shape);
                if (color == null) {
                    color = Color.BLACK;
                }
                g2d.setColor(color);
                g2d.draw(shape);
            }

            if (currentLine != null) {
                Color color = mapColors.get(currentLine);
                if (color == null) {
                    color = currentColor;
                }
                g2d.setColor(color);
                g2d.draw(currentLine);
            }
            g2d.dispose();
        }

    }

}

Also, I avoid using KeyListener and use the key bindings API instead, it's less troublesome

See How to Use Key Bindings for more details

这篇关于如何在JAVA中在运行时设置笔画颜色?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆