blob: 6f339e2a9a8078afd5c5564adc80585a8e784e62 [file] [log] [blame]
Owen Lina2fba682011-08-17 22:07:43 +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.gallery3d.ui;
18
Owen Lin73a04ff2012-03-14 17:27:24 +080019import android.content.Context;
20import android.view.MotionEvent;
21import android.view.View.MeasureSpec;
22
Owen Lina2fba682011-08-17 22:07:43 +080023import com.android.gallery3d.R;
24import com.android.gallery3d.anim.AlphaAnimation;
Owen Lina2fba682011-08-17 22:07:43 +080025import com.android.gallery3d.app.AlbumDataAdapter;
26import com.android.gallery3d.app.GalleryActivity;
Chih-Chung Chang70a73a72011-09-19 11:09:39 +080027import com.android.gallery3d.data.MediaItem;
Owen Lina2fba682011-08-17 22:07:43 +080028import com.android.gallery3d.data.MediaSet;
Chih-Chung Chang70a73a72011-09-19 11:09:39 +080029import com.android.gallery3d.data.Path;
Owen Lina2fba682011-08-17 22:07:43 +080030
Chih-Chung Chang980724b2012-02-22 08:00:31 +080031public class FilmStripView extends GLView implements UserInteractionListener {
Owen Lina2fba682011-08-17 22:07:43 +080032 @SuppressWarnings("unused")
33 private static final String TAG = "FilmStripView";
34
35 private static final int HIDE_ANIMATION_DURATION = 300; // 0.3 sec
36
37 public interface Listener {
Chih-Chung Chang36064d12011-09-14 12:07:17 +080038 // Returns false if it cannot jump to the specified index at this time.
39 boolean onSlotSelected(int slotIndex);
Owen Lina2fba682011-08-17 22:07:43 +080040 }
41
42 private int mTopMargin, mMidMargin, mBottomMargin;
43 private int mContentSize, mBarSize, mGripSize;
44 private AlbumView mAlbumView;
Owen Lin83a036c2012-03-22 14:14:40 +080045 private SlotView mSlotView;
Owen Lina2fba682011-08-17 22:07:43 +080046 private ScrollBarView mScrollBarView;
47 private AlbumDataAdapter mAlbumDataAdapter;
48 private StripDrawer mStripDrawer;
49 private Listener mListener;
50 private UserInteractionListener mUIListener;
Owen Lina2fba682011-08-17 22:07:43 +080051 private NinePatchTexture mBackgroundTexture;
52
53 // The layout of FileStripView is
54 // topMargin
55 // ----+----+
56 // / +----+--\
57 // contentSize | | thumbSize
58 // \ +----+--/
59 // ----+----+
60 // midMargin
61 // ----+----+
62 // / +----+--\
63 // barSize | | gripSize
64 // \ +----+--/
65 // ----+----+
66 // bottomMargin
67 public FilmStripView(GalleryActivity activity, MediaSet mediaSet,
68 int topMargin, int midMargin, int bottomMargin, int contentSize,
69 int thumbSize, int barSize, int gripSize, int gripWidth) {
70 mTopMargin = topMargin;
71 mMidMargin = midMargin;
72 mBottomMargin = bottomMargin;
73 mContentSize = contentSize;
74 mBarSize = barSize;
75 mGripSize = gripSize;
76
77 mStripDrawer = new StripDrawer((Context) activity);
Chih-Chung Chang07069de2011-09-14 20:50:28 +080078 SlotView.Spec spec = new SlotView.Spec();
79 spec.slotWidth = thumbSize;
80 spec.slotHeight = thumbSize;
Owen Lin83a036c2012-03-22 14:14:40 +080081 mSlotView = new SlotView((Context) activity, spec);
82 mAlbumView = new AlbumView(activity, mSlotView, thumbSize);
83 mSlotView.setSlotRenderer(mAlbumView);
84 mSlotView.setOverscrollEffect(SlotView.OVERSCROLL_NONE);
Owen Lina2fba682011-08-17 22:07:43 +080085 mAlbumView.setSelectionDrawer(mStripDrawer);
Owen Lin83a036c2012-03-22 14:14:40 +080086 mSlotView.setListener(new SlotView.SimpleListener() {
Chih-Chung Chang70a73a72011-09-19 11:09:39 +080087 @Override
88 public void onDown(int index) {
89 FilmStripView.this.onDown(index);
90 }
91 @Override
92 public void onUp() {
93 FilmStripView.this.onUp();
94 }
95 @Override
96 public void onSingleTapUp(int slotIndex) {
97 FilmStripView.this.onSingleTapUp(slotIndex);
98 }
99 @Override
100 public void onLongTap(int slotIndex) {
101 FilmStripView.this.onLongTap(slotIndex);
102 }
103 @Override
104 public void onScrollPositionChanged(int position, int total) {
105 FilmStripView.this.onScrollPositionChanged(position, total);
106 }
107 });
Owen Lin83a036c2012-03-22 14:14:40 +0800108 mSlotView.setUserInteractionListener(this);
Owen Lina2fba682011-08-17 22:07:43 +0800109 mAlbumDataAdapter = new AlbumDataAdapter(activity, mediaSet);
Owen Lin83a036c2012-03-22 14:14:40 +0800110 addComponent(mSlotView);
Owen Lina2fba682011-08-17 22:07:43 +0800111 mScrollBarView = new ScrollBarView(activity.getAndroidContext(),
112 mGripSize, gripWidth);
Owen Lina2fba682011-08-17 22:07:43 +0800113 addComponent(mScrollBarView);
114
115 mAlbumView.setModel(mAlbumDataAdapter);
116 mBackgroundTexture = new NinePatchTexture(activity.getAndroidContext(),
117 R.drawable.navstrip_translucent);
Owen Lina2fba682011-08-17 22:07:43 +0800118 }
119
120 public void setListener(Listener listener) {
121 mListener = listener;
122 }
123
124 public void setUserInteractionListener(UserInteractionListener listener) {
125 mUIListener = listener;
126 }
127
Owen Lina2fba682011-08-17 22:07:43 +0800128 public void show() {
Owen Linace280a2011-08-30 10:38:59 +0800129 if (getVisibility() == GLView.VISIBLE) return;
130 startAnimation(null);
131 setVisibility(GLView.VISIBLE);
Owen Lina2fba682011-08-17 22:07:43 +0800132 }
133
134 public void hide() {
Owen Linace280a2011-08-30 10:38:59 +0800135 if (getVisibility() == GLView.INVISIBLE) return;
136 AlphaAnimation animation = new AlphaAnimation(1, 0);
137 animation.setDuration(HIDE_ANIMATION_DURATION);
138 startAnimation(animation);
139 setVisibility(GLView.INVISIBLE);
Owen Lina2fba682011-08-17 22:07:43 +0800140 }
141
142 @Override
143 protected void onVisibilityChanged(int visibility) {
144 super.onVisibilityChanged(visibility);
145 if (visibility == GLView.VISIBLE) {
146 onUserInteraction();
147 }
148 }
149
150 @Override
151 protected void onMeasure(int widthSpec, int heightSpec) {
152 int height = mTopMargin + mContentSize + mMidMargin + mBarSize + mBottomMargin;
153 MeasureHelper.getInstance(this)
154 .setPreferredContentSize(MeasureSpec.getSize(widthSpec), height)
155 .measure(widthSpec, heightSpec);
156 }
157
158 @Override
159 protected void onLayout(
160 boolean changed, int left, int top, int right, int bottom) {
161 if (!changed) return;
Owen Lin83a036c2012-03-22 14:14:40 +0800162 mSlotView.layout(0, mTopMargin, right - left, mTopMargin + mContentSize);
Owen Lina2fba682011-08-17 22:07:43 +0800163 int barStart = mTopMargin + mContentSize + mMidMargin;
164 mScrollBarView.layout(0, barStart, right - left, barStart + mBarSize);
165 int width = right - left;
166 int height = bottom - top;
167 }
168
169 @Override
170 protected boolean onTouch(MotionEvent event) {
171 // consume all touch events on the "gray area", so they don't go to
172 // the photo view below. (otherwise you can scroll the picture through
173 // it).
174 return true;
175 }
176
177 @Override
178 protected boolean dispatchTouchEvent(MotionEvent event) {
Owen Lina2fba682011-08-17 22:07:43 +0800179 switch (event.getAction()) {
180 case MotionEvent.ACTION_DOWN:
181 case MotionEvent.ACTION_MOVE:
182 onUserInteractionBegin();
183 break;
184 case MotionEvent.ACTION_UP:
185 case MotionEvent.ACTION_CANCEL:
186 onUserInteractionEnd();
187 break;
188 }
189
190 return super.dispatchTouchEvent(event);
191 }
192
193 @Override
194 protected void render(GLCanvas canvas) {
Owen Lina2fba682011-08-17 22:07:43 +0800195 mBackgroundTexture.draw(canvas, 0, 0, getWidth(), getHeight());
196 super.render(canvas);
Owen Lina2fba682011-08-17 22:07:43 +0800197 }
198
Chih-Chung Chang70a73a72011-09-19 11:09:39 +0800199 private void onDown(int index) {
200 MediaItem item = mAlbumDataAdapter.get(index);
201 Path path = (item == null) ? null : item.getPath();
202 mStripDrawer.setPressedPath(path);
Owen Lin83a036c2012-03-22 14:14:40 +0800203 mSlotView.invalidate();
Chih-Chung Chang70a73a72011-09-19 11:09:39 +0800204 }
205
206 private void onUp() {
207 mStripDrawer.setPressedPath(null);
Owen Lin83a036c2012-03-22 14:14:40 +0800208 mSlotView.invalidate();
Chih-Chung Chang70a73a72011-09-19 11:09:39 +0800209 }
210
211 private void onSingleTapUp(int slotIndex) {
Chih-Chung Chang36064d12011-09-14 12:07:17 +0800212 if (mListener.onSlotSelected(slotIndex)) {
213 mAlbumView.setFocusIndex(slotIndex);
214 }
Owen Lina2fba682011-08-17 22:07:43 +0800215 }
216
Chih-Chung Chang70a73a72011-09-19 11:09:39 +0800217 private void onLongTap(int slotIndex) {
Owen Lina2fba682011-08-17 22:07:43 +0800218 onSingleTapUp(slotIndex);
219 }
220
Chih-Chung Chang70a73a72011-09-19 11:09:39 +0800221 private void onScrollPositionChanged(int position, int total) {
222 mScrollBarView.setContentPosition(position, total);
223 }
224
Owen Lina2fba682011-08-17 22:07:43 +0800225 // Called by AlbumView
Owen Linace280a2011-08-30 10:38:59 +0800226 @Override
Owen Lina2fba682011-08-17 22:07:43 +0800227 public void onUserInteractionBegin() {
228 mUIListener.onUserInteractionBegin();
229 }
230
231 // Called by AlbumView
Owen Linace280a2011-08-30 10:38:59 +0800232 @Override
Owen Lina2fba682011-08-17 22:07:43 +0800233 public void onUserInteractionEnd() {
234 mUIListener.onUserInteractionEnd();
235 }
236
237 // Called by AlbumView
Owen Linace280a2011-08-30 10:38:59 +0800238 @Override
Owen Lina2fba682011-08-17 22:07:43 +0800239 public void onUserInteraction() {
240 mUIListener.onUserInteraction();
241 }
242
Owen Lina2fba682011-08-17 22:07:43 +0800243 public void setFocusIndex(int slotIndex) {
244 mAlbumView.setFocusIndex(slotIndex);
Owen Lin83a036c2012-03-22 14:14:40 +0800245 mSlotView.makeSlotVisible(slotIndex);
Owen Lina2fba682011-08-17 22:07:43 +0800246 }
247
248 public void setStartIndex(int slotIndex) {
Owen Lin83a036c2012-03-22 14:14:40 +0800249 mSlotView.setStartIndex(slotIndex);
Owen Lina2fba682011-08-17 22:07:43 +0800250 }
251
252 public void pause() {
253 mAlbumView.pause();
254 mAlbumDataAdapter.pause();
255 }
256
257 public void resume() {
258 mAlbumView.resume();
259 mAlbumDataAdapter.resume();
260 }
261}