blob: 911a6ce9f2e5cc78201765f6e851236d698b178b [file] [log] [blame]
Joe Onorato00acb122009-08-04 16:04:30 -04001/*
2 * Copyright (C) 2008 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17
18package com.android.launcher2;
19
20import android.content.Context;
21import android.content.res.TypedArray;
22import android.graphics.Bitmap;
23import android.graphics.Canvas;
24import android.graphics.Matrix;
25import android.graphics.Paint;
26import android.graphics.PixelFormat;
27import android.graphics.Point;
28import android.os.IBinder;
29import android.util.AttributeSet;
30import android.util.Log;
31import android.view.Gravity;
32import android.view.View;
33import android.view.ViewGroup;
34import android.view.KeyEvent;
35import android.view.WindowManager;
36import android.view.WindowManagerImpl;
37
38public class DragView extends View implements TweenCallback {
39 // Number of pixels to add to the dragged item for scaling. Should be even for pixel alignment.
40 private static final int DRAG_SCALE = 24;
41
42 private Bitmap mBitmap;
43 private Paint mPaint;
44 private int mRegistrationX;
45 private int mRegistrationY;
46
47 SymmetricalLinearTween mTween;
48 private float mScale;
49 private float mAnimationScale = 1.0f;
50
51 private WindowManager.LayoutParams mLayoutParams;
52 private WindowManager mWindowManager;
53
54 /**
55 * Construct the drag view.
56 * <p>
57 * The registration point is the point inside our view that the touch events should
58 * be centered upon.
59 *
60 * @param context A context
61 * @param bitmap The view that we're dragging around. We scale it up when we draw it.
62 * @param registrationX The x coordinate of the registration point.
63 * @param registrationY The y coordinate of the registration point.
64 */
65 public DragView(Context context, Bitmap bitmap, int registrationX, int registrationY) {
66 super(context);
67
68 mWindowManager = WindowManagerImpl.getDefault();
69
70 mTween = new SymmetricalLinearTween(false, 110 /*ms duration*/, this);
71
72 int width = bitmap.getWidth();
73 int height = bitmap.getHeight();
74
75 Matrix scale = new Matrix();
76 float scaleFactor = width;
77 scaleFactor = mScale = (scaleFactor + DRAG_SCALE) / scaleFactor;
78 scale.setScale(scaleFactor, scaleFactor);
79
80 mBitmap = Bitmap.createBitmap(bitmap, 0, 0, width, height, scale, true);
81
82 // The point in our scaled bitmap that the touch events are located
83 mRegistrationX = registrationX + (DRAG_SCALE / 2);
84 mRegistrationY = registrationY + (DRAG_SCALE / 2);
85 }
86
87 @Override
88 protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
89 int widthSize = resolveSize(mBitmap.getWidth(), widthMeasureSpec);
90 int heightSize = resolveSize(mBitmap.getHeight(), heightMeasureSpec);
91 setMeasuredDimension(widthSize, heightSize);
92 }
93
94 @Override
95 protected void onDraw(Canvas canvas) {
96 if (false) {
97 // for debugging
98 Paint p = new Paint();
99 p.setStyle(Paint.Style.FILL);
100 p.setColor(0xaaffffff);
101 canvas.drawRect(0, 0, getWidth(), getHeight(), p);
102 }
103 float scale = mAnimationScale;
104 if (scale < 0.999f) { // allow for some float error
105 float width = mBitmap.getWidth();
106 float offset = (width-(width*scale))/2;
107 canvas.translate(offset, offset);
108 canvas.scale(scale, scale);
109 }
110 canvas.drawBitmap(mBitmap, 0.0f, 0.0f, mPaint);
111 }
112
113 @Override
114 protected void onDetachedFromWindow() {
115 super.onDetachedFromWindow();
116 mBitmap.recycle();
117 }
118
119 public void onTweenValueChanged(float value, float oldValue) {
120 mAnimationScale = (1.0f+((mScale-1.0f)*value))/mScale;
121 invalidate();
122 }
123
124 public void onTweenStarted() {
125 }
126
127 public void onTweenFinished() {
128 }
129
130 public void setPaint(Paint paint) {
131 mPaint = paint;
132 invalidate();
133 }
134
135 /**
136 * Create a window containing this view and show it.
137 *
138 * @param windowToken obtained from v.getWindowToken() from one of your views
139 * @param touchX the x coordinate the user touched in screen coordinates
140 * @param touchY the y coordinate the user touched in screen coordinates
141 */
142 public void show(IBinder windowToken, int touchX, int touchY) {
143 WindowManager.LayoutParams lp;
144 int pixelFormat;
145
146 pixelFormat = PixelFormat.TRANSLUCENT;
147
148 lp = new WindowManager.LayoutParams(
149 ViewGroup.LayoutParams.WRAP_CONTENT,
150 ViewGroup.LayoutParams.WRAP_CONTENT,
151 touchX-mRegistrationX, touchY-mRegistrationY,
152 WindowManager.LayoutParams.TYPE_APPLICATION_SUB_PANEL,
153 WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
154 | WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS
155 /*| WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM*/,
156 pixelFormat);
157// lp.token = mStatusBarView.getWindowToken();
158 lp.gravity = Gravity.LEFT | Gravity.TOP;
159 lp.token = windowToken;
160 lp.setTitle("DragView");
161 mLayoutParams = lp;
162
163 mWindowManager.addView(this, lp);
164
165 mAnimationScale = 1.0f/mScale;
166 mTween.start(true);
167 }
168
169 /**
170 * Move the window containing this view.
171 *
172 * @param touchX the x coordinate the user touched in screen coordinates
173 * @param touchY the y coordinate the user touched in screen coordinates
174 */
175 void move(int touchX, int touchY) {
176 WindowManager.LayoutParams lp = mLayoutParams;
177 lp.x = touchX - mRegistrationX;
178 lp.y = touchY - mRegistrationY;
179 mWindowManager.updateViewLayout(this, lp);
180 }
181
182 void remove() {
183 mWindowManager.removeView(this);
184 }
185}
186