Still celebrating National IT Professionals Day with 3 months of free Premium Membership. Use Code ITDAY17

x
?
Solved

Applet Image Rotation Blues

Posted on 2004-04-14
17
Medium Priority
?
571 Views
Last Modified: 2010-08-05
Hello all!
I've managed to get my images rotating, but I've run into some trouble.
I am currently making a game involving a space ship. What I am working on is so that you can turn the ship and steer the ship, by rotating the image. However, I've run into a problem. When rotating an image, it rotates on an axis point located in the top left corner. In order to make it look like my ship is turning, I need the axis point to be in the middle of my ships image. I have no idea how to move this axis point. This is where I need help.


Here is my code, it's not long:

//////////////////////////////////////////////////////////////////////////////////////////////////////////
import java.awt.image.*;
import java.awt.*;
import java.applet.*;
import java.awt.event.*;
import java.util.Random;
import java.lang.Thread;
import java.awt.geom.*;

public class SpaceBlast extends Applet implements Runnable, KeyListener, ActionListener, MouseListener
{
      
    Thread t;
    Graphics bufferg; //for future use with double buffering
    Image offscreen;
    double theta=0;      
    double x = 500;
    double y = 500;
    double scalex = .2;
    double scaley = .2;
    double shiftx = 0;
    double shifty = 0;
    double radians = -Math.PI/4;
    double rd=.17;
    boolean otherway;
      
      public void init()
      {   this.setLayout(null);
                     t=new Thread(this);
                     addKeyListener(this);
           t.start();            
           repaint();
                 }
      
      public void actionPerformed(ActionEvent e)
                {}
               public void keyPressed(KeyEvent e)
      {  
         if(e.getKeyChar()=='s')
          { rd-=.0001; }
         if(e.getKeyChar()=='a')
          { rd+=.0001; }
                 }
      public void keyReleased(KeyEvent e)
      {}
      public void keyTyped(KeyEvent e)
      {}
      public void mouseClicked(MouseEvent e)
                {}
                public void mouseReleased(MouseEvent e)
                {}
                public void mousePressed(MouseEvent e)
                {}
               public void mouseExited(MouseEvent e)
                {}
               public void mouseEntered(MouseEvent e)
               {}

      public void paint(Graphics g)
      {   Graphics2D g2d = (Graphics2D) g;
                     Image pic= getImage(getCodeBase(), "SD.gif");
                     AffineTransform tx = new AffineTransform();
   
                      tx.scale(scalex, scaley);
                      tx.shear(shiftx, shifty);
                      tx.translate(x, y);
       
                      radians = -Math.PI/rd;
       
                      tx.rotate(radians);
   
                      g2d.drawImage(pic, tx, this);
                      g.drawString(rd+"",10,10);

          
      }
      //public void update(Graphics g) //for later use with Double buffering
      //{ paint(g); }
      

      public void run()
      {  
          while(rd<2000){
          repaint();
                    try{t.sleep(150);}catch(Exception exc){}
            } ;
    }
}
/////////////////////////////////////////////////////////////

Thank you for your help!
I'm also kinda new to java, so please explain it the best you can.
Thanks!
0
Comment
Question by:Punkman
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 7
  • 5
  • 5
17 Comments
 
LVL 92

Expert Comment

by:objects
ID: 10829226
you need to translate by the image centre offset.
0
 
LVL 92

Expert Comment

by:objects
ID: 10829236
>  Image pic= getImage(getCodeBase(), "SD.gif");

no need to get image everytime you paint
do thisd instead in init().
0
 
LVL 92

Expert Comment

by:objects
ID: 10829243
0
Build and deliver software with DevOps

A digital transformation requires faster time to market, shorter software development lifecycles, and the ability to adapt rapidly to changing customer demands. DevOps provides the solution.

 
LVL 86

Expert Comment

by:CEHJ
ID: 10829333
Try

tx.translate((int)(pic.getWidth() / 2 * scalex), (int)(pic.getHeight() / 2 * scaley));
0
 
LVL 92

Expert Comment

by:objects
ID: 10829373
Thought u didn't need to use AffineTransform :D
0
 
LVL 86

Expert Comment

by:CEHJ
ID: 10829386
You don't
0
 
LVL 92

Accepted Solution

by:
objects earned 352 total points
ID: 10829400
But still u suggest using it, anyways that code won't work.

try using:

 tx.rotate(radians, xcentre, ycentre);

where xcentre and ycentre are the centre of the required rotation.
0
 
LVL 86

Expert Comment

by:CEHJ
ID: 10829414
>>But still u suggest using it

Only because it's already there
0
 

Author Comment

by:Punkman
ID: 10832137
>>tx.rotate(radians, xcentre, ycentre);

Thanks objects, this works great!
How would I go about getting the center of the image though?

I tried using
(int)(pic.getWidth() / 2 * scalex), (int)(pic.getHeight() / 2 * scaley))

