2017-01-20 10 views
-1

Привета Я пытаюсь создать сердца формы для моего приложения и я мог сделать полую, и это работает хорошо, теперь мне нужно сделать это с заполненным методом, но он создан два Arc2D.Double и два Line2D.Double, поэтому из-за этого просто заполнение дуги и две строки нет. Я попытался добавить эти две строки в два разных «Района» и добавить эти две области в один, но также не работал.Как заполнить между двумя Line2D.Double?

Есть ли способ сделать это (заполнение между двумя линиями)? Спасибо заранее.

Мои коды: Класс Сердечные

`public class HeartShape { 

    private ArrayList<Shape> shapes; 
    public HeartShape() { 

    } 

    public ArrayList<Shape> Heart(double x, double y, double HEART_RADIUS) { 
     shapes = new ArrayList<>(); 
     double r = HEART_RADIUS; 
     double root2 = Math.sqrt(2); 
     double cx = x; 
     double cy = y; 
     double dx = r/root2; 
     double heights = 3 * dx + r; 
     double top = cy - heights/2; 
     double bottom = cy + heights/2; 
     Shape s = new Arc2D.Double(cx - dx - r, top, 2 * r, 2 * r, 45, 180, Arc2D.OPEN); 
     shapes.add(s); 
     s = new Arc2D.Double(cx + dx - r, top, 2 * r, 2 * r, -45, 180, Arc2D.OPEN); 
     shapes.add(s); 
     s = new Line2D.Double(cx, bottom, cx - 2 * dx, bottom - 2 * dx); 
     shapes.add(s); 
     s = new Line2D.Double(cx, bottom, cx + 2 * dx, bottom - 2 * dx); 
     shapes.add(s); 
     if (shapes != null) { 
      return shapes; 
     } else { 
      return null; 
     } 
    } 

    public void drawHeart(Graphics2D g2d, boolean isFilled) { 

     if (isFilled == true) { 
        shapes.forEach((ss) -> { 
         g2d.fill(ss); 
        }); 
     } else { 
        shapes.forEach((ss) -> { 
         g2d.draw(ss); 
        }); 
     } 

    }` 

И DrawinTest:

public class DrawinTest extends JPanel{ 
private int HEART_RADIUS; 
private Point startpoint; 
private int x, y, width, height; 
private HeartShape heartShape = new HeartShape(); 
/** 
* @param args the command line arguments 
*/ 
public static void main(String[] args) { 
    new DrawinTest(); 
} 

public DrawinTest() { 
    JFrame f = new JFrame("Test Area"); 
    f.setPreferredSize(new Dimension(600, 500)); 
    f.setLocationRelativeTo(null); 
    f.setLayout(new BorderLayout(0, 1)); 
    f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    this.addMouseListener(new MyMouseListener()); 
    this.addMouseMotionListener(new MyMouseListener()); 
    this.setBackground(Color.WHITE); 
    f.setContentPane(this); 
    f.setVisible(true); 
    f.pack(); 
} 

@Override 
public void paintComponent(Graphics g) { 
    super.paintComponent(g); 

    Graphics2D g2d = (Graphics2D)g; 
    g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); 
    g2d.setStroke(new BasicStroke(3)); 
    g2d.setColor(Color.RED); 

    if(heartShape != null) { 
     heartShape.Heart(x, y, HEART_RADIUS); 
     heartShape.drawHeart(g2d, false); 

    } 
    g2d.dispose(); 
} 

class MyMouseListener implements MouseListener,MouseMotionListener { 

    @Override 
    public void mouseClicked(MouseEvent e) {} 

    @Override 
    public void mousePressed(MouseEvent e) { 
     startpoint = new Point(e.getPoint()); 
    } 

    @Override 
    public void mouseReleased(MouseEvent e) {} 

    @Override 
    public void mouseEntered(MouseEvent e) {} 

    @Override 
    public void mouseExited(MouseEvent e) {} 

