我最近问过为什么引力不能在我的Android应用程序(link)中运行,我仍然遇到问题。我将视图更改为“Playground”类,但现在它只是强制关闭。我究竟做错了什么?
package com.game.myapp;
import android.app.Activity;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.os.Bundle;
public class InGame extends Activity{
Playground v;
private int radius;
private int xPosition;
private int yPosition;
private Paint paint;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Rewrite this, it sucks. Seriously.
super.onCreate(savedInstanceState);
v = new Playground(this);
setContentView(v);
}
public InGame(int x, int y, int radius, int color)
{
this.xPosition = x; this.yPosition = y; this.radius = radius;
paint = new Paint(color);
}
void moveBall(int x, int y){
xPosition = x; yPosition =y;
}
void onDraw(Canvas canvas){
canvas.drawCircle(xPosition, yPosition, radius, paint);
}
}
游乐场课程:
package com.game.myapp;
import android.content.Context;
import android.graphics.Canvas;
import android.view.View;
public class Playground extends View{
public static InGame ball;
public Playground(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
@Override
public void onDraw(Canvas canvas)
{
super.onDraw(canvas);
if (ball != null ){
ball.onDraw(canvas);
}
}
}
继承LogCat:
11-04 16:36:33.945: D/dalvikvm(13177): newInstance failed: no <init>()
11-04 16:36:33.949: D/AndroidRuntime(13177): Shutting down VM
11-04 16:36:33.949: W/dalvikvm(13177): threadid=1: thread exiting with uncaught exception (group=0x4001e578)
11-04 16:36:33.953: E/AndroidRuntime(13177): FATAL EXCEPTION: main
11-04 16:36:33.953: E/AndroidRuntime(13177): java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{com.game.myapp/com.game.myapp.InGame}: java.lang.InstantiationException: com.game.myapp.InGame
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1573)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1667)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.ActivityThread.access$1500(ActivityThread.java:117)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:935)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.os.Handler.dispatchMessage(Handler.java:99)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.os.Looper.loop(Looper.java:130)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.ActivityThread.main(ActivityThread.java:3687)
11-04 16:36:33.953: E/AndroidRuntime(13177): at java.lang.reflect.Method.invokeNative(Native Method)
11-04 16:36:33.953: E/AndroidRuntime(13177): at java.lang.reflect.Method.invoke(Method.java:507)
11-04 16:36:33.953: E/AndroidRuntime(13177): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:842)
11-04 16:36:33.953: E/AndroidRuntime(13177): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:600)
11-04 16:36:33.953: E/AndroidRuntime(13177): at dalvik.system.NativeStart.main(Native Method)
11-04 16:36:33.953: E/AndroidRuntime(13177): Caused by: java.lang.InstantiationException: com.game.myapp.InGame
11-04 16:36:33.953: E/AndroidRuntime(13177): at java.lang.Class.newInstanceImpl(Native Method)
11-04 16:36:33.953: E/AndroidRuntime(13177): at java.lang.Class.newInstance(Class.java:1409)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.Instrumentation.newActivity(Instrumentation.java:1021)
11-04 16:36:33.953: E/AndroidRuntime(13177): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1565)
11-04 16:36:33.953: E/AndroidRuntime(13177): ... 11 more
答案 0 :(得分:4)
这是完整的代码。我刚刚写了这个并测试了它。有用。我为活动添加了一个计时器,每秒向右和向下移动球10个像素。请研究它,从中学习并根据您的需要进行调整。
Ball class。
package com.example;
import android.graphics.Canvas;
import android.graphics.Paint;
public class Ball{
private int radius;
private int xPosition;
private int yPosition;
private int color;
private Paint paint;
public Ball(int x, int y, int radius, int color)
{
this.xPosition = x; this.yPosition = y; this.radius = radius;
paint = new Paint();
paint.setColor(color);
}
int getX(){return this.xPosition;}
int getY(){return this.yPosition;}
void moveBall(int x, int y){
xPosition = x; yPosition =y;
}
void onDraw(Canvas canvas){
canvas.drawCircle(xPosition, yPosition, radius, paint);
}
}
游乐场课程
package com.example;
import android.content.Context;
import android.graphics.Canvas;
import android.util.AttributeSet;
import android.widget.ImageView;
public class Playground extends ImageView {
private Ball ball;
public Playground(Context context) {
this(context,null);
}
public Playground(Context context, AttributeSet attrs) {
this(context, attrs,0);
}
public Playground(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public void setBall(Ball ball){
this.ball = ball;
}
@Override
public void onDraw(Canvas canvas)
{
super.onDraw(canvas);
if (ball != null ){
ball.onDraw(canvas);
}
}
}
活动类
package com.example;
import android.app.Activity;
import android.graphics.Color;
import android.os.Bundle;
import java.util.Timer;
import java.util.TimerTask;
public class MyActivity extends Activity {
/**
* Called when the activity is first created.
*/
Playground playground;
Ball ball;
Timer myTimer;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
playground = (Playground) findViewById(R.id.playground);
ball = new Ball(100, 100, 20, Color.RED);
playground.setBall(ball);
myTimer = new Timer();
myTimer.schedule(new TimerTask() {
@Override
public void run() {
Update();
}
}, 0, 1000);
}
private void Update() {
this.runOnUiThread(moveBall);
}
private Runnable moveBall = new Runnable() {
public void run() {
ball.moveBall(ball.getX() + 10, ball.getY() + 10);
playground.invalidate();
}
};
}
[编辑] XML
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<com.example.Playground
android:id="@+id/playground"
android:layout_width="fill_parent"
android:layout_height="fill_parent"/>
</LinearLayout>
OOP的要点。
Ball不了解游乐场或活动。它有一个方法可能被要求它在画布上绘制的东西调用但是它知道它可能是一个不可见的画布,或一个按钮的画布,或一个位图的画布 - 它不知道或不需要知道。无论如何调用该方法都可以解决这个问题。
游乐场不了解活动或球。它知道可能有一个Ball类的实例,如果它有,它应该调用它的onDraw方法,但它不知道球是什么或它绘制什么。 Ball担心这一点。
活动不知道Ball或Playground,除了它有一个并且调用Ball移动方法然后告诉Playground重绘自己。
关键是,您可以更改绘制方法,移动方法和其他所有内容而无需重新编码(一般情况下都可以)。例如,您可以更改Ball类中的onDraw以绘制矩形。当然,班级的名字现在是一个糟糕的选择,但你明白了......
答案 1 :(得分:2)
您的InGame
Activity
中没有默认构造函数,Android必须能够对其进行实例化。
显式构造函数的存在将导致不定义隐式的无参数构造函数。您可能需要提供自己的无参数构造函数,将其成员初始化为默认值。
我会删除显式构造函数并将初始化放入onCreate(Bundle)
方法。