protected:
/**
+ * @brief Update the part containing check component.
+ */
+ void updateCheckPart();
+
+ /**
* @see GenlistItem::getContent()
* @remark Use it in derived class to create check component
*/
*/
typedef std::function<void()> SelectCallback;
+ /**
+ * @brief Called before item is destroyed.
+ */
+ typedef std::function<void()> DestroyCallback;
+
GenlistItem();
virtual ~GenlistItem();
bool isRealized() const;
/**
+ * @return Whether the item is inserted into genlist.
+ */
+ bool isInserted() const;
+
+ /**
* @return Whether the item is a group item.
*/
virtual bool isGroupItem() const { return false; }
void setSelectCallback(SelectCallback callback);
/**
+ * @brief Set item destruction callback.
+ * @param[in] callback Callback to be called before item is destroyed
+ */
+ void setDestroyCallback(SelectCallback callback);
+
+ /**
* @brief Scroll genlist to item.
* @param[in] position Item position on screen
* @param[in] isAnimated Whether scrolling is animated or immediate
bool m_IsFocusPending;
SelectCallback m_OnSelected;
+ DestroyCallback m_OnDestroy;
};
}
using namespace Ui;
GenlistCheckItem::GenlistCheckItem()
- : m_IsChecked(false)
+ : m_CheckPart("*"), m_IsChecked(false)
{ }
bool GenlistCheckItem::isChecked() const
m_OnChecked = std::move(callback);
}
+void GenlistCheckItem::updateCheckPart()
+{
+ elm_genlist_item_fields_update(getObjectItem(), m_CheckPart.c_str(), ELM_GENLIST_ITEM_FIELD_CONTENT);
+}
+
Evas_Object *GenlistCheckItem::getContent(Evas_Object *parent, const char *part)
{
m_CheckPart = part;
GenlistItem::~GenlistItem()
{
+ if (m_OnDestroy) {
+ m_OnDestroy();
+ }
+
if (m_Item) {
pop();
}
return m_IsRealized;
}
+bool GenlistItem::isInserted() const
+{
+ return m_Item != nullptr;
+}
+
Elm_Object_Item *GenlistItem::getObjectItem() const
{
return m_Item;
m_OnSelected = std::move(callback);
}
+void GenlistItem::setDestroyCallback(DestroyCallback callback)
+{
+ m_OnDestroy = std::move(callback);
+}
+
void GenlistItem::scrollTo(Elm_Genlist_Item_Scrollto_Type position, bool isAnimated)
{
auto scroll = isAnimated ? elm_genlist_item_bring_in : elm_genlist_item_show;
void NaviframePage::setTitle(const char *title)
{
elm_object_item_translatable_part_text_set(m_NaviItem, "elm.text.title", title);
- elm_naviframe_item_title_enabled_set(m_NaviItem, title != nullptr, EINA_TRUE);
+ elm_naviframe_item_title_enabled_set(m_NaviItem, title && *title, EINA_TRUE);
}
void NaviframePage::setStyle(const char *style)
--- /dev/null
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef CONTACTS_SELECT_ALL_H
+#define CONTACTS_SELECT_ALL_H
+
+#include "Ui/GenlistCheckItem.h"
+
+namespace Contacts
+{
+ /**
+ * @brief "Select all" genlist item
+ */
+ class SelectAllItem : public Ui::GenlistCheckItem
+ {
+ protected:
+ /**
+ * @see GenlistItem::getText()
+ */
+ virtual char *getText(Evas_Object *parent, const char *part) override;
+
+ /**
+ * @see GenlistItem::getContent()
+ */
+ virtual Evas_Object *getContent(Evas_Object *parent, const char *part) override;
+ };
+}
+
+#endif /* CONTACTS_SELECT_ALL_H */
--- /dev/null
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef CONTACTS_SELECT_ITEM_H
+#define CONTACTS_SELECT_ITEM_H
+
+#include "Contacts/Common/SelectMode.h"
+#include "Ui/GenlistCheckItem.h"
+
+namespace Contacts
+{
+ /**
+ * @brief Genlist item for SelectView that supports selection mode switching.
+ */
+ class SelectItem : public Ui::GenlistCheckItem
+ {
+ public:
+ SelectItem();
+
+ /**
+ * @return Item selection mode.
+ */
+ SelectMode getSelectMode() const;
+
+ /**
+ * @brief Set item selection mode.
+ */
+ void setSelectMode(SelectMode selectMode);
+
+ protected:
+ /**
+ * @return Selection result associated with the item.
+ */
+ virtual SelectResult getSelectResult() const = 0;
+
+ /**
+ * @see GenlistItem::getContent()
+ */
+ virtual Evas_Object *getContent(Evas_Object *parent, const char *part) override;
+
+ /**
+ * @see GenlistItem::onSelected()
+ */
+ virtual void onSelected() override;
+
+ /**
+ * @brief Called when selection mode was changed.
+ * @param[in] selectMode New selection mode
+ */
+ virtual void onSelectModeChanged(SelectMode selectMode) { }
+
+ private:
+ friend class SelectView;
+
+ SelectMode m_SelectMode;
+ };
+}
+
+#endif /* CONTACTS_SELECT_ITEM_H */
--- /dev/null
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef CONTACTS_SELECT_VIEW_H
+#define CONTACTS_SELECT_VIEW_H
+
+#include "Contacts/Common/SelectAllItem.h"
+#include "Contacts/Common/SelectMode.h"
+#include "Ui/View.h"
+
+#include <memory>
+#include <vector>
+
+namespace Ui
+{
+ class GenlistItem;
+}
+
+namespace Contacts
+{
+ class SelectItem;
+
+ /**
+ * @brief Base class for a view that support single and multiple selection modes.
+ */
+ class SelectView : public Ui::View
+ {
+ public:
+ SelectView();
+
+ /**
+ * @brief Set selection mode.
+ * @param[in] selectMode Selection mode
+ */
+ void setSelectMode(SelectMode selectMode);
+
+ /**
+ * @brief Set item selection limit.
+ * @param[in] count Maximal selectable items count
+ */
+ void setSelectLimit(size_t selectLimit);
+
+ /**
+ * @brief Set selection callback.
+ * @param[in] callback Selection callback
+ */
+ void setSelectCallback(SelectCallback callback);
+
+ protected:
+ /**
+ * @return View selection mode.
+ */
+ SelectMode getSelectMode() const;
+
+ /**
+ * @return Current seleciton limit.
+ */
+ size_t getSelectLimit() const;
+
+ /**
+ * @return Current selected items count.
+ */
+ size_t getSelectCount() const;
+
+ /**
+ * @return Page title format for the current selection mode.
+ */
+ virtual const char *getPageTitle() const;
+
+ /**
+ * @brief Creates "Done" and "Cancel" buttons in #SelectMulti mode.
+ * @see View::onPageAttached()
+ */
+ virtual void onPageAttached() override;
+
+ /**
+ * @brief Should be called when selectable item is inserted.
+ * @param[in] item Inserted item
+ */
+ void onItemInserted(SelectItem *item);
+
+ /**
+ * @brief Should be called when selectable item is about to be removed.
+ * @param[in] item Item being removed
+ */
+ void onItemRemove(SelectItem *item);
+
+ /**
+ * @brief Called when selectable item is pressed it #SelectNone mode.
+ * @param[in] item Pressed item
+ */
+ virtual void onItemPressed(SelectItem *item) { }
+
+ /**
+ * @brief Called when "Select All" item should be inserted.
+ * @param[in] item "Select All" genlist item
+ */
+ virtual void onSelectAllInsert(Ui::GenlistItem *item) { }
+
+ /**
+ * @brief Called when "Select All" item is about to be removed.
+ */
+ virtual void onSelectAllRemove() { }
+
+ /**
+ * @brief Called when selection mode was changed.
+ * @param[in] selectMode New selection mode
+ */
+ virtual void onSelectModeChanged(SelectMode selectMode) { }
+
+ /**
+ * @brief Called when selection limit was changed.
+ * @param[in] selectLimit New selection limit
+ */
+ virtual void onSelectLimitChanged(size_t selectLimit) { }
+
+ private:
+ void updatePageTitle();
+ void updatePageButtons();
+ void updateSelectAllItem();
+
+ void createPageButtons();
+ void destroyPageButtons();
+
+ void onItemSelected(SelectItem *item);
+ void onItemChecked(SelectItem *item, bool isChecked);
+ void onSelectAllChecked(bool isChecked);
+ void onSelectAllDestroy();
+
+ void onDonePressed(Evas_Object *button, void *eventInfo);
+ void onCancelPressed(Evas_Object *button, void *eventInfo);
+
+ std::unique_ptr<SelectAllItem> m_SelectAllItem;
+ std::vector<SelectItem *> m_Items;
+
+ Evas_Object *m_DoneButton;
+ Evas_Object *m_CancelButton;
+
+ size_t m_SelectCount;
+ size_t m_SelectLimit;
+
+ SelectMode m_SelectMode;
+ SelectCallback m_OnSelected;
+ };
+}
+
+#endif /* CONTACTS_SELECT_VIEW_H */
--- /dev/null
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include "Contacts/Common/SelectAllItem.h"
+#include <app_i18n.h>
+
+using namespace Contacts;
+
+char *SelectAllItem::getText(Evas_Object *parent, const char *part)
+{
+ if (strcmp(part, "elm.text") == 0) {
+ return strdup(_("IDS_PB_MBODY_SELECT_ALL"));
+ }
+
+ return nullptr;
+}
+
+Evas_Object *SelectAllItem::getContent(Evas_Object *parent, const char *part)
+{
+ if (strcmp(part, "elm.swallow.end") == 0) {
+ return GenlistCheckItem::getContent(parent, part);
+ }
+
+ return nullptr;
+}
--- /dev/null
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include "Contacts/Common/SelectItem.h"
+
+using namespace Contacts;
+
+SelectItem::SelectItem()
+ : m_SelectMode(SelectNone)
+{
+}
+
+SelectMode SelectItem::getSelectMode() const
+{
+ return m_SelectMode;
+}
+
+void SelectItem::setSelectMode(SelectMode selectMode)
+{
+ m_SelectMode = selectMode;
+ updateCheckPart();
+
+ onSelectModeChanged(m_SelectMode);
+}
+
+Evas_Object *SelectItem::getContent(Evas_Object *parent, const char *part)
+{
+ if (m_SelectMode == SelectMulti) {
+ return GenlistCheckItem::getContent(parent, part);
+ }
+
+ return nullptr;
+}
+
+void SelectItem::onSelected()
+{
+ if (m_SelectMode == SelectMulti) {
+ GenlistCheckItem::onSelected();
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include "Contacts/Common/SelectView.h"
+#include "Contacts/Common/SelectItem.h"
+
+#include "Ui/Genlist.h"
+#include "Utils/Callback.h"
+
+#include <app_i18n.h>
+#include <algorithm>
+
+#define TITLE_BUFFER_SIZE 32
+
+using namespace Contacts;
+using namespace std::placeholders;
+
+SelectView::SelectView()
+ : m_DoneButton(nullptr), m_CancelButton(nullptr),
+ m_SelectCount(0), m_SelectLimit(0),
+ m_SelectMode(SelectNone)
+{
+}
+
+void SelectView::setSelectMode(SelectMode selectMode)
+{
+ if (m_SelectMode != selectMode) {
+ m_SelectMode = selectMode;
+
+ updatePageTitle();
+ updatePageButtons();
+ updateSelectAllItem();
+
+ for (auto &&item : m_Items) {
+ item->setSelectMode(m_SelectMode);
+ }
+
+ onSelectModeChanged(m_SelectMode);
+ }
+}
+
+void SelectView::setSelectLimit(size_t selectLimit)
+{
+ if (m_SelectLimit != selectLimit) {
+ m_SelectLimit = selectLimit;
+
+ if (m_SelectLimit) {
+ for (size_t i = m_Items.size() - 1; m_SelectCount > m_SelectLimit; --i) {
+ if (m_Items[i]->isChecked()) {
+ m_Items[i]->setChecked(false);
+ --m_SelectCount;
+ }
+ }
+ }
+
+ updatePageTitle();
+ updateSelectAllItem();
+ onSelectLimitChanged(m_SelectLimit);
+ }
+}
+
+void SelectView::setSelectCallback(SelectCallback callback)
+{
+ m_OnSelected = std::move(callback);
+}
+
+SelectMode SelectView::getSelectMode() const
+{
+ return m_SelectMode;
+}
+
+size_t SelectView::getSelectLimit() const
+{
+ return m_SelectLimit;
+}
+
+size_t SelectView::getSelectCount() const
+{
+ return m_SelectCount;
+}
+
+const char *SelectView::getPageTitle() const
+{
+ switch (m_SelectMode) {
+ case SelectSingle:
+ return "IDS_PB_HEADER_SELECT";
+ case SelectMulti:
+ if (m_SelectLimit) {
+ return "%zu/%zu";
+ } else {
+ return "IDS_PB_HEADER_PD_SELECTED_ABB";
+ }
+ default:
+ return "";
+ }
+}
+
+void SelectView::onPageAttached()
+{
+ updatePageTitle();
+ updatePageButtons();
+}
+
+void SelectView::onItemInserted(SelectItem *item)
+{
+ item->setSelectMode(m_SelectMode);
+ item->setSelectCallback(std::bind(&SelectView::onItemSelected, this, item));
+ item->setCheckCallback(std::bind(&SelectView::onItemChecked, this, item, _1));
+ m_Items.push_back(item);
+
+ updateSelectAllItem();
+}
+
+void SelectView::onItemRemove(SelectItem *item)
+{
+ if (item->isChecked()) {
+ --m_SelectCount;
+ updatePageTitle();
+ }
+
+ m_Items.erase(std::remove(m_Items.begin(), m_Items.end(), item), m_Items.end());
+ updateSelectAllItem();
+}
+
+void SelectView::updatePageTitle()
+{
+ Ui::NavigatorPage *page = getPage();
+ if (!page) {
+ return;
+ }
+
+ char title[TITLE_BUFFER_SIZE];
+ snprintf(title, sizeof(title), _(getPageTitle()), m_SelectCount, m_SelectLimit);
+ page->setTitle(title);
+}
+
+void SelectView::updatePageButtons()
+{
+ Ui::NavigatorPage *page = getPage();
+ if (!page) {
+ return;
+ }
+
+ switch (m_SelectMode) {
+ case SelectNone:
+ case SelectSingle:
+ destroyPageButtons();
+ break;
+
+ case SelectMulti:
+ createPageButtons();
+ page->setContent("title_right_btn", m_DoneButton);
+ page->setContent("title_left_btn", m_CancelButton);
+ break;
+ }
+}
+
+void SelectView::updateSelectAllItem()
+{
+ if (m_SelectMode == SelectMulti && !m_SelectLimit && !m_Items.empty()) {
+ if (!m_SelectAllItem) {
+ m_SelectAllItem.reset(new SelectAllItem());
+ m_SelectAllItem->setCheckCallback(std::bind(&SelectView::onSelectAllChecked, this, _1));
+ m_SelectAllItem->setDestroyCallback(std::bind(&SelectView::onSelectAllDestroy, this));
+ onSelectAllInsert(m_SelectAllItem.get());
+ m_SelectAllItem->scrollTo();
+ }
+
+ m_SelectAllItem->setChecked(m_SelectCount == m_Items.size());
+ } else {
+ if (m_SelectAllItem) {
+ onSelectAllRemove();
+ m_SelectAllItem.reset();
+ }
+ }
+}
+
+void SelectView::createPageButtons()
+{
+ m_DoneButton = elm_button_add(getEvasObject());
+ elm_object_style_set(m_DoneButton, "naviframe/title_right");
+ elm_object_translatable_text_set(m_DoneButton, "IDS_PB_BUTTON_DONE_ABB3");
+ evas_object_smart_callback_add(m_DoneButton, "clicked",
+ makeCallback(&SelectView::onDonePressed), this);
+
+ m_CancelButton = elm_button_add(getEvasObject());
+ elm_object_style_set(m_CancelButton, "naviframe/title_left");
+ elm_object_translatable_text_set(m_CancelButton, "IDS_PB_BUTTON_CANCEL");
+ evas_object_smart_callback_add(m_CancelButton, "clicked",
+ makeCallback(&SelectView::onCancelPressed), this);
+}
+
+void SelectView::destroyPageButtons()
+{
+ evas_object_del(m_DoneButton);
+ evas_object_del(m_CancelButton);
+
+ m_DoneButton = nullptr;
+ m_CancelButton = nullptr;
+}
+
+void SelectView::onItemSelected(SelectItem *item)
+{
+ switch (m_SelectMode) {
+ case SelectNone:
+ onItemPressed(item);
+ break;
+ case SelectSingle:
+ {
+ SelectResult result = item->getSelectResult();
+ if (m_OnSelected && m_OnSelected({ &result, 1 })) {
+ delete this;
+ }
+ }
+ break;
+ default:
+ break;
+ }
+}
+
+void SelectView::onItemChecked(SelectItem *item, bool isChecked)
+{
+ if (m_SelectLimit && m_SelectCount == m_SelectLimit && isChecked) {
+ item->setChecked(false);
+ } else {
+ size_t checkCount = isChecked ? ++m_SelectCount : m_SelectCount--;
+ if (checkCount == m_Items.size()) {
+ updateSelectAllItem();
+ }
+
+ updatePageTitle();
+ }
+}
+
+void SelectView::onSelectAllChecked(bool isChecked)
+{
+ for (auto &&item : m_Items) {
+ item->setChecked(isChecked);
+ }
+
+ m_SelectCount = isChecked ? m_Items.size() : 0;
+ updatePageTitle();
+}
+
+void SelectView::onSelectAllDestroy()
+{
+ m_SelectAllItem.release();
+}
+
+void SelectView::onDonePressed(Evas_Object *button, void *eventInfo)
+{
+ std::vector<SelectResult> results;
+ for (auto &&item : m_Items) {
+ if (item->isChecked()) {
+ results.push_back(item->getSelectResult());
+ }
+ }
+
+ if (m_OnSelected && m_OnSelected({ results.data(), results.size()})) {
+ delete this;
+ }
+}
+
+void SelectView::onCancelPressed(Evas_Object *button, void *eventInfo)
+{
+ delete this;
+}
menu->create(getEvasObject());
menu->addItem("IDS_LOGS_OPT_DELETE", [this] {
- ListView *deleteView = new ListView();
- getNavigator()->navigateTo(deleteView);
- deleteView->setSelectMode(SelectMulti);
- deleteView->setSelectCallback([](SelectResults results) {
+ ListView *view = new ListView();
+ view->setSelectMode(SelectMulti);
+ view->setSelectCallback([](SelectResults results) {
std::vector<int> ids;
for (auto &&result : results) {
ids.push_back(result.itemId);
contacts_db_delete_records(_contacts_person._uri, ids.data(), ids.size());
return true;
});
+ getNavigator()->navigateTo(view);
});
menu->addItem("IDS_PB_OPT_SETTINGS", [this] {