blob: 1ee1c4ac032d350ce3512234fb9c2b8c4ab5d343 [file] [log] [blame]
Winson Chung29d6fea2010-12-01 15:47:31 -08001/*
2 * Copyright (C) 2010 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
17package com.android.launcher2;
18
19import android.appwidget.AppWidgetProviderInfo;
20import android.content.Context;
21import android.content.pm.PackageManager;
22import android.content.pm.ResolveInfo;
Winson Chung59e1f9a2010-12-21 11:31:54 -080023import android.content.res.Resources;
Winson Chungc93e5ae2012-07-23 20:48:26 -070024import android.graphics.Rect;
Winson Chung29d6fea2010-12-01 15:47:31 -080025import android.util.AttributeSet;
26import android.view.MotionEvent;
Adam Cohened66b2b2012-01-23 17:28:51 -080027import android.view.View;
Winson Chung29d6fea2010-12-01 15:47:31 -080028import android.widget.ImageView;
29import android.widget.LinearLayout;
30import android.widget.TextView;
31
32import com.android.launcher.R;
Winson Chung29d6fea2010-12-01 15:47:31 -080033
34/**
35 * The linear layout used strictly for the widget/wallpaper tab of the customization tray
36 */
Michael Jurka82369a12012-01-12 08:08:38 -080037public class PagedViewWidget extends LinearLayout {
Winson Chung29d6fea2010-12-01 15:47:31 -080038 static final String TAG = "PagedViewWidgetLayout";
39
Michael Jurka141dbd02011-11-03 13:50:45 -070040 private static boolean sDeletePreviewsWhenDetachedFromWindow = true;
Winson Chunge4a647f2011-09-30 14:41:25 -070041
Winson Chung63257c12011-05-05 17:06:13 -070042 private String mDimensionsFormatString;
Adam Cohened66b2b2012-01-23 17:28:51 -080043 CheckForShortPress mPendingCheckForShortPress = null;
44 ShortPressListener mShortPressListener = null;
45 boolean mShortPressTriggered = false;
Adam Cohen0e56cc92012-05-11 15:57:05 -070046 static PagedViewWidget sShortpressTarget = null;
Michael Jurkadac85912012-05-18 15:04:49 -070047 boolean mIsAppWidget;
Winson Chungc93e5ae2012-07-23 20:48:26 -070048 private final Rect mOriginalImagePadding = new Rect();
Michael Jurka05713af2013-01-23 12:39:24 +010049 private Object mInfo;
Winson Chung04998342011-01-05 13:54:43 -080050
Winson Chung29d6fea2010-12-01 15:47:31 -080051 public PagedViewWidget(Context context) {
52 this(context, null);
53 }
54
55 public PagedViewWidget(Context context, AttributeSet attrs) {
56 this(context, attrs, 0);
57 }
58
59 public PagedViewWidget(Context context, AttributeSet attrs, int defStyle) {
60 super(context, attrs, defStyle);
61
Winson Chung59e1f9a2010-12-21 11:31:54 -080062 final Resources r = context.getResources();
Winson Chung63257c12011-05-05 17:06:13 -070063 mDimensionsFormatString = r.getString(R.string.widget_dims_format);
Winson Chung59e1f9a2010-12-21 11:31:54 -080064
Winson Chung29d6fea2010-12-01 15:47:31 -080065 setWillNotDraw(false);
66 setClipToPadding(false);
67 }
68
Winson Chungc93e5ae2012-07-23 20:48:26 -070069 @Override
70 protected void onFinishInflate() {
71 super.onFinishInflate();
72
73 final ImageView image = (ImageView) findViewById(R.id.widget_preview);
74 mOriginalImagePadding.left = image.getPaddingLeft();
75 mOriginalImagePadding.top = image.getPaddingTop();
76 mOriginalImagePadding.right = image.getPaddingRight();
77 mOriginalImagePadding.bottom = image.getPaddingBottom();
78 }
79
Michael Jurka141dbd02011-11-03 13:50:45 -070080 public static void setDeletePreviewsWhenDetachedFromWindow(boolean value) {
81 sDeletePreviewsWhenDetachedFromWindow = value;
82 }
83
Winson Chung09945932011-09-20 14:22:40 -070084 @Override
85 protected void onDetachedFromWindow() {
86 super.onDetachedFromWindow();
87
Michael Jurka141dbd02011-11-03 13:50:45 -070088 if (sDeletePreviewsWhenDetachedFromWindow) {
89 final ImageView image = (ImageView) findViewById(R.id.widget_preview);
90 if (image != null) {
91 FastBitmapDrawable preview = (FastBitmapDrawable) image.getDrawable();
Michael Jurka05713af2013-01-23 12:39:24 +010092 if (mInfo != null && preview != null && preview.getBitmap() != null) {
93 WidgetPreviewLoader.releaseBitmap(mInfo, preview.getBitmap());
Michael Jurka141dbd02011-11-03 13:50:45 -070094 }
95 image.setImageDrawable(null);
Winson Chungc93e5ae2012-07-23 20:48:26 -070096 }
Winson Chung09945932011-09-20 14:22:40 -070097 }
98 }
99
Winson Chung29d6fea2010-12-01 15:47:31 -0800100 public void applyFromAppWidgetProviderInfo(AppWidgetProviderInfo info,
Michael Jurka82369a12012-01-12 08:08:38 -0800101 int maxWidth, int[] cellSpan) {
Michael Jurkadac85912012-05-18 15:04:49 -0700102 mIsAppWidget = true;
Michael Jurka05713af2013-01-23 12:39:24 +0100103 mInfo = info;
Winson Chung29d6fea2010-12-01 15:47:31 -0800104 final ImageView image = (ImageView) findViewById(R.id.widget_preview);
Winson Chung4b576be2011-04-27 17:40:20 -0700105 if (maxWidth > -1) {
106 image.setMaxWidth(maxWidth);
107 }
Winson Chung6a0f57d2011-06-29 20:10:49 -0700108 image.setContentDescription(info.label);
Winson Chung29d6fea2010-12-01 15:47:31 -0800109 final TextView name = (TextView) findViewById(R.id.widget_name);
110 name.setText(info.label);
111 final TextView dims = (TextView) findViewById(R.id.widget_dims);
Winson Chung35d4a252011-08-11 15:12:11 -0700112 if (dims != null) {
Winson Chunge3e03bc2012-05-01 15:10:11 -0700113 int hSpan = Math.min(cellSpan[0], LauncherModel.getCellCountX());
114 int vSpan = Math.min(cellSpan[1], LauncherModel.getCellCountY());
115 dims.setText(String.format(mDimensionsFormatString, hSpan, vSpan));
Winson Chung35d4a252011-08-11 15:12:11 -0700116 }
Winson Chung29d6fea2010-12-01 15:47:31 -0800117 }
118
Michael Jurka82369a12012-01-12 08:08:38 -0800119 public void applyFromResolveInfo(PackageManager pm, ResolveInfo info) {
Michael Jurkadac85912012-05-18 15:04:49 -0700120 mIsAppWidget = false;
Michael Jurka05713af2013-01-23 12:39:24 +0100121 mInfo = info;
Winson Chung6a0f57d2011-06-29 20:10:49 -0700122 CharSequence label = info.loadLabel(pm);
Winson Chung1ed747a2011-05-03 16:18:34 -0700123 final ImageView image = (ImageView) findViewById(R.id.widget_preview);
Winson Chung6a0f57d2011-06-29 20:10:49 -0700124 image.setContentDescription(label);
Winson Chung1ed747a2011-05-03 16:18:34 -0700125 final TextView name = (TextView) findViewById(R.id.widget_name);
Winson Chung6a0f57d2011-06-29 20:10:49 -0700126 name.setText(label);
Winson Chung1ed747a2011-05-03 16:18:34 -0700127 final TextView dims = (TextView) findViewById(R.id.widget_dims);
Winson Chung46af2e82011-05-09 16:00:53 -0700128 if (dims != null) {
129 dims.setText(String.format(mDimensionsFormatString, 1, 1));
Winson Chung46af2e82011-05-09 16:00:53 -0700130 }
Winson Chung1ed747a2011-05-03 16:18:34 -0700131 }
132
Michael Jurka038f9d82011-11-03 13:50:45 -0700133 public int[] getPreviewSize() {
134 final ImageView i = (ImageView) findViewById(R.id.widget_preview);
135 int[] maxSize = new int[2];
Winson Chungc93e5ae2012-07-23 20:48:26 -0700136 maxSize[0] = i.getWidth() - mOriginalImagePadding.left - mOriginalImagePadding.right;
137 maxSize[1] = i.getHeight() - mOriginalImagePadding.top;
Michael Jurka038f9d82011-11-03 13:50:45 -0700138 return maxSize;
139 }
140
141 void applyPreview(FastBitmapDrawable preview, int index) {
Michael Jurka81efbad2011-11-03 13:50:45 -0700142 final PagedViewWidgetImageView image =
Michael Jurkadac85912012-05-18 15:04:49 -0700143 (PagedViewWidgetImageView) findViewById(R.id.widget_preview);
Winson Chunge4a647f2011-09-30 14:41:25 -0700144 if (preview != null) {
Michael Jurka81efbad2011-11-03 13:50:45 -0700145 image.mAllowRequestLayout = false;
Winson Chunge4a647f2011-09-30 14:41:25 -0700146 image.setImageDrawable(preview);
Michael Jurkadac85912012-05-18 15:04:49 -0700147 if (mIsAppWidget) {
148 // center horizontally
149 int[] imageSize = getPreviewSize();
150 int centerAmount = (imageSize[0] - preview.getIntrinsicWidth()) / 2;
Winson Chungc93e5ae2012-07-23 20:48:26 -0700151 image.setPadding(mOriginalImagePadding.left + centerAmount,
152 mOriginalImagePadding.top,
153 mOriginalImagePadding.right,
154 mOriginalImagePadding.bottom);
Michael Jurkadac85912012-05-18 15:04:49 -0700155 }
Winson Chung68e4c642011-11-10 15:48:25 -0800156 image.setAlpha(1f);
Michael Jurka81efbad2011-11-03 13:50:45 -0700157 image.mAllowRequestLayout = true;
Winson Chunge4a647f2011-09-30 14:41:25 -0700158 }
159 }
160
Adam Cohened66b2b2012-01-23 17:28:51 -0800161 void setShortPressListener(ShortPressListener listener) {
162 mShortPressListener = listener;
163 }
164
165 interface ShortPressListener {
166 void onShortPress(View v);
167 void cleanUpShortPress(View v);
168 }
169
170 class CheckForShortPress implements Runnable {
171 public void run() {
Adam Cohenc93ea442012-05-16 17:15:26 -0700172 if (sShortpressTarget != null) return;
Adam Cohened66b2b2012-01-23 17:28:51 -0800173 if (mShortPressListener != null) {
174 mShortPressListener.onShortPress(PagedViewWidget.this);
Adam Cohen263301a2012-05-17 12:24:40 -0700175 sShortpressTarget = PagedViewWidget.this;
Adam Cohened66b2b2012-01-23 17:28:51 -0800176 }
177 mShortPressTriggered = true;
178 }
179 }
180
181 private void checkForShortPress() {
Adam Cohen0e56cc92012-05-11 15:57:05 -0700182 if (sShortpressTarget != null) return;
Adam Cohened66b2b2012-01-23 17:28:51 -0800183 if (mPendingCheckForShortPress == null) {
184 mPendingCheckForShortPress = new CheckForShortPress();
185 }
186 postDelayed(mPendingCheckForShortPress, 120);
187 }
188
189 /**
190 * Remove the longpress detection timer.
191 */
192 private void removeShortPressCallback() {
193 if (mPendingCheckForShortPress != null) {
194 removeCallbacks(mPendingCheckForShortPress);
195 }
196 }
197
198 private void cleanUpShortPress() {
199 removeShortPressCallback();
200 if (mShortPressTriggered) {
201 if (mShortPressListener != null) {
202 mShortPressListener.cleanUpShortPress(PagedViewWidget.this);
203 }
204 mShortPressTriggered = false;
205 }
206 }
207
Adam Cohen0e56cc92012-05-11 15:57:05 -0700208 static void resetShortPressTarget() {
209 sShortpressTarget = null;
210 }
211
Winson Chung29d6fea2010-12-01 15:47:31 -0800212 @Override
213 public boolean onTouchEvent(MotionEvent event) {
Adam Cohened66b2b2012-01-23 17:28:51 -0800214 super.onTouchEvent(event);
215
216 switch (event.getAction()) {
217 case MotionEvent.ACTION_UP:
218 cleanUpShortPress();
219 break;
220 case MotionEvent.ACTION_DOWN:
221 checkForShortPress();
222 break;
223 case MotionEvent.ACTION_CANCEL:
224 cleanUpShortPress();
225 break;
226 case MotionEvent.ACTION_MOVE:
227 break;
228 }
Adam Cohen0e56cc92012-05-11 15:57:05 -0700229
Winson Chung29d6fea2010-12-01 15:47:31 -0800230 // We eat up the touch events here, since the PagedView (which uses the same swiping
231 // touch code as Workspace previously) uses onInterceptTouchEvent() to determine when
232 // the user is scrolling between pages. This means that if the pages themselves don't
233 // handle touch events, it gets forwarded up to PagedView itself, and it's own
234 // onTouchEvent() handling will prevent further intercept touch events from being called
235 // (it's the same view in that case). This is not ideal, but to prevent more changes,
236 // we just always mark the touch event as handled.
Adam Cohened66b2b2012-01-23 17:28:51 -0800237 return true;
Winson Chung29d6fea2010-12-01 15:47:31 -0800238 }
Winson Chung29d6fea2010-12-01 15:47:31 -0800239}