1 // Copyright (c) 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef IOS_CHROME_BROWSER_UI_BOOKMARKS_BOOKMARK_UTILS_IOS_H_
6 #define IOS_CHROME_BROWSER_UI_BOOKMARKS_BOOKMARK_UTILS_IOS_H_
7 
8 #import <UIKit/UIKit.h>
9 
10 #include <memory>
11 #include <set>
12 #include <vector>
13 
14 #include "base/strings/string16.h"
15 #include "base/time/time.h"
16 
17 class ChromeBrowserState;
18 class GURL;
19 @class MDCSnackbarMessage;
20 
21 namespace bookmarks {
22 class BookmarkModel;
23 class BookmarkNode;
24 }  // namespace bookmarks
25 
26 namespace bookmark_utils_ios {
27 
28 typedef std::vector<const bookmarks::BookmarkNode*> NodeVector;
29 typedef std::set<const bookmarks::BookmarkNode*> NodeSet;
30 
31 // Finds bookmark node passed in |id|, in the |model|.
32 const bookmarks::BookmarkNode* FindFolderById(bookmarks::BookmarkModel* model,
33                                               int64_t id);
34 
35 // The iOS code is doing some munging of the bookmark folder names in order
36 // to display a slighly different wording for the default folders.
37 NSString* TitleForBookmarkNode(const bookmarks::BookmarkNode* node);
38 
39 // Returns the subtitle relevant to the bookmark navigation ui.
40 NSString* subtitleForBookmarkNode(const bookmarks::BookmarkNode* node);
41 
42 // Returns the current status bar height.
43 CGFloat StatusBarHeight();
44 
45 #pragma mark - Updating Bookmarks
46 
47 // Creates the bookmark if |node| is NULL. Otherwise updates |node|.
48 // |folder| is the intended parent of |node|.
49 // Returns a snackbar with an undo action, returns nil if operation wasn't
50 // successful or there's nothing to undo.
51 // TODO(crbug.com/1099901): Refactor to include position and replace two
52 // functions below.
53 MDCSnackbarMessage* CreateOrUpdateBookmarkWithUndoToast(
54     const bookmarks::BookmarkNode* node,
55     NSString* title,
56     const GURL& url,
57     const bookmarks::BookmarkNode* folder,
58     bookmarks::BookmarkModel* bookmark_model,
59     ChromeBrowserState* browser_state);
60 
61 // Creates a new bookmark with |title|, |url|, at |position| under parent
62 // |folder|. Returns a snackbar with an undo action. Returns nil if operation
63 // failed or there's nothing to undo.
64 MDCSnackbarMessage* CreateBookmarkAtPositionWithUndoToast(
65     NSString* title,
66     const GURL& url,
67     const bookmarks::BookmarkNode* folder,
68     int position,
69     bookmarks::BookmarkModel* bookmark_model,
70     ChromeBrowserState* browser_state);
71 
72 // Updates a bookmark node position, and returns a snackbar with an undo action.
73 // Returns nil if the operation wasn't successful or there's nothing to undo.
74 MDCSnackbarMessage* UpdateBookmarkPositionWithUndoToast(
75     const bookmarks::BookmarkNode* node,
76     const bookmarks::BookmarkNode* folder,
77     int position,
78     bookmarks::BookmarkModel* bookmark_model,
79     ChromeBrowserState* browser_state);
80 
81 // Deletes all bookmarks in |model| that are in |bookmarks|, and returns a
82 // snackbar with an undo action. Returns nil if the operation wasn't successful
83 // or there's nothing to undo.
84 MDCSnackbarMessage* DeleteBookmarksWithUndoToast(
85     const std::set<const bookmarks::BookmarkNode*>& bookmarks,
86     bookmarks::BookmarkModel* model,
87     ChromeBrowserState* browser_state);
88 
89 // Deletes all nodes in |bookmarks|.
90 void DeleteBookmarks(const std::set<const bookmarks::BookmarkNode*>& bookmarks,
91                      bookmarks::BookmarkModel* model);
92 
93 // Move all |bookmarks| to the given |folder|, and returns a snackbar with an
94 // undo action. Returns nil if the operation wasn't successful or there's
95 // nothing to undo.
96 MDCSnackbarMessage* MoveBookmarksWithUndoToast(
97     const std::set<const bookmarks::BookmarkNode*>& bookmarks,
98     bookmarks::BookmarkModel* model,
99     const bookmarks::BookmarkNode* folder,
100     ChromeBrowserState* browser_state);
101 
102 // Move all |bookmarks| to the given |folder|.
103 // Returns whether this method actually moved bookmarks (for example, only
104 // moving a folder to its parent will return |false|).
105 bool MoveBookmarks(const std::set<const bookmarks::BookmarkNode*>& bookmarks,
106                    bookmarks::BookmarkModel* model,
107                    const bookmarks::BookmarkNode* folder);
108 
109 // Category name for all bookmarks related snackbars.
110 extern NSString* const kBookmarksSnackbarCategory;
111 
112 // Returns the parent, if all the bookmarks are siblings.
113 // Otherwise returns the mobile_node.
114 const bookmarks::BookmarkNode* defaultMoveFolder(
115     const std::set<const bookmarks::BookmarkNode*>& bookmarks,
116     bookmarks::BookmarkModel* model);
117 
118 #pragma mark - Segregation of nodes by time.
119 
120 // A container for nodes which have been aggregated by some time property.
121 // e.g. (creation date) or (last access date).
122 class NodesSection {
123  public:
124   NodesSection();
125   virtual ~NodesSection();
126 
127   // |vector| is sorted by the relevant time property.
128   NodeVector vector;
129   // A representative time of all nodes in vector.
130   base::Time time;
131   // A string representation of |time|.
132   // e.g. (March 2014) or (4 March 2014).
133   std::string timeRepresentation;
134 };
135 
136 // Given the nodes in |vector|, segregates them by some time property into
137 // NodesSections.
138 // Automatically clears, populates and sorts |nodesSectionVector|.
139 // This method is not thread safe - it should only be called from the ui thread.
140 void segregateNodes(
141     const NodeVector& vector,
142     std::vector<std::unique_ptr<NodesSection>>& nodesSectionVector);
143 
144 #pragma mark - Useful bookmark manipulation.
145 
146 // Sorts a vector full of folders by title.
147 void SortFolders(NodeVector* vector);
148 
149 // Returns a vector of root level folders and all their folder descendants,
150 // sorted depth-first, then alphabetically. The returned nodes are visible, and
151 // are guaranteed to not be descendants of any nodes in |obstructions|.
152 NodeVector VisibleNonDescendantNodes(const NodeSet& obstructions,
153                                      bookmarks::BookmarkModel* model);
154 
155 // Whether |vector1| contains only elements of |vector2| in the same order.
156 BOOL IsSubvectorOfNodes(const NodeVector& vector1, const NodeVector& vector2);
157 
158 // Returns the indices in |vector2| of the items in |vector2| that are not
159 // present in |vector1|.
160 // |vector1| MUST be a subvector of |vector2| in the sense of |IsSubvector|.
161 std::vector<NodeVector::size_type> MissingNodesIndices(
162     const NodeVector& vector1,
163     const NodeVector& vector2);
164 
165 #pragma mark - Cache position in table view.
166 
167 // Creates bookmark path for |folderId| passed in. For eg: for folderId = 76,
168 // Root node(0) --> MobileBookmarks (3) --> Test1(76) will be returned as [0, 3,
169 // 76].
170 NSArray* CreateBookmarkPath(bookmarks::BookmarkModel* model, int64_t folderId);
171 
172 }  // namespace bookmark_utils_ios
173 
174 #endif  // IOS_CHROME_BROWSER_UI_BOOKMARKS_BOOKMARK_UTILS_IOS_H_
175