2 package com.android.gallery3d.filtershow.imageshow;
4 import android.content.Context;
5 import android.content.res.Resources;
6 import android.graphics.Bitmap;
7 import android.graphics.BitmapFactory;
8 import android.graphics.BitmapShader;
9 import android.graphics.Canvas;
10 import android.graphics.Color;
11 import android.graphics.Matrix;
12 import android.graphics.Paint;
13 import android.graphics.PorterDuff;
14 import android.graphics.PorterDuffColorFilter;
15 import android.graphics.RectF;
16 import android.graphics.Shader;
17 import android.graphics.drawable.Drawable;
18 import android.graphics.drawable.NinePatchDrawable;
19 import android.os.Handler;
20 import android.util.AttributeSet;
21 import android.view.MotionEvent;
23 import com.android.gallery3d.R;
24 import com.android.gallery3d.filtershow.editors.EditorDraw;
25 import com.android.gallery3d.filtershow.filters.FilterDrawRepresentation;
26 import com.android.gallery3d.filtershow.filters.ImageFilterDraw;
28 public class ImageDraw extends ImageShow {
30 private static final String LOGTAG = "ImageDraw";
31 private int mCurrentColor = Color.RED;
32 final static float INITAL_STROKE_RADIUS = 40;
33 private float mCurrentSize = INITAL_STROKE_RADIUS;
34 private byte mType = 0;
35 private FilterDrawRepresentation mFRep;
36 private EditorDraw mEditorDraw;
37 private long mTimeout;
38 private Paint mCheckerdPaint = makeCheckedPaint();
39 private Paint mShadowPaint = new Paint();
40 private Paint mIconPaint = new Paint();
41 private Paint mBorderPaint = new Paint();
42 private Handler mHandler;
43 private FilterDrawRepresentation.StrokeData mTmpStrokData =
44 new FilterDrawRepresentation.StrokeData();
45 private Bitmap mBitmap;
46 private float mDisplayRound;
47 private float mDisplayBorder;
48 private int DISPLAY_TIME = 500;
49 private Matrix mRotateToScreen = new Matrix();
50 private Matrix mToOrig;
51 private int mBorderColor;
52 private int mBorderShadowSize;
53 private NinePatchDrawable mShadow;
55 Runnable mUpdateRunnable = new Runnable() {
63 public ImageDraw(Context context, AttributeSet attrs) {
64 super(context, attrs);
66 setupConstants(context);
70 public ImageDraw(Context context) {
73 setupConstants(context);
77 private void setupConstants(Context context){
78 Resources res = context.getResources();
79 mDisplayRound = res.getDimensionPixelSize(R.dimen.draw_rect_round);
80 mDisplayBorder = res.getDimensionPixelSize(R.dimen.draw_rect_border);
81 mBorderShadowSize = res.getDimensionPixelSize(R.dimen.draw_rect_shadow);
82 float edge = res.getDimensionPixelSize(R.dimen.draw_rect_border_edge);
84 mBorderColor = res.getColor(R.color.draw_rect_border);
85 mBorderPaint.setColor(mBorderColor);
86 mBorderPaint.setStyle(Paint.Style.STROKE);
87 mBorderPaint.setStrokeWidth(edge);
88 mShadowPaint.setStyle(Paint.Style.FILL);
89 mShadowPaint.setColor(Color.BLACK);
90 mShadowPaint.setShadowLayer(mBorderShadowSize,mBorderShadowSize,
91 mBorderShadowSize,Color.BLACK);
92 mShadow = (NinePatchDrawable) res.getDrawable(R.drawable.geometry_shadow);
95 public void setEditor(EditorDraw editorDraw) {
96 mEditorDraw = editorDraw;
99 public void setFilterDrawRepresentation(FilterDrawRepresentation fr) {
102 new FilterDrawRepresentation.StrokeData();
105 public Drawable getIcon(Context context) {
111 public void resetParameter() {
117 public void setColor(int color) {
118 mCurrentColor = color;
121 public void setSize(int size) {
125 public void setStyle(byte style) {
126 mType = (byte) (style % ImageFilterDraw.NUMBER_OF_STYLES);
129 public int getStyle() {
133 public int getSize() {
134 return (int) mCurrentSize;
137 float[] mTmpPoint = new float[2]; // so we do not malloc
139 public boolean onTouchEvent(MotionEvent event) {
140 if (event.getPointerCount() > 1) {
141 boolean ret = super.onTouchEvent(event);
142 if (mFRep.getCurrentDrawing() != null) {
143 mFRep.clearCurrentSection();
144 mEditorDraw.commitLocalRepresentation();
148 if (event.getAction() != MotionEvent.ACTION_DOWN) {
149 if (mFRep.getCurrentDrawing() == null) {
150 return super.onTouchEvent(event);
154 if (event.getAction() == MotionEvent.ACTION_DOWN) {
156 mTmpPoint[0] = event.getX();
157 mTmpPoint[1] = event.getY();
158 mToOrig.mapPoints(mTmpPoint);
159 mFRep.startNewSection( mTmpPoint[0], mTmpPoint[1]);
162 if (event.getAction() == MotionEvent.ACTION_MOVE) {
164 int historySize = event.getHistorySize();
165 for (int h = 0; h < historySize; h++) {
168 mTmpPoint[0] = event.getHistoricalX(p, h);
169 mTmpPoint[1] = event.getHistoricalY(p, h);
170 mToOrig.mapPoints(mTmpPoint);
171 mFRep.addPoint(mTmpPoint[0], mTmpPoint[1]);
176 if (event.getAction() == MotionEvent.ACTION_UP) {
177 mTmpPoint[0] = event.getX();
178 mTmpPoint[1] = event.getY();
179 mToOrig.mapPoints(mTmpPoint);
180 mFRep.endSection(mTmpPoint[0], mTmpPoint[1]);
182 mEditorDraw.commitLocalRepresentation();
187 private void calcScreenMapping() {
188 mToOrig = getScreenToImageMatrix(true);
189 mToOrig.invert(mRotateToScreen);
192 private static Paint makeCheckedPaint(){
193 int[] colors = new int[16 * 16];
194 for (int i = 0; i < colors.length; i++) {
195 int y = i / (16 * 8);
197 colors[i] = (x == y) ? 0xFF777777 : 0xFF222222;
199 Bitmap bitmap = Bitmap.createBitmap(colors, 16, 16, Bitmap.Config.ARGB_8888);
200 BitmapShader bs = new BitmapShader(bitmap, Shader.TileMode.REPEAT, Shader.TileMode.REPEAT);
201 Paint p = new Paint();
206 private void setupTimer() {
207 mHandler = new Handler(getActivity().getMainLooper());
210 private void scheduleWakeup(int delay) {
211 mHandler.removeCallbacks(mUpdateRunnable);
212 mHandler.postDelayed(mUpdateRunnable, delay);
215 public Bitmap getBrush(int brushid) {
217 BitmapFactory.Options opt = new BitmapFactory.Options();
218 opt.inPreferredConfig = Bitmap.Config.ALPHA_8;
219 bitmap = BitmapFactory.decodeResource(getActivity().getResources(), brushid, opt);
220 bitmap = bitmap.extractAlpha();
225 public Bitmap createScaledBitmap(Bitmap src, int dstWidth, int dstHeight, boolean filter) {
226 Matrix m = new Matrix();
227 m.setScale(dstWidth / (float) src.getWidth(), dstHeight / (float) src.getHeight());
228 Bitmap result = Bitmap.createBitmap(dstWidth, dstHeight, src.getConfig());
229 Canvas canvas = new Canvas(result);
231 Paint paint = new Paint();
232 paint.setFilterBitmap(filter);
233 canvas.drawBitmap(src, m, paint);
239 public void displayDrawLook() {
243 int color = mTmpStrokData.mColor;
244 byte type = mTmpStrokData.mType;
245 float radius = mTmpStrokData.mRadius;
246 mFRep.fillStrokeParameters(mTmpStrokData);
247 if (type != mTmpStrokData.mType || radius != mTmpStrokData.mRadius) {
248 mBitmap = getBrush(mEditorDraw.getBrushIcon(mTmpStrokData.mType));
249 float size = mRotateToScreen.mapRadius(mTmpStrokData.mRadius) * 2;
250 mBitmap = createScaledBitmap(mBitmap, (int) size, (int) size, true);
253 if (color == mTmpStrokData.mColor
254 && type == mTmpStrokData.mType
255 && radius == mTmpStrokData.mRadius) {
259 mTimeout = DISPLAY_TIME + System.currentTimeMillis();
260 scheduleWakeup(DISPLAY_TIME);
263 public void drawLook(Canvas canvas) {
267 int cw = canvas.getWidth();
268 int ch = canvas.getHeight();
269 int centerx = cw / 2;
270 int centery = ch / 2;
272 mFRep.fillStrokeParameters(mTmpStrokData);
273 mIconPaint.setAntiAlias(true);
274 mIconPaint.setColor(mTmpStrokData.mColor);
276 mIconPaint.setColorFilter(new PorterDuffColorFilter(mTmpStrokData.mColor,
277 PorterDuff.Mode.MULTIPLY));
278 float rad = mRotateToScreen.mapRadius(mTmpStrokData.mRadius);
279 RectF rec = new RectF();
280 rec.set(centerx - mDisplayBorder - rad,
281 centery - mDisplayBorder - rad,
282 centerx + mDisplayBorder + rad,
283 centery + mDisplayBorder + rad);
284 mShadow.setBounds((int) (mBorderShadowSize + rec.left),
285 (int) (mBorderShadowSize + rec.top),
286 (int) (mBorderShadowSize + rec.right),
287 (int) (mBorderShadowSize + rec.bottom));
288 mShadow.draw(canvas);
289 canvas.drawRoundRect(rec, mDisplayRound, mDisplayRound, mCheckerdPaint);
290 canvas.drawRoundRect(rec, mDisplayRound, mDisplayRound, mBorderPaint);
291 canvas.drawBitmap(mBitmap,
292 centerx - mBitmap.getWidth() / 2,
293 centery - mBitmap.getHeight() / 2, mIconPaint);
297 public void onDraw(Canvas canvas) {
298 super.onDraw(canvas);
300 if (System.currentTimeMillis() < mTimeout) {