1 Reply Latest reply: Feb 22, 2011 3:30 AM by StanislavL RSS

    rotation JComponent (shapes) in canvas with null layout manager

    anicer
      I have 2 problem with above code:

      1)Rotation is not normal - smoothing rotation does not work.
      2)SetSize or setBounds or setDimension of ShapeComponent's placed in canvas (JPanel canvas = new JPanel(null);) has some problems. I would like to see shape of ShapeComponent during rotation.

      Please tell me, what is wrong? I want to create some easy GUI shape editor.

      Thx.
      import java.awt.*;
      import java.awt.event.MouseEvent;
      import java.awt.geom.*;
      import javax.swing.*;
      import javax.swing.event.MouseInputAdapter;
      
      class ShapeComponent extends JComponent {
          AffineTransform at = new AffineTransform();
          private Point shapeLocation;
          private Shape shape;
          double thetaStart = 0;
      
          public ShapeComponent(Shape shape, Point pointShapeLocation, Color color) {
              this.shape = shape;
              this.shapeLocation = pointShapeLocation;
      
              setBackground(color);
      
              setBounds(shape.getBounds());
              setLocation(pointShapeLocation);
      
              MouseInputAdapter mouseAdapter = new MouseHandler();
              addMouseMotionListener(mouseAdapter);
              addMouseListener(mouseAdapter);
          }
      
          @Override
          public void paintComponent(Graphics g) {
              super.paintComponent(g);
              Graphics2D g2d = (Graphics2D) g;
      
              g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
      
              at.rotate(thetaStart, getWidth() / 2.0, getHeight() / 2.0);
              g2d.transform(at);
      //        g2d.rotate(thetaStart, getWidth() / 2.0, getHeight() / 2.0);
      
              g2d.setPaint(getBackground());
              g2d.fill(shape);
      
              g2d.setPaint(Color.BLACK);
              Area a = new Area(shape.getBounds2D());
              g2d.draw(new Rectangle2D.Float(a.getBounds().x, a.getBounds().y, a.getBounds().width - 1, a.getBounds().height - 1));
      
              g2d.setPaint(Color.BLUE);
              g2d.draw(new Rectangle2D.Float(0, 0, getBounds().width - 1, getBounds().height - 1));
          }
      
          @Override
          public boolean contains(int x, int y) {
              return shape.contains(x, y);
          }
      
          @Override
          public Dimension getPreferredSize() {
              return new Dimension(shape.getBounds().width, shape.getBounds().height);
          }
      
          private class MouseHandler extends MouseInputAdapter {
      
              Point2D.Double center = new Point2D.Double();
      
              boolean rotating = false;
      
              @Override
              public void mouseDragged(MouseEvent e) {
      
                  double dy = e.getY() - center.y;
                  double dx = e.getX() - center.x;
                  double theta = Math.atan2(dy, dx);
      
                  thetaStart = theta;
                  repaint();
              }
          }
      }
      
      
      public class Main {
      
          public static void main(String[] args) {
              SwingUtilities.invokeLater(new Runnable() {
                  public void run() {
      
                      JPanel canvas = new JPanel(null);
                      canvas.setBackground(Color.WHITE);
                      canvas.setPreferredSize(new Dimension(600, 400));
      
                      //1 shape
                      ShapeComponent shapeComponent = new ShapeComponent(
                              new Ellipse2D.Double(0, 0, 100, 200),
                              new Point(30, 30),
                              new Color(255, 0, 0, 100));
                      canvas.add(shapeComponent);
                      canvas.setComponentZOrder(shapeComponent, 0);
      
                      //2 shape
                      shapeComponent = new ShapeComponent(
                              new Ellipse2D.Double(0, 0, 200, 110),
                              new Point(130, 30),
                              new Color(0, 0, 255, 150));
                      canvas.add(shapeComponent);
                      canvas.setComponentZOrder(shapeComponent, 0);
      
                      JFrame f = new JFrame("Test ShapeComponent");
                      f.getContentPane().add(canvas, BorderLayout.CENTER);
                      f.pack();
                      f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                      f.setLocationRelativeTo(null);
                      f.setVisible(true);
                  }
              });
          }
      }
        • 1. Re: rotation JComponent (shapes) in canvas with null layout manager
          StanislavL
          Bounds of the rotated Shape shoudl be changed when you rotate it.
              public Dimension getPreferredSize() {
                  Area a=new Area(shape);
                  a=a.createTransformedArea(at);
                  return new Dimension(a.getBounds().width, a.getBounds().height);
              }
          ALso position should be changed. When you rotate a shape 90 degrees new width becomes old height and new height becomes old widht. Also location should be moved to keep the center.

          Alternatively the shape should be square widht=height=Math.max(shapeWidth,shapeHeight); and the shape should be always drawn in the center.