TizenRefApp-8458 [Gallery] Implement select mode in PreviewPage 57/127757/1
authorIgor Nazarov <i.nazarov@samsung.com>
Fri, 28 Apr 2017 16:34:52 +0000 (19:34 +0300)
committerIgor Nazarov <i.nazarov@samsung.com>
Fri, 28 Apr 2017 16:34:52 +0000 (19:34 +0300)
- Implemented select mode in PreviewPage.

Change-Id: Ia2627e988e903575f33c54c3869074dd507e147c

inc/presenters/PreviewPage.h
inc/resources.h
src/presenters/PreviewPage.cpp
src/resources.cpp

index 6743b56f9e2f05d6477e3eea890103b5c3205c06..7a3cc8b13785e643bbefe766322d1fd32ddd1a14 100644 (file)
 #include "view/IImageGridListener.h"
 
 #include "IMoreOptionsListener.h"
+#include "ISelectModeListener.h"
 
 namespace gallery {
 
        class PreviewPage final : public Page,
                        private IImageGridListener,
-                       private IMoreOptionsListener {
+                       private IMoreOptionsListener,
+                       private ISelectModeListener {
        public:
                class Builder {
                public:
@@ -51,10 +53,11 @@ namespace gallery {
        private:
                friend class ucl::RefCountObj<PreviewPage>;
                PreviewPage(ucl::RefCountObjBase &rc, const ucl::NaviframeSRef &navi,
-                               ExitRequestHandler onExitRequest, const IMediaAlbumSRef &album);
+                               ExitRequestHandler onExitRequest, const IMediaAlbumSRef &album,
+                               bool selectModeStartup);
                virtual ~PreviewPage();
 
-               ucl::Result prepare(bool enableSelectMode);
+               ucl::Result prepare();
                void showItem(int itemIndex);
                void selectItem(int itemIndex);
                int getSafeItemIndex(int itemIndex) const;
@@ -66,9 +69,10 @@ namespace gallery {
                bool onEachMedia(MediaItemSRef &&media);
 
                void closeTempViews();
-               void switchToSelectMode(int itemIndex);
+               void switchToSelectMode();
                void switchToNormalMode();
                void toggleItemSelected(int itemIndex);
+               void confirmItemsDelete();
                void openViewer(int itemIndex, int x, int y);
 
                void onPageExitRequest(Page &page);
@@ -91,26 +95,36 @@ namespace gallery {
                virtual void onItemUnrealized(int itemIndex) final override;
                virtual void onItemEvent(int itemIndex,
                                int event, int x, int y) final override;
+               virtual void onTransitionFinished() final override;
 
                // IMoreOptionsListener //
 
                virtual void onMoreOptionClicked(MoreOptionsPresenter &sender,
                                const MoreOption &option) final override;
 
+               // ISelectModeListener //
+
+               virtual void onSelectModeEvent(int event) final override;
+
        private:
                class Item;
                using ItemUPtr = std::unique_ptr<Item>;
 
        private:
                const IMediaAlbumSRef m_album;
+               const bool m_selectModeStartup;
                ImageGridSRef m_imageGrid;
                std::vector<ItemUPtr> m_items;
                IJobSRef m_job;
                PageContentSRef m_content;
                MoreOptionsPresenterSRef m_more;
+               SelectModePresenterSRef m_smp;
                AlertDialogWRef m_alert;
                ProcessingPresenterSRef m_processing;
                PageWRef m_page;
+               int m_selectCount;
+               bool m_isInSelectMode;
+               bool m_needReload;
        };
 }
 
index 34b62076827031e79440a727040ad11b17c8f175..b1ffda45c527f4c02f7cd9d1d044101a8913de02 100644 (file)
@@ -41,6 +41,7 @@ namespace gallery {
        extern const ucl::TString STR_DELETE;
        extern const ucl::TString STR_DELETE_CAPS;
        extern const ucl::TString STR_DELETE_1_PHOTO;
+       extern const ucl::TString STR_DELETE_N_PHOTO;
        extern const ucl::TString STR_DELETING;
        extern const ucl::TString STR_DELETED;
        extern const ucl::TString STR_FAILED;
index b9d1fa241a1b64f8d3297eeafc4724af84af7e0b..5eb1e58c7111a2dfecf0214c1a89c5b84a648c4e 100644 (file)
@@ -24,6 +24,7 @@
 #include "view/ImageGrid.h"
 
 #include "presenters/MoreOptionsPresenter.h"
+#include "presenters/SelectModePresenter.h"
 #include "presenters/AlertDialog.h"
 #include "presenters/ProcessingPresenter.h"
 #include "presenters/ViewerPage.h"
@@ -100,16 +101,15 @@ namespace gallery {
                }
 
                auto result = makeShared<PreviewPage>(
-                               m_navi, onExitRequest, m_album);
+                               m_navi, onExitRequest, m_album, m_selectModeStartup);
 
-               FAIL_RETURN_VALUE(result->prepare(m_selectModeStartup), {},
-                               "result->prepare() failed!");
+               FAIL_RETURN_VALUE(result->prepare(), {}, "result->prepare() failed!");
 
                if (m_startItemIndex > 0) {
                        result->showItem(m_startItemIndex);
-                       if (m_selectModeStartup) {
-                               result->selectItem(m_startItemIndex);
-                       }
+               }
+               if (m_selectModeStartup) {
+                       result->selectItem(m_startItemIndex);
                }
 
                return result;
@@ -201,9 +201,14 @@ namespace gallery {
        PreviewPage::PreviewPage(RefCountObjBase &rc,
                        const NaviframeSRef &navi,
                        const ExitRequestHandler onExitRequest,
-                       const IMediaAlbumSRef &album) :
+                       const IMediaAlbumSRef &album,
+                       const bool selectModeStartup) :
                Page(rc, navi, onExitRequest),
-               m_album(album)
+               m_album(album),
+               m_selectModeStartup(selectModeStartup),
+               m_selectCount(0),
+               m_isInSelectMode(false),
+               m_needReload(false)
        {
        }
 
@@ -220,19 +225,27 @@ namespace gallery {
 
        void PreviewPage::reload()
        {
-               // TODO Temp solution.
-               // Need to add synchronization with curent state in the future.
-               switchToNormalMode();
+               if (m_imageGrid->isInTransition()) {
+                       m_needReload = true;
+                       return;
+               }
 
-               ImageGrid::Unrealizer u(*m_imageGrid);
+               {
+                       ImageGrid::Unrealizer u(*m_imageGrid);
 
-               m_items.clear();
+                       m_items.clear();
 
-               FAIL_LOG(m_album->forEachMedia(
-                               DELEGATE(PreviewPage::onEachMedia, this)),
-                               "m_album->forEachMedia() failed!");
+                       FAIL_LOG(m_album->forEachMedia(
+                                       DELEGATE(PreviewPage::onEachMedia, this)),
+                                       "m_album->forEachMedia() failed!");
 
-               m_imageGrid->setItemCount(m_items.size());
+                       m_imageGrid->setItemCount(m_items.size());
+               }
+
+               // TODO Temp solution.
+               // Need to add synchronization with curent state in the future.
+               closeTempViews();
+               switchToNormalMode();
 
                checkViewerPage();
        }
@@ -258,13 +271,15 @@ namespace gallery {
 
        int PreviewPage::getCurrentItemIndex() const
        {
-               return m_imageGrid->getScrolledToItemIndex();
+               return getSafeItemIndex(m_imageGrid->getScrolledToItemIndex());
        }
 
-       Result PreviewPage::prepare(const bool enableSelectMode)
+       Result PreviewPage::prepare()
        {
                m_content = PageContent::Builder().
-                               setFlags(PageContent::FLAG_MORE_OPTIONS).
+                               setFlags(PageContent::FLAG_BOTTOM_BUTTON |
+                                               PageContent::FLAG_SELECT_BUTTON |
+                                               PageContent::FLAG_MORE_OPTIONS).
                                build(getNaviframe());
                if (!m_content) {
                        LOG_RETURN(RES_FAIL, "PageContent::build() failed!");
@@ -273,7 +288,7 @@ namespace gallery {
                m_imageGrid = ImageGrid::Builder().
                                setListener(this).
                                setType(ImageGrid::Type::LINEAR).
-                               setSelectModeStartup(enableSelectMode).
+                               setSelectModeStartup(m_selectModeStartup).
                                build(*m_content);
                if (!m_imageGrid) {
                        LOG_RETURN(RES_FAIL, "ImageGrid::build() failed!");
@@ -293,6 +308,13 @@ namespace gallery {
                m_content->set(m_more->getWidget(), PageContent::Part::MORE_OPTIONS);
                addDeactivatorSource(m_more->getWidget());
 
+               m_smp = SelectModePresenter::Builder().
+                               setFlags(SelectModePresenter::FLAG_NO_MORE_OPTIONS).
+                               build(*m_content);
+               if (!m_smp) {
+                       LOG_RETURN(RES_FAIL, "SelectModePresenter::build() failed!");
+               }
+
                FAIL_RETURN(m_album->forEachMedia(
                                DELEGATE(PreviewPage::onEachMedia, this)),
                                "m_album->forEachMedia() failed!");
@@ -310,6 +332,11 @@ namespace gallery {
                                PreviewPage::onAlbumChanged, asWeak(*this)));
 
                m_more->setListener(asWeakThis<IMoreOptionsListener>(this));
+               m_smp->setListener(asWeakThis<ISelectModeListener>(this));
+
+               if (m_selectModeStartup) {
+                       switchToSelectMode();
+               }
 
                return RES_OK;
        }
@@ -321,10 +348,15 @@ namespace gallery {
 
        void PreviewPage::selectItem(const int itemIndex)
        {
+               if (!m_isInSelectMode) {
+                       LOG_RETURN_VOID(RES_INVALID_ARGUMENTS, "Not in select mode!");
+               }
                if (getSafeItemIndex(itemIndex) != itemIndex) {
                        LOG_RETURN_VOID(RES_INVALID_ARGUMENTS, "itemIndex out of range!");
                }
-               m_items[itemIndex]->setSelected(true);
+               if (!m_items[itemIndex]->isSelected()) {
+                       toggleItemSelected(itemIndex);
+               }
        }
 
        int PreviewPage::getSafeItemIndex(const int itemIndex) const
@@ -363,7 +395,9 @@ namespace gallery {
                        m_more->activateBy(info.deactivator);
                }
 
-               if (isActive()) {
+               m_smp->activateBy(info.deactivator);
+
+               if (isActive() || m_smp->isActive()) {
                        m_imageGrid->activateRotary();
                }
        }
@@ -374,15 +408,16 @@ namespace gallery {
                        m_more->deactivateBy(info.deactivator);
                }
 
-               m_imageGrid->deactivateRotary();
+               m_smp->deactivateBy(info.deactivator);
+
+               if (!m_smp->isActive()) {
+                       m_imageGrid->deactivateRotary();
+               }
        }
 
        void PreviewPage::onBackKey()
        {
-               if (m_imageGrid->isInTransition()) {
-                       return;
-               }
-               if (m_imageGrid->isInSelectMode()) {
+               if (m_isInSelectMode) {
                        switchToNormalMode();
                        return;
                }
@@ -406,7 +441,7 @@ namespace gallery {
                        return;
                }
 
-               if (m_imageGrid->isInSelectMode()) {
+               if (m_isInSelectMode) {
                        if (event == ImageGrid::ITEM_EVENT_CLICK) {
                                toggleItemSelected(itemIndex);
                                m_imageGrid->bringInItem(itemIndex);
@@ -415,12 +450,27 @@ namespace gallery {
                }
 
                switch (event) {
+               case ImageGrid::ITEM_EVENT_TAP_AND_HOLD:
+                       switchToSelectMode();
+                       toggleItemSelected(itemIndex);
+                       break;
                case ImageGrid::ITEM_EVENT_DOUBLE_TAP:
                        openViewer(itemIndex, x, y);
                        break;
                }
        }
 
+       void PreviewPage::onTransitionFinished()
+       {
+               if (m_needReload) {
+                       m_needReload = false;
+                       reload();
+               } else {
+                       m_imageGrid->update();
+               }
+               activateBy(m_imageGrid.get());
+       }
+
        void PreviewPage::onMoreOptionClicked(MoreOptionsPresenter &sender,
                        const MoreOption &option)
        {
@@ -428,12 +478,7 @@ namespace gallery {
 
                switch (option.id) {
                case impl::MORE_OPTION_ID_DELETE:
-                       m_alert = AlertDialog::Builder().
-                                       setType(AlertDialog::Type::OK_CANCEL).
-                                       setText(STR_DELETE_1_PHOTO).
-                                       setHandler(WEAK_DELEGATE(
-                                               PreviewPage::onAlertEvent, asWeak(*this))).
-                                       build(getNaviframe());
+                       confirmItemsDelete();
                        break;
                default:
                        WLOG("Unknown option id: %d;", option.id);
@@ -441,20 +486,75 @@ namespace gallery {
                }
        }
 
+       void PreviewPage::onSelectModeEvent(const int event)
+       {
+               if (m_more->isOpened()) {
+                       return;
+               }
+
+               switch (event) {
+               case SelectModePresenter::EVENT_SELECT_ALL:
+               case SelectModePresenter::EVENT_DESELECT_ALL:
+                       {
+                               const bool isSelect =
+                                               (event == SelectModePresenter::EVENT_SELECT_ALL);
+                               for (auto &item: m_items) {
+                                       item->setSelected(isSelect);
+                               }
+                               m_selectCount = (isSelect * m_items.size());
+                               m_smp->update(m_selectCount);
+                       }
+                       break;
+
+               case SelectModePresenter::EVENT_BOTTOM_BUTTON_CLICK:
+                       confirmItemsDelete();
+                       break;
+               }
+       }
+
+       void PreviewPage::confirmItemsDelete()
+       {
+               const int itemCount = (m_isInSelectMode ? m_selectCount : 1);
+               if (itemCount == 0) {
+                       WLOG("itemCount == 0");
+                       return;
+               }
+
+               m_alert = AlertDialog::Builder().
+                               setType(AlertDialog::Type::OK_CANCEL).
+                               setText((itemCount == 1) ?
+                                       STR_DELETE_1_PHOTO :
+                                       TString(STR_DELETE_N_PHOTO.format(itemCount))).
+                               setHandler(WEAK_DELEGATE(
+                                       PreviewPage::onAlertEvent, asWeak(*this))).
+                               build(getNaviframe());
+       }
+
        bool PreviewPage::onAlertEvent(AlertDialog &dialog, int event)
        {
                if (event != AlertDialog::EVENT_OK) {
                        return true;
                }
 
-               const int itemIndex = getCurrentItemIndex();
-               if (itemIndex < 0) {
-                       ELOG("Invalid item index!");
-                       return true;
+               MediaItems items;
+
+               if (m_isInSelectMode) {
+                       for (auto &item: m_items) {
+                               if (item->isSelected()) {
+                                       items.emplace_back(item->getMedia());
+                               }
+                       }
+               } else {
+                       const int itemIndex = getCurrentItemIndex();
+                       if (itemIndex < 0) {
+                               ELOG("Invalid item index!");
+                               return true;
+                       }
+                       items.emplace_back(m_items[itemIndex]->getMedia());
                }
 
                m_job = MediaItem::RemoverBuilder().
-                               setItems({m_items[itemIndex]->getMedia()}).
+                               setItems(items).
                                build(WEAK_DELEGATE(
                                        PreviewPage::onJobComplete, asWeak(*this)));
                if (!m_job) {
@@ -489,36 +589,68 @@ namespace gallery {
        void PreviewPage::closeTempViews()
        {
                if (m_alert) {
-                       m_alert->dismiss();
+                       m_alert->dispose();
                }
                if (m_more) {
                        m_more->setOpened(false);
                }
        }
 
-       void PreviewPage::switchToSelectMode(const int itemIndex)
+       void PreviewPage::switchToSelectMode()
        {
-               closeTempViews();
+               if (m_isInSelectMode) {
+                       return;
+               }
+               m_isInSelectMode = true;
 
+               m_selectCount = 0;
                for (auto &item: m_items) {
                        item->setSelected(false);
                }
 
-               m_items[itemIndex]->setSelected(true);
+               m_content->setMoreOptionsVisible(false);
+
+               m_smp->setBottomButtonText(STR_DELETE_CAPS);
+               m_smp->update(m_selectCount, m_items.size());
+               m_smp->setVisible(true);
 
                m_imageGrid->setSelectModeEnabled(true);
+               if (m_imageGrid->isInTransition()) {
+                       deactivateBy(m_imageGrid.get());
+               }
        }
 
        void PreviewPage::switchToNormalMode()
        {
-               closeTempViews();
+               if (!m_isInSelectMode) {
+                       return;
+               }
+               m_isInSelectMode = false;
+
+               m_content->setMoreOptionsVisible(true);
+
+               m_smp->setVisible(false);
 
                m_imageGrid->setSelectModeEnabled(false);
+               if (m_imageGrid->isInTransition()) {
+                       deactivateBy(m_imageGrid.get());
+               }
        }
 
        void PreviewPage::toggleItemSelected(const int itemIndex)
        {
                m_items[itemIndex]->toggleSelected();
+
+               m_selectCount = 0;
+               for (auto &item: m_items) {
+                       m_selectCount += item->isSelected();
+               }
+
+               m_smp->update(m_selectCount);
+
+               if (m_selectCount == 0) {
+                       m_more->setOpened(false);
+               }
        }
 
        void PreviewPage::openViewer(const int itemIndex, const int x, const int y)
index 45f5bd4f1ef2e4e9e8541de259357715072e1add..bfd9ff61128def23e4ac0e3281bb3c24b1a5f2d7 100644 (file)
@@ -27,6 +27,7 @@ namespace gallery {
        const ucl::TString STR_DELETE {"Delete"};
        const ucl::TString STR_DELETE_CAPS {"DELETE"};
        const ucl::TString STR_DELETE_1_PHOTO {"Delete 1 photo?"};
+       const ucl::TString STR_DELETE_N_PHOTO {"Delete %d photo?"};
        const ucl::TString STR_DELETING {"Deleting..."};
        const ucl::TString STR_DELETED {"Deleted."};
        const ucl::TString STR_FAILED {"Failed."};