This should work.... but instead it rotates the picture by that top left corner again.
However, the >>tx.rotate(radians, xcentre, ycentre); does work with other, much higher numbers.

How do I go about making xcenter and ycenter the center of my image?
(the coord system for them seems off or something)
0
 

Author Comment

by:Punkman
ID: 10832248
Ok, fixed it : )
It turns out that you don't need to take scalex and scaley into account, as it does that for you.
So the code is:
(int)(pic.getWidth() / 2), (int)(pic.getHeight() / 2)

Thanks!!

Ok, I've raised the points up a bit, as I have one final question.
I can now rotate my image around it's center point. But how would I go about moving my image in the direction it's facing?
0
 

Author Comment

by:Punkman
ID: 10832294
Oh, and more importantly, How do I apply double buffering to this now that I am using:
Graphics2D g2d = (Graphics2D) g;    ?

I need to use both g and g2d in the game.

Thanks again : )
0
 

Author Comment

by:Punkman
ID: 10835494
If the points are too low, I'll up them a bit if you want.
0
 
LVL 86

Assisted Solution

by:CEHJ
CEHJ earned 348 total points
ID: 10836094
Here's a working an example that spins an image round and moves it rightwards from the center having it reappear at the centre when it's moved out of view. Obviously you can use your own image to test it:

import java.awt.*;
import java.awt.image.*;
import javax.swing.*;

public class F extends JFrame implements Runnable {
  Image image;
  double theta, rotationFactor, delta;
  JPanel rotatorPanel;

  int deltaX, paintCount;

  private void setGui() {
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            // Choose image here
    ImageIcon icon = new ImageIcon("next.gif");
    image = icon.getImage();
    delta = 0.2f;
    rotatorPanel = new JPanel() {

      public void paintComponent(Graphics g) {
        g.clearRect(0, 0, getWidth(), getHeight());
        theta = Math.PI * rotationFactor;
        Graphics2D g2d = (Graphics2D)g;
        g2d.translate((int)(getWidth() / 2) + deltaX, (int)(getHeight() / 2));
        g2d.rotate(theta);
        g2d.drawImage(image, -(int)(image.getWidth(null) / 2), -(int)(image.getHeight(null) / 2), null);
      }

      public Dimension getPreferredSize() {
        return new Dimension(image.getWidth(null), image.getHeight(null));
      }
    };
    getContentPane().add(rotatorPanel);
  }

  public void run() {
    deltaX = -(int)(image.getWidth(null) / 2);
    for(;;) {
      rotationFactor -= delta;
      try {
        Thread.sleep(50);
        repaint();
        deltaX = (deltaX + 1) % getWidth();
      }
      catch(InterruptedException e) {
        /* ignore */
      }
    }
  }


  public static void main(String[] args) {
    F f = new F();
    f.setGui();
    f.pack();
    f.setVisible(true);
    new Thread(f).start();
  }
}


0
 
LVL 92

Expert Comment

by:objects
ID: 10837746
> It turns out that you don't need to take scalex and scaley into account

That is correct

> I can now rotate my image around it's center point.
> But how would I go about moving my image in the direction it's facing?

Maintain its x,y position and just translate transform matrix by that amount.
Use the current direction to change the x,y position.
 
> Oh, and more importantly, How do I apply double buffering to this now that I am using:
> Graphics2D g2d = (Graphics2D) g;    ?

Do all your painting of ship etc to the Graphics context of the image. bufferg can also be declared as a Gaphics2D.
And then paint that offscreen image to the screen in your paint method.

0
 

Author Comment

by:Punkman
ID: 10880813
Thanks guys! The program now works and looks GREAT!! Thank you both!
0
 
LVL 86

Expert Comment

by:CEHJ
ID: 10880826
8-)
0
 
LVL 92

Expert Comment

by:objects
ID: 10884038
0

Featured Post

Free Tool: ZipGrep

ZipGrep is a utility that can list and search zip (.war, .ear, .jar, etc) archives for text patterns, without the need to extract the archive's contents.

One of a set of tools we're offering as a way to say thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Java contains several comparison operators (e.g., <, <=, >, >=, ==, !=) that allow you to compare primitive values. However, these operators cannot be used to compare the contents of objects. Interface Comparable is used to allow objects of a cl…
Introduction This article is the last of three articles that explain why and how the Experts Exchange QA Team does test automation for our web site. This article covers our test design approach and then goes through a simple test case example, how …
Viewers will learn about the different types of variables in Java and how to declare them. Decide the type of variable desired: Put the keyword corresponding to the type of variable in front of the variable name: Use the equal sign to assign a v…
Viewers will learn about arithmetic and Boolean expressions in Java and the logical operators used to create Boolean expressions. We will cover the symbols used for arithmetic expressions and define each logical operator and how to use them in Boole…
Suggested Courses

662 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question