Multiple paint() methods in Java applet? - java

So I am trying to generate random rectangles that the player must avoid. My collision method was working with a single, randomly generated rectangle. I want to draw 10 or so of these and then I will add a finish line and a timer.
Right now, I understand my problem, but I am not sure how to fix it. The ball/player's movement is executed by changing the x or y coordinates by 10 and then repainting the circle. I currently have the rectangles in the same paint method, so each time the player moves the rectangles are regenerated. I would like them to stay in the same place after the initial random generation. I don't really know how to do this though...
Also, if I can get the rectangles to stay in the same place, will my collision method still work with multiple rectangles? or would I need to revise that as well?
I am just going to post the whole program's code because I'm not sure which parts will need to be revised.
import java.awt.*;
import java.awt.Rectangle;
import java.awt.Shape;
import javafx.scene.shape.*;
import java.awt.event.*;
import java.util.Random;
import java.awt.geom.Area;
import javax.swing.JOptionPane;
import java.applet.Applet;
public class Main extends Applet
implements ActionListener{
boolean end = false;
private Rectangle rectangle;
//creates buttons to move player
private Button run = new Button("Run");
private Button jump = new Button("Jump");
private Button fall = new Button("Fall");
//creates player and obstacles
private Circle player = new Circle(110,110,20);
private makeRect block = new makeRect(150, 120, 30, 10);
//initiates the buttons with actionListener
public void init(){
add(run);
add(jump);
add(fall);
run.addActionListener(this);
jump.addActionListener(this);
fall.addActionListener(this);
}
//draws the player and blocks on the screen
public void paint(Graphics g){
for(int numBlocks = 0; numBlocks<11; numBlocks++){
block.draw(g);}
player.draw(g);
}
//if methods to be control movement
public void actionPerformed(ActionEvent e){
if(e.getSource() instanceof Button){
if(e.getSource() == run)
player.horiz(10);
else if (e.getSource()== jump){
player.vert(-10);
}
else if (e.getSource()== fall){
player.down(10);
}
repaint();
collision();
}
}
public void collision(){
if(player.getBounds().intersects(block.getBounds())){
JOptionPane.showMessageDialog(this, "Game Over", "Game Over", JOptionPane.YES_NO_OPTION);
System.exit(ABORT);
end = true;
}
}
class Circle{
private final Color theColor = Color.BLUE;
private int radius;
private int x,y;
public Circle(){
x = 110; y = 110;
radius = 20;
}
public Circle(int x0, int y0, int rad){
x = x0; y = y0; radius = rad;
}
public void draw(Graphics g){
g.fillOval(x - radius, y-radius, 2*radius, 2*radius);
g.setColor(theColor);
}
public void horiz(int val){
for(int c = 0; c<val+1; c++){
x++;
repaint();}
}
public void vert(int val){
y += val;
}
public void down(int val){
y += val;
}
public Rectangle getBounds(){
return new Rectangle(x-radius, y-radius, 2*radius, 2*radius);
}
}
class makeRect{
private int Xmax = 250;
private int Xmin = 140;
private int Wmax = 50;
private int Hmax = 25;
private int Wmin = 10;
private int Hmin = 5;
Random rand = new Random();
private int randx;
private int randh;
private int x, y, width, height;
public makeRect(){
x = 150; y = 120;
width = 30; height = 10;
}
public makeRect(int x0, int y0, int w0, int h0){
x = x0; y = y0; width = w0; height = h0;
}
public void draw(Graphics g) {
int randx = rand.nextInt((Xmax-Xmin)+1)+Xmin;
int randh = rand.nextInt((Hmax-Hmin)+1)+Hmin;
int randw = rand.nextInt((Wmax-Wmin)+1)+Wmin;
g.drawRect(randx, 110+randh, randh, randw);
}
public Rectangle getBounds(){
return new Rectangle(randx, 110+randh, 30, 10);
}
}
}
Thanks!

For that you will need to construct 10 rects (consider using array) first upon initialization, with random postition for each. I mean, postition randomization occurs when the rects are constructed, not when it's drawn.
What you have there is a same rectangle drawn 10 times at different places each time the paint() gets called.

