1 package org.coolreader.crengine; 2 3 import java.io.File; 4 import java.io.FileOutputStream; 5 import java.io.IOException; 6 import java.io.OutputStreamWriter; 7 import java.util.ArrayList; 8 import java.util.Collections; 9 import java.util.Comparator; 10 11 import android.util.Log; 12 13 public class BookInfo { 14 private FileInfo fileInfo; 15 private Bookmark lastPosition; 16 private ArrayList<Bookmark> bookmarks = new ArrayList<Bookmark>(); 17 setShortcutBookmark(int shortcut, Bookmark bookmark)18 synchronized public void setShortcutBookmark(int shortcut, Bookmark bookmark) 19 { 20 bookmark.setShortcut(shortcut); 21 for ( int i=0; i<bookmarks.size(); i++ ) { 22 Bookmark bm = bookmarks.get(i); 23 if ( bm.getType()==Bookmark.TYPE_POSITION && bm.getShortcut()==shortcut ) { 24 bookmark.setId(bm.getId()); 25 bookmarks.set(i, bookmark); 26 return; 27 } 28 } 29 bookmarks.add(bookmark); 30 } 31 findShortcutBookmark( int shortcut )32 synchronized public Bookmark findShortcutBookmark( int shortcut ) 33 { 34 for ( Bookmark bm : bookmarks ) 35 if ( bm.getType()==Bookmark.TYPE_POSITION && bm.getShortcut()==shortcut ) 36 return bm; 37 return null; 38 } 39 updateAccess()40 public void updateAccess() 41 { 42 if (lastPosition != null) { 43 lastPosition.setTimeStamp(System.currentTimeMillis()); 44 } 45 } 46 updateTimeElapsed(long timeElapsed)47 public void updateTimeElapsed(long timeElapsed) 48 { 49 if (lastPosition != null) { 50 lastPosition.setTimeElapsed(timeElapsed); 51 } 52 } 53 54 /** 55 * Deep copy. 56 * @param bookInfo is source object to copy from. 57 */ BookInfo(BookInfo bookInfo)58 public BookInfo(BookInfo bookInfo) { 59 this.fileInfo = new FileInfo(bookInfo.fileInfo); 60 if (bookInfo.lastPosition != null) 61 this.lastPosition = new Bookmark(bookInfo.lastPosition); 62 for (int i=0; i < bookInfo.getBookmarkCount(); i++) { 63 this.addBookmark(new Bookmark(bookInfo.getBookmark(i))); 64 } 65 } 66 BookInfo(FileInfo fileInfo)67 public BookInfo(FileInfo fileInfo) 68 { 69 this.fileInfo = fileInfo; //new FileInfo(fileInfo); 70 } 71 getLastPosition()72 public Bookmark getLastPosition() 73 { 74 return lastPosition; 75 } 76 setLastPosition( Bookmark position )77 public void setLastPosition( Bookmark position ) 78 { 79 synchronized (this) { 80 if ( lastPosition!=null ) { 81 if (position.getStartPos()!=null && position.getStartPos().equals(lastPosition.getStartPos())) 82 return; // not changed 83 position.setId(lastPosition.getId()); 84 } 85 lastPosition = position; 86 fileInfo.lastAccessTime = lastPosition.getTimeStamp(); 87 } 88 } 89 getFileInfo()90 public FileInfo getFileInfo() 91 { 92 return fileInfo; 93 } 94 addBookmark( Bookmark bm )95 synchronized public void addBookmark( Bookmark bm ) 96 { 97 if (bm.getType() == Bookmark.TYPE_LAST_POSITION) { 98 lastPosition = bm; 99 } else { 100 if (findBookmarkIndex(bm) >= 0) { 101 L.w("duplicate bookmark added " + bm.getUniqueKey()); 102 } else { 103 bookmarks.add(bm); 104 } 105 } 106 } 107 getBookmarkCount()108 synchronized public int getBookmarkCount() 109 { 110 return bookmarks.size(); 111 } 112 getBookmark( int index )113 synchronized public Bookmark getBookmark( int index ) 114 { 115 return bookmarks.get(index); 116 } 117 getAllBookmarks()118 synchronized public ArrayList<Bookmark> getAllBookmarks() 119 { 120 ArrayList<Bookmark> list = new ArrayList<Bookmark>(bookmarks.size() + 1); 121 if (lastPosition != null) 122 list.add(lastPosition); 123 list.addAll(bookmarks); 124 return list; 125 } 126 findBookmark(Bookmark bm)127 synchronized public Bookmark findBookmark(Bookmark bm) 128 { 129 if ( bm==null ) 130 return null; 131 int index = findBookmarkIndex(bm); 132 if (index < 0) 133 return null; 134 return bookmarks.get(index); 135 } 136 findBookmarkIndex(Bookmark bm)137 private int findBookmarkIndex(Bookmark bm) 138 { 139 if (bm == null) 140 return -1; 141 for ( int i=0; i<bookmarks.size(); i++ ) { 142 Bookmark item = bookmarks.get(i); 143 if (item.equalUniqueKey(bm)) 144 return i; 145 } 146 return -1; 147 } 148 syncBookmark(Bookmark bm)149 synchronized public Bookmark syncBookmark(Bookmark bm) 150 { 151 if ( bm==null ) 152 return null; 153 int index = findBookmarkIndex(bm); 154 if (index < 0) { 155 addBookmark(bm); 156 return bm; 157 } 158 Bookmark item = bookmarks.get(index); 159 if (item.getTimeStamp() >= bm.getTimeStamp()) 160 return null; 161 item.setType(bm.getType()); 162 item.setTimeStamp(bm.getTimeStamp()); 163 item.setPosText(bm.getPosText()); 164 item.setCommentText(bm.getCommentText()); 165 return item; 166 } 167 updateBookmark(Bookmark bm)168 synchronized public Bookmark updateBookmark(Bookmark bm) 169 { 170 if ( bm==null ) 171 return null; 172 int index = findBookmarkIndex(bm); 173 if ( index<0 ) { 174 Log.e("cr3", "cannot find bookmark " + bm); 175 return null; 176 } 177 Bookmark item = bookmarks.get(index); 178 item.setTimeStamp(bm.getTimeStamp()); 179 item.setPosText(bm.getPosText()); 180 item.setCommentText(bm.getCommentText()); 181 return item; 182 } removeBookmark(Bookmark bm)183 synchronized public Bookmark removeBookmark(Bookmark bm) 184 { 185 if ( bm==null ) 186 return null; 187 int index = findBookmarkIndex(bm); 188 if ( index<0 ) { 189 Log.e("cr3", "cannot find bookmark " + bm); 190 return null; 191 } 192 return bookmarks.remove(index); 193 } 194 sortBookmarks()195 synchronized public void sortBookmarks() { 196 Collections.sort(bookmarks, new Comparator<Bookmark>() { 197 @Override 198 public int compare(Bookmark bm1, Bookmark bm2) { 199 if ( bm1.getPercent() < bm2.getPercent() ) 200 return -1; 201 if ( bm1.getPercent() > bm2.getPercent() ) 202 return 1; 203 return 0; 204 } 205 }); 206 } 207 getBookmarksExportText()208 synchronized public String getBookmarksExportText() { 209 StringBuilder buf = new StringBuilder(); 210 File pathname = new File(fileInfo.getPathName()); 211 buf.append("# file name: " + pathname.getName() + "\n"); 212 buf.append("# file path: " + pathname.getParent() + "\n"); 213 buf.append("# book title: " + fileInfo.title + "\n"); 214 buf.append("# author: " + fileInfo.authors + "\n"); 215 buf.append("\n"); 216 for ( Bookmark bm : bookmarks ) { 217 if ( bm.getType()!=Bookmark.TYPE_COMMENT && bm.getType()!=Bookmark.TYPE_CORRECTION ) 218 continue; 219 int percent = bm.getPercent(); 220 String ps = String.valueOf(percent%100); 221 if ( ps.length()<2 ) 222 ps = "0" + ps; 223 ps = String.valueOf(percent/100) + "." + ps + "%"; 224 buf.append("## " + ps + " - " + (bm.getType()==Bookmark.TYPE_COMMENT ? "comment" : "correction") + "\n"); 225 if ( bm.getTitleText()!=null ) 226 buf.append("## " + bm.getTitleText() + "\n"); 227 if ( bm.getPosText()!=null ) 228 buf.append("<< " + bm.getPosText() + "\n"); 229 if ( bm.getCommentText()!=null ) 230 buf.append(">> " + bm.getCommentText() + "\n"); 231 buf.append("\n"); 232 } 233 return buf.toString(); 234 } 235 exportBookmarks( String fileName )236 synchronized public boolean exportBookmarks( String fileName ) { 237 Log.i("cr3", "Exporting bookmarks to file " + fileName); 238 try (FileOutputStream stream = new FileOutputStream(new File(fileName)); 239 OutputStreamWriter writer = new OutputStreamWriter(stream, "UTF-8")) { 240 writer.write(0xfeff); 241 writer.write("# Cool Reader 3 - exported bookmarks\r\n"); 242 File pathname = new File(fileInfo.getPathName()); 243 writer.write("# file name: " + pathname.getName() + "\r\n"); 244 writer.write("# file path: " + pathname.getParent() + "\r\n"); 245 writer.write("# book title: " + fileInfo.title + "\r\n"); 246 writer.write("# author: " + fileInfo.authors + "\r\n"); 247 writer.write("# series: " + fileInfo.series + "\r\n"); 248 writer.write("\r\n"); 249 for ( Bookmark bm : bookmarks ) { 250 if ( bm.getType()!=Bookmark.TYPE_COMMENT && bm.getType()!=Bookmark.TYPE_CORRECTION ) 251 continue; 252 int percent = bm.getPercent(); 253 String ps = String.valueOf(percent%100); 254 if ( ps.length()<2 ) 255 ps = "0" + ps; 256 ps = percent / 100 + "." + ps + "%"; 257 writer.write("## " + ps + " - " + (bm.getType()==Bookmark.TYPE_COMMENT ? "comment" : "correction") + "\r\n"); 258 if ( bm.getTitleText()!=null ) 259 writer.write("## " + bm.getTitleText() + "\r\n"); 260 if ( bm.getPosText()!=null ) 261 writer.write("<< " + bm.getPosText() + "\r\n"); 262 if ( bm.getCommentText()!=null ) 263 writer.write(">> " + bm.getCommentText() + "\r\n"); 264 writer.write("\r\n"); 265 } 266 return true; 267 } catch ( IOException e ) { 268 Log.e("cr3", "Cannot write bookmark file " + fileName); 269 return false; 270 } 271 } 272 removeBookmark( int index )273 synchronized public Bookmark removeBookmark( int index ) 274 { 275 return bookmarks.remove(index); 276 } 277 setBookmarks(ArrayList<Bookmark> list)278 synchronized public void setBookmarks(ArrayList<Bookmark> list) 279 { 280 lastPosition = null; 281 bookmarks = new ArrayList<Bookmark>(); 282 if (list == null) 283 return; 284 for (Bookmark bm : list) 285 addBookmark(bm); 286 } 287 288 @Override toString()289 public String toString() { 290 return "BookInfo [fileInfo=" + fileInfo + ", lastPosition=" 291 + lastPosition + "]"; 292 } 293 294 295 296 } 297