⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 snakeview.java

📁 Android的应用实例
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
/*  * Copyright (C) 2007 Google Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * *      http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */package com.example.android.snake;import java.util.ArrayList;import java.util.Map;import java.util.Random;import android.content.Context;import android.content.res.Resources;import android.os.Handler;import android.os.Message;import android.util.AttributeSet;import android.os.Bundle;import android.util.Log;import android.view.KeyEvent;import android.view.View;import android.widget.TextView;/** * SnakeView: implementation of a simple game of Snake *  *  */public class SnakeView extends TileView {    private static final String TAG = "SnakeView";    /**     * Current mode of application: READY to run, RUNNING, or you have already     * lost. static final ints are used instead of an enum for performance     * reasons.     */    private int mMode = READY;    public static final int PAUSE = 0;    public static final int READY = 1;    public static final int RUNNING = 2;    public static final int LOSE = 3;    /**     * Current direction the snake is headed.     */    private int mDirection = NORTH;    private int mNextDirection = NORTH;    private static final int NORTH = 1;    private static final int SOUTH = 2;    private static final int EAST = 3;    private static final int WEST = 4;    /**     * Labels for the drawables that will be loaded into the TileView class     */    private static final int RED_STAR = 1;    private static final int YELLOW_STAR = 2;    private static final int GREEN_STAR = 3;    /**     * mScore: used to track the number of apples captured mMoveDelay: number of     * milliseconds between snake movements. This will decrease as apples are     * captured.     */    private long mScore = 0;    private long mMoveDelay = 600;    /**     * mLastMove: tracks the absolute time when the snake last moved, and is used     * to determine if a move should be made based on mMoveDelay.     */    private long mLastMove;        /**     * mStatusText: text shows to the user in some run states     */    private TextView mStatusText;    /**     * mSnakeTrail: a list of Coordinates that make up the snake's body     * mAppleList: the secret location of the juicy apples the snake craves.     */    private ArrayList<Coordinate> mSnakeTrail = new ArrayList<Coordinate>();    private ArrayList<Coordinate> mAppleList = new ArrayList<Coordinate>();    /**     * Everyone needs a little randomness in their life     */    private static final Random RNG = new Random();    /**     * Create a simple handler that we can use to cause animation to happen.  We     * set ourselves as a target and we can use the sleep()     * function to cause an update/invalidate to occur at a later date.     */    private RefreshHandler mRedrawHandler = new RefreshHandler();    class RefreshHandler extends Handler {        @Override        public void handleMessage(Message msg) {            SnakeView.this.update();            SnakeView.this.invalidate();        }        public void sleep(long delayMillis) {        	this.removeMessages(0);            sendMessageDelayed(obtainMessage(0), delayMillis);        }    };    /**     * Constructs a SnakeView based on inflation from XML     *      * @param context     * @param attrs     */    public SnakeView(Context context, AttributeSet attrs) {        super(context, attrs);        initSnakeView();   }    public SnakeView(Context context, AttributeSet attrs, int defStyle) {    	super(context, attrs, defStyle);    	initSnakeView();    }    private void initSnakeView() {        setFocusable(true);        Resources r = this.getContext().getResources();                resetTiles(4);        loadTile(RED_STAR, r.getDrawable(R.drawable.redstar));        loadTile(YELLOW_STAR, r.getDrawable(R.drawable.yellowstar));        loadTile(GREEN_STAR, r.getDrawable(R.drawable.greenstar));    	    }        private void initNewGame() {        mSnakeTrail.clear();        mAppleList.clear();        // For now we're just going to load up a short default eastbound snake        // that's just turned north                mSnakeTrail.add(new Coordinate(7, 7));        mSnakeTrail.add(new Coordinate(6, 7));        mSnakeTrail.add(new Coordinate(5, 7));        mSnakeTrail.add(new Coordinate(4, 7));        mSnakeTrail.add(new Coordinate(3, 7));        mSnakeTrail.add(new Coordinate(2, 7));        mNextDirection = NORTH;        // Two apples to start with        addRandomApple();        addRandomApple();        mMoveDelay = 600;        mScore = 0;    }    /**     * Given a ArrayList of coordinates, we need to flatten them into an array of     * ints before we can stuff them into a map for flattening and storage.     *      * @param cvec : a ArrayList of Coordinate objects     * @return : a simple array containing the x/y values of the coordinates     * as [x1,y1,x2,y2,x3,y3...]     */    private int[] coordArrayListToArray(ArrayList<Coordinate> cvec) {        int count = cvec.size();        int[] rawArray = new int[count * 2];        for (int index = 0; index < count; index++) {            Coordinate c = cvec.get(index);            rawArray[2 * index] = c.x;            rawArray[2 * index + 1] = c.y;        }        return rawArray;    }    /**     * Save game state so that the user does not lose anything     * if the game process is killed while we are in the      * background.     *      * @return a Bundle with this view's state     */    public Bundle saveState() {        Bundle map = new Bundle();        map.putIntArray("mAppleList", coordArrayListToArray(mAppleList));        map.putInt("mDirection", Integer.valueOf(mDirection));        map.putInt("mNextDirection", Integer.valueOf(mNextDirection));        map.putLong("mMoveDelay", Long.valueOf(mMoveDelay));        map.putLong("mScore", Long.valueOf(mScore));        map.putIntArray("mSnakeTrail", coordArrayListToArray(mSnakeTrail));        return map;    }    /**     * Given a flattened array of ordinate pairs, we reconstitute them into a     * ArrayList of Coordinate objects     *      * @param rawArray : [x1,y1,x2,y2,...]     * @return a ArrayList of Coordinates     */    private ArrayList<Coordinate> coordArrayToArrayList(int[] rawArray) {        ArrayList<Coordinate> coordArrayList = new ArrayList<Coordinate>();        int coordCount = rawArray.length;        for (int index = 0; index < coordCount; index += 2) {            Coordinate c = new Coordinate(rawArray[index], rawArray[index + 1]);            coordArrayList.add(c);        }        return coordArrayList;    }    /**     * Restore game state if our process is being relaunched     *      * @param icicle a Bundle containing the game state     */    public void restoreState(Bundle icicle) {        setMode(PAUSE);        mAppleList = coordArrayToArrayList(icicle.getIntArray("mAppleList"));        mDirection = icicle.getInt("mDirection");        mNextDirection = icicle.getInt("mNextDirection");        mMoveDelay = icicle.getLong("mMoveDelay");        mScore = icicle.getLong("mScore");        mSnakeTrail = coordArrayToArrayList(icicle.getIntArray("mSnakeTrail"));    }    /*     * handles key events in the game. Update the direction our snake is traveling     * based on the DPAD. Ignore events that would cause the snake to immediately     * turn back on itself.     *      * (non-Javadoc)     *      * @see android.view.View#onKeyDown(int, android.os.KeyEvent)     */    @Override    public boolean onKeyDown(int keyCode, KeyEvent msg) {        if (keyCode == KeyEvent.KEYCODE_DPAD_UP) {            if (mMode == READY | mMode == LOSE) {                /*                 * At the beginning of the game, or the end of a previous one,                 * we should start a new game.                 */                initNewGame();                setMode(RUNNING);                update();                return (true);            }            if (mMode == PAUSE) {                /*                 * If the game is merely paused, we should just continue where                 * we left off.                 */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -