前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >手把手教你写《雷神》游戏(五)

手把手教你写《雷神》游戏(五)

作者头像
提莫队长
发布2019-02-21 11:03:25
4270
发布2019-02-21 11:03:25
举报
文章被收录于专栏:刘晓杰刘晓杰

这是游戏的主界面的编写部分 首先,由于是游戏,所以必须提到一个组件SurfaceView。在这里我们自定义一个GameView继承自SurfaceView

注意:因为SurfaceView虽然继承自View,但并没重写onDraw(),所以子类可以重写onDraw()但并不能自动调用。

要想在SurfaceView中画出bitmap等,必须用如下格式

代码语言:javascript
复制
private void draw() {
        Canvas canvas = surfaceHolder.lockCanvas();
        if (canvas == null)
            return;

        //draw something

        surfaceHolder.unlockCanvasAndPost(canvas);
    }

然后开启一个线程,每隔一定时间调用这个draw函数、

GameView在创建的时候做如下这些事: 1.初始化一些参数,比如屏幕宽高,bitmap的生成 2.获得SurfaceHolder这个接口。在surfaceCreated中生成一个Thread来不断地调用draw函数,同时初始化玩家机型。另外设置接口。这个需要MainActivity来管理。因为MainActivity要重写返回键的功能来通知Thread是否要运行

接下来是draw函数的实现

代码语言:javascript
复制
private void draw() {
    Canvas canvas = surfaceHolder.lockCanvas();
    if (canvas == null)
        return;
    drawBackground(canvas);
    drawPlane(canvas);
    drawEnemy(canvas);
    drawBullet(canvas);
    judgeHit();

    surfaceHolder.unlockCanvasAndPost(canvas);
}

每个函数的实现在源码里面都有,注释也很详细,这里就不贴出来了。

最后设置监听器,用来通知MainActivity是否播放音乐

GameView.java伪代码:(源代码在代码包里面)

代码语言:javascript
复制
public class GameView extends SurfaceView {
    private Handler handler = new Handler() {
        @Override
        public void handleMessage(Message msg) {
            switch (msg.what) {
            case 0x001:
                draw();
                break;
            }
        }
    };

    private Context context;

    public GameView(final Context context, AttributeSet attrs) {
        super(context, attrs);
        this.context = context;

        //初始化一些参数,比如屏幕宽高,bitmap的生成

        /**
         * 通过SurfaceHolder接口访问这个surface,getHolder()方法可以得到这个接口
         */
        surfaceHolder = getHolder();
        surfaceHolder.addCallback(new Callback() {
            @Override
            public void surfaceDestroyed(SurfaceHolder arg0) {
                flag = false;
            }

            @Override
            public void surfaceCreated(SurfaceHolder arg0) {
                flag = true;
                // flag用来控制thread的运行
                //这个需要MainActivity来管理。因为MainActivity要重写返回键的功能
                //来通知Thread是否要运行
                ((MainActivity) context).setOnListener(new FinishListener() {
                    @Override
                    public void onFinish() {
                        flag = false;
                    }

                    @Override
                    public void onReStart() {
                        flag = true;
                    }
                });
                //生成一个Thread来不断地调用draw函数
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        while (true) {
                            if (flag) {
                                // 移动背景
                                backY -= 5;
                                if (backY <= 0) {
                                    backY = background.getHeight() / 2;
                                }
                                try {
                                    Thread.sleep(50);// //////////////////
                                } catch (InterruptedException e) {
                                    e.printStackTrace();
                                }
                                handler.sendEmptyMessage(0x001);
                            }
                        }
                    }
                }).start();

                // 初始化玩家机型SharedPreferences
            }

            @Override
            public void surfaceChanged(SurfaceHolder arg0, int arg1, int arg2,
                    int arg3) {
            }
        });
    }

    private void draw() {
        Canvas canvas = surfaceHolder.lockCanvas();
        if (canvas == null)
            return;
        drawBackground(canvas);
        drawPlane(canvas);
        drawEnemy(canvas);
        drawBullet(canvas);
        judgeHit();

        surfaceHolder.unlockCanvasAndPost(canvas);
    }

    private int lastX, lastY;

    /**
     * 用来设置playerPlane的位置 (non-Javadoc)
     * 
     * @see android.view.View#onTouchEvent(android.view.MotionEvent)
     */
    @Override
    public boolean onTouchEvent(MotionEvent event) {
        int action = event.getAction();
        switch (action) {
        case MotionEvent.ACTION_DOWN:
            lastX = (int) event.getX();
            lastY = (int) event.getY();
            break;
        case MotionEvent.ACTION_MOVE:
            //....
            break;
        case MotionEvent.ACTION_UP:
            break;
        }
        return true;
    }

    // 以下是监听MainActivity的监听器,用来通知MainActivity是否播放音乐
    public interface BombListener {
        public void PlayBomb();

        public void stopBgMusic();
    }

    private BombListener listener;

    public void setListener(BombListener listener) {
        this.listener = listener;
    }
}

接下来是MainActivity 过程: 1.判断游戏音乐的开启和关闭 2.监听器来通知播放音乐,由GameView传过来 3.重写返回键功能。判断是继续游戏还是结束 伪代码:

代码语言:javascript
复制
public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        // 全屏
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
                WindowManager.LayoutParams.FLAG_FULLSCREEN);
        setContentView(R.layout.main);

        //判断游戏音乐是否关闭
        generateOption();

        //监听器来通知播放音乐,由GameView传过来
        gameView = (GameView) findViewById(R.id.gameView1);
        gameView.setListener(new BombListener() {
            @Override
            public void PlayBomb() {
                if (soundPool != null) {
                    soundPool.play(soundIDbombAFD, 1, 1, 0, 0, 1);
                }
            }

            @Override
            public void stopBgMusic() {
                if (mediaPlayer != null) {
                    mediaPlayer.stop();
                }
            }
        });
    }

    /**
     * 判断游戏音乐是否关闭
     */
    private void generateOption() {
        //MediaPlayer加载gamebg.mp3,soundpool加载bomb.WAV
    }

    //生命周期处理函数

    /**
     * 重写返回键功能 (non-Javadoc)
     * 
     * @see android.app.Activity#onBackPressed()
     */
    @Override
    public void onBackPressed() {
        finishListener.onFinish();
        if (mediaPlayer != null) {
            if (mediaPlayer.isPlaying())
                mediaPlayer.pause();
            isPause = true;
        }
        new AlertDialog.Builder(MainActivity.this)
                .setTitle("选择:")
                .setPositiveButton("中途结束游戏",
                        new DialogInterface.OnClickListener() {
                            @Override
                            public void onClick(DialogInterface dialog,
                                    int which) {
                                dialog.dismiss();
                                setResult(Activity.RESULT_OK, new Intent(
                                        MainActivity.this, Login.class));
                                finish();
                            }
                        })
                .setNegativeButton("继续", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        finishListener.onReStart();
                        if (mediaPlayer != null) {
                            if (isPause) {
                                mediaPlayer.start();
                                isPause = false;
                            }
                        }
                    }
                }).show();
    }

    // 以下是监听GameView的监听器
    public interface FinishListener {
        public void onFinish();

        public void onReStart();
    }

    private FinishListener finishListener;

    public void setOnListener(FinishListener finishListener2) {
        this.finishListener = finishListener2;
    }
}

这个软件该展示的也都展示了。接下来就是代码链接: http://download.csdn.net/detail/lxj1137800599/9519094

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2016年05月13日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档