1、画图程序代码/*002* Copyright (C) 2007 The Android Open Source Project003*004* Licensed under the Apache License, Version 2.0 (the “License“);005* you may not use this file except in compliance with the License.006* You may obtain a copy of the License at007*008* http:/www.apache.org/licenses/LICENSE-2.000
2、9*010* Unless required by applicable law or agreed to in writing, software011* distributed under the License is distributed on an “AS IS“ BASIS,012* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.013* See the License for the specific language governing permissions and014* li
3、mitations under the License.015*/016017package com.example.android.apis.graphics;018019import android.app.Activity;020import android.content.Context;021import android.graphics.Bitmap;022import android.graphics.Canvas;023import android.graphics.Paint;024import android.graphics.Rect;025import android.
4、os.Bundle;026import android.os.Handler;027import android.os.Message;028import android.view.Menu;029import android.view.MenuItem;030import android.view.MotionEvent;031import android.view.View;032033/Need the following import to get access to the app resources, since this034/class is in a sub-package.
5、035036037/*038* Demonstrates the handling of touch screen and trackball events to039* implement a simple painting app.040*/041public class TouchPaint extends GraphicsActivity 042/* Used as a pulse to gradually fade the contents of the window. */043private static final int FADE_MSG = 1;044045/* Menu
6、ID for the command to clear the window. */046private static final int CLEAR_ID = Menu.FIRST;047/* Menu ID for the command to toggle fading. */048private static final int FADE_ID = Menu.FIRST+1;049050/* How often to fade the contents of the window (in ms). */051private static final int FADE_DELAY = 1
7、00;052053/* The view responsible for drawing the window. */054MyView mView;055/* Is fading mode enabled? */056boolean mFading;057058Override protected void onCreate(Bundle savedInstanceState) 059super.onCreate(savedInstanceState);060061/ Create and attach the view that is responsible for painting.06
8、2mView = new MyView(this);063setContentView(mView);064mView.requestFocus();065066/ Restore the fading option if we are being thawed from a067/ previously saved state. Note that we are not currently remembering068/ the contents of the bitmap.069mFading = savedInstanceState != null ? savedInstanceStat
9、e.getBoolean(“fading“, true) : true;070071072Override public boolean onCreateOptionsMenu(Menu menu) 073menu.add(0, CLEAR_ID, 0, “Clear“);074menu.add(0, FADE_ID, 0, “Fade“).setCheckable(true);075return super.onCreateOptionsMenu(menu);076077078Override public boolean onPrepareOptionsMenu(Menu menu) 07
10、9menu.findItem(FADE_ID).setChecked(mFading);080return super.onPrepareOptionsMenu(menu);081082083Override public boolean onOptionsItemSelected(MenuItem item) 084switch (item.getItemId() 085case CLEAR_ID:086mView.clear();087return true;088case FADE_ID:089mFading = !mFading;090if (mFading) 091startFadi
11、ng();092 else 093stopFading();094095return true;096default:097return super.onOptionsItemSelected(item);098099100101Override protected void onResume() 102super.onResume();103/ If fading mode is enabled, then as long as we are resumed we want104/ to run pulse to fade the contents.105if (mFading) 106st
12、artFading();107108109110Override protected void onSaveInstanceState(Bundle outState) 111super.onSaveInstanceState(outState);112/ Save away the fading state to restore if needed later. Note that113/ we do not currently save the contents of the display.114outState.putBoolean(“fading“, mFading);1151161
13、17Override protected void onPause() 118super.onPause();119/ Make sure to never run the fading pulse while we are paused or120/ stopped.121stopFading();122123124/*125* Start up the pulse to fade the screen, clearing any existing pulse to126* ensure that we dont have multiple pulses running at a time.
14、127*/128void startFading() 129mHandler.removeMessages(FADE_MSG);130mHandler.sendMessageDelayed(131mHandler.obtainMessage(FADE_MSG), FADE_DELAY);132133134/*135* Stop the pulse to fade the screen.136*/137void stopFading() 138mHandler.removeMessages(FADE_MSG);139140141private Handler mHandler = new Han
15、dler() 142Override public void handleMessage(Message msg) 143switch (msg.what) 144/ Upon receiving the fade pulse, we have the view perform a145/ fade and then enqueue a new message to pulse at the desired146/ next time.147case FADE_MSG: 148mView.fade();149mHandler.sendMessageDelayed(150mHandler.obt
16、ainMessage(FADE_MSG), FADE_DELAY);151break;152153default:154super.handleMessage(msg);155156157;158159public class MyView extends View 160private static final int FADE_ALPHA = 0x06;161private static final int MAX_FADE_STEPS = 256/FADE_ALPHA + 4;162private Bitmap mBitmap;163private Canvas mCanvas;164p
17、rivate final Rect mRect = new Rect();165private final Paint mPaint;166private final Paint mFadePaint;167private boolean mCurDown;168private int mCurX;169private int mCurY;170private float mCurPressure;171private float mCurSize;172private int mCurWidth;173private int mFadeSteps = MAX_FADE_STEPS;17417
18、5public MyView(Context c) 176super(c);177mPaint = new Paint();178mPaint.setAntiAlias(true);179mPaint.setARGB(255, 255, 255, 255);180mFadePaint = new Paint();181mFadePaint.setDither(true);182mFadePaint.setARGB(FADE_ALPHA, 0, 0, 0);183184185public void clear() 186if (mCanvas != null) 187mPaint.setARGB
19、(0xff, 0, 0, 0);188mCanvas.drawPaint(mPaint);189invalidate();190mFadeSteps = MAX_FADE_STEPS;191192193194public void fade() 195if (mCanvas != null 208209210if (curW w) curW = w;211if (curH h) curH = h;212213Bitmap newBitmap = Bitmap.createBitmap(curW, curH,214Bitmap.Config.RGB_565);215Canvas newCanva
20、s = new Canvas();216newCanvas.setBitmap(newBitmap);217if (mBitmap != null) 218newCanvas.drawBitmap(mBitmap, 0, 0, null);219220mBitmap = newBitmap;221mCanvas = newCanvas;222mFadeSteps = MAX_FADE_STEPS;223224225Override protected void onDraw(Canvas canvas) 226if (mBitmap != null) 227canvas.drawBitmap(
21、mBitmap, 0, 0, null);228229230231Override public boolean onTrackballEvent(MotionEvent event) 232boolean oldDown = mCurDown;233mCurDown = true;234int N = event.getHistorySize();235int baseX = mCurX;236int baseY = mCurY;237final float scaleX = event.getXPrecision();238final float scaleY = event.getYPr
22、ecision();239for (int i=0; iN; i+) 240/Log.i(“TouchPaint“, “Intermediate trackball #“ + i241/ + “: x=“ + event.getHistoricalX(i)242/ + “, y=“ + event.getHistoricalY(i);243drawPoint(baseX+event.getHistoricalX(i)*scaleX,244baseY+event.getHistoricalY(i)*scaleY,245event.getHistoricalPressure(i),246event
23、.getHistoricalSize(i);247248/Log.i(“TouchPaint“, “Trackball: x=“ + event.getX()249/ + “, y=“ + event.getY();250drawPoint(baseX+event.getX()*scaleX, baseY+event.getY()*scaleY,251event.getPressure(), event.getSize();252mCurDown = oldDown;253return true;254255256Override public boolean onTouchEvent(Mot
24、ionEvent event) 257int action = event.getAction();258mCurDown = action = MotionEvent.ACTION_DOWN259| action = MotionEvent.ACTION_MOVE;260int N = event.getHistorySize();261for (int i=0; iN; i+) 262/Log.i(“TouchPaint“, “Intermediate pointer #“ + i);263drawPoint(event.getHistoricalX(i), event.getHistor
25、icalY(i),264event.getHistoricalPressure(i),265event.getHistoricalSize(i);266267drawPoint(event.getX(), event.getY(), event.getPressure(),268event.getSize();269return true;270271272private void drawPoint(float x, float y, float pressure, float size) 273/Log.i(“TouchPaint“, “Drawing: “ + x + “x“ + y +
26、 “ p=“274/ + pressure + “ s=“ + size);275mCurX = (int)x;276mCurY = (int)y;277mCurPressure = pressure;278mCurSize = size;279mCurWidth = (int)(mCurSize*(getWidth()/3);280if (mCurWidth 1) mCurWidth = 1;281if (mCurDown 283mPaint.setARGB(pressureLevel, 255, 255, 255);284mCanvas.drawCircle(mCurX, mCurY, mCurWidth, mPaint);285mRect.set(mCurX-mCurWidth-2, mCurY-mCurWidth-2,286mCurX+mCurWidth+2, mCurY+mCurWidth+2);287invalidate(mRect);288289mFadeSteps = 0;290291292