Related

How do I paint multiple objetcs that move at different speeds in Java?

I am working on homework for class, and its late because I can't seem to understand the material despite all the research that I am doing. I am a beginner and do not know much in the way of java. Also, this is my first post so please be forgiving when you are reading this.
I am building on source code from my textbook, which I updated recently for past homework, but now I am trying to generate a class that draws multiple squares and moves those objects independently and at different speeds. They will all need to rebound off the walls as well. I followed the instructions and created two arrays that will hold the random x and y values between 1 and 10. However, I struggle with arrays and I am sure that I am not doing it correctly. So, I would love some feedback to see if I have it set up correctly.
I have a the jpanel pulling up and drawing, and as long as there is 1 square it is working fine bouncing off the walls, but things change when I draw more than one. The do not move independently and they also share the same speed. Some even disappear from time to time. This has really thrown me off. I appreciate any help!
In short, I am trying to paint new squares that all travel in different directions and at different speeds. Per the instructions we are suppose create and use a two arrays that handle the x and y values.
Here is what I have so far:
public class DotsPanel extends JPanel
{
private int delay = 15;
private final int SIZE = 7, IMAGE_SIZE = 3; // radius of each dot
private Timer timer;
private int x, y, i;
private ArrayList<Point> pointList;
static int [] xarray = new int [1000];
static int [] yarray = new int [1000];
Random rand = new Random();
//-----------------------------------------------------------------
// Constructor: Sets up this panel to listen for mouse events.
//-----------------------------------------------------------------
public DotsPanel()
{
pointList = new ArrayList<Point>();
int [] xarray = new int [1000];
int [] yarray = new int [1000];
timer = new Timer(delay, new ReboundListener());
addMouseListener (new DotsListener());
addMouseMotionListener (new DotsListener());
setBackground(Color.gray);
setPreferredSize(new Dimension(700, 500));
for(int i = 0; i < xarray.length; i++)
{
xarray[i] = rand.nextInt(7);
yarray[i] = rand.nextInt(7);
}
timer.start();
}
//-----------------------------------------------------------------
// Draws all of the dots stored in the list.
//-----------------------------------------------------------------
public void paintComponent(Graphics page)
{
super.paintComponent(page);
page.setColor(Color.BLUE);
for (Point spot : pointList)
{
page.fillRect(spot.x-SIZE, spot.y-SIZE, 25, 25);
page.drawString("Count: " + pointList.size(), 5, 15);
}
}
//*****************************************************************
// Represents the listener for mouse events.
//*****************************************************************
private class DotsListener implements MouseListener, MouseMotionListener
{
//--------------------------------------------------------------
// Adds the current point to the list of points and redraws
// the panel whenever the mouse button is pressed.
//--------------------------------------------------------------
public void mousePressed(MouseEvent event)
{
pointList.add(event.getPoint());
repaint();
}
public void mouseDragged(MouseEvent event)
{
// initially I had two xarray and yarray in here just like in
// mouseClicked
// but it did not change anything when removed
}
//--------------------------------------------------------------
// Provide empty definitions for unused event methods.
//--------------------------------------------------------------
public void mouseClicked(MouseEvent event)
{
xarray[i] = rand.nextInt(7);
yarray[i] = rand.nextInt(7);
}
public void mouseReleased(MouseEvent event) {}
public void mouseEntered(MouseEvent event) {}
public void mouseExited(MouseEvent event) {}
public void mouseMoved(MouseEvent e) {}
}
private class ReboundListener implements ActionListener
{
//--------------------------------------------------------------
// Updates the position of the image and possibly the direction
// of movement whenever the timer fires an action event.
//--------------------------------------------------------------
public void actionPerformed(ActionEvent event)
{
for (Point spot : pointList)
{
spot.x += xarray[i];
spot.y += yarray[i];
if (spot.x <= 0 || spot.x >= 700)
xarray[i] = xarray[i] * -1;
if (spot.y <= 0 || spot.y >= 500)
yarray[i] = yarray[i] * -1;
repaint();
}
}
}
}
However, I struggle with arrays and I am sure that I am not doing it correctly.
I wouldn't use Arrays.
Instead, have a Ball object manage its own state. Then you can have different color, speed, size etc for each Ball. Then when the Timer fires you just calculate the new position and repaint the Ball.
Here is an example to get you started:
import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;
import java.util.*;
import javax.swing.*;
import javax.swing.Timer;
public class BallAnimation4
{
private static void createAndShowUI()
{
BallPanel panel = new BallPanel();
JFrame frame = new JFrame("BallAnimation4");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add( panel );
frame.setSize(800, 600);
frame.setLocationRelativeTo( null );
//frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
frame.setVisible( true );
panel.addBalls(5);
panel.startAnimation();
}
public static void main(String[] args)
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowUI();
}
});
}
}
class BallPanel extends JPanel implements ActionListener
{
private ArrayList<Ball> balls = new ArrayList<Ball>();
public BallPanel()
{
setLayout( null );
setBackground( Color.BLACK );
}
public void addBalls(int ballCount)
{
Random random = new Random();
for (int i = 0; i < ballCount; i++)
{
Ball ball = new Ball();
ball.setRandomColor(true);
ball.setLocation(random.nextInt(getWidth()), random.nextInt(getHeight()));
ball.setMoveRate(32, 32, 1, 1, true);
// ball.setMoveRate(16, 16, 1, 1, true);
ball.setSize(32, 32);
balls.add( ball );
}
}
#Override
public void paintComponent(Graphics g)
{
super.paintComponent(g);
for (Ball ball: balls)
{
ball.draw(g);
}
}
public void startAnimation()
{
Timer timer = new Timer(75, this);
timer.start();
}
public void actionPerformed(ActionEvent e)
{
move();
repaint();
}
private void move()
{
for (Ball ball : balls)
{
ball.move(this);
}
}
class Ball
{
public Color color = Color.BLACK;
public int x = 0;
public int y = 0;
public int width = 1;
public int height = 1;
private int moveX = 1;
private int moveY = 1;
private int directionX = 1;
private int directionY = 1;
private int xScale = moveX;
private int yScale = moveY;
private boolean randomMove = false;
private boolean randomColor = false;
private Random myRand = null;
public Ball()
{
myRand = new Random();
setRandomColor(randomColor);
}
public void move(JPanel parent)
{
int iRight = parent.getSize().width;
int iBottom = parent.getSize().height;
x += 5 + (xScale * directionX);
y += 5 + (yScale * directionY);
if (x <= 0)
{
x = 0;
directionX *= (-1);
xScale = randomMove ? myRand.nextInt(moveX) : moveX;
if (randomColor) setRandomColor(randomColor);
}
if (x >= iRight - width)
{
x = iRight - width;
directionX *= (-1);
xScale = randomMove ? myRand.nextInt(moveX) : moveX;
if (randomColor) setRandomColor(randomColor);
}
if (y <= 0)
{
y = 0;
directionY *= (-1);
yScale = randomMove ? myRand.nextInt(moveY) : moveY;
if (randomColor) setRandomColor(randomColor);
}
if (y >= iBottom - height)
{
y = iBottom - height;
directionY *= (-1);
yScale = randomMove ? myRand.nextInt(moveY) : moveY;
if (randomColor) setRandomColor(randomColor);
}
}
public void draw(Graphics g)
{
g.setColor(color);
g.fillOval(x, y, width, height);
}
public void setColor(Color c)
{
color = c;
}
public void setLocation(int x, int y)
{
this.x = x;
this.y = y;
}
public void setMoveRate(int xMove, int yMove, int xDir, int yDir, boolean randMove)
{
this.moveX = xMove;
this.moveY = yMove;
directionX = xDir;
directionY = yDir;
randomMove = randMove;
}
public void setRandomColor(boolean randomColor)
{
this.randomColor = randomColor;
switch (myRand.nextInt(3))
{
case 0: color = Color.BLUE;
break;
case 1: color = Color.GREEN;
break;
case 2: color = Color.RED;
break;
default: color = Color.BLACK;
break;
}
}
public void setSize(int width, int height)
{
this.width = width;
this.height = height;
}
}
}
Since your Arrays only contain the Point you want to paint you don't have any information about the speed each point should be moved at. The best you could do is create a random amount each point should be moved each time its location is changed. This would give erratic movement as each time you move a point the distance would be random.
If you want more constant speed then you would need to create a second Array to contain the distance each point should move every time.
This starts to get messy creating a new Array every time you want a new property to be unique for the object you want to paint. That is why the approach to create a custom Object with multiple properties is easier to manage.

