I am a very beginner programmer, so I follow a youtube-tutorial that shows me how to build a simple snake app. The men at the youtube-tutorial got an older version of AndroidStudio than me. He uses AndroidStudio version 2.1.2, I use AndroidStudio version 2.2.2 with java language.
My problem is that he uses the commands getMap and map and it works. When I do that it doesn't work.My guestion is what i have to replace in the >methods "getMap" and "map"
The youtube-tutorial that I follow: https://www.youtube.com/watch?v=bPlG7ra83lo
At 12:00 he uses this command first time.
Game Engine
package pelgrom.laurens.snake101.engine;
import android.service.quicksettings.Tile;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import pelgrom.laurens.snake101.Classes.Coordinate;
import pelgrom.laurens.snake101.enums.TileType;
/**
* Created by Laptop on 23-1-2017.
*/
public class GameEngine {
public static final int GameWidth = 28;
public static final int Gameheight = 42;
private List<Coordinate> walls = new ArrayList<>();
public GameEngine() {
}
public void initGame(){
AddWalls();
}
public TileType()() getMap() {
TileType()() map = new TileType(GameWidth) (Gameheight);
for (int x = 0; x < GameWidth; x++) {
for (int y = 0; y < Gameheight; y++) {
map(X)(Y) = TileType.Nothing;
}
}
for (Coordinate wall: walls) {
map(wall.getX())(wall.getY()) = TileType.Wall;
}
return map;
}
//fout zit hem in de "map" en de "getMap"
private void AddWalls() {
//Top and bottom walls
for (int x = 0; x < GameWidth; x ++) {
walls.add(new Coordinate(x,0));
walls.add(new Coordinate(x,Gameheight-1));
}
//Left and Right walls
for (int y = 1; y < Gameheight; y++){
walls.add(new Coordinate(0,y));
walls.add (new Coordinate(GameWidth -1 , y));
}
}
}
`
SnakeView
`package pelgrom.laurens.snake101.views;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.view.View;
import pelgrom.laurens.snake101.enums.TileType;
/**
* Created by Laptop on 23-1-2017.
*/
public class SnakeView extends View {
private Paint mPaint = new Paint();
private TileType snakeViewMap()();
public SnakeView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public void setSnakeViewMap(TileType()() map )( this.snakeViewMap = map; )
#Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
if( snakeViewMap != null ){
float tileSizeX = canvas.getWidth() / snakeViewMap.length;
float tileSizeY = canvas.getHeight() / snakeViewMap.length;
float circleSize = Math.min(tileSizeX, tileSizeY) / 2;
for (int x = 0; x < snakeViewMap.lenght; x++) {
for (int y = 0; y < snakeViewMap(x). lenght; y++) {
switch (snakeViewMap(x)) {
case Nothing:
mPaint.setColor(Color.WHITE);
break;
case Wall:
mPaint.setColor(Color.GREEN);
break;
case SnakeHead:
mPaint.setColor(Color.RED);
break;
case SnakeTail:
mPaint.setColor(Color.GREEN);
break;
case Apple:
mPaint.setColor(Color.RED);
break;
}
canvas.drawCircle(x * tileSizeX + tileSizeX / 2f + circleSize / 2, y * tileSizeY + tileSizeY / 2f + circleSize / 2, circleSize, mPaint);
}
}
}
}
}
`
main activity
`package pelgrom.laurens.snake101;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import pelgrom.laurens.snake101.engine.GameEngine;
import pelgrom.laurens.snake101.views.SnakeView;
public class Activity extends AppCompatActivity {
private GameEngine gameEngine;
private SnakeView snakeView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.layout);
gameEngine = new GameEngine();
gameEngine.initGame();
snakeView = (SnakeView)findViewById(R.id.snakeView);
snakeView.setSnakeViewMap(gameEngine.getMapAsync());
snakeView.invalidate();
}
}
`
The problem with your code is that you are using Round Bracket () while it has to square brackets [] since you are declaring two dimensional arrays. Replace them like :
public TileType[][] getMap() {
TileType[][] map = new TileType[GameWidth][Gameheight];
for (int x = 0; x < GameWidth; x++) {
for (int y = 0; y < Gameheight; y++) {
map[x][y] = TileType.Nothing;
}
}
for (Coordinate wall: walls) {
map[wall.getX()][wall.getY()] = TileType.Wall;
}
return map;
}
PS: you really need to start with the basics.
Related
I am still pretty new to java and javafx and I have created a minesweeper game. I want to add a small menu bar where the user can select the game difficulty (the number of tiles). I have created a menu method, but I am unsure of where to add it to scene. Everywhere I have tried to put the menu method I get exception errors.
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
import javafx.application.Application;
import javafx.event.ActionEvent;
import javafx.fxml.FXML;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.scene.control.Alert;
import javafx.scene.control.Alert.AlertType;
import javafx.scene.control.ButtonType;
import javafx.scene.control.Menu;
import javafx.scene.control.MenuItem;
import javafx.scene.layout.Pane;
import javafx.scene.layout.StackPane;
import javafx.scene.paint.Color;
import javafx.scene.shape.Rectangle;
import javafx.scene.text.Font;
import javafx.scene.text.Text;
import javafx.stage.Stage;
public class Minesweeper extends Application {
private int TILE_SIZE = 50;
private static final int W = 800;
private static final int H = 600;
private int X_TILES = W / TILE_SIZE;
private int Y_TILES = H / TILE_SIZE;
private final String[] gameType = {"Easy", "Medium", "Hard", "Very Hard"};
private String difficulty;
#FXML
private Menu gameMenu;
private Tile[][] grid = new Tile[X_TILES][Y_TILES];
private Scene scene;
public void menu() {
for(String game : gameType){
MenuItem menuItem = new MenuItem(game);
menuItem.setUserData(game);
menuItem.setOnAction((ActionEvent event) -> {
selectGame(event);
});
gameMenu.getItems().add(menuItem);
}
}
private void selectGame(ActionEvent event) {
MenuItem menuItem = (MenuItem)event.getSource();
difficulty = (String)menuItem.getUserData();
switch (difficulty) {
case "Easy":
TILE_SIZE = 200;
break;
case "Medium":
TILE_SIZE = 100;
break;
case "Hard":
TILE_SIZE = 50;
break;
case "Very Hard":
TILE_SIZE = 40;
break;
default:
break;
}
}
private Parent createContent() {
Pane root = new Pane();
root.setPrefSize(W, H);
for (int y = 0; y < Y_TILES; y++) {
for (int x = 0; x < X_TILES; x++) {
Tile tile = new Tile(x, y, Math.random() < 0.2);
grid[x][y] = tile;
root.getChildren().add(tile);
}
}
for (int y = 0; y < Y_TILES; y++) {
for (int x = 0; x < X_TILES; x++) {
Tile tile = grid[x][y];
if (tile.hasBomb)
continue;
long bombs = getNeighbors(tile).stream().filter(t -> t.hasBomb).count();
if (bombs > 0)
tile.text.setText(String.valueOf(bombs));
}
}
return root;
}
private List<Tile> getNeighbors(Tile tile) {
List<Tile> neighbors = new ArrayList<>();
int[] points = new int[] {
-1, -1,
-1, 0,
-1, 1,
0, -1,
0, 1,
1, -1,
1, 0,
1, 1
};
for (int i = 0; i < points.length; i++) {
int dx = points[i];
int dy = points[++i];
int newX = tile.x + dx;
int newY = tile.y + dy;
if (newX >= 0 && newX < X_TILES
&& newY >= 0 && newY < Y_TILES) {
neighbors.add(grid[newX][newY]);
}
}
return neighbors;
}
private class Tile extends StackPane {
private int x, y;
private boolean hasBomb;
private boolean isOpen = false;
private Rectangle border = new Rectangle(TILE_SIZE - 2, TILE_SIZE - 2);
private Text text = new Text();
Alert alert = new Alert(AlertType.CONFIRMATION, "Game Over! Play Again?");
public Tile(int x, int y, boolean hasBomb) {
this.x = x;
this.y = y;
this.hasBomb = hasBomb;
border.setStroke(Color.LIGHTGRAY);
text.setFont(Font.font(18));
text.setText(hasBomb ? "X" : "");
text.setVisible(false);
getChildren().addAll(border, text);
setTranslateX(x * TILE_SIZE);
setTranslateY(y * TILE_SIZE);
setOnMouseClicked(e -> open());
}
public void open() {
if (isOpen)
return;
if (hasBomb) {
Optional<ButtonType> result = alert.showAndWait();
if (result.isPresent() && result.get() == ButtonType.OK) {
scene.setRoot(createContent());
}
return;
}
isOpen = true;
text.setVisible(true);
border.setFill(null);
if (text.getText().isEmpty()) {
getNeighbors(this).forEach(Tile::open);
}
switch (text.getText()) {
case "1":
text.setFill(Color.BLUE);
break;
case "2":
text.setFill(Color.FORESTGREEN);
break;
case "3":
text.setFill(Color.RED);
break;
case "4":
text.setFill(Color.DARKBLUE);
break;
case "5":
text.setFill(Color.MAROON);
break;
case "6":
text.setFill(Color.AQUAMARINE);
break;
case "7":
text.setFill(Color.BLACK);
break;
case "8":
text.setFill(Color.GRAY);
break;
default:
break;
}
}
}
#Override
public void start(Stage stage) throws Exception {
scene = new Scene(createContent());
stage.setScene(scene);
stage.show();
}
public static void main(String[] args) {
launch(args);
}
}
You can add it like this:
public MenuBar menu() {
gameMenu = new Menu("Difficulty");
for(String game : gameType){
MenuItem menuItem = new MenuItem(game);
menuItem.setUserData(game);
menuItem.setOnAction((ActionEvent event) -> {
selectGame(event);
});
gameMenu.getItems().add(menuItem);
}
MenuBar menuBar = new MenuBar(gameMenu);
return menuBar;
}
private Parent createContent() {
VBox root = new VBox();
Pane content = new Pane();
content.setPrefSize(W, H);
for (int y = 0; y < Y_TILES; y++) {
for (int x = 0; x < X_TILES; x++) {
Tile tile = new Tile(x, y, Math.random() < 0.2);
grid[x][y] = tile;
content.getChildren().add(tile);
}
}
for (int y = 0; y < Y_TILES; y++) {
for (int x = 0; x < X_TILES; x++) {
Tile tile = grid[x][y];
if (tile.hasBomb)
continue;
long bombs = getNeighbors(tile).stream().filter(t -> t.hasBomb).count();
if (bombs > 0)
tile.text.setText(String.valueOf(bombs));
}
}
root.getChildren().addAll(menu(), content);
return root;
}
In the menu method I created the instance for gameMenu which is annotated in your example with #FXML, so this line might not be needed. The method however returns a MenuBar that contains the menu.
This bar is then added as a child to the root element. I also introduced a new layer for layouting (VBox) with the menu and the original content as children.
See also this oracle article.
I understand that this is technically a repeat question, but all of the similar questions include code I do not understand, so I decided to ask the question using code I understand.
I am attempting to make a flappy bird style game to try android programing and I cannot get Rect.intersects to change the player's score when the player collides with an object (cloud)
Thanks in advance!!
View class:
package com.gregsapps.fallingbird;
import java.util.ArrayList;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.view.View;
public class GameView extends View{
private Bird bird;
private boolean runOnce = false;
private Context context;
private Paint red;
ArrayList<Cloud> clouds = new ArrayList<Cloud>();
private int cloudDelay;
private Collision collision;
//private Paint textPaint;
public GameView(Context context) {
super(context);
this.context = context;
this.setDrawingCacheEnabled(true);
red = new Paint();
red.setColor(Color.RED);
red.setTextSize(100f);
collision = new Collision();
//textPaint.setColor(Color.BLACK);
//textPaint.setTextAlign(Align.RIGHT);
// TODO add setup code
}
protected void onDraw(Canvas canvas){
update(canvas);
System.out.println(bird.score);
//TODO add drawing code
this.buildDrawingCache();
//bird.canvasImage = this.getDrawingCache(true);
canvas.drawColor(Color.rgb(10, 255, 255));
canvas.drawRect(bird.birdRect, red);
canvas.drawBitmap(bird.image, bird.x, bird.y, null);
for(int i = 0; i < clouds.size(); i++){
System.out.println("Drawing cloud");
Cloud cloud = (Cloud) clouds.get(i);
cloud.move(5);
System.out.println(cloud.leftX + "/t" + cloud.rightX);
canvas.drawRect(cloud.rightCloud, red);
canvas.drawRect(cloud.leftCloud, red);
canvas.drawBitmap(cloud.image, cloud.leftX, cloud.leftY, null);
canvas.drawBitmap(cloud.image, cloud.rightX, cloud.rightY, null);
if(cloud.leftY <= -144)clouds.remove(cloud);
if(bird.y > cloud.leftY + bird.height) bird.score++;
if(Rect.intersects(bird.birdRect, cloud.leftCloud)){
bird.score = 0;
}
else if(Rect.intersects(bird.birdRect, cloud.rightCloud)){
bird.score = 0;
}
}
canvas.drawLine(canvas.getWidth()/2 - 1, 0, canvas.getWidth()/2 - 1, canvas.getHeight(), red);
cloudDelay --;
if(cloudDelay <= 0){
System.out.println("new cloud");
Cloud cloud = new Cloud(com.gregsapps.fallingbird.R.drawable.cloud, context);
System.out.println("added");
clouds.add(cloud);
cloudDelay = 175;
}
canvas.drawText(Integer.toString(bird.score/12), 50, 100, red);
invalidate();
}
private void update(Canvas canvas){
//TODO add code to update stuff
if(runOnce == false){
bird = new Bird(canvas, com.gregsapps.fallingbird.R.drawable.bird, context);
runOnce = true;
StaticVarHandler.canvasHeight = canvas.getHeight();
StaticVarHandler.canvasWidth = canvas.getWidth();
}
bird.move();
}
}
Cloud class:
package com.gregsapps.fallingbird;
import java.util.Random;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Rect;
public class Cloud {
public int leftX;
public int leftY;
public int rightX;
public int rightY;
private Random random;
public Bitmap image;
private Context context;
public Rect leftCloud;
public Rect rightCloud;
public int height;
public int width;
Cloud(int image, Context context){
this.context = context;
this.image = BitmapFactory.decodeResource(this.context.getResources(), R.drawable.cloud);
random = new Random();
leftX = random.nextInt(StaticVarHandler.canvasWidth-(StaticVarHandler.birdWidth*2));
rightX = leftX + StaticVarHandler.birdWidth*2;
rightY = leftY = StaticVarHandler.canvasHeight+this.image.getHeight();
leftX -= this.image.getWidth();
leftCloud = new Rect(leftX, leftY, this.image.getWidth(), this.image.getHeight());
rightCloud = new Rect(rightX, rightY, this.image.getWidth(), this.image.getHeight());
}
public void move(int scrollSpeed){
leftCloud.offset(0, -scrollSpeed);
rightCloud.offset(0, -scrollSpeed);
leftY-=scrollSpeed;
rightY-=scrollSpeed;
}
}
Bird class:
package com.gregsapps.fallingbird;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Rect;
public class Bird {
public int x;
public int y;
private int speed;
public Bitmap image;
Context context;
private int gravity;
public int width;
public int height;
private int canvasWidth;
private int canvasHeight;
public Bitmap canvasImage;
public boolean touch;
public int touchX;
public int touchY;
private int gravDelay = 0;
private int jump = 0;
public int score;
public Rect birdRect;
Bird(Canvas canvas, int image, Context context){
this.context = context;
this.image = BitmapFactory.decodeResource(this.context.getResources(), image);
x = canvas.getWidth()/2 - this.image.getWidth()/2;
y = 10;
speed = this.image.getWidth()/10;
//setup gravity, speed, width and height attributes
speed = canvas.getWidth()/25;
gravity = speed/10;
StaticVarHandler.birdWidth = width = this.image.getWidth();
height = this.image.getHeight();
canvasWidth = canvas.getWidth();
canvasHeight = canvas.getHeight();
System.out.println(canvasWidth);
System.out.println(canvas.getWidth());
birdRect = new Rect(x, y, this.image.getWidth(), this.image.getHeight());
}
public void move(){
gravDelay --;
jump --;
if(StaticVarHandler.touch) jump = 3;
if(jump >= 0){
if(StaticVarHandler.touchX < canvasWidth/2){
x -= speed/3;
}
if(StaticVarHandler.touchX > canvasWidth/2){
x += speed/3;
}
StaticVarHandler.touch = false;
if(jump == 0) gravDelay = 7;
}
else if(gravDelay <= 0){
System.out.println("GRAVITY");
if(x+width/2 < canvasWidth/2){
x += gravity;
//code to move bird via gravity
}
if(x+width/2 > canvasWidth/2){
x -= gravity;
//same as above but other side
}
gravDelay = 1;
}
if(x <= 0){
score = 0;
x = 0;
}
else if(x+width >= canvasWidth){
score = 0;
x = canvasWidth - width;
}
birdRect.offsetTo(x-1, y-1);
}
private void collisionCheck(){
if(longEquation()){
}
}
}
I think I found your problem.
birdRect = new Rect(x, y, this.image.getWidth(), this.image.getHeight());
and
leftCloud = new Rect(leftX, leftY, this.image.getWidth(), this.image.getHeight());
rightCloud = new Rect(rightX, rightY, this.image.getWidth(), this.image.getHeight());
Should not use getWidth() or getHeight() but should use x + width and y + height.
public Rect (int left, int top, int right, int bottom)
Added in API level 1 Create a new rectangle with the specified
coordinates. Note: no range checking is performed, so the caller must
ensure that left <= right and top <= bottom.
Parameters
left The X coordinate of the left side of the rectangle
top The Y coordinate of the top of the rectangle
right The X
coordinate of the right side of the rectangle
bottom The Y coordinate
of the bottom of the rectangle
This is from the documentation.
I'm trying to recreate Space Invaders in LibGDX to get grip on game-developing but when I try to set every enemy (for now they are just squares) to move in sequence the update() method makes them change their postitions way too fast. Is there some way to slow down this rendering on whole project or any other proper way to solve this? I also tried to handle movement in Timer class and scheulde it but it caused memory overload and threads weren't fired in the same time for every object.
package regularmikey.objects;
import java.util.Timer;
import java.util.TimerTask;
import com.badlogic.gdx.graphics.glutils.ShapeRenderer;
import com.badlogic.gdx.graphics.glutils.ShapeRenderer.ShapeType;
public class Aliens {
public float x;
public float y;
public float fx;
public float fy;
public int step_count = 0;
public Aliens(float x, float y) {
this.fx = this.x = x;
this.fy = this.y = y;
};
public void update(float dt){
if(step_count == 10) {
step_count = 0;
y = y - 1;
x = fx;
}
x = x + 3;
step_count++;
};
PlayState class
package regularmikey.gamestates;
import java.util.ArrayList;
import com.badlogic.gdx.graphics.glutils.ShapeRenderer;
import regularmikey.managers.GameStateManager;
import regularmikey.objects.Aliens;
import regularmikey.objects.Bullet;
import regularmikey.objects.Player;
public class PlayState extends GameState {
private Player player;
private ArrayList<Bullet> bullets;
private ArrayList<Aliens> aliens;
private ShapeRenderer sr;
public PlayState(GameStateManager gsm) {
super(gsm);
}
#Override
public void init() {
sr = new ShapeRenderer();
bullets = new ArrayList<Bullet>();
aliens = new ArrayList<Aliens>();
player = new Player(bullets);
spawnAliens();
}
#Override
public void update(float dt) {
player.update(dt);
for(int i = 0; i < aliens.size(); i++) {
aliens.get(i).update(dt);
}
}
public void spawnAliens() {
aliens.clear();
float i, j;
for(j = 100; j <= 510; j = j + 45) {
for(i = 250; i <= 445; i = i + 45) {
aliens.add(new Aliens(j, i));
}
}
}
#Override
public void draw() {
player.draw(sr);
for(int i = 0; i < aliens.size(); i++) {
aliens.get(i).draw(sr);
}
}
#Override
public void handleinput() {
// TODO Auto-generated method stub
}
#Override
public void dispose() {
// TODO Auto-generated method stub
}
}
public void draw(ShapeRenderer sr) {
sr.setColor(1, 1, 1, 1);
sr.begin(ShapeType.Line);
sr.rect(x, y, 30, 30);
sr.end();
};
}
The key here is the dt variable that is passed along with the update() method, which is short for Delta Time.
Delta time is a commonly used factor in game development that represents the time that has passed since the last frame.
I can't exactly make out the way you are making your aliens move about, but the usual way to make entities in your game move smoothly (regardless of the frame rate):
void update(float deltaTime){
this.position = currentPosition + (this.movementSpeed × deltaTime);
}
This doesn't take into consideration the direction in which the entity is moving, amongst others. But that is besides the point of this example.
So, in your case, you could so something like this:
package regularmikey.objects;
import java.util.Timer;
import java.util.TimerTask;
import com.badlogic.gdx.graphics.glutils.ShapeRenderer;
import com.badlogic.gdx.graphics.glutils.ShapeRenderer.ShapeType;
public class Aliens {
public float x;
public float y;
public float fx;
public float fy;
public int step_count = 0;
private float moveTimer;
private float moveTreshold;
public Aliens(float x, float y) {
this.fx = this.x = x;
this.fy = this.y = y;
moveTimer = 0; // This will act as a stopwatch
moveTreshold = 3000; // Alien will move once it passes this treshold
};
public void update(float dt){
// check whether we passed the treshold for moving or not
if(moveTimer += dt; > moveTreshold){
if(step_count == 10) {
step_count = 0;
y = y - 1;
x = fx;
}
x = x + 3;
step_count++;
moveTimer = 0; // reset the timer
}
};
I am making a 2D game and I've decided implementing a player-following camera to it, so you can explore a big map, and load a small part of the map in the window.
But now I have a little problem, I want the map to follow the player, so the player is always centered, example on how it should look like this but a bit more centered ( did it in paint) :
(source: gyazo.com)
But currently it looks like this:
(source: gyazo.com)
Because offX & offY = 0, I need to think of a formula to make the camera centered by the player.
This is how I work out (move the camera), right in the drawMap method:
private void renderMap(Graphics2D g) {
int[][] tiledMap = this.map.getMap();
for (int i = 0; i < this.map.getHeight(); i++) {
for (int j = 0; j < this.map.getWidth(); j++) {
int currentRow = tiledMap[i][j] ;
if (currentRow == 0) {
g.drawImage(img, (j + offX) * map.getTileSize(), (i + offY) * map.getTileSize(), this);
}
if (currentRow == 1) {
g.setColor(Color.green);
g.fillRect((j + offX) * map.getTileSize(),
(i + offY) * map.getTileSize(), map.getTileSize(),
map.getTileSize());
}
}
}
}
Basically it ads the offX to the tile x and offY to the tile y.
The tilesize is 30 px, so the map is moving by tile size which is a problem I need to sort aswell, OR just move the player by the tile size, and then the walking will be just too fast, because the camera can only load by one tile, if we move one tile per player movement, the camera eventually won't stay centred to the player.
How can I make the camera be centred all the time to the player?
This is my code:
package snow;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Random;
import java.util.ArrayList;
import javax.imageio.ImageIO;
import javax.imageio.ImageReader;
import javax.swing.JPanel;
public class GameController extends JPanel {
private static final long serialVersionUID = 1L;
private Player myPlayer = new Player(5, 5, 25, 25);
private TileMap map;
private Image img;
public GameController() {
this.map = new TileMap(new File("src/snow/Tiles/map1.txt"));
try {
this.img = ImageIO.read(new File("data/snow.png"));
} catch (IOException e1) {
e1.printStackTrace();
}
try {
this.map.buildTile();
} catch (NumberFormatException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public void update() {
}
public void render(Graphics2D g) {
g.setColor(Color.red);
g.fillRect(myPlayer.getX(), myPlayer.getY(),
myPlayer.getWidth(), myPlayer.getHeight());
}
public void paintComponent(Graphics g) {
Graphics2D gfx = (Graphics2D) g;
g.setColor(Color.BLACK);
g.fillRect(0, 0, 765, 503);
renderMap(gfx);
render(gfx);
}
private void renderMap(Graphics2D g) {
int[][] tiledMap = this.map.getMap();
for (int i = 0; i < this.map.getHeight(); i++) {
for (int j = 0; j < this.map.getWidth(); j++) {
int currentRow = tiledMap[i][j] ;
if (currentRow == 0) {
g.drawImage(img, (j + offX) * map.getTileSize(), (i + offY) * map.getTileSize(), this);
}
if (currentRow == 1) {
g.setColor(Color.green);
g.fillRect((j + offX) * map.getTileSize(),
(i + offY) * map.getTileSize(), map.getTileSize(),
map.getTileSize());
}
}
}
}
private int offX = 0, offY = 0;
public void movePlayer(int x, int y) {
int[][] tiledMap = this.map.getMap();
myPlayer.updateX(x);
myPlayer.updateY(y);
offX = +10;
offY = +7;
}
}
package snow;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
public class TileMap {
private File tileMap;
private int tileWidth;
private int tileHeight;
private int tileSize = 30;
private int[][] map;
public TileMap(File tileMap) {
this.tileMap = tileMap;
}
public void buildTile() throws NumberFormatException, IOException {
try {
BufferedReader reader = new BufferedReader(new FileReader(this.tileMap));
this.tileWidth = Integer.parseInt(reader.readLine());
this.tileHeight = Integer.parseInt(reader.readLine());
map = new int[this.tileHeight][this.tileWidth];
for (int i = 0; i < this.tileHeight; i++) {
String line = reader.readLine();
String[] chars = line.split(" ");
for (int j = 0; j < this.tileWidth; j++) {
if (j >= chars.length) {
return;
}
map[i][j] = Integer.parseInt(chars[j]);
}
}
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
public int[][] getMap() {
return this.map;
}
public int getWidth() {
return this.tileWidth;
}
public int getHeight() {
return this.tileHeight;
}
public int getTileSize() {
return this.tileSize;
}
}
I don't entirely understand your code, but I would suggest that inside this code block
for (int i = 0; i < this.map.getHeight(); i++) {
for (int j = 0; j < this.map.getWidth(); j++) {
you say something like
currentRow = map[myPlayer.getX()-this.map.getWidth()/2][myPlayer.getY()-this.map.getHeight()/2]
and then leave the rest of your drawing code as is.
i am trying to implement Deceleration on the bouncy ball. i am able to move the ball up and down but i wanted to add Declaration so when i drop the ball from height it jumps then strike the ground bounce once again and slowly slowly its speed decreases and stop at the end.
Here is My code
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.drawable.BitmapDrawable;
import android.os.Handler;
import android.util.AttributeSet;
import android.widget.ImageView;
public class AnimatedView extends ImageView{
private Context mContext;
int x = -1;
int y = -1;
private int xVelocity = 0;
private int yVelocity = 25;
private Handler h;
private final int FRAME_RATE = 20;
public AnimatedView(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
h = new Handler();
}
private Runnable r = new Runnable() {
#Override
public void run() {
invalidate();
}
};
protected void onDraw(Canvas c) {
BitmapDrawable ball = (BitmapDrawable) mContext.getResources().getDrawable(R.drawable.ball);
if (x<0 && y <0) {
x = this.getWidth()/2;
y = this.getHeight()/2;
} else {
x += xVelocity;
y += yVelocity;
if ((x > this.getWidth() - ball.getBitmap().getWidth()) || (x < 0)) {
xVelocity = xVelocity*-1;
}
if ((y > this.getHeight() - ball.getBitmap().getHeight()) || (y < 0)) {
yVelocity = yVelocity*-1;
}
}
c.drawBitmap(ball.getBitmap(), x, y, null);
h.postDelayed(r, FRAME_RATE);
}
Hope Anyone Can Help me.
Thanks in Advance
Acceleration is to velocity as velocity is to position. You just need to do what you're doing with your position to your velocity.
The simplest solution is to add
yVelocity += yAccel;
to the top of onDraw where yAccel is a int that you want added to the yVelocity every tick. Based on your velocity values
private int yAccel = -2;
might be appropriate.
edit: You should also add checks to ensure the ball does not go into the ground. I added these in the blocks that reverse the velocity, the following code works for me. If it don't work for you, there might be something wrong with another part of your project.
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.drawable.BitmapDrawable;
import android.os.Handler;
import android.util.AttributeSet;
import android.widget.ImageView;
public class AnimatedView extends ImageView {
private Context mContext;
int x = -1;
int y = -1;
private int xVelocity = 0;
private int yVelocity = 25;
private int yAccel = 2;
private Handler h;
private final int FRAME_RATE = 20;
public AnimatedView(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
h = new Handler();
}
private Runnable r = new Runnable() {
#Override
public void run() {
invalidate();
}
};
protected void onDraw(Canvas c) {
yVelocity += yAccel;
BitmapDrawable ball = (BitmapDrawable) mContext.getResources()
.getDrawable(R.drawable.cakes);
if (x < 0 && y < 0) {
x = this.getWidth() / 2;
y = this.getHeight() / 2;
} else {
x += xVelocity;
y += yVelocity;
if ((x > this.getWidth() - ball.getBitmap().getWidth()) || (x < 0)) {
xVelocity = xVelocity * -1;
x = Math.min(this.getWidth() - ball.getBitmap().getWidth(), x);
x = Math.max(0, x);
}
if ((y > this.getHeight() - ball.getBitmap().getHeight())
|| (y < 0)) {
yVelocity = (int)(yVelocity * -0.8f);
y = Math.min(this.getHeight() - ball.getBitmap().getHeight(), y);
y = Math.max(0, y);
}
}
c.drawBitmap(ball.getBitmap(), x, y, null);
h.postDelayed(r, FRAME_RATE);
}
}