This is a (very) simple JAVA implementation of the game “hero vs monsters” as part of the year 1 BSE lab. The implementation is mainly for demonstrating the custom view and touch event. Video tutorial is at the end of the article.
The UI
it will be a very simple UI with only one view (game view) that extends Android View. In the scene, a hero is trying to kill monsters appears in different locations.
You will need to prepare some image resource, i.e. hero and monsters. No XML layout is needed as we will set the game view to the content view in the MainActivity
. And that is all we need for the MainActivity.
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(new GameView(this));
}
}
The Game View
We will create a custom view, namely GameView, to display hero and monsters. The class will extends View and implement Runnable interface.
public class GameView extends View {...}
As we need a hero and monster, we will declare some corresponding variables right below the class name.
private Bitmap hero;
private Rect heroBounds;//to track the location of hero
private Bitmap monster;
private Rect monsterBounds;//to track the location of monster
We init these above variables with an initialisation method and call the init method in constructors:
//Constructor
public GameView(Context context) {
super(context);
init();
}
//Init method
private void init() {
hero = BitmapFactory.decodeResource(getResources(), R.drawable.ic_hero);
monster = BitmapFactory.decodeResource(getResources(), R.drawable.ic_monster);
heroBounds = new Rect(0 , 0, hero.getWidth(), hero.getHeight());
//Make monster appear in random place
monsterBounds = new Rect(200 , 200,
200 + monster.getWidth(), 200 + monster.getHeight());
}
After that, we will display monster and hero on screen by overriding the onDraw
method.
@Override
public void onDraw(Canvas canvas) {
canvas.drawBitmap(hero, null, heroBounds, null);
if(monster != null)
canvas.drawBitmap(monster, null, monsterBounds, null);
}
Next, as we want to move the hero around the screen we will override the method onTouchEvent
. We will move the hero to follow the finger movement, check the collision with monsters, and we tell the view to redraw the view using the
method defined in View.postinvalidate
@Override
public boolean onTouchEvent(MotionEvent event) {
heroBounds.offsetTo((int)event.getX() - heroBounds.width()/2,
(int)event.getY() - heroBounds.height()/2);
//Check collision
Rect herotemps = new Rect(heroBounds);
if(herotemps.intersect(monsterBounds)) {
//monster = null;
randomMonster();
}
postinvalidate();
//or use handler (same idea)
//hander.sendEmptyMessage(0);
return true;
}
In case you want to use handler, you can uncomment the hander statement and add the hander variable.
//right below the monsterBounds declaration
Handler handler = new Handler(Looper.getMainLooper()) {
@Override
public void handleMessage(@NonNull Message msg) {
invalidate();
}
};
Finally, we need to handle the regeneration of the new monster at the new location with randomMonster
method. Just make sure that the monster is not out of the screen bounds.
public void randomMonster(){
Random r = new Random();
int x = r.nextInt(getWidth() - 2 *monster.getWidth());
int y = r.nextInt(getHeight() - 2 * monster.getHeight());
monsterBounds = new Rect(x , y,
x + monster.getWidth(), y + monster.getHeight());
}
Video tutorial
Enjoy the 10 min video to understand the custom view and simple interaction.
Wrapping up
It is quite simple to complete the game with just a few lines of code. Nevertheless, using custom views is NOT recommended for animation in more complicated gaming projects. Refer to surface view tutorial for advanced game animation. Other useful links:
- Mobile game tutorials
- Subscribe to Petamind channel
- GitHub source code