I currently have a JPanel inside a JFrame and i need the view to follow an object, the reason i cant move the world is because the object is orbiting another object and so working out how to move the world would be a little more difficult.
Asked
Active
Viewed 1,068 times
-2
-
1[How to add a scrolling camera to a 2D Java game?](http://gamedev.stackexchange.com/a/44270) – Lukas Rotter Sep 18 '15 at 17:57
-
What do i use though? I tried JScrollPane and JViewport but i don't really understand them. – Tom Haffenden Sep 18 '15 at 18:02
-
You don't need a JViewPort, this solution will work with only a JPanel and graphics on it. – Lukas Rotter Sep 18 '15 at 18:08
-
Did you achieve want you want yet? If not, do you want me to post an example, maybe? – Lukas Rotter Sep 19 '15 at 13:40
-
I never got the effect i wanted no. I'll explain what im trying to do and you can tell me if it's even possible.I have an object rotated by a transformer whilst being offset so it orbits another object. I want the view to zoom into the object no matter where it is aswell as follow it whilst it orbits. – Tom Haffenden Sep 20 '15 at 14:40
1 Answers
2
Ok, below is an example on how to do this. Note that a SSCCE doesn't need to be OO, so you probably shouldn't copy + paste this into your current project. I will not explain the steps, because pretty much everything was explained in the link I posted. Still, here are the references for the 2D camera and for the object moving in circular path.
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.geom.AffineTransform;
import javax.swing.Timer;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class Example {
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
new Example();
}
});
}
public Example() {
JFrame frame = new JFrame();
frame.setContentPane(new DrawingPanel());
frame.setSize(400, 300);
frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
frame.setVisible(true);
}
class DrawingPanel extends JPanel {
int angle = 0;
int rotation = 0;
int radius = 150;
int ovalX = 150;
int ovalY = 150;
int ovalWidth = 100;
int ovalHeight = 100;
int ovalCenterX = ovalX + ovalWidth / 2;
int ovalCenterY = ovalY + ovalHeight / 2;
int recX;
int recY;
int recWidth = 50;
int recHeight = 50;
int recCenterX;
int recCenterY;
int WORLD_SIZE_X = 6000;
int WORLD_SIZE_Y = 6000;
int camX;
int camY;
public DrawingPanel() {
ActionListener al = new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
angle++;
rotation++;
recCenterX = (int) ((int) ovalCenterX + Math.sin(Math.toRadians(angle)) * radius);
recCenterY = (int) ((int) ovalCenterY + Math.cos(Math.toRadians(angle)) * radius);
recX = recCenterX - recWidth / 2;
recY = recCenterY - recHeight / 2;
repaint();
}
};
Timer timer = new Timer(15, al);
timer.start();
}
@Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D gg = (Graphics2D) g;
gg.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
int VIEWPORT_SIZE_X = getWidth();
int VIEWPORT_SIZE_Y = getHeight();
int offsetMaxX = WORLD_SIZE_X - VIEWPORT_SIZE_X;
int offsetMaxY = WORLD_SIZE_Y - VIEWPORT_SIZE_Y;
camX = recCenterX - VIEWPORT_SIZE_X / 2;
camY = recCenterY - VIEWPORT_SIZE_Y / 2;
if (camX > offsetMaxX) {
camX = offsetMaxX;
}
if (camY > offsetMaxY) {
camY = offsetMaxY;
}
gg.translate(-camX, -camY);
gg.setColor(Color.BLUE);
gg.fillOval(ovalX, ovalY, ovalWidth, ovalHeight);
AffineTransform old = gg.getTransform();
gg.rotate(Math.toRadians(rotation), recCenterX, recCenterY);
gg.setColor(Color.RED);
gg.drawRect(recX, recY, recWidth, recHeight);
gg.setTransform(old);
gg.setColor(Color.GREEN);
gg.drawLine(ovalCenterX, ovalCenterY, recCenterX, recCenterY);
}
}
}

Community
- 1
- 1

Lukas Rotter
- 4,158
- 1
- 15
- 35
-
i copied your code into eclipse however the view stays centred on the middle of the screen instead of the orbiting blue circle. Were the references for me to work it out? if so thanks, ill get right on it. – Tom Haffenden Sep 21 '15 at 19:31
-
@TomHaffenden Well, the red square is orbiting + rotating, not the blue circle - And the camera follows the red square. – Lukas Rotter Sep 21 '15 at 19:45
-
So... Did this actually solve the issue? If yes, please consider to [accept](http://meta.stackexchange.com/a/5235) this anwer. :) Glad it helped! – Lukas Rotter Sep 22 '15 at 21:29
-
Yeah thanks. Forgot about the accept thing as it won't let me for 2 days afterwards. Anyway one other question i have is what is the purpose of putting a JFrame using an actionListnener inside a runnable method? – Tom Haffenden Sep 23 '15 at 22:10
-
@TomHaffenden The frame isn't using it directly, the `swing.Timer` is: `Timer timer = new Timer(15, al);` - Al is the actionlistener. Every 15 milliseconds the `actionPerformed()` method is executed. You can also start `util.Timer`s in a different way. See [this](http://stackoverflow.com/questions/4044726/how-to-set-a-timer-in-java). But if you mean the `EventQueue` one, see [this](http://stackoverflow.com/a/22534931/4857909). – Lukas Rotter Sep 24 '15 at 09:38
-
1