Change ball color when colliding

I'm making an java app (for exercise) where there must be a panel and 2 buttons.
Each time you press the start button a ball must be displayed and it moves based on thread. The user can display all the way up to 10 independent balls.
By pressing the stop button, 1 ball must be removed with each time the stop button is pressed (example, when there is 4 balls, the user must press 4 times stop button to remove all the balls independently)
All the x- and y coordinates of the balls must be stored in a Matrix
When 1 or more ball(s) are colliding with each other, only the colliding balls must change color from red to blue
Ok I'm almost done with it completely ( from point 1 to 4 ), but here comes my problem. When a ball is colliding with another, instead of changing the colors of the colliding balls to blue, my code is changing all the balls color from red to blue. I know that my error lies at the new Balls().setColor(Color.Blue), but I have no idea how to change only the colliding balls.
Below follows a screen shot of the java app and the code.
Can anyone help me with this headache?
Printscreen:
source code:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.List;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;`
public class BouncingBalls extends JPanel implements ActionListener {
protected List<Ball> balls = new ArrayList<Ball>(10);
private final Container container;
private final DrawCanvas canvas;
private int canvasWidth;
private int canvasHeight;
public JButton start, stop;
int [][] coords= new int[11][2];
int ammountOfBalls = 0;
static Color clr= Color.RED;
public static int random(int maxRange) {
return (int) Math.round((Math.random() * maxRange));
}
public BouncingBalls(int width, int height) {
setLayout(new FlowLayout());
start= new JButton("start");
start.addActionListener(this);
stop= new JButton("stop");
stop.addActionListener(this);
add(start);
add(stop);
add(new JLabel(""));
container = new Container();
canvasWidth = width;
canvasHeight = height;
canvas = new DrawCanvas();
this.setLayout(new FlowLayout());
this.add(canvas);
start();
}
public void start() {
Thread t = new Thread() {
#Override
public void run() {
while (true) {
update();
getPositions();
collisionDetection();
repaint();
try {
Thread.sleep(30);
} catch (InterruptedException e) {
}
}
}
private void collisionDetection() {
// The algorithm that detects collision
for(int i=0;i<ammountOfBalls;i++){
for(int j=i+1; j<ammountOfBalls; j++){
if(collisionMethod(i,j)){ // my collision method
//HOW DO I CHANGE ONLY THE COLLIDING BALLS COLOR HERE????
new Ball().setColor(Color.BLUE); // this line here changes the color of all the balls on the panel
System.out.println("Its a hit");
}
}
}
}
private void getPositions() {
int row=0;
for (Ball ball : balls) {
int x =ball.getXPosition();
int y =ball.getYPosition();
coords[row][0]=x;
coords[row][1]=y;
row++;
}
}
private boolean collisionMethod(int i, int j) {
float xd = coords[i][0]-coords[j][0];
float yd=coords[i][1]-coords[j][1];
float radius= new Ball().ballRadius;
float sqrRadius= radius * radius;
float distSqr= (xd * xd) + (yd * yd);
if(distSqr <= sqrRadius)
return true;
return false;
}
};
t.start();
}
public void update() {
for (Ball ball : balls) {
ball.move(container);
}
}
#Override
public void actionPerformed(ActionEvent e) {
if(e.getSource() == start){
if(ammountOfBalls < 10){
// to limit the ammount of balls to 10
balls.add(new Ball());
ammountOfBalls++;
}
}
else if( e.getSource() == stop){
if(ammountOfBalls > 0){
ammountOfBalls --;
balls.remove(ammountOfBalls);
}
}
}
class DrawCanvas extends JPanel {
#Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
container.draw(g);
for (Ball ball : balls) {
ball.draw(g);
}
}
#Override
public Dimension getPreferredSize() {
return (new Dimension(700, 400));
}
}
public static void main(String[] args) {
JFrame f = new JFrame("Bouncing Balls");
f.setDefaultCloseOperation(f.EXIT_ON_CLOSE);
f.setPreferredSize(new Dimension(800,500));
f.setContentPane(new BouncingBalls(800,800));
f.pack();
f.setVisible(true);
}
public static class Ball {
public int random(int maxRange) {
return (int) Math.round(Math.random() * maxRange);
}
int x = random(700); // method to get random coords for the x-value
int y = random(400); // method to get random coords for the y-value ...... these are used to get random positions for the balls instead of only static
int xMovement = 10;
int yMovement = 10;
int ballRadius = 20;
int i = 0;
public Color getColor(){
return clr;
}
public Color setColor(Color color){
clr=color;
return clr;
}
public void draw(Graphics g) {
g.setColor(getColor());
g.fillOval(x,y,ballRadius,ballRadius);
}
public int getXPosition(){
return x;
}
public int getYPosition(){
return y;
}
public void move(Container container) {
x += xMovement;
y += yMovement;
if (x - ballRadius < 0) {
xMovement = -xMovement;
x = ballRadius;
}
else if (x + ballRadius > 700) {
xMovement = -xMovement;
x = 700 - ballRadius;
}
if (y - ballRadius < 0) {
yMovement = -yMovement;
y = ballRadius;
}
else if (y + ballRadius > 400) {
yMovement = -yMovement;
y = 400 - ballRadius;
}
}
}
public static class Container {
private static final int hightPanel = 800;
private static final int widthPanel= 800;
public void draw(Graphics g) {
g.setColor(Color.WHITE);
g.fillRect(0, 0, widthPanel, hightPanel);
}
}
}
`
You have defined clr as a static field of your application. When your Ball class calls setColor() you are changing the value of clr to blue... and then any Ball that calls getColor() will see that clr is blue.
Solution: Don't make clr an application-wide static field. Define it in the Ball class as a non-static field, so each Ball has its own color.

