OSDN Git Service

Fix hardcoded date/time formats in 3D Gallery.
[android-x86/packages-apps-Gallery2.git] / src / com / cooliris / media / HudLayer.java
1 package com.cooliris.media;
2
3 import java.util.ArrayList;
4 import java.util.List;
5
6 import javax.microedition.khronos.opengles.GL11;
7
8 import android.app.AlertDialog;
9 import android.content.ComponentName;
10 import android.content.Context;
11 import android.content.Intent;
12 import android.content.pm.ActivityInfo;
13 import android.content.pm.PackageManager;
14 import android.content.pm.ResolveInfo;
15 import android.content.res.Resources;
16 import android.net.Uri;
17 import android.util.FloatMath;
18 import android.util.Log;
19 import android.view.MotionEvent;
20
21 import com.cooliris.media.MenuBar.Menu;
22 import com.cooliris.media.PopupMenu.Option;
23
24 public final class HudLayer extends Layer {
25     public static final int MODE_NORMAL = 0;
26     public static final int MODE_SELECT = 1;
27
28     private Context mContext;
29     private GridLayer mGridLayer;
30     private final ImageButton mTopRightButton = new ImageButton();
31     private final ImageButton mZoomInButton = new ImageButton();
32     private final ImageButton mZoomOutButton = new ImageButton();
33     private static PathBarLayer sPathBar;
34     private static TimeBar sTimeBar;
35     private MenuBar.Menu[] mNormalBottomMenu = null;
36     private MenuBar.Menu[] mSingleViewIntentBottomMenu = null;
37     private final MenuBar mSelectionMenuBottom;
38     private final MenuBar mSelectionMenuTop;
39     private final MenuBar mFullscreenMenu;
40     private final LoadingLayer mLoadingLayer = new LoadingLayer();
41     private RenderView mView = null;
42
43     private int mMode = MODE_NORMAL;
44
45     // Camera button - launches the camera intent when pressed.
46     private static final int CAMERA_BUTTON_ICON = R.drawable.btn_camera;
47     private static final int CAMERA_BUTTON_ICON_PRESSED = R.drawable.btn_camera_pressed;
48     private static final int ZOOM_IN_ICON = R.drawable.btn_hud_zoom_in_normal;
49     private static final int ZOOM_IN_ICON_PRESSED = R.drawable.btn_hud_zoom_in_pressed;
50     private static final int ZOOM_OUT_ICON = R.drawable.btn_hud_zoom_out_normal;
51     private static final int ZOOM_OUT_ICON_PRESSED = R.drawable.btn_hud_zoom_out_pressed;
52
53     private final Runnable mCameraButtonAction = new Runnable() {
54         public void run() {
55             // Launch the camera intent.
56             Intent intent = new Intent();
57             intent.setClassName("com.android.camera", "com.android.camera.Camera");
58             intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
59             mContext.startActivity(intent);
60         }
61     };
62
63     // Grid mode button - switches the media browser to grid mode.
64     private static final int GRID_MODE_ICON = R.drawable.mode_stack;
65     private static final int GRID_MODE_PRESSED_ICON = R.drawable.mode_stack;
66
67     private final Runnable mZoomInButtonAction = new Runnable() {
68         public void run() {
69             mGridLayer.zoomInToSelectedItem();
70             mGridLayer.markDirty(1);
71         }
72     };
73
74     private final Runnable mZoomOutButtonAction = new Runnable() {
75         public void run() {
76             mGridLayer.zoomOutFromSelectedItem();
77             mGridLayer.markDirty(1);
78         }
79     };
80
81     private final Runnable mGridModeButtonAction = new Runnable() {
82         public void run() {
83             mGridLayer.setState(GridLayer.STATE_GRID_VIEW);
84         }
85     };
86
87     /**
88      * Stack mode button - switches the media browser to grid mode.
89      */
90     private static final int STACK_MODE_ICON = R.drawable.mode_grid;
91     private static final int STACK_MODE_PRESSED_ICON = R.drawable.mode_grid;
92     private final Runnable mStackModeButtonAction = new Runnable() {
93         public void run() {
94             mGridLayer.setState(GridLayer.STATE_TIMELINE);
95         }
96     };
97     private float mAlpha;
98     private float mAnimAlpha;
99     private boolean mAutoHide;
100     private float mTimeElapsedSinceFullOpacity;
101     private String mCachedCaption;
102     private String mCachedPosition;
103     private String mCachedCurrentLabel;
104
105     HudLayer(Context context) {
106         mAlpha = 1.0f;
107         if (sTimeBar == null) {
108             sTimeBar = new TimeBar(context);
109             sPathBar = new PathBarLayer();
110         }
111         mTopRightButton.setSize((int) (100 * Gallery.PIXEL_DENSITY), (int) (94 * Gallery.PIXEL_DENSITY));
112
113         mZoomInButton.setSize(43 * Gallery.PIXEL_DENSITY, 43 * Gallery.PIXEL_DENSITY);
114         mZoomOutButton.setSize(43 * Gallery.PIXEL_DENSITY, 43 * Gallery.PIXEL_DENSITY);
115         mZoomInButton.setImages(ZOOM_IN_ICON, ZOOM_IN_ICON_PRESSED);
116         mZoomInButton.setAction(mZoomInButtonAction);
117         mZoomOutButton.setImages(ZOOM_OUT_ICON, ZOOM_OUT_ICON_PRESSED);
118         mZoomOutButton.setAction(mZoomOutButtonAction);
119
120         // The Share submenu is populated dynamically when opened.
121         Resources resources = context.getResources();
122         PopupMenu.Option[] deleteOptions = {
123                 new PopupMenu.Option(context.getResources().getString(R.string.confirm_delete), resources
124                         .getDrawable(R.drawable.icon_delete), new Runnable() {
125                     public void run() {
126                         deleteSelection();
127                     }
128                 }),
129                 new PopupMenu.Option(context.getResources().getString(R.string.cancel), resources
130                         .getDrawable(R.drawable.icon_cancel), new Runnable() {
131                     public void run() {
132
133                     }
134                 }), };
135         mSelectionMenuBottom = new MenuBar(context);
136
137         MenuBar.Menu shareMenu = new MenuBar.Menu.Builder(context.getResources().getString(R.string.share)).icon(
138                 R.drawable.icon_share).onSelect(new Runnable() {
139             public void run() {
140                 updateShareMenu();
141             }
142         }).build();
143
144         MenuBar.Menu deleteMenu = new MenuBar.Menu.Builder(context.getResources().getString(R.string.delete)).icon(
145                 R.drawable.icon_delete).options(deleteOptions).build();
146
147         MenuBar.Menu moreMenu = new MenuBar.Menu.Builder(context.getResources().getString(R.string.more)).icon(
148                 R.drawable.icon_more).onSelect(new Runnable() {
149             public void run() {
150                 buildMoreOptions();
151             }
152         }).build();
153
154         mNormalBottomMenu = new MenuBar.Menu[] { shareMenu, deleteMenu, moreMenu };
155         mSingleViewIntentBottomMenu = new MenuBar.Menu[] { shareMenu, moreMenu };
156
157         mSelectionMenuBottom.setMenus(mNormalBottomMenu);
158         mSelectionMenuTop = new MenuBar(context);
159         mSelectionMenuTop.setMenus(new MenuBar.Menu[] {
160                 new MenuBar.Menu.Builder(context.getResources().getString(R.string.select_all)).onSelect(new Runnable() {
161                     public void run() {
162                         mGridLayer.selectAll();
163                     }
164                 }).build(), new MenuBar.Menu.Builder("").build(),
165                 new MenuBar.Menu.Builder(context.getResources().getString(R.string.deselect_all)).onSelect(new Runnable() {
166                     public void run() {
167                         mGridLayer.deselectOrCancelSelectMode();
168                     }
169                 }).build() });
170         mFullscreenMenu = new MenuBar(context);
171         mFullscreenMenu.setMenus(new MenuBar.Menu[] {
172                 new MenuBar.Menu.Builder(context.getResources().getString(R.string.slideshow)).icon(R.drawable.icon_play)
173                         .onSingleTapUp(new Runnable() {
174                             public void run() {
175                                 if (getAlpha() == 1.0f)
176                                     mGridLayer.startSlideshow();
177                                 else
178                                     setAlpha(1.0f);
179                             }
180                         }).build(), /* new MenuBar.Menu.Builder("").build(), */
181                 new MenuBar.Menu.Builder(context.getResources().getString(R.string.menu)).icon(R.drawable.icon_more)
182                         .onSingleTapUp(new Runnable() {
183                             public void run() {
184                                 if (getAlpha() == 1.0f)
185                                     mGridLayer.enterSelectionMode();
186                                 else
187                                     setAlpha(1.0f);
188                             }
189                         }).build() });
190     }
191     
192     public void setContext(Context context) {
193         if (mContext != context) {
194             mContext = context;
195             sTimeBar.regenerateStringsForContext(context);
196         }
197     }
198
199     private void buildMoreOptions() {
200         ArrayList<MediaBucket> buckets = mGridLayer.getSelectedBuckets();
201
202         int numBuckets = buckets.size();
203         boolean albumMode = false;
204         boolean singleItem = false;
205         boolean isPicasa = false;
206         int mediaType = MediaItem.MEDIA_TYPE_IMAGE;
207         if (numBuckets > 1) {
208             albumMode = true;
209         }
210         if (numBuckets == 1) {
211             MediaBucket bucket = buckets.get(0);
212             MediaSet mediaSet = bucket.mediaSet;
213             if (mediaSet == null) {
214                 return;
215             }
216             isPicasa = mediaSet.mPicasaAlbumId != Shared.INVALID;
217             if (bucket.mediaItems == null || bucket.mediaItems.size() == 0) {
218                 albumMode = true;
219             } else {
220                 ArrayList<MediaItem> items = bucket.mediaItems;
221                 int numItems = items.size();
222                 mediaType = items.get(0).getMediaType();
223                 if (numItems == 1) {
224                     singleItem = true;
225                 } else {
226                     for (int i = 1; i < numItems; ++i) {
227                         if (items.get(0).getMediaType() != mediaType) {
228                             albumMode = true;
229                             break;
230                         }
231                     }
232                 }
233             }
234         }
235
236         Option[] optionAll = new Option[] { new PopupMenu.Option(mContext.getResources().getString(R.string.details), mContext
237                 .getResources().getDrawable(R.drawable.ic_menu_view_details), new Runnable() {
238             public void run() {
239                 ArrayList<MediaBucket> buckets = mGridLayer.getSelectedBuckets();
240                 final AlertDialog.Builder builder = new AlertDialog.Builder((Gallery) mContext);
241                 builder.setTitle(mContext.getResources().getString(R.string.details));
242                 boolean foundDataToDisplay = true;
243
244                 if (buckets == null) {
245                     foundDataToDisplay = false;
246                 } else {
247                     CharSequence[] strings = DetailMode.populateDetailModeStrings(mContext, buckets);
248                     if (strings == null) {
249                         foundDataToDisplay = false;
250                     } else {
251                         builder.setItems(strings, null);
252                     }
253                 }
254
255                 mGridLayer.deselectAll();
256                 if (foundDataToDisplay) {
257                     builder.setNeutralButton(R.string.details_ok, null);
258                     ((Gallery) mContext).getHandler().post(new Runnable() {
259                         public void run() {
260                             builder.show();
261                         }
262                     });
263                 }
264             }
265         }) };
266
267         Option[] optionSingle = new Option[] { new PopupMenu.Option(mContext.getResources().getString(R.string.show_on_map),
268                 mContext.getResources().getDrawable(R.drawable.ic_menu_mapmode), new Runnable() {
269                     public void run() {
270                         ArrayList<MediaBucket> buckets = mGridLayer.getSelectedBuckets();
271                         MediaItem item = MediaBucketList.getFirstItemSelection(buckets);
272                         if (item == null) {
273                             return;
274                         }
275                         mGridLayer.deselectAll();
276                         Util.openMaps(mContext, item.mLatitude, item.mLongitude);
277                     }
278                 }), };
279
280         Option[] optionImageMultiple = new Option[] {
281                 new PopupMenu.Option(mContext.getResources().getString(R.string.rotate_left), mContext.getResources().getDrawable(
282                         R.drawable.ic_menu_rotate_left), new Runnable() {
283                     public void run() {
284                         mGridLayer.rotateSelectedItems(-90.0f);
285                     }
286                 }),
287                 new PopupMenu.Option(mContext.getResources().getString(R.string.rotate_right), mContext.getResources().getDrawable(
288                         R.drawable.ic_menu_rotate_right), new Runnable() {
289                     public void run() {
290                         mGridLayer.rotateSelectedItems(90.0f);
291                     }
292                 }), };
293
294         if (isPicasa) {
295             optionImageMultiple = new Option[] {};
296         }
297         Option[] optionImageSingle;
298         if (isPicasa) {
299             optionImageSingle = new Option[] { new PopupMenu.Option(mContext.getResources().getString(R.string.set_as_wallpaper),
300                     mContext.getResources().getDrawable(R.drawable.ic_menu_set_as), new Runnable() {
301                         public void run() {
302                             ArrayList<MediaBucket> buckets = mGridLayer.getSelectedBuckets();
303                             MediaItem item = MediaBucketList.getFirstItemSelection(buckets);
304                             if (item == null) {
305                                 return;
306                             }
307                             mGridLayer.deselectAll();
308                             if (item.mParentMediaSet.mPicasaAlbumId != Shared.INVALID) {
309                                 final Intent intent = new Intent("android.intent.action.ATTACH_DATA");
310                                 intent.setClassName("com.cooliris.media", "com.cooliris.media.Photographs");
311                                 intent.setData(Uri.parse(item.mContentUri));
312                                 intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
313                                 ((Gallery) mContext).startActivityForResult(intent, 0);
314                             }
315                         }
316                     }) };
317         } else {
318             optionImageSingle = new Option[] {
319                     new PopupMenu.Option((isPicasa) ? mContext.getResources().getString(R.string.set_as_wallpaper) : mContext
320                             .getResources().getString(R.string.set_as), mContext.getResources().getDrawable(
321                             R.drawable.ic_menu_set_as), new Runnable() {
322                         public void run() {
323                             ArrayList<MediaBucket> buckets = mGridLayer.getSelectedBuckets();
324                             MediaItem item = MediaBucketList.getFirstItemSelection(buckets);
325                             if (item == null) {
326                                 return;
327                             }
328                             mGridLayer.deselectAll();
329                             if (item.mParentMediaSet.mPicasaAlbumId != Shared.INVALID) {
330                                 final Intent intent = new Intent("android.intent.action.ATTACH_DATA");
331                                 intent.setClassName("com.cooliris.media", "com.cooliris.media.Photographs");
332                                 intent.setData(Uri.parse(item.mContentUri));
333                                 intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
334                                 ((Gallery) mContext).startActivityForResult(intent, 0);
335                             } else {
336                                 Intent intent = Util.createSetAsIntent(Uri.parse(item.mContentUri), item.mMimeType);
337                                 intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
338                                 ((Gallery) mContext).startActivity(Intent.createChooser(intent, ((Gallery) mContext)
339                                         .getText(R.string.set_image)));
340                             }
341                         }
342                     }),
343                     new PopupMenu.Option(mContext.getResources().getString(R.string.crop), mContext.getResources().getDrawable(
344                             R.drawable.ic_menu_crop), new Runnable() {
345                         public void run() {
346                             ArrayList<MediaBucket> buckets = mGridLayer.getSelectedBuckets();
347                             MediaItem item = MediaBucketList.getFirstItemSelection(buckets);
348                             if (item == null) {
349                                 return;
350                             }
351                             mGridLayer.deselectAll();
352                             final Intent intent = new Intent("com.android.camera.action.CROP");
353                             intent.setClassName("com.cooliris.media", "com.cooliris.media.CropImage");
354                             intent.setData(Uri.parse(item.mContentUri));
355                             ((Gallery) mContext).startActivityForResult(intent, Gallery.CROP_MSG_INTERNAL);
356                         }
357                     }) };
358         }
359         Option[] options = optionAll;
360         if (!albumMode) {
361             if (!singleItem) {
362                 if (mediaType == MediaItem.MEDIA_TYPE_IMAGE)
363                     options = concat(options, optionImageMultiple);
364             } else {
365                 MediaItem item = MediaBucketList.getFirstItemSelection(buckets);
366                 if (item.mLatitude != 0.0f && item.mLongitude != 0.0f) {
367                     options = concat(options, optionSingle);
368                 }
369                 if (mediaType == MediaItem.MEDIA_TYPE_IMAGE) {
370                     options = concat(options, optionImageSingle);
371                     options = concat(options, optionImageMultiple);
372                 }
373             }
374         }
375
376         // We are assuming that the more menu is the last item in the menu array.
377         int lastIndex = mSelectionMenuBottom.getMenus().length - 1;
378         mSelectionMenuBottom.getMenus()[lastIndex].options = options;
379     }
380
381     private static final Option[] concat(Option[] A, Option[] B) {
382         Option[] C = (Option[]) new Option[A.length + B.length];
383         System.arraycopy(A, 0, C, 0, A.length);
384         System.arraycopy(B, 0, C, A.length, B.length);
385         return C;
386     }
387
388     public void updateNumItemsSelected(int numItems) {
389         String items = " " + ((numItems == 1) ? mContext.getString(R.string.item) : mContext.getString(R.string.items));
390         Menu menu = new MenuBar.Menu.Builder(numItems + items).config(MenuBar.MENU_TITLE_STYLE_TEXT).build();
391         mSelectionMenuTop.updateMenu(menu, 1);
392     }
393
394     protected void deleteSelection() {
395         mGridLayer.deleteSelection();
396     }
397
398     void setGridLayer(GridLayer layer) {
399         mGridLayer = layer;
400     }
401
402     int getMode() {
403         return mMode;
404     }
405
406     void setMode(int mode) {
407         if (mMode != mode) {
408             mMode = mode;
409             updateViews();
410         }
411     }
412
413     @Override
414     protected void onSizeChanged() {
415         final float width = mWidth;
416         final float height = mHeight;
417         closeSelectionMenu();
418
419         sTimeBar.setPosition(0f, height - TimeBar.HEIGHT * Gallery.PIXEL_DENSITY);
420         sTimeBar.setSize(width, TimeBar.HEIGHT * Gallery.PIXEL_DENSITY);
421         mSelectionMenuTop.setPosition(0f, 0);
422         mSelectionMenuTop.setSize(width, MenuBar.HEIGHT * Gallery.PIXEL_DENSITY);
423         mSelectionMenuBottom.setPosition(0f, height - MenuBar.HEIGHT * Gallery.PIXEL_DENSITY);
424         mSelectionMenuBottom.setSize(width, MenuBar.HEIGHT * Gallery.PIXEL_DENSITY);
425
426         mFullscreenMenu.setPosition(0f, height - MenuBar.HEIGHT * Gallery.PIXEL_DENSITY);
427         mFullscreenMenu.setSize(width, MenuBar.HEIGHT * Gallery.PIXEL_DENSITY);
428
429         sPathBar.setPosition(0f, -4f * Gallery.PIXEL_DENSITY);
430         computeSizeForPathbar();
431
432         mTopRightButton.setPosition(width - mTopRightButton.getWidth(), 0f);
433         mZoomInButton.setPosition(width - mZoomInButton.getWidth(), 0f);
434         mZoomOutButton.setPosition(width - mZoomInButton.getWidth(), mZoomInButton.getHeight());
435     }
436
437     private void computeSizeForPathbar() {
438         float pathBarWidth = mWidth
439                 - ((mGridLayer.getState() == GridLayer.STATE_FULL_SCREEN) ? 32 * Gallery.PIXEL_DENSITY
440                         : 120 * Gallery.PIXEL_DENSITY);
441         sPathBar.setSize(pathBarWidth, FloatMath.ceil(39 * Gallery.PIXEL_DENSITY));
442         sPathBar.recomputeComponents();
443     }
444
445     public void setFeed(MediaFeed feed, int state, boolean needsLayout) {
446         sTimeBar.setFeed(feed, state, needsLayout);
447     }
448
449     public void onGridStateChanged() {
450         updateViews();
451     }
452
453     private void updateViews() {
454         if (mGridLayer == null)
455             return;
456         final int state = mGridLayer.getState();
457         // Show the selection menu in selection mode.
458         final boolean selectionMode = mMode == MODE_SELECT;
459         final boolean fullscreenMode = state == GridLayer.STATE_FULL_SCREEN;
460         final boolean stackMode = state == GridLayer.STATE_MEDIA_SETS || state == GridLayer.STATE_TIMELINE;
461         mSelectionMenuTop.setHidden(!selectionMode || fullscreenMode);
462         mSelectionMenuBottom.setHidden(!selectionMode);
463         mFullscreenMenu.setHidden(!fullscreenMode || selectionMode);
464         mZoomInButton.setHidden(mFullscreenMenu.isHidden());
465         mZoomOutButton.setHidden(mFullscreenMenu.isHidden());
466
467         // Show the time bar in stack and grid states, except in selection mode.
468         sTimeBar.setHidden(fullscreenMode || selectionMode || stackMode);
469         // mTimeBar.setHidden(selectionMode || (state != GridLayer.STATE_TIMELINE && state != GridLayer.STATE_GRID_VIEW));
470
471         // Hide the path bar and top-right button in selection mode.
472         sPathBar.setHidden(selectionMode);
473         mTopRightButton.setHidden(selectionMode || fullscreenMode);
474         computeSizeForPathbar();
475
476         // Configure the top-right button.
477         int image = 0;
478         int pressedImage = 0;
479         Runnable action = null;
480         final ImageButton topRightButton = mTopRightButton;
481         int height = (int) (94 * Gallery.PIXEL_DENSITY);
482         switch (state) {
483         case GridLayer.STATE_MEDIA_SETS:
484             image = CAMERA_BUTTON_ICON;
485             pressedImage = CAMERA_BUTTON_ICON_PRESSED;
486             action = mCameraButtonAction;
487             break;
488         case GridLayer.STATE_GRID_VIEW:
489             height /= 2;
490             image = STACK_MODE_ICON;
491             pressedImage = STACK_MODE_PRESSED_ICON;
492             action = mStackModeButtonAction;
493             break;
494         case GridLayer.STATE_TIMELINE:
495             image = GRID_MODE_ICON;
496             pressedImage = GRID_MODE_PRESSED_ICON;
497             action = mGridModeButtonAction;
498             break;
499         default:
500             break;
501         }
502         topRightButton.setSize((int) (100 * Gallery.PIXEL_DENSITY), height);
503         topRightButton.setImages(image, pressedImage);
504         topRightButton.setAction(action);
505     }
506
507     public TimeBar getTimeBar() {
508         return sTimeBar;
509     }
510
511     public PathBarLayer getPathBar() {
512         return sPathBar;
513     }
514
515     public GridLayer getGridLayer() {
516         return mGridLayer;
517     }
518
519     @Override
520     public boolean update(RenderView view, float frameInterval) {
521         float factor = 1.0f;
522         if (mAlpha == 1.0f) {
523             // Speed up the animation when it becomes visible.
524             factor = 4.0f;
525         }
526         mAnimAlpha = FloatUtils.animate(mAnimAlpha, mAlpha, frameInterval * factor);
527         boolean timeElapsedSinceFullOpacity_Reset = mTimeElapsedSinceFullOpacity == 0.0f;
528
529         if (mAutoHide) {
530             if (mAlpha == 1.0f && mMode != MODE_SELECT) {
531                 mTimeElapsedSinceFullOpacity += frameInterval;
532                 if (mTimeElapsedSinceFullOpacity > 5.0f)
533                     setAlpha(0);
534             }
535         }
536         if (mAnimAlpha != mAlpha || (mTimeElapsedSinceFullOpacity < 5.0f && !timeElapsedSinceFullOpacity_Reset))
537             return true;
538
539         return false;
540     }
541
542     public void renderOpaque(RenderView view, GL11 gl) {
543
544     }
545
546     public void renderBlended(RenderView view, GL11 gl) {
547         view.setAlpha(mAnimAlpha);
548     }
549
550     public void setAlpha(float alpha) {
551         float oldAlpha = mAlpha;
552         mAlpha = alpha;
553         if (oldAlpha != alpha) {
554             if (mView != null)
555                 mView.requestRender();
556         }
557         if (alpha == 1.0f) {
558             mTimeElapsedSinceFullOpacity = 0.0f;
559         }
560     }
561
562     public float getAlpha() {
563         return mAlpha;
564     }
565
566     public void setTimeBarTime(long time) {
567         // mTimeBar.setTime(time);
568     }
569
570     @Override
571     public void generate(RenderView view, RenderView.Lists lists) {
572         lists.opaqueList.add(this);
573         lists.blendedList.add(this);
574         lists.hitTestList.add(this);
575         lists.updateList.add(this);
576         mTopRightButton.generate(view, lists);
577         mZoomInButton.generate(view, lists);
578         mZoomOutButton.generate(view, lists);
579         sTimeBar.generate(view, lists);
580         mSelectionMenuTop.generate(view, lists);
581         mSelectionMenuBottom.generate(view, lists);
582         mFullscreenMenu.generate(view, lists);
583         sPathBar.generate(view, lists);
584         // mLoadingLayer.generate(view, lists);
585         mView = view;
586     }
587
588     @Override
589     public boolean containsPoint(float x, float y) {
590         return false;
591     }
592
593     public void cancelSelection() {
594         mSelectionMenuBottom.close();
595         closeSelectionMenu();
596         setMode(MODE_NORMAL);
597     }
598
599     public void closeSelectionMenu() {
600         mSelectionMenuBottom.close();
601     }
602
603     @Override
604     public boolean onTouchEvent(MotionEvent event) {
605         if (mMode == MODE_SELECT) {
606             /*
607              * setMode(MODE_NORMAL); ArrayList<MediaBucket> displayBuckets = mGridLayer.getSelectedBuckets(); // use this list, and
608              * then clear the items return true;
609              */
610             return false;
611         } else {
612             return false;
613         }
614     }
615
616     public boolean isLoaded() {
617         return mLoadingLayer.isLoaded();
618     }
619
620     void reset() {
621         mLoadingLayer.reset();
622         sTimeBar.regenerateStringsForContext(mContext);
623     }
624
625     public void fullscreenSelectionChanged(MediaItem item, int index, int count) {
626         // request = new ReverseGeocoder.Request();
627         // request.firstLatitude = request.secondLatitude = item.latitude;
628         // request.firstLongitude = request.secondLongitude = item.longitude;
629         // mGeo.enqueue(request);
630         if (item == null)
631             return;
632         String location = index + "/" + count;
633         mCachedCaption = item.mCaption;
634         mCachedPosition = location;
635         mCachedCurrentLabel = location;
636         sPathBar.changeLabel(location);
637     }
638
639     private void updateShareMenu() {
640         // Get the first selected item. Wire this up to multiple-item intents when we move
641         // to Eclair.
642         ArrayList<MediaBucket> selection = mGridLayer.getSelectedBuckets();
643         ArrayList<Uri> uris = new ArrayList<Uri>();
644         String mimeType = null;
645         if (!selection.isEmpty()) {
646             int mediaType = Shared.INVALID;
647             int numBuckets = selection.size();
648             for (int j = 0; j < numBuckets; ++j) {
649                 MediaBucket bucket = selection.get(j);
650                 ArrayList<MediaItem> items = null;
651                 int numItems = 0;
652                 if (bucket.mediaItems != null && !bucket.mediaItems.isEmpty()) {
653                     items = bucket.mediaItems;
654                     numItems = items.size();
655                 } else if (bucket.mediaSet != null) {
656                     // We need to delete the entire bucket.
657                     items = bucket.mediaSet.getItems();
658                     numItems = bucket.mediaSet.getNumItems();
659                 }
660                 for (int i = 0; i < numItems; ++i) {
661                     MediaItem item = items.get(i);
662                     if (mimeType == null) {
663                         mimeType = item.mMimeType;
664                         mediaType = item.getMediaType();
665                         MediaSet parentMediaSet = item.mParentMediaSet;
666                         if (parentMediaSet != null && parentMediaSet.mPicasaAlbumId != Shared.INVALID) {
667                             // This will go away once http uri's are supported for all media types.
668                             // This ensures that just the link is shared as a text
669                             mimeType = "text/plain";
670                         }
671                     }
672                     if (mediaType == item.getMediaType()) {
673                         // add this uri
674                         if (item.mContentUri != null) {
675                             Uri uri = Uri.parse(item.mContentUri);
676                             uris.add(uri);
677                         }
678                     }
679                 }
680             }
681         }
682         PopupMenu.Option[] options = null;
683         if (uris.size() != 0) {
684             final Intent intent = new Intent();
685             if (mimeType == null)
686                 mimeType = "image/jpeg";
687             if (mimeType.contains("text")) {
688                 // We need to share this as a text string.
689                 intent.setAction(Intent.ACTION_SEND);
690                 intent.setType(mimeType);
691
692                 // Create a newline-separated list of URLs.
693                 StringBuilder builder = new StringBuilder();
694                 for (int i = 0, size = uris.size(); i < size; ++i) {
695                     builder.append(uris.get(i));
696                     if (i != size - 1) {
697                         builder.append('\n');
698                     }
699                 }
700                 intent.putExtra(Intent.EXTRA_TEXT, builder.toString());
701             } else {
702                 if (uris.size() == 1) {
703                     intent.setAction(Intent.ACTION_SEND);
704                     intent.putExtra(Intent.EXTRA_STREAM, uris.get(0));
705                 } else {
706                     intent.setAction(Intent.ACTION_SEND_MULTIPLE);
707                     intent.putExtra(Intent.EXTRA_STREAM, uris);
708                 }
709                 intent.setType(mimeType);
710             }
711             intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
712
713             // Query the system for matching activities.
714             PackageManager packageManager = mContext.getPackageManager();
715             List<ResolveInfo> activities = packageManager.queryIntentActivities(intent, 0);
716             int numActivities = activities.size();
717             options = new PopupMenu.Option[numActivities];
718             for (int i = 0; i != numActivities; ++i) {
719                 final ResolveInfo info = activities.get(i);
720                 String label = info.loadLabel(packageManager).toString();
721                 options[i] = new PopupMenu.Option(label, info.loadIcon(packageManager), new Runnable() {
722                     public void run() {
723                         startResolvedActivity(intent, info);
724                     }
725                 });
726             }
727         }
728         mSelectionMenuBottom.getMenus()[0].options = options;
729     }
730
731     private void startResolvedActivity(Intent intent, ResolveInfo info) {
732         final Intent resolvedIntent = new Intent(intent);
733         ActivityInfo ai = info.activityInfo;
734         resolvedIntent.setComponent(new ComponentName(ai.applicationInfo.packageName, ai.name));
735         ((Gallery) mContext).getHandler().post(new Runnable() {
736             public void run() {
737                 mContext.startActivity(resolvedIntent);
738             }
739         });
740     }
741
742     public void autoHide(boolean hide) {
743         mAutoHide = hide;
744     }
745
746     public void swapFullscreenLabel() {
747         mCachedCurrentLabel = (mCachedCurrentLabel == mCachedCaption || mCachedCaption == null) ? mCachedPosition : mCachedCaption;
748         sPathBar.changeLabel(mCachedCurrentLabel);
749     }
750
751     public void clear() {
752
753     }
754
755     public void shutDown() {
756         
757     }
758
759     public void enterSelectionMode() {
760         setAlpha(1.0f);
761         setMode(HudLayer.MODE_SELECT);
762
763         // if we are in single view mode, show the bottom menu without the delete button.
764         if (mGridLayer.noDeleteMode()) {
765             mSelectionMenuBottom.setMenus(mSingleViewIntentBottomMenu);
766         } else {
767             mSelectionMenuBottom.setMenus(mNormalBottomMenu);
768         }
769     }
770
771     public Layer getMenuBar() {
772         return mFullscreenMenu;
773     }
774 }