我是 Android 编程的初学者,我正在开发一款小型泡泡射击游戏。但是,我面临一个我无法弄清楚的奇怪问题。我有一段处理应用程序启动器的代码,如果我在课堂上编写整个代码,应用程序运行顺利。但是,如果我将代码“切割”成不同的类,那么启动器的移动就会出现明显的滞后。
我的主要问题是:什么会导致这种滞后,以及避免这种滞后的最佳方法是什么(现在和将来)。
提前致谢,
亲切的问候,
这是我在一个类中编写所有内容时的代码。
package com.example.bubbleshootergame;
// imports are delete to shorten the post
public class GameThree extends Activity implements OnTouchListener {
OurView v;
Bitmap launcher;
float x, y, rotationAngle;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
v = new OurView(this);
v.setOnTouchListener(this);
launcher = BitmapFactory.decodeResource(getResources(),
R.drawable.launcher);
setContentView(v);
}
@Override
protected void onPause() {
// TODO Auto-generated method stub
super.onPause();
v.pause();
}
@Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
v.resume();
}
public class OurView extends SurfaceView implements Runnable {
Thread t = null;
SurfaceHolder holder;
boolean bool = false;
public OurView(Context context) {
super(context);
// TODO Auto-generated constructor stub
holder = getHolder();
}
@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
View content = getWindow().findViewById(Window.ID_ANDROID_CONTENT);
// x & y are the width and height of the usable screen size
x = content.getWidth();
y = content.getHeight();
}
@Override
public void run() {
// TODO Auto-generated method stub
while (bool == true) {
if (!holder.getSurface().isValid()) {
continue;
}
Canvas c = holder.lockCanvas();
Paint Blackline = new Paint();
Blackline.setColor(Color.rgb(0, 0, 0));
Blackline.setStrokeWidth(10);
// background color of canvas
c.drawARGB(255, 255, 255, 255);
c.drawRect(0, (float) 0.85*y, x, (float) 0.84*y, Blackline);
// rotate by angle 'rotationAngle' around point x/2 and y
// this corresponds the middle of the launcher
c.rotate(rotationAngle, x / 2, y - (launcher.getHeight() / 2));
// draw the bitmap (this case the launcher) around the center of
// the width of the launcher and bottom of the launcher
c.drawBitmap(launcher, x / 2 - (launcher.getWidth() / 2), y
- (launcher.getHeight()), null);
holder.unlockCanvasAndPost(c);
}
}
public void pause() {
// TODO Auto-generated method stub
bool = false;
while (true) {
try {
t.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
break;
}
t = null;
}
public void resume() {
// TODO Auto-generated method stub
bool = true;
t = new Thread(this);
t.start();
}
}
@Override
public boolean onTouch(View v, MotionEvent event) {
// TODO Auto-generated method stub
float currentX = event.getX();
float currentY = event.getY();
if (currentY >= 0.85*y ){
}
else
switch (event.getAction()) {
case MotionEvent.ACTION_MOVE: {
double rotationAngleRadians = Math.atan2(currentX - x / 2, y
- currentY);
rotationAngle = (int) Math.toDegrees(rotationAngleRadians);
return true;
}
}
return true;
}
}
以下是使用不同类时的代码块: MainActivity
package com.gabrudar.conquestappgame;
public class MainActivity extends Activity implements OnTouchListener {
GameView view;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
view = new GameView(this);
view.setOnTouchListener(this);
setContentView(view);
}
@Override
protected void onPause() {
super.onPause();
view.pause();
}
@Override
protected void onResume() {
super.onResume();
view.resume();
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
@Override
public boolean onTouch(View v, MotionEvent event) {
// TODO Auto-generated method stub
try {
Thread.sleep(50);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
view.processTouch(event);
return true;
}
}
游戏视图:
package com.gabrudar.conquestappgame;
public class GameView extends SurfaceView implements Runnable {
Thread gameThread = null;
SurfaceHolder holder;
boolean continueRunning = false;
Bitmap blob;
Bitmap background;
Sprite sprite;
Rect screenRect;
Bitmap Launcher;
LauncherC launcher;
long startTime;
float deltaTime;
public GameView(Context context) {
super(context);
holder = getHolder();
screenRect = new Rect();
background = BitmapFactory.decodeResource(getResources(), R.drawable.androidbg);
blob = BitmapFactory.decodeResource(getResources(), R.drawable.spritesheet);
Launcher = BitmapFactory.decodeResource(getResources(),
R.drawable.launcher);
launcher = new LauncherC(Launcher);
}
@Override
public void run() {
startTime = System.nanoTime();
while (continueRunning == true){
if (!holder.getSurface().isValid()){
continue;
}
deltaTime = (System.nanoTime() - startTime)/1000000;
startTime = System.nanoTime();
Canvas c = holder.lockCanvas();
onDraw(c);
holder.unlockCanvasAndPost(c);
}
}
public void pause() {
continueRunning = false;
while(true){
try{
gameThread.join();
}catch(InterruptedException e){
e.printStackTrace();
}
break;
}
gameThread = null;
}
public void resume() {
continueRunning = true;
gameThread = new Thread(this);
gameThread.start();
}
protected void update(float dt) {
}
protected void onDraw(Canvas canvas) {
this.getDrawingRect(screenRect);
canvas.drawBitmap(background, null, screenRect, null);
launcher.onDraw(canvas);
}
public void processTouch(MotionEvent me) {
launcher.Toucher(me);
}
}
启动器:
package com.gabrudar.conquestappgame;
public class LauncherC {
float rotationAngle,x1,y1;
Bitmap L1;
public LauncherC(Bitmap Launcher){
L1 = Launcher;
}
public void onDraw(Canvas c) {
// TODO Auto-generated method stub
Paint Blackline = new Paint();
Blackline.setColor(Color.rgb(0, 0, 0));
Blackline.setStrokeWidth(10);
x1 = c.getWidth();
y1 = c.getHeight();
c.drawRect(0, (float) 0.85 * y1, x1, (float) 0.84 * y1, Blackline);
c.rotate(rotationAngle, x1 / 2, y1 - (L1.getHeight() / 2));
c.drawBitmap(L1, x1 / 2 - (L1.getWidth() / 2), y1
- (L1.getHeight()), null);
}
public void Toucher(MotionEvent event){
// TODO Auto-generated method stub
float currentX = event.getX();
float currentY = event.getY();
if (currentY >= 0.85 * y1) {
} else
switch (event.getAction()) {
case MotionEvent.ACTION_MOVE: {
double rotationAngleRadians = Math.atan2(currentX - x1 / 2, y1
- currentY);
rotationAngle = (int) Math.toDegrees(rotationAngleRadians);
break;
}
}
}
}