Changing size of JFrame in an argument

Alright, so I have a class called Ball, where I'm putting some arguments inside the constructor. Here I have intial position, size and speed, but I also need to be able to set the size of the window (the JFrame) in the argument, so that when I call e.g. ball(xpos,ypos,size,speed,windowx,windowy) it will set the size of the JFrame according to what I put in windowx and windowy.
Right now I'm just trying stuff like a headless chicken without really knowing what I'm doing :P, so if someone could point me in the right direction, I would be very grateful!
package com.company;
import javax.swing.*;
import java.awt.*;
import java.util.Random;
public class Main extends JPanel {
static Ball[] balls = new Ball[20];
Random rand = new Random();
Main() {
for(int i = 0; i<20;i++){
float r = rand.nextFloat();
float g = rand.nextFloat();
float b = rand.nextFloat();
Color randomColor = new Color(r, g, b);
balls[i] = new Ball(Ball.randInt(100, 500),Ball.randInt(100, 500),Ball.randInt(10, 50),rand.nextInt(6-1)+1,randomColor,600,600);
}
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D) g;
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
for(int i=0;i<20;i++) {
balls[i].draw(g);
}
}
public static void main(String[] args) throws InterruptedException{
Main m = new Main();
JFrame frame = new JFrame("Title"); //create a new window and set title on window
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); //set the window to close when the cross in the corner is pressed
frame.setSize(600,600);
frame.add(m); //add the content of the game object to the window
frame.setVisible(true); //make the window visible
while(true){
Thread.sleep(10);
for(int i= 0;i<balls.length;i++){
balls[i].update();
}
m.repaint();
}
}
}
Ball class:
package com.company;
import javax.swing.*;
import java.awt.*;
import java.util.Random;
/**
* Created by John on 25/02/2015.
*/
public class Ball extends JPanel{
float _speedX;
float _speedY;
int _size;
float _x;
float _y;
float _speed;
Color _color;
int _windowX;
int _windowY;
Ball(int x, int y, int sz, float speed, Color c, int windowX, int windowY){
_x = x;
_y = y;
_speed=speed;
_speedX = speed;
_speedY = speed;
_size = sz;
_color = c;
_windowX = windowX;
_windowY = windowY;
}
public void update(){
_x += _speedX;
_y += _speedY;
if (_x+_size<0 || _x+_size>_windowX-_size){
_speedX*=-1;
}
if (_y+_size<0 || _y+_size>_windowY-_size){
_speedY*=-1;
}
this.repaint();
}
public static int randInt(int min, int max) {
Random rand = new Random();
int randomNum = rand.nextInt((max - min) + 1) + min;
return randomNum;
}
public void draw(Graphics g) {
g.setColor(_color);
g.fillOval((int)_x,(int) _y, _size, _size);
}
public void setPreferredSize(int wX, int wY) {
_windowX=wX;
_windowY=wY;
setPreferredSize(new Dimension(_windowX,_windowY));
}
}

Java, Slick, An object that shouldnt move is moving?

In my game I'm making, I need NPC's/mobs.
I made a class called peasant (my first mob).
In the main class from which the game is running, I have all the information, as well as calling an object called mob1 from Peasant
I need to make it so that if the player is within 300 pixels of the mob, it starts to move towards it. Ive tried doing this but so far, even if the player is 2000 pixels away, the mob starts moving???
Here is my Peasant class
package Entitys.NPCs;
public class Peasant {
public Peasant(float InitX, float InitY, int MobID){
MobX = InitX;
MobY = InitY;
}
//This class shall be used as an object creator. This will randomly move a graphic around, near to a player
private float MobX;
private float MobY;
private int AmountMoved = 0;
private boolean MoveRight = true;
private boolean MoveLeft;
public boolean PlayerDetected = false;
long timer;
//Used to find the mobs X
public float getX(){
return MobX;
}
//Used to find the mobs Y
public float getY(){
return MobY;
}
//Used to set the mobs X
public void setX(float X){
MobX = X;
}
//Used to set the mobs Y
public void setY(float Y){
MobY = Y;
}
//Used to simply move the mob on its X co-ords
public void moveX(int delta){
MobX += delta*0.1f;
}
//Used to simply move the mob on its Y co-ords
public void moveY(int delta){
MobY += delta*0.1f;
}
public void autoEveryThing(int delta, float playerX, float playerY) {
// If the player has not been spotted the NPC/Mob will move left and
// right by 100 Pixels.
if(MobX-300<playerX){
PlayerDetected=true;
}
if(PlayerDetected=true){
if(MobX>playerX){
MobX-=delta*0.12;
}
}
}
}
And here is the main class:
package Worlds.World1;
import org.lwjgl.input.Mouse;
import org.newdawn.slick.Animation;
import org.newdawn.slick.Color;
import org.newdawn.slick.GameContainer;
import org.newdawn.slick.Graphics;
import org.newdawn.slick.Image;
import org.newdawn.slick.Input;
import org.newdawn.slick.SlickException;
import org.newdawn.slick.state.BasicGameState;
import org.newdawn.slick.state.StateBasedGame;
import Entitys.NPCs.*;
import Main.SimpleMob;
public class World1A extends BasicGameState{
String mousePosition;
Image world;
Animation player, playerLeft, playerRight;
int[] duration = {200,200};
float playerX;
float playerY;
float WorldX;
float WorldY;
float PlayerVisibleScreenX;
float PlayerVisibleScreenY;
String MovementDirection;
Peasant mob1;
public World1A(int state){
}
public void init(GameContainer gc, StateBasedGame sbg) throws SlickException{
Image [] WalkingLeft = {new Image("res/Sprites/buckysLeft.png"),new Image("res/Sprites/buckysLeft.png")};
Image [] WalkingRight = {new Image("res/Sprites/buckysRight.png"),new Image("res/Sprites/buckysRight.png")};
playerLeft = new Animation(WalkingLeft, duration, false);
playerRight = new Animation(WalkingRight, duration, false);
player = playerRight;
WorldX = 0;
WorldY = 0;
world= new Image("res/WorldImages/WorldBackGround.png");
mousePosition="null";
MovementDirection = "Not Moved Yet";
mob1= new Peasant(2000, 200, 1);
if(WorldX<=0){
playerX = Math.abs(WorldX);
}else{
playerX=0-WorldX;
}
}
public void render(GameContainer gc, StateBasedGame sbg, Graphics g) throws SlickException{
player.draw(450, 300);
if(WorldX>0){
world.draw(0, 0);
g.fillOval(0+mob1.getX(), 0+mob1.getY(), 50, 50);
g.fillRect(0, 0+340, 500, 10);
player.draw(-WorldX + 450, 300);
}else{
world.draw(WorldX, WorldY);
g.fillOval(WorldX+mob1.getX(), WorldY+mob1.getY(), 50, 50);
g.fillRect(WorldX, WorldY+340, 500, 10);
g.fillOval(WorldX+mob1.getX(), WorldY+mob1.getY(), 50, 50);
player.draw(450, 300);
}
g.setColor(Color.white);
//All this is co-ords ect, it is for developement help
g.drawString(String.valueOf(mob1.getX()), 50, 200);
g.drawString("World X: "+ String.valueOf(WorldX), 50, 225);
g.drawString("Player X: "+ String.valueOf(playerX), 50, 250);
g.drawString("Player Detetcted?: "+ String.valueOf(mob1.PlayerDetected), 50, 265);
}
public void update(GameContainer gc, StateBasedGame sbg, int delta) throws SlickException{
if(WorldX<=0){
playerX = Math.abs(WorldX);
}else{
playerX=0-WorldX;
}
mob1.autoEveryThing(delta, playerX, playerY);
int posX = Mouse.getX();
int posY = Mouse.getY();
mousePosition = "X: " + posX + "\nY: " + posY;
Input input = gc.getInput();
if(input.isKeyDown(Input.KEY_LEFT)){
WorldX += delta * 0.1f;
MovementDirection = "Left";
player = playerLeft;
}else if(input.isKeyDown(Input.KEY_RIGHT)){
WorldX -= delta * 0.1f;
MovementDirection = "Right";
player = playerRight;
}else{
MovementDirection = "Not Moving";
}
}
//DO NOT CHANGE
public int getID(){
return 2;
}
}
The autoEveryThing method in the Peasant class should make it so that if(mobX-300
But when I first run this it starts moving towards the player?
even though (2000-300<0) is false, it still sets the PlayerDetected boolean to true???
Why does this happen?
Thanks
EDIT:
After trying to go through thi and fix it I found somthing strange, even if I take out the whole bit which can change PlayerDetected to true, the mob still moves towards the player. This meens that PlayerDetected is becominbg true somwhere, but I cant figure out where?
if(PlayerDetected=true){
is wrong you should use ==
if(PlayerDetected==true){
or even better
boolean isPlayerDetected;
if (isPlayerDetected)
further consider
double dx = mobX - playerX;
double dy = mobY - playerY;
double distance = Math.sqrt(dx*dx + dy*dy);
if (distance < 300) {
// is within distacne threshold
}

JApplet Textfield/jbutton/nested loop program, create a wall, input number of rows in textfield

I am currently using JCreator, and can not find what is wrong with my code, for some reason its not reading what i input in the JTextField. I am not looking to change my code drastically, if any1 could just point out what i did wrong, or give me some code examples of what it should look like, that would be great. again, not looking for "this is better then this" when they do the same thing.
import java.awt.*;
import javax.swing.*;
import java.util.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
public class Wall extends JApplet implements ActionListener {
double count;
Boolean Submit = false;
JButton btn1;
JTextField tf,field;
int x = 0;
int y = 575;
int x1 = 50;
int y1 = 25;
int textnumber;
Random randomNum = new Random();//initialize random variable
int count2;
public void init() {
setLayout( new FlowLayout( ) );
tf = new JTextField(5);
field = new JTextField( "<===== Enter Brick Rows 1-20", 16 );
add( tf );
add( field );
btn1 = new JButton("Submit");
add(btn1);
btn1.addActionListener(this);
}
public void actionPerformed(ActionEvent event){
if (event.getSource()== btn1){
Submit = true;
}
}
public void paint(Graphics g, double BrickNumbers) {
super.paint(g);
while(Submit == true){
DrawBrick(g,BrickNumbers);
}
}
public void DrawBrick(Graphics g, double BrickNumbers){
String Value = tf.getText();
BrickNumbers = Double.parseDouble(Value);
if(Submit == true){
count = BrickNumbers;
for(double count = BrickNumbers; ((count>=1) && (count <=20)); count--){
int d = 1+ randomNum.nextInt(255);//get d variable
int e = 1+ randomNum.nextInt(255);//get e variable
int f = 1+ randomNum.nextInt(255);//get f variable
Color randomcolor = new Color(d,e,f);
g.setColor(randomcolor);
g.fillRect(x, y, x1, y1);
g.fillRect(x+ 50, y, x1, y1);
g.fillRect(x+100, y, x1, y1);
g.fillRect(x+150, y, x1, y1);
g.fillRect(x+200, y, x1, y1);
g.fillRect(x+250, y, x1, y1);
y = y - 25;
}
}
repaint();
}
}
You've got some bad code in your painting method including:
you've got a while (true) loop in your paint(...) method which will lock your GUI and prevent it from responding to anything.
You're trying to read in from the JTextField in a method called from the paint method. You should never have program logic in your painting code or in methods it calls.
You shouldn't be overriding paint(...) of a JApplet to begin with but rather paintComponent(...) in a JPanel that the JApplet holds.
Consider adding code to read the JTextField(s) in your actionPerformed method as that seems to be the best place for this logic.
Edit
Your paint method won't ever get called since it isn't a true overload of JApplet's paint method. Yours has 2 parameters and a paint method should only have one.
In your actionPerformed method, get the value from the JTextField,
convert it into an int with Integer.parseInt(...) not a double since you're never going to draw a fraction of a brick
and with the int obtained set an int class field, perhaps called brickCount or something like that, and then call repaint().
In your JPanel's paintComponent(...) method (which like paint should only have one parameter, Graphics), call paintBricks(), and have this method use the brickCount field value to decide how many bricks to paint.
Never call repaint() from within paint(...) paintComponent(...) or from any methods called from within these methods.
Edit 2
Here's an example that doesn't do what your program needs to do, but illustrates how to get information from a JTextField and use it in a drawing:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class SimpleApplet extends JApplet {
#Override
public void init() {
getContentPane().add(new SimpleAppletMainPanel());
}
}
class SimpleAppletMainPanel extends JPanel {
private static final Color CIRCLE_COLOR = Color.red.darker();
private static final int CIRCLE_STROKE_WIDTH = 10;
private static final int GAP = 3;
private static final Stroke CIRCLE_STROKE = new BasicStroke((float)CIRCLE_STROKE_WIDTH);
private JTextField textField = new JTextField(5);
private JButton myButton = new JButton("Submit");
private int count = 0;
public SimpleAppletMainPanel() {
ActionListener actionListener = new ActionListener() {
public void actionPerformed(ActionEvent arg0) {
try {
count = Integer.parseInt(textField.getText());
repaint();
} catch (NumberFormatException e) {
e.printStackTrace();
}
}
};
myButton.addActionListener(actionListener);
textField.addActionListener(actionListener);
add(new JLabel("Enter a number, 1-10:"));
add(textField);
add(myButton);
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
for (int i = 0; i < count; i++) {
drawCircle(g, i);
}
}
private void drawCircle(Graphics g, int layer) {
int centerX = getWidth() / 2;
int centerY = getHeight() / 2;
int radius = layer * (CIRCLE_STROKE_WIDTH + GAP) + GAP;
int x = centerX - radius ;
int y = centerY - radius;
Graphics2D g2b = (Graphics2D) g.create();
g2b.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
g2b.setStroke(CIRCLE_STROKE);
g2b.setColor(CIRCLE_COLOR);
g2b.drawOval(x, y, radius * 2, radius * 2);
g2b.dispose();
}
}
This will result in the following:

Categories