Android原生游戏开发:使用JustWeEngine开发微信打飞机
使用JustWeEngine开发微信打飞机:
作者博客: 博客园
引擎地址:JustWeEngine
示例代码:EngineDemo
JustWeEngine?
JustWeEngine是托管在Github 的一个开源的Android原生开发框架,可以让Android的开发人员
非常便捷,无需切换语言和编译器的制作Android原生游戏。
使用方法
引入Engine作为Library进行使用。
引入"/jar"文件夹下的jar包。
使用Gradle构建:
- Step 1. Add the JitPack repository to your build file
Add it in your root build.gradle at the end of repositories:
allprojects {
repositories {
...
maven { url "https://jitpack.io" }
}
}- Step 2. Add the dependency
dependencies {
compile 'com.github.lfkdsk:JustWeEngine:v1.01'
}- Step 1. Add the JitPack repository to your build file
使用Maven构建:
- Step 1. Add the JitPack repository to your build file
<repositories>
<repository>
<id>jitpack.io</id>
<url>https://jitpack.io</url>
</repository>
</repositories>- Step 2. Add the dependency
<dependency>
<groupId>com.github.lfkdsk</groupId>
<artifactId>JustWeEngine</artifactId>
<version>v1.01</version>
</dependency>
1.Activity继承基类:
由于框架全部使用SurfaceView进行绘制,不使用诸如Button、Layout等原生控件,所以应该首先新建类继承引擎核心类Engine,负责游戏的流程,注释中已有明确的标明功能。
public class Game extends Engine {
// 一般在构造函数完成变量的初始化
public Game() {
// 控制debug模式是否开始,debug模式打印日志、帧数、pause次数等信息
super(true);
}
// 载入一些UI参数和设置屏幕放向,默认背景色,设定屏幕的扫描方式等
@Override
public void init() {
// 初始化UI默认参数,必须调用该方法,其中有一些用于多机型适配的参数需要初始化
UIdefaultData.init(this);
}
// 通常用于精灵,背景,图片等物体的设置和载入
@Override
public void load() {
}
// draw 和 update 在线程中进行不断的循环刷新
// draw 负责绘制 update 负责更新数据和对象信息
@Override
public void draw() {
}
@Override
public void update() {
}
// 将touch 事件传回 功能和所设定的屏幕扫描方式有关
@Override
public void touch(MotionEvent event) {
}
// 将碰撞事件传回 传回精灵和物品的基类
// 用于处理碰撞事件 默认使用矩形碰撞
@Override
public void collision(BaseSub baseSub) {
}
}
2.添加图片、文字、对象:
2.1 添加文字:
printer = new GameTextPrinter();
printer.setTextColor(Color.BLACK);
printer.setTextSize(24);
printer.setLineSpaceing(28);
初始化文字绘制printer,并设置颜色尺寸和图片。
@Override
public void draw() {
canvas = super.getCanvas();
printer.setCanvas(canvas);
printer.drawText("Engine demo", 10, 20);
}
在draw中即可绘制。
2.2 使用图片:
首先添加一张大的图片,需要的敌军战机,和可控的飞机都在这张图上。
GameTexture texture1 = new GameTexture(this);
texture1.loadFromAsset("pic/shoot.png");
并且初始化敌人的图片和子弹的图片:
shoot = new GameTexture(this);
shoot.loadFromAsset("pic/flare.png");
enemyPic = new GameTexture(this);
enemyPic.loadFromAsset("pic/enemy.png");
2.3 对象:
我们要新建一个BaseSprite对象并设置一些基础属性。
BaseSprite ship;
// 新建对象,每张帧图片宽100高124
ship = new BaseSprite(this, 100, 124, FrameType.COMMON);
// 从刚才的那张图片取出帧
ship.setTexture(texture1);
// 添加两帧 参数是坐标
ship.addRectFrame(0, 100, 100, 124);
ship.addRectFrame(167, 361, 100, 124);
// 添加动画 在两帧之间不断切换
ship.addAnimation(new FrameAnimation(0, 1, 1));
// 设定位置
ship.setPosition(UIdefaultData.centerInHorizontalX - ship.getWidthWithScale() / 2,
UIdefaultData.screenHeight + ship.getHeightWidthScale());
// 设定拉伸后的大小
ship.setDipScale(96, 96);
// 添加固定动画 即小飞机出场
ship.addfixedAnimation("start",
new MoveAnimation(UIdefaultData.centerInHorizontalX - ship.getWidthWithScale() / 2,
UIdefaultData.screenHeight - 2 * ship.getHeightWidthScale(), new Float2(10, 10)));
// 设定名称和类别 对象分组
ship.setName("SHIP");
ship.setIdentifier(SHIP);
// 添加到精灵组中
addToSpriteGroup(ship);
2.4添加背景:
GameTexture tex = new GameTexture(this);
if (!tex.loadFromAsset("pic/background.png")) {
fatalError("Error loading space");
}
backGround2X = Bitmap.createBitmap(
UIdefaultData.screenWidth,
UIdefaultData.screenHeight * 2,
Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(backGround2X);
Rect dst = new Rect(0, 0, UIdefaultData.screenWidth - 1,
UIdefaultData.screenHeight);
canvas.drawBitmap(tex.getBitmap(), null, dst, null);
dst = new Rect(0, UIdefaultData.screenHeight,
UIdefaultData.screenWidth,
UIdefaultData.screenHeight * 2);
canvas.drawBitmap(tex.getBitmap(), null, dst, null);
bg_rect = new Rect(0, 0, UIdefaultData.screenWidth, UIdefaultData.screenHeight);
bg_scroll = new Point(0, 0);
这里获取了一张背景图片,并且创建了一张Bitmap包含两份的背景图片,这是为了让背景滚动起来。
2.5生成子弹、敌人:
public void fireBullet() {
if (!shoottimer.stopWatch(300)) return;
BaseSprite bullet;
if (getTypeSizeFromRecycleGroup(BULLET) > 0) {
bullet = (BaseSprite) recycleSubFromGroup(BULLET);
bullet.clearAllAnimation();
removeFromRecycleGroup(bullet);
} else {
bullet = new BaseSprite(this);
bullet.setTexture(shoot);
bullet.setDipScale(8, 18);
bullet.setIdentifier(BULLET);
}
double angle = 270.0;
float speed = 20.0f;
int lifetime = 2500;
bullet.addAnimation(new V elocityAnimation(angle, speed,
lifetime));
bullet.setPosition(ship.s_position.x +
ship.getWidthWithScale() / 2
- bullet.getWidthWithScale() / 2,
ship.s_position.y - 24);
bullet.setAlive(true);
addToSpriteGroup(bullet);
}
private void addEnemy() {
BaseSprite enemy;
if (getTypeSizeFromRecycleGroup(ENEMY) > 0) {
enemy = (BaseSprite) recycleSubFromGroup(ENEMY);
enemy.clearAllAnimation();
removeFromRecycleGroup(enemy);
} else {
enemy = new BaseSprite(this);
enemy.setTexture(enemyPic);
enemy.setIdentifier(ENEMY);
enemy.setDipScale(49, 36);
}
double angle = 90.0;
float speed = 5.0f;
int lifetime = 5000;
enemy.addAnimation(new VelocityAnimation(angle, speed,
lifetime));
enemy.setPosition(random.nextInt(UIdefaultData.screenWidth),
-enemy.getWidthWithScale());
enemy.setAlive(true);
addToSpriteGroup(enemy);
enemyNum++;
}
2.6进行绘制:
更新draw 和 update的方法进行绘制:
@Override
public void draw() {
canvas = super.getCanvas();
canvas.drawBitmap(backGround2X, bg_rect, bg_rect, paint);
printer.setCanvas(canvas);
printer.drawText("Engine demo", 10, 20);
}
@Override
public void update() {
//
if (timer.stopWatch(20)) {
scrollBackground();
}
// 进行入场动画
if (ship.getFixedAnimation("start").animating) {
ship.fixedAnimation("start");
} else {
// 射击和新建敌人
fireBullet();
// int size = getTypeSizeFromRecycleGroup(ENEMY);
// if (size > 0)
// enemyNum -= size;
if (enemyTimer.stopWatch(200)) {
addEnemy();
}
}
}
2.7碰撞监测和touch事件:
@Override
public void touch(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_MOVE:
offsetX = event.getX() - startX;
offsetY = event.getY() - startY;
if (Math.abs(offsetX) > Math.abs(offsetY)) {
if (ship.s_position.x + offsetX > 0
&& ship.s_position.x + offsetX +
ship.getHeightWidthScale() < UIdefaultData.screenWidth) {
ship.s_position.x += offsetX;
resetEvent(event);
}
} else {
if (ship.s_position.y + offsetY > 0
&& ship.s_position.y + offsetY +
ship.getHeightWidthScale() < UIdefaultData.screenHeight) {
ship.s_position.y += offsetY;
resetEvent(event);
}
}
break;
case MotionEvent.ACTION_DOWN:
startX = (int) event.getX();
startY = (int) event.getY();
break;
}
}
@Override
public void collision(BaseSub baseSub) {
BaseSprite other = (BaseSprite) baseSub.getOffender();
if (baseSub.getIdentifier() == BULLET &&
other.getIdentifier() == ENEMY) {
other.setAlive(false);
removeFromSpriteGroup(other);
addToRecycleGroup(other);
enemyNum--;
}
}
2.8滚动背景:
private void resetEvent(MotionEvent event) {
startX = (int) event.getX();
startY = (int) event.getY();
}
public void scrollBackground() {
bg_scroll.y += 10.0f;
bg_rect.top = bg_scroll.y;
bg_rect.bottom = bg_rect.top + UIdefaultData.screenHeight - 1;
if (bg_scroll.y + bg_rect.height() > backGround2X.getHeight()) {
bg_scroll.y = bg_scroll.y - bg_rect.height();
}
}
Android原生游戏开发:使用JustWeEngine开发微信打飞机的更多相关文章
- 《React Native 精解与实战》书籍连载「Android 平台与 React Native 混合开发」
此文是我的出版书籍<React Native 精解与实战>连载分享,此书由机械工业出版社出版,书中详解了 React Native 框架底层原理.React Native 组件布局.组件与 ...
- Android 原生开发、H5、React-Native使用利弊和场景技术分享
http://m.blog.csdn.net/article/details?id=51778086 发表于2016/6/28 18:52:46 1176人阅读 最近工作中接触到React ...
- Android原生(Native)C开发之四:SDL移植笔记
http://www.apkbus.com/forum.php?mod=viewthread&tid=1989 SDL(Simple DirectMedia Layer)是一套开放源码的跨平台 ...
- pygame开发PC端微信打飞机游戏
pygame开发PC端微信打飞机游戏 一.项目简介 1. 介绍 本项目类似曾经火爆的微信打飞机游戏.游戏将使用Python语言开发,主要用到pygame的API.游戏最终将会以python源文件gam ...
- React Native Android原生模块开发实战|教程|心得|怎样创建React Native Android原生模块
尊重版权,未经授权不得转载 本文出自:贾鹏辉的技术博客(http://blog.csdn.net/fengyuzhengfan/article/details/54691503) 告诉大家一个好消息. ...
- RN与android原生开发混合后的环境报错问题
RN与android原生开发混合后的环境报错问题 需要先安装nodejs$ yarn --version1.12.1更新当前版本yarn upgrade --latest安装 | Yarnhttps: ...
- Android 3D游戏开发
OpenGL ES(OpenGL Embedded System) Android 3D游戏开发技术宝典:OpenGL ES 2.0(android 3d游戏开发技术宝典 -opengl es 2.0 ...
- 我的Android进阶之旅------>Android疯狂连连看游戏的实现之开发游戏界面(二)
连连看的游戏界面十分简单,大致可以分为两个区域: 游戏主界面区 控制按钮和数据显示区 1.开发界面布局 本程序使用一个RelativeLayout作为整体的界面布局元素,界面布局上面是一个自定义组件, ...
- 像写Flutter一样开发Android原生应用
要问到Flutter和Android原生App,在开发是有何区别,编程方式是绕不开的话题.Flutter采用声明式编程,Android原生开发则采用命令式编程. 声明式编程 VS. 命令式编程 我们首 ...
随机推荐
- Linux-网络连接-(VMware与CentOS)
VMware虚拟机中安装CentOS,进行网络连接,分为两步,内网连接,与外网连接. 前提: 当你正确安装VMware后,网络适配器会增加2个新的网卡:(可在设备管理器->网络适配器中查看) 第 ...
- 在window下配置laravel开发环境
1.由于有一点php基础,所以非常想更进一步,就选择据说在国外最流行的php框架来学习了,laravel框架,官网上介绍是为艺术而生,从知乎和一些论坛上看到,laravel学起来并不简单,首先配置问题 ...
- 【夯实PHP系列】PHP正则表达式
一. 概述 1. 正则表达式的测试地址: http://tool.chinaz.com/regex/ 二.具体的常用正则表达式 1. 邮箱正则表达式: 1)\w[-\w.+]*@([A-Za-z0-9 ...
- ABP之Javascript生成
还是服务 在调试SimpleTaskSystem的AngularJs demo时,一开始我只看到对服务的应用. app.controller(controllerId, [ '$scope', 'ab ...
- webapi 中的本地登录
WebApi 身份验证方式 asp.net WebApi 中有三种身份验证方式 个人用户账户.用户可以在网站注册,也可以使用 google, facebook 等外部服务登录. 工作和学校账户.使用活 ...
- [翻译]Java HashMap工作原理
大部分Java开发者都在使用Map,特别是HashMap.HashMap是一种简单但强大的方式去存储和获取数据.但有多少开发者知道HashMap内部如何工作呢?几天前,我阅读了java.util.Ha ...
- 安全退出,清空Session或Cookie
概览: 网站中点击退出,如果仅仅是重定向到登录/出页面,此时在浏览器地址栏中输入登录后的某个页面地址如主页,你会发现不用登录就能访问.这种所谓的退出并不是安全的. 那么怎样做到安全退出呢? 那就是点击 ...
- css3相册图片3D旋转展示特效
查看效果:http://hovertree.com/texiao/css/14/ 本效果用css3的animation实现动画 定义和用法animation 属性是一个简写属性,用于设置六个动画属性: ...
- Struts2(1) —— 概述
1.Struts2框架介绍 Struts2框架是MVC流程框架,适合分层开发,框架应用实现不依赖于Servlet,使用大量的拦截器来处理用户请求,属于无侵入式的设计. 2.Struts2框架的流程原理 ...
- UIPickerView的使用(一)
简介:UIPickerView是一个选择器控件,它比UIDatePicker更加通用,它可以生成单列的选择器,也可生成多列的选择器,而且开发者完全可以自定义选择项的外观,因此用法非常灵活.UIPick ...