    @Override 
    public void mouseDragged(MouseEvent e) { 
     x = Math.min(startpoint.x, e.getX()); 
     y = Math.min(startpoint.y, e.getY()); 
     width = Math.abs(startpoint.x - e.getX()); 
     height = Math.abs(startpoint.y - e.getY()); 
     HEART_RADIUS = Math.min(width, height); 
     repaint(); 
    } 

    @Override 
    public void mouseMoved(MouseEvent e) {} 

    } 
} 

До сих пор его вида:

EmptyFilled

+0

Используйте API 'Shape' для создания закрытой формы - [В качестве концептуального примера] (http://stackoverflow.com)/questions/30041397/how-to-paint-a-group-of-quadcurves-using-java-graphics2d/30042600 # 30042600) – MadProgrammer

+0

@MadProgrammer благодарит вас за быстрый повтор, можете ли вы показать мне, как это сделать, пожалуйста? Потому что мои мозги устали от этого. –

+0

Да, я добавил пример ссылки на предыдущий комментарий;) – MadProgrammer

ответ

2

В Shape сек API имеет ряд действительно интересных интерфейсов, один из моих любимых Path2D

В принципе, что это позволяет сделать, это добавить другие Shape с, что делает его очень полезным в этой ситуации.

public class HeartShape { 

    private Shape shape; 

    public HeartShape() { 

    } 

    public Shape Heart(double x, double y, double HEART_RADIUS) { 
     double r = HEART_RADIUS; 
     double root2 = Math.sqrt(2); 
     double cx = x; 
     double cy = y; 
     double dx = r/root2; 
     double heights = 3 * dx + r; 
     double top = cy - heights/2; 
     double bottom = cy + heights/2; 

     Path2D base = new Path2D.Double(); 
     Shape s = new Arc2D.Double(cx - dx - r, top, 2 * r, 2 * r, 45, 180, Arc2D.OPEN); 
     base.append(s, false); 
     s = new Line2D.Double(cx, bottom, cx - 2 * dx, bottom - 2 * dx); 
     base.append(s, true); 
     s = new Line2D.Double(cx, bottom, cx + 2 * dx, bottom - 2 * dx); 
     base.append(s, true); 
     s = new Arc2D.Double(cx + dx - r, top, 2 * r, 2 * r, -45, 180, Arc2D.OPEN); 
     base.append(s, true); 

     base.closePath(); 

     shape = base; 

     return base; 
    } 

    public void drawHeart(Graphics2D g2d, boolean isFilled) { 
     System.out.println("..."); 
     if (isFilled) { 
      g2d.fill(shape); 
     } else { 
      g2d.draw(shape); 
     } 
    } 
} 

Как показано в this example, вам не нужно заново создать форму, когда вы хотите, чтобы изменить его размер, вы можете просто создать экземпляр этого в размере «по умолчанию» и использовать AffineTransform для изменить его размер намного проще;)

+0

Отличный ответ и +1 для вас. Большое вам спасибо. –

+0

@CoderACJHP Рад, что это могло бы помочь;) – MadProgrammer

+1

Может ли кто-нибудь объяснить мне, почему этот ответ привлечет нижестоящий? Каким образом это не отвечает на вопрос? Каким образом это будет улучшено? Если вопрос не получил никаких новых downvotes, я предполагаю, что вы не найдете проблемы с этим вопросом, так как никаких других ответов не было отменено или добавлены новые ответы, я предполагаю, что вы лично делаете с нами лично ... что стыдно – MadProgrammer

1

Я думаю, что вместо использования массива списка фигур вы должны использовать GenericPath и присоединить каждую отдельную фигуру к нему с помощью GenericPath.append(). Один вы закончили добавлять кусочки сердца, используя GenericPath.closePath(), чтобы закрыть его, чтобы его можно было заполнить. Затем вы должны иметь возможность использовать новый объект GenericPath в качестве пути к рисованию с помощью g2d.draw