mirror of
https://github.com/geometer/FBReaderJ.git
synced 2025-10-05 10:49:24 +02:00
bookmarks improvements
mobipocket support (in progress) misc fixes git-svn-id: https://only.mawhrin.net/repos/FBReaderJ/trunk@967 6a642e6f-84f6-412e-ac94-c4a38d5a04b0
This commit is contained in:
parent
b346321526
commit
1f14fd2b58
57 changed files with 897 additions and 1242 deletions
|
@ -221,10 +221,14 @@
|
|||
</group>
|
||||
<group name="Unicode">
|
||||
<encoding region="Unicode" name="UTF-8">
|
||||
<code number="65001"/>
|
||||
</encoding>
|
||||
<encoding region="Unicode" name="UTF-7">
|
||||
<code number="65000"/>
|
||||
</encoding>
|
||||
<encoding region="Unicode" name="UTF-16">
|
||||
</encoding>
|
||||
<encoding region="Unicode" name="UTF-16BE">
|
||||
</encoding>
|
||||
</group>
|
||||
</known-encodings>
|
||||
|
|
|
@ -50,6 +50,7 @@
|
|||
<data android:pathPattern=".*\\.epub" />
|
||||
<data android:pathPattern=".*\\.oeb" />
|
||||
<data android:pathPattern=".*\\.fb2" />
|
||||
<data android:pathPattern=".*\\.mobi" />
|
||||
</intent-filter>
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.VIEW" />
|
||||
|
|
Binary file not shown.
Before Width: | Height: | Size: 177 B |
|
@ -12,14 +12,33 @@
|
|||
android:layout_height="fill_parent"
|
||||
android:singleLine="true"
|
||||
/>
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:minHeight="?android:attr/listPreferredItemHeight"
|
||||
android:paddingLeft="5dip"
|
||||
android:layout_marginTop="5dip"
|
||||
android:layout_marginBottom="5dip"
|
||||
android:orientation="vertical"
|
||||
android:gravity="center_vertical|left"
|
||||
>
|
||||
<TextView
|
||||
android:id="@+id/bookmark_item_text"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_marginLeft="5dip"
|
||||
android:layout_marginTop="5dip"
|
||||
android:layout_marginBottom="5dip"
|
||||
android:gravity="center_vertical|left"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_alignParentTop="true"
|
||||
android:singleLine="false"
|
||||
android:textAppearance="?android:attr/textAppearanceLarge"
|
||||
android:gravity="center_vertical|left"
|
||||
/>
|
||||
<TextView
|
||||
android:id="@+id/bookmark_item_booktitle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="7dip"
|
||||
android:layout_below="@id/bookmark_item_text"
|
||||
android:singleLine="true"
|
||||
android:textAppearance="?android:attr/textAppearanceSmall"
|
||||
/>
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
android:layout_height="wrap_content"
|
||||
android:paddingTop="5dip"
|
||||
/>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:minHeight="?android:attr/listPreferredItemHeight"
|
||||
|
|
|
@ -68,7 +68,8 @@ public class BookDownloader extends Activity {
|
|||
ourFileName = path.get(path.size() - 1);
|
||||
if (!ourFileName.endsWith(".fb2.zip") &&
|
||||
!ourFileName.endsWith(".fb2") &&
|
||||
!ourFileName.endsWith(".epub")) {
|
||||
!ourFileName.endsWith(".epub") &&
|
||||
!ourFileName.endsWith(".mobi")) {
|
||||
startNextMatchingActivity(intent);
|
||||
finish();
|
||||
return;
|
||||
|
@ -126,6 +127,10 @@ public class BookDownloader extends Activity {
|
|||
|
||||
private void runFBReader(final File file) {
|
||||
finish();
|
||||
final Activity oldActivity = org.geometerplus.android.fbreader.FBReader.Instance;
|
||||
if (oldActivity != null) {
|
||||
oldActivity.finish();
|
||||
}
|
||||
startActivity(new Intent(Intent.ACTION_VIEW, Uri.fromFile(file), this, FBReader.class));
|
||||
}
|
||||
|
||||
|
|
|
@ -28,16 +28,27 @@ import android.content.Context;
|
|||
import org.geometerplus.zlibrary.ui.android.R;
|
||||
|
||||
class SimpleContainer extends ViewGroup {
|
||||
private final View myChild;
|
||||
private final View myEditText;
|
||||
private final Button myOkButton;
|
||||
private final Button myCancelButton;
|
||||
|
||||
SimpleContainer(Context context, View child) {
|
||||
SimpleContainer(Context context) {
|
||||
super(context);
|
||||
myChild = child;
|
||||
addView(child);
|
||||
myEditText = new EditText(context);
|
||||
myOkButton = new Button(context);
|
||||
myOkButton.setText("ok");
|
||||
myCancelButton = new Button(context);
|
||||
myCancelButton.setText("cancel");
|
||||
addView(myOkButton);
|
||||
addView(myCancelButton);
|
||||
addView(myEditText);
|
||||
}
|
||||
|
||||
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
|
||||
myChild.layout(left + 5, top + 5, right - 5, bottom - 5);
|
||||
final int buttonHeight = Math.max(54, Math.max(myOkButton.getHeight(), myCancelButton.getHeight()));
|
||||
myEditText.layout(left + 8, top + 8, right - 8, bottom - buttonHeight - 16);
|
||||
myOkButton.layout(left + 8, bottom - buttonHeight - 8, (left + right) / 2 - 4, bottom - 8);
|
||||
myCancelButton.layout((left + right) / 2 + 4, bottom - buttonHeight - 8, right - 8, bottom - 8);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -46,21 +57,7 @@ public class BookmarkEditActivity extends Activity {
|
|||
public void onCreate(Bundle bundle) {
|
||||
super.onCreate(bundle);
|
||||
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
||||
final LinearLayout v = new LinearLayout(this);
|
||||
v.setOrientation(LinearLayout.VERTICAL);
|
||||
v.addView(new EditText(this));
|
||||
/*
|
||||
final LinearLayout h = new LinearLayout(this);
|
||||
v.addView(h);
|
||||
final Button okButton = new Button(this);
|
||||
okButton.setText("ok");
|
||||
h.addView(okButton);
|
||||
final Button cancelButton = new Button(this);
|
||||
cancelButton.setText("cancel");
|
||||
h.addView(cancelButton);
|
||||
*/
|
||||
final SimpleContainer container = new SimpleContainer(this, v);
|
||||
//final SimpleContainer container = new SimpleContainer(this, new EditText(this));
|
||||
final SimpleContainer container = new SimpleContainer(this);
|
||||
setContentView(container);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -74,7 +74,10 @@ public class BookmarksActivity extends TabActivity implements MenuItem.OnMenuIte
|
|||
|
||||
AllBooksBookmarks = Bookmark.bookmarks();
|
||||
Collections.sort(AllBooksBookmarks, new Bookmark.ByTimeComparator());
|
||||
final long bookId = ((FBReader)FBReader.Instance()).Model.Book.getId();
|
||||
final FBReader fbreader = (FBReader)FBReader.Instance();
|
||||
|
||||
if (fbreader.Model != null) {
|
||||
final long bookId = fbreader.Model.Book.getId();
|
||||
for (Bookmark bookmark : AllBooksBookmarks) {
|
||||
if (bookmark.getBookId() == bookId) {
|
||||
myThisBookBookmarks.add(bookmark);
|
||||
|
@ -83,6 +86,9 @@ public class BookmarksActivity extends TabActivity implements MenuItem.OnMenuIte
|
|||
|
||||
myThisBookView = createTab("thisBook", R.id.this_book);
|
||||
new BookmarksAdapter(myThisBookView, myThisBookBookmarks, true);
|
||||
} else {
|
||||
findViewById(R.id.this_book).setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
myAllBooksView = createTab("allBooks", R.id.all_books);
|
||||
new BookmarksAdapter(myAllBooksView, AllBooksBookmarks, false);
|
||||
|
@ -196,25 +202,52 @@ public class BookmarksActivity extends TabActivity implements MenuItem.OnMenuIte
|
|||
|
||||
final ZLTextPosition position = new ZLTextPosition(cursor);
|
||||
final StringBuilder builder = new StringBuilder();
|
||||
int wordCounter = 0;
|
||||
final StringBuilder sentenceBuilder = new StringBuilder();
|
||||
cursor = new ZLTextWordCursor(cursor);
|
||||
|
||||
int wordCounter = 0;
|
||||
int sentenceCounter = 0;
|
||||
int storedWordCounter = 0;
|
||||
boolean lineIsNonEmpty = false;
|
||||
mainLoop:
|
||||
do {
|
||||
for (; !cursor.isEndOfParagraph(); cursor.nextWord()) {
|
||||
while ((wordCounter < 20) && (sentenceCounter < 3)) {
|
||||
while (cursor.isEndOfParagraph()) {
|
||||
if (!cursor.nextParagraph()) {
|
||||
break mainLoop;
|
||||
}
|
||||
if (sentenceBuilder.length() > 0) {
|
||||
builder.append(sentenceBuilder);
|
||||
builder.append("\n");
|
||||
sentenceBuilder.delete(0, sentenceBuilder.length());
|
||||
++sentenceCounter;
|
||||
storedWordCounter = wordCounter;
|
||||
lineIsNonEmpty = false;
|
||||
}
|
||||
}
|
||||
final ZLTextElement element = cursor.getElement();
|
||||
if (element instanceof ZLTextWord) {
|
||||
final ZLTextWord word = (ZLTextWord)element;
|
||||
if (builder.length() > 0) {
|
||||
builder.append(" ");
|
||||
if (lineIsNonEmpty) {
|
||||
sentenceBuilder.append(" ");
|
||||
}
|
||||
builder.append(word.Data, word.Offset, word.Length);
|
||||
if (++wordCounter >= 10) {
|
||||
break mainLoop;
|
||||
sentenceBuilder.append(word.Data, word.Offset, word.Length);
|
||||
++wordCounter;
|
||||
lineIsNonEmpty = true;
|
||||
switch (word.Data[word.Offset + word.Length - 1]) {
|
||||
case '.':
|
||||
case '!':
|
||||
case '?':
|
||||
builder.append(sentenceBuilder);
|
||||
sentenceBuilder.delete(0, sentenceBuilder.length());
|
||||
++sentenceCounter;
|
||||
storedWordCounter = wordCounter;
|
||||
}
|
||||
}
|
||||
cursor.nextWord();
|
||||
}
|
||||
if (storedWordCounter < 4) {
|
||||
builder.append(sentenceBuilder);
|
||||
}
|
||||
} while ((builder.length() == 0) && cursor.nextParagraph());
|
||||
|
||||
// TODO: text edit dialog
|
||||
final Bookmark bookmark = new Bookmark(fbreader.Model.Book, builder.toString(), position);
|
||||
|
@ -227,7 +260,7 @@ mainLoop:
|
|||
bookmark.onOpen();
|
||||
final FBReader fbreader = (FBReader)FBReader.Instance();
|
||||
final long bookId = bookmark.getBookId();
|
||||
if (fbreader.Model.Book.getId() != bookId) {
|
||||
if ((fbreader.Model == null) || (fbreader.Model.Book.getId() != bookId)) {
|
||||
final Book book = Book.getById(bookId);
|
||||
if (book != null) {
|
||||
finish();
|
||||
|
@ -247,11 +280,11 @@ mainLoop:
|
|||
|
||||
private final class BookmarksAdapter extends BaseAdapter implements AdapterView.OnItemClickListener, View.OnCreateContextMenuListener {
|
||||
private final List<Bookmark> myBookmarks;
|
||||
private final boolean myShowAddBookmarkButton;
|
||||
private final boolean myCurrentBook;
|
||||
|
||||
BookmarksAdapter(ListView listView, List<Bookmark> bookmarks, boolean showAddBookmarkButton) {
|
||||
BookmarksAdapter(ListView listView, List<Bookmark> bookmarks, boolean currentBook) {
|
||||
myBookmarks = bookmarks;
|
||||
myShowAddBookmarkButton = showAddBookmarkButton;
|
||||
myCurrentBook = currentBook;
|
||||
listView.setAdapter(this);
|
||||
listView.setOnItemClickListener(this);
|
||||
listView.setOnCreateContextMenuListener(this);
|
||||
|
@ -259,11 +292,11 @@ mainLoop:
|
|||
|
||||
public void onCreateContextMenu(ContextMenu menu, View view, ContextMenu.ContextMenuInfo menuInfo) {
|
||||
final int position = ((AdapterView.AdapterContextMenuInfo)menuInfo).position;
|
||||
if (position > 0) {
|
||||
if (getItem(position) != null) {
|
||||
menu.setHeaderTitle(getItem(position).getText());
|
||||
final ZLResource resource = ZLResource.resource("bookmarksView");
|
||||
menu.add(0, OPEN_ITEM_ID, 0, resource.getResource("open").getValue());
|
||||
menu.add(0, EDIT_ITEM_ID, 0, resource.getResource("edit").getValue());
|
||||
//menu.add(0, EDIT_ITEM_ID, 0, resource.getResource("edit").getValue());
|
||||
menu.add(0, DELETE_ITEM_ID, 0, resource.getResource("delete").getValue());
|
||||
}
|
||||
}
|
||||
|
@ -271,7 +304,27 @@ mainLoop:
|
|||
public View getView(int position, View convertView, ViewGroup parent) {
|
||||
final View view = (convertView != null) ? convertView :
|
||||
LayoutInflater.from(parent.getContext()).inflate(R.layout.bookmark_item, parent, false);
|
||||
final ImageView imageView = (ImageView)view.findViewById(R.id.bookmark_item_icon);
|
||||
final TextView textView = (TextView)view.findViewById(R.id.bookmark_item_text);
|
||||
final TextView bookTitleView = (TextView)view.findViewById(R.id.bookmark_item_booktitle);
|
||||
|
||||
final Bookmark bookmark = getItem(position);
|
||||
if (bookmark == null) {
|
||||
imageView.setVisibility(View.VISIBLE);
|
||||
imageView.setImageResource(R.drawable.tree_icon_plus);
|
||||
textView.setText(ZLResource.resource("bookmarksView").getResource("new").getValue());
|
||||
bookTitleView.setVisibility(View.GONE);
|
||||
} else {
|
||||
imageView.setVisibility(View.GONE);
|
||||
textView.setText(bookmark.getText());
|
||||
if (myCurrentBook) {
|
||||
bookTitleView.setVisibility(View.GONE);
|
||||
} else {
|
||||
bookTitleView.setVisibility(View.VISIBLE);
|
||||
bookTitleView.setText(bookmark.getBookTitle());
|
||||
}
|
||||
}
|
||||
/*
|
||||
((ImageView)view.findViewById(R.id.bookmark_item_icon)).setImageResource(
|
||||
(bookmark != null) ? R.drawable.tree_icon_strut : R.drawable.tree_icon_plus
|
||||
);
|
||||
|
@ -280,6 +333,7 @@ mainLoop:
|
|||
bookmark.getText() :
|
||||
ZLResource.resource("bookmarksView").getResource("new").getValue()
|
||||
);
|
||||
*/
|
||||
return view;
|
||||
}
|
||||
|
||||
|
@ -296,14 +350,14 @@ mainLoop:
|
|||
}
|
||||
|
||||
public final Bookmark getItem(int position) {
|
||||
if (myShowAddBookmarkButton) {
|
||||
if (myCurrentBook) {
|
||||
--position;
|
||||
}
|
||||
return (position >= 0) ? myBookmarks.get(position) : null;
|
||||
}
|
||||
|
||||
public final int getCount() {
|
||||
return myShowAddBookmarkButton ? myBookmarks.size() + 1 : myBookmarks.size();
|
||||
return myCurrentBook ? myBookmarks.size() + 1 : myBookmarks.size();
|
||||
}
|
||||
|
||||
public final void onItemClick(AdapterView parent, View view, int position, long id) {
|
||||
|
|
|
@ -54,9 +54,9 @@ public class LibraryTabActivity extends TabActivity implements MenuItem.OnMenuIt
|
|||
final TabHost host = getTabHost();
|
||||
LayoutInflater.from(this).inflate(R.layout.library, host.getTabContentView(), true);
|
||||
|
||||
new LibraryAdapter(createTab("byAuthor", R.id.by_author), Library.Instance().byAuthor());
|
||||
new LibraryAdapter(createTab("byTag", R.id.by_tag), Library.Instance().byTag());
|
||||
new LibraryAdapter(createTab("recent", R.id.recent), Library.Instance().recentBooks());
|
||||
new LibraryAdapter(createTab("byAuthor", R.id.by_author), Library.Instance().byAuthor(), false);
|
||||
new LibraryAdapter(createTab("byTag", R.id.by_tag), Library.Instance().byTag(), false);
|
||||
new LibraryAdapter(createTab("recent", R.id.recent), Library.Instance().recentBooks(), true);
|
||||
findViewById(R.id.search_results).setVisibility(View.GONE);
|
||||
|
||||
host.setCurrentTabByTag(mySelectedTabOption.getValue());
|
||||
|
@ -66,7 +66,7 @@ public class LibraryTabActivity extends TabActivity implements MenuItem.OnMenuIt
|
|||
void showSearchResultsTab(LibraryTree tree) {
|
||||
if (mySearchResultsAdapter == null) {
|
||||
mySearchResultsAdapter =
|
||||
new LibraryAdapter(createTab("searchResults", R.id.search_results), tree);
|
||||
new LibraryAdapter(createTab("searchResults", R.id.search_results), tree, true);
|
||||
} else {
|
||||
mySearchResultsAdapter.resetTree(tree);
|
||||
}
|
||||
|
@ -125,17 +125,24 @@ public class LibraryTabActivity extends TabActivity implements MenuItem.OnMenuIt
|
|||
|
||||
private final class LibraryAdapter extends ZLTreeAdapter {
|
||||
private final LibraryTree myLibraryTree;
|
||||
private final boolean myIsFlat;
|
||||
|
||||
LibraryAdapter(ListView view, LibraryTree tree) {
|
||||
LibraryAdapter(ListView view, LibraryTree tree, boolean isFlat) {
|
||||
super(view, tree);
|
||||
myLibraryTree = tree;
|
||||
myIsFlat = isFlat;
|
||||
}
|
||||
|
||||
public View getView(int position, View convertView, ViewGroup parent) {
|
||||
final View view = (convertView != null) ? convertView :
|
||||
LayoutInflater.from(parent.getContext()).inflate(R.layout.library_tree_item, parent, false);
|
||||
final LibraryTree tree = (LibraryTree)getItem(position);
|
||||
setIcon((ImageView)view.findViewById(R.id.library_tree_item_icon), tree);
|
||||
final ImageView iconView = (ImageView)view.findViewById(R.id.library_tree_item_icon);
|
||||
if (myIsFlat) {
|
||||
iconView.setVisibility(View.GONE);
|
||||
} else {
|
||||
setIcon(iconView, tree);
|
||||
}
|
||||
((TextView)view.findViewById(R.id.library_tree_item_name)).setText(tree.getName());
|
||||
((TextView)view.findViewById(R.id.library_tree_item_childrenlist)).setText(tree.getSecondString());
|
||||
return view;
|
||||
|
@ -147,7 +154,10 @@ public class LibraryTabActivity extends TabActivity implements MenuItem.OnMenuIt
|
|||
}
|
||||
finish();
|
||||
final FBReader fbreader = (FBReader)FBReader.Instance();
|
||||
fbreader.openBook(((BookTree)tree).Book, null);
|
||||
final Book book = ((BookTree)tree).Book;
|
||||
if ((fbreader.Model == null) || (fbreader.Model.Book.getId() != book.getId())) {
|
||||
fbreader.openBook(book, null);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,6 +30,8 @@ import android.database.Cursor;
|
|||
import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
||||
import org.geometerplus.zlibrary.core.dialogs.ZLDialogManager;
|
||||
import org.geometerplus.zlibrary.core.options.ZLStringOption;
|
||||
import org.geometerplus.zlibrary.core.options.ZLIntegerOption;
|
||||
import org.geometerplus.zlibrary.core.config.ZLConfig;
|
||||
import org.geometerplus.zlibrary.text.view.ZLTextPosition;
|
||||
import org.geometerplus.zlibrary.ui.android.library.ZLAndroidApplication;
|
||||
|
||||
|
@ -43,6 +45,16 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
migrate();
|
||||
}
|
||||
|
||||
protected void executeAsATransaction(Runnable actions) {
|
||||
myDatabase.beginTransaction();
|
||||
try {
|
||||
actions.run();
|
||||
myDatabase.setTransactionSuccessful();
|
||||
} finally {
|
||||
myDatabase.endTransaction();
|
||||
}
|
||||
}
|
||||
|
||||
private void migrate() {
|
||||
final int version = myDatabase.getVersion();
|
||||
if (version >= 6) {
|
||||
|
@ -77,16 +89,6 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
});
|
||||
}
|
||||
|
||||
protected void executeAsATransaction(Runnable actions) {
|
||||
myDatabase.beginTransaction();
|
||||
try {
|
||||
actions.run();
|
||||
myDatabase.setTransactionSuccessful();
|
||||
} finally {
|
||||
myDatabase.endTransaction();
|
||||
}
|
||||
}
|
||||
|
||||
private static void bindString(SQLiteStatement statement, int index, String value) {
|
||||
if (value != null) {
|
||||
statement.bindString(index, value);
|
||||
|
@ -484,6 +486,7 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
myDatabase.delete("BookSeries", myBookIdWhereClause, parameters);
|
||||
myDatabase.delete("BookTag", myBookIdWhereClause, parameters);
|
||||
myDatabase.delete("Bookmarks", myBookIdWhereClause, parameters);
|
||||
myDatabase.delete("BookState", myBookIdWhereClause, parameters);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
@ -631,20 +634,21 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
protected List<Bookmark> listBookmarks(long bookId) {
|
||||
LinkedList<Bookmark> list = new LinkedList<Bookmark>();
|
||||
Cursor cursor = myDatabase.rawQuery(
|
||||
"SELECT bookmark_id,book_id,bookmark_text,creation_time,modification_time,access_time,access_counter,paragraph,word,char FROM Bookmarks WHERE book_id = ?", new String[] { "" + bookId }
|
||||
"SELECT Bookmarks.bookmark_id,Bookmarks.book_id,Books.title,Bookmarks.bookmark_text,Bookmarks.creation_time,Bookmarks.modification_time,Bookmarks.access_time,Bookmarks.access_counter,Bookmarks.paragraph,Bookmarks.word,Bookmarks.char FROM Bookmarks INNER JOIN Books ON Books.book_id = Bookmarks.book_id WHERE book_id = ?", new String[] { "" + bookId }
|
||||
);
|
||||
while (cursor.moveToNext()) {
|
||||
list.add(createBookmark(
|
||||
cursor.getLong(0),
|
||||
cursor.getLong(1),
|
||||
cursor.getString(2),
|
||||
getDate(cursor, 3),
|
||||
cursor.getString(3),
|
||||
getDate(cursor, 4),
|
||||
getDate(cursor, 5),
|
||||
(int)cursor.getLong(6),
|
||||
getDate(cursor, 6),
|
||||
(int)cursor.getLong(7),
|
||||
(int)cursor.getLong(8),
|
||||
(int)cursor.getLong(9)
|
||||
(int)cursor.getLong(9),
|
||||
(int)cursor.getLong(10)
|
||||
));
|
||||
}
|
||||
cursor.close();
|
||||
|
@ -653,21 +657,23 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
|
||||
protected List<Bookmark> listAllBookmarks() {
|
||||
LinkedList<Bookmark> list = new LinkedList<Bookmark>();
|
||||
myDatabase.execSQL("DELETE FROM Bookmarks WHERE book_id = -1");
|
||||
Cursor cursor = myDatabase.rawQuery(
|
||||
"SELECT bookmark_id,book_id,bookmark_text,creation_time,modification_time,access_time,access_counter,paragraph,word,char FROM Bookmarks", null
|
||||
"SELECT Bookmarks.bookmark_id,Bookmarks.book_id,Books.title,Bookmarks.bookmark_text,Bookmarks.creation_time,Bookmarks.modification_time,Bookmarks.access_time,Bookmarks.access_counter,Bookmarks.paragraph,Bookmarks.word,Bookmarks.char FROM Bookmarks INNER JOIN Books ON Books.book_id = Bookmarks.book_id", null
|
||||
);
|
||||
while (cursor.moveToNext()) {
|
||||
list.add(createBookmark(
|
||||
cursor.getLong(0),
|
||||
cursor.getLong(1),
|
||||
cursor.getString(2),
|
||||
getDate(cursor, 3),
|
||||
cursor.getString(3),
|
||||
getDate(cursor, 4),
|
||||
getDate(cursor, 5),
|
||||
(int)cursor.getLong(6),
|
||||
getDate(cursor, 6),
|
||||
(int)cursor.getLong(7),
|
||||
(int)cursor.getLong(8),
|
||||
(int)cursor.getLong(9)
|
||||
(int)cursor.getLong(9),
|
||||
(int)cursor.getLong(10)
|
||||
));
|
||||
}
|
||||
cursor.close();
|
||||
|
@ -726,6 +732,32 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
myDeleteBookmarkStatement.execute();
|
||||
}
|
||||
|
||||
protected ZLTextPosition getStoredPosition(long bookId) {
|
||||
ZLTextPosition position = null;
|
||||
Cursor cursor = myDatabase.rawQuery(
|
||||
"SELECT paragraph,word,char FROM BookState WHERE book_id = " + bookId, null
|
||||
);
|
||||
if (cursor.moveToNext()) {
|
||||
position = new ZLTextPosition((int)cursor.getLong(0), (int)cursor.getLong(1), (int)cursor.getLong(2));
|
||||
}
|
||||
cursor.close();
|
||||
return position;
|
||||
}
|
||||
|
||||
private SQLiteStatement myStorePositionStatement;
|
||||
protected void storePosition(long bookId, ZLTextPosition position) {
|
||||
if (myStorePositionStatement == null) {
|
||||
myStorePositionStatement = myDatabase.compileStatement(
|
||||
"INSERT OR REPLACE INTO BookState (book_id,paragraph,word,char) VALUES (?,?,?,?)"
|
||||
);
|
||||
}
|
||||
myStorePositionStatement.bindLong(1, bookId);
|
||||
myStorePositionStatement.bindLong(2, position.ParagraphIndex);
|
||||
myStorePositionStatement.bindLong(3, position.WordIndex);
|
||||
myStorePositionStatement.bindLong(4, position.CharIndex);
|
||||
myStorePositionStatement.execute();
|
||||
}
|
||||
|
||||
private void createTables() {
|
||||
myDatabase.execSQL(
|
||||
"CREATE TABLE Books(" +
|
||||
|
@ -848,6 +880,34 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
|||
"paragraph INTEGER NOT NULL," +
|
||||
"word INTEGER NOT NULL," +
|
||||
"char INTEGER NOT NULL)");
|
||||
|
||||
myDatabase.execSQL(
|
||||
"CREATE TABLE BookState(" +
|
||||
"book_id INTEGER UNIQUE NOT NULL REFERENCES Books(book_id)," +
|
||||
"paragraph INTEGER NOT NULL," +
|
||||
"word INTEGER NOT NULL," +
|
||||
"char INTEGER NOT NULL)");
|
||||
Cursor cursor = myDatabase.rawQuery(
|
||||
"SELECT book_id,file_name FROM Books", null
|
||||
);
|
||||
final SQLiteStatement statement = myDatabase.compileStatement("INSERT INTO BookState (book_id,paragraph,word,char) VALUES (?,?,?,?)");
|
||||
while (cursor.moveToNext()) {
|
||||
final long bookId = cursor.getLong(0);
|
||||
final String fileName = cursor.getString(1);
|
||||
final int position = new ZLIntegerOption(fileName, "PositionInBuffer", 0).getValue();
|
||||
final int paragraph = new ZLIntegerOption(fileName, "Paragraph_" + position, 0).getValue();
|
||||
final int word = new ZLIntegerOption(fileName, "Word_" + position, 0).getValue();
|
||||
final int chr = new ZLIntegerOption(fileName, "Char_" + position, 0).getValue();
|
||||
if ((paragraph != 0) || (word != 0) || (chr != 0)) {
|
||||
statement.bindLong(1, bookId);
|
||||
statement.bindLong(2, paragraph);
|
||||
statement.bindLong(3, word);
|
||||
statement.bindLong(4, chr);
|
||||
statement.execute();
|
||||
}
|
||||
ZLConfig.Instance().removeGroup(fileName);
|
||||
}
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
private void updateTables6() {
|
||||
|
|
|
@ -70,23 +70,11 @@ public final class ZLSQLiteConfig extends ZLConfig {
|
|||
myUnsetValueStatement = myDatabase.compileStatement("DELETE FROM config WHERE groupName = ? AND name = ?");
|
||||
myDeleteGroupStatement = myDatabase.compileStatement("DELETE FROM config WHERE groupName = ?");
|
||||
|
||||
/*
|
||||
final Cursor cursor = myDatabase.rawQuery("SELECT name FROM config WHERE groupName LIKE ? GROUP BY name", new String[] { "/%" });
|
||||
while (cursor.moveToNext()) {
|
||||
System.err.println(" = " + cursor.getString(0));
|
||||
}
|
||||
cursor.close();
|
||||
*/
|
||||
}
|
||||
|
||||
synchronized public void executeAsATransaction(Runnable actions) {
|
||||
myDatabase.beginTransaction();
|
||||
try {
|
||||
actions.run();
|
||||
myDatabase.setTransactionSuccessful();
|
||||
} finally {
|
||||
myDatabase.endTransaction();
|
||||
}
|
||||
}
|
||||
|
||||
synchronized public void removeGroup(String name) {
|
||||
|
|
|
@ -23,6 +23,7 @@ import java.io.*;
|
|||
|
||||
import android.app.Application;
|
||||
import android.content.res.Resources;
|
||||
import android.content.res.AssetFileDescriptor;
|
||||
import android.content.Intent;
|
||||
import android.net.Uri;
|
||||
|
||||
|
@ -97,12 +98,36 @@ public final class ZLAndroidLibrary extends ZLibrary {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean exists() {
|
||||
return myExists;
|
||||
}
|
||||
|
||||
public InputStream getInputStream() {
|
||||
return myExists ? myApplication.getResources().openRawResource(myResourceId) : null;
|
||||
@Override
|
||||
public long size() {
|
||||
try {
|
||||
AssetFileDescriptor descriptor =
|
||||
myApplication.getResources().openRawResourceFd(myResourceId);
|
||||
long length = descriptor.getLength();
|
||||
descriptor.close();
|
||||
return length;
|
||||
} catch (IOException e) {
|
||||
return 0;
|
||||
} catch (Resources.NotFoundException e) {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream getInputStream() throws IOException {
|
||||
if (!myExists) {
|
||||
throw new IOException("No such file: " + getPath());
|
||||
}
|
||||
try {
|
||||
return myApplication.getResources().openRawResource(myResourceId);
|
||||
} catch (Resources.NotFoundException e) {
|
||||
throw new IOException(e.getMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -144,7 +144,7 @@ public final class ZipFile {
|
|||
return createZipInputStream(header);
|
||||
}
|
||||
if (myAllFilesAreRead) {
|
||||
return null;
|
||||
throw new ZipException("Entry " + entryName + " is not found");
|
||||
}
|
||||
}
|
||||
// ready to read file header
|
||||
|
@ -165,14 +165,11 @@ public final class ZipFile {
|
|||
} while (!readFileHeader(baseStream, entryName));
|
||||
LocalFileHeader header = myFileHeaders.get(entryName);
|
||||
if (header != null) {
|
||||
try {
|
||||
return createZipInputStream(header);
|
||||
} catch (ZipException e) {
|
||||
}
|
||||
}
|
||||
} finally {
|
||||
storeBaseStream(baseStream);
|
||||
}
|
||||
return null;
|
||||
throw new ZipException("Entry " + entryName + " is not found");
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,6 +30,18 @@ import org.geometerplus.fbreader.library.Book;
|
|||
import org.geometerplus.fbreader.formats.*;
|
||||
|
||||
public final class BookModel {
|
||||
public static BookModel createModel(Book book) {
|
||||
FormatPlugin plugin = PluginCollection.instance().getPlugin(book.File);
|
||||
if (plugin == null) {
|
||||
return null;
|
||||
}
|
||||
BookModel model = new BookModel(book);
|
||||
if (plugin.readModel(model)) {
|
||||
return model;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public final Book Book;
|
||||
public final ZLTextPlainModel BookTextModel = new ZLTextPlainModel(65536, "/sdcard/Books/.FBReader", "cache");
|
||||
public final TOCTree TOCTree = new TOCTree();
|
||||
|
@ -49,12 +61,8 @@ public final class BookModel {
|
|||
}
|
||||
}
|
||||
|
||||
public BookModel(final Book book) {
|
||||
private BookModel(Book book) {
|
||||
Book = book;
|
||||
FormatPlugin plugin = PluginCollection.instance().getPlugin(book.File);
|
||||
if (plugin != null) {
|
||||
plugin.readModel(this);
|
||||
}
|
||||
}
|
||||
|
||||
ZLTextPlainModel getFootnoteModel(String id) {
|
||||
|
|
|
@ -1,56 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
|
||||
public class DummyEncodingConverterProvider extends ZLEncodingConverterProvider {
|
||||
|
||||
public ZLEncodingConverter createConverter() {
|
||||
return new DummyEncodingConverter();
|
||||
}
|
||||
|
||||
public ZLEncodingConverter createConverter(String encoding) {
|
||||
return createConverter();
|
||||
}
|
||||
|
||||
public boolean providesConverter(String encoding) {
|
||||
final String lowerCasedEncoding = encoding.toLowerCase();
|
||||
return ("utf-8".equals(lowerCasedEncoding)) || ("us-ascii".equals(lowerCasedEncoding));
|
||||
}
|
||||
|
||||
private static class DummyEncodingConverter extends ZLEncodingConverter {
|
||||
|
||||
private DummyEncodingConverter() {}
|
||||
|
||||
public boolean fillTable(int[] map) {
|
||||
for (int i = 0; i < 255; ++i) {
|
||||
map[i] = i;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
public void reset() {}
|
||||
|
||||
//size=end-start
|
||||
public String convert(char [] src, int start, int end) {
|
||||
return new String(src, start, end - start);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -1,169 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
|
||||
import org.geometerplus.zlibrary.core.config.ZLConfig;
|
||||
import org.geometerplus.zlibrary.core.filesystem.ZLResourceFile;
|
||||
import org.geometerplus.zlibrary.core.library.ZLibrary;
|
||||
import org.geometerplus.zlibrary.core.options.ZLBooleanOption;
|
||||
import org.geometerplus.zlibrary.core.xml.ZLStringMap;
|
||||
import org.geometerplus.zlibrary.core.xml.ZLXMLReaderAdapter;
|
||||
|
||||
public class ZLEncodingCollection {
|
||||
private static ZLEncodingCollection ourInstance;
|
||||
|
||||
private final ArrayList/*<ZLEncodingSet>*/ mySets = new ArrayList();
|
||||
private final HashMap/*<String,ZLEncodingConverterInfo>*/ myInfosByName = new HashMap();
|
||||
private final ArrayList/*<ZLEncodingConverterProvider>*/ myProviders = new ArrayList();
|
||||
|
||||
private ZLEncodingCollection() {
|
||||
registerProvider(new DummyEncodingConverterProvider());
|
||||
// registerProvider(new MyEncodingConverterProvider());
|
||||
}
|
||||
|
||||
public static ZLEncodingCollection instance() {
|
||||
if (ourInstance == null) {
|
||||
ourInstance = new ZLEncodingCollection();
|
||||
}
|
||||
return ourInstance;
|
||||
}
|
||||
|
||||
public static ZLResourceFile encodingDescriptionFile() {
|
||||
return ZLResourceFile.createResourceFile("data/encodings/Encodings.xml");
|
||||
}
|
||||
|
||||
public ArrayList<ZLEncodingSet> sets() {
|
||||
init();
|
||||
return mySets;
|
||||
}
|
||||
public ZLEncodingConverterInfo info(String name) {
|
||||
init();
|
||||
String lowerCaseName = name.toLowerCase();
|
||||
if (lowerCaseName == "iso-8859-1") {
|
||||
lowerCaseName = "windows-1252";
|
||||
}
|
||||
return (ZLEncodingConverterInfo)myInfosByName.get(lowerCaseName);
|
||||
}
|
||||
|
||||
public ZLEncodingConverterInfo info(int code) {
|
||||
String name = "" + code;
|
||||
return info(name);
|
||||
}
|
||||
|
||||
public ZLEncodingConverter defaultConverter() {
|
||||
return new DummyEncodingConverterProvider().createConverter();
|
||||
}
|
||||
public void registerProvider(ZLEncodingConverterProvider provider) {
|
||||
myProviders.add(provider);
|
||||
}
|
||||
|
||||
// private void addInfo(ZLEncodingConverterInfo info) {}
|
||||
|
||||
ArrayList/*<ZLEncodingConverterProvider>*/ providers() {
|
||||
return myProviders;
|
||||
}
|
||||
|
||||
private void init() {
|
||||
if (mySets.isEmpty()) {
|
||||
// String prefix = encodingDescriptionPath() + File.separator;
|
||||
// System.out.println("trying to read " + prefix + "Encodings.xml");
|
||||
new ZLEncodingCollectionReader(this).read(encodingDescriptionFile());
|
||||
}
|
||||
}
|
||||
|
||||
private static class ZLEncodingCollectionReader extends ZLXMLReaderAdapter {
|
||||
private final ZLEncodingCollection myCollection;
|
||||
private ZLEncodingSet myCurrentSet;
|
||||
private ZLEncodingConverterInfo myCurrentInfo;
|
||||
private final ArrayList/*<String>*/ myNames = new ArrayList();
|
||||
|
||||
private static final String GROUP = "group";
|
||||
private static final String ENCODING = "encoding";
|
||||
private static final String NAME = "name";
|
||||
private static final String REGION = "region";
|
||||
private static final String ALIAS = "alias";
|
||||
private static final String CODE = "code";
|
||||
private static final String NUMBER = "number";
|
||||
|
||||
public ZLEncodingCollectionReader(ZLEncodingCollection collection) {
|
||||
myCollection = collection;
|
||||
}
|
||||
|
||||
public boolean dontCacheAttributeValues() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean endElementHandler(String tag) {
|
||||
if (myCurrentInfo != null && (ENCODING.equals(tag))) {
|
||||
if (myCurrentInfo.canCreateConverter()) {
|
||||
myCurrentSet.addInfo(myCurrentInfo);
|
||||
final int size = myNames.size();
|
||||
for (int i = 0; i < size; i++) {
|
||||
myCollection.myInfosByName.put(((String) myNames.get(i)).toLowerCase(), myCurrentInfo);
|
||||
}
|
||||
}
|
||||
myCurrentInfo = null;
|
||||
myNames.clear();
|
||||
} else if (myCurrentSet != null && (GROUP.equals(tag))) {
|
||||
if (!myCurrentSet.infos().isEmpty()) {
|
||||
myCollection.mySets.add(myCurrentSet);
|
||||
}
|
||||
myCurrentSet = null;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean startElementHandler(String tag, ZLStringMap attributes) {
|
||||
if (GROUP.equals(tag)) {
|
||||
final String name = attributes.getValue(NAME);
|
||||
if (name != null) {
|
||||
myCurrentSet = new ZLEncodingSet(name);
|
||||
}
|
||||
} else if (myCurrentSet != null) {
|
||||
if (ENCODING.equals(tag)) {
|
||||
final String name = attributes.getValue(NAME);
|
||||
final String region = attributes.getValue(REGION);
|
||||
if ((name != null) && (region != null)) {
|
||||
final String sName = name;
|
||||
myCurrentInfo = new ZLEncodingConverterInfo(sName, region);
|
||||
myNames.add(sName);
|
||||
}
|
||||
} else if (myCurrentInfo != null) {
|
||||
String name = null;
|
||||
if (CODE.equals(tag)) {
|
||||
name = attributes.getValue(NUMBER);
|
||||
} else if (ALIAS.equals(tag)) {
|
||||
name = attributes.getValue(NAME);
|
||||
}
|
||||
if (name != null) {
|
||||
final String sName = name;
|
||||
myCurrentInfo.addAlias(sName);
|
||||
myNames.add(sName);
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,33 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
|
||||
public abstract class ZLEncodingConverter {
|
||||
protected ZLEncodingConverter() {}
|
||||
|
||||
//abstract public void convert(String dst, const char *srcStart, const char *srcEnd);
|
||||
abstract public String convert(char [] src, int start, int end);
|
||||
//convert(dst, src.toCharArray(), src.data() + src.length());
|
||||
public abstract void reset();
|
||||
public abstract boolean fillTable(int[] map);
|
||||
|
||||
//private ZLEncodingConverter(ZLEncodingConverter zl);
|
||||
//private ZLEncodingConverter &operator=(ZLEncodingConverter zl);
|
||||
}
|
|
@ -1,79 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
|
||||
public class ZLEncodingConverterInfo {
|
||||
private String myName = "";
|
||||
private String myVisibleName = "";
|
||||
private ArrayList/*<String>*/ myAliases = new ArrayList();
|
||||
|
||||
public ZLEncodingConverterInfo(String name, String region) {
|
||||
myName = name;
|
||||
myVisibleName = region + " (" + name + ")";
|
||||
addAlias(myName);
|
||||
}
|
||||
|
||||
public void addAlias(String alias) {
|
||||
myAliases.add(alias);
|
||||
}
|
||||
|
||||
public String name() {
|
||||
return myName;
|
||||
}
|
||||
|
||||
public String visibleName() {
|
||||
return myVisibleName;
|
||||
}
|
||||
|
||||
public ZLEncodingConverter createConverter() {
|
||||
ZLEncodingCollection collection = ZLEncodingCollection.instance();
|
||||
ArrayList<ZLEncodingConverterProvider> providers = collection.providers();
|
||||
for (Iterator it = providers.iterator(); it.hasNext(); ) {
|
||||
for (Iterator jt = myAliases.iterator(); jt.hasNext(); ) {
|
||||
ZLEncodingConverterProvider itp = (ZLEncodingConverterProvider)it.next();
|
||||
String str = (String)jt.next();
|
||||
if (itp.providesConverter(str)) {
|
||||
return itp.createConverter(str);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ZLEncodingCollection.instance().defaultConverter();
|
||||
}
|
||||
|
||||
public boolean canCreateConverter() {
|
||||
ZLEncodingCollection collection = ZLEncodingCollection.instance();
|
||||
ArrayList<ZLEncodingConverterProvider> providers = collection.providers();
|
||||
for (Iterator it = providers.iterator(); it.hasNext();) {
|
||||
final ZLEncodingConverterProvider privider = (ZLEncodingConverterProvider)it.next();
|
||||
for (Iterator jt = myAliases.iterator(); jt.hasNext(); ) {
|
||||
if (privider.providesConverter((String)jt.next())) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
//private ZLEncodingConverterInfo(const ZLEncodingConverterInfo&);
|
||||
//private ZLEncodingConverterInfo &operator=(const ZLEncodingConverterInfo&);
|
||||
}
|
|
@ -1,28 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
|
||||
public abstract class ZLEncodingConverterProvider {
|
||||
protected ZLEncodingConverterProvider() {
|
||||
}
|
||||
|
||||
public abstract boolean providesConverter(String encoding);
|
||||
public abstract ZLEncodingConverter createConverter(String encoding);
|
||||
}
|
|
@ -1,43 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
public class ZLEncodingSet {
|
||||
private String myName = "";
|
||||
private ArrayList/*<ZLEncodingConverterInfo>*/ myInfos = new ArrayList();
|
||||
|
||||
public ZLEncodingSet(String name) {
|
||||
|
||||
}
|
||||
|
||||
public void addInfo(ZLEncodingConverterInfo info) {
|
||||
myInfos.add(info);
|
||||
}
|
||||
|
||||
public String name() {
|
||||
return myName;
|
||||
}
|
||||
|
||||
public ArrayList/*<ZLEncodingConverterInfo>*/ infos() {
|
||||
return myInfos;
|
||||
}
|
||||
}
|
|
@ -1,107 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encodingOption;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingCollection;
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingConverterInfo;
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingSet;
|
||||
import org.geometerplus.zlibrary.core.options.ZLStringOption;
|
||||
import org.geometerplus.zlibrary.core.util.*;
|
||||
|
||||
import org.geometerplus.zlibrary.core.dialogs.ZLComboOptionEntry;
|
||||
|
||||
public class EncodingEntry extends ZLComboOptionEntry {
|
||||
private static final String AUTO = "auto";
|
||||
private static ArrayList/*<String>*/ AUTO_ENCODING;
|
||||
final ArrayList/*<std::string>*/ mySetNames = new ArrayList();
|
||||
private final HashMap/*<String, ArrayList<String>>*/ myValues = new HashMap();
|
||||
private final HashMap/*<String,String>*/ myInitialValues = new HashMap();
|
||||
private final HashMap/*<String,String>*/ myValueByName = new HashMap();
|
||||
private ZLStringOption myEncodingOption;
|
||||
String myInitialSetName = "";
|
||||
|
||||
public EncodingEntry(ZLStringOption encodingOption) {
|
||||
myEncodingOption = encodingOption;
|
||||
final String value = myEncodingOption.getValue();
|
||||
if (AUTO.equals(value)) {
|
||||
myInitialSetName = value;
|
||||
myInitialValues.put(value, value);
|
||||
setActive(false);
|
||||
return;
|
||||
}
|
||||
|
||||
final ArrayList/*<ZLEncodingSet>*/ sets = ZLEncodingCollection.instance().sets();
|
||||
|
||||
System.out.println("sets size = " + sets.size());
|
||||
|
||||
for (int i = 0; i < sets.size(); i++) {
|
||||
ZLEncodingSet es = (ZLEncodingSet) sets.get(i);
|
||||
final ArrayList/*<ZLEncodingConverterInfo>*/ infos = es.infos();
|
||||
// System.out.println(es.name());
|
||||
mySetNames.add(es.name());
|
||||
ArrayList/*<String>*/ names = new ArrayList();
|
||||
for (int j = 0; j < infos.size(); j++) {
|
||||
ZLEncodingConverterInfo eci = (ZLEncodingConverterInfo) infos.get(j);
|
||||
if (eci.name().equals(value)) {
|
||||
myInitialSetName = es.name();
|
||||
myInitialValues.put(myInitialSetName, eci.visibleName());
|
||||
}
|
||||
names.add(eci.visibleName());
|
||||
myValueByName.put(eci.visibleName(), eci.name());
|
||||
}
|
||||
myValues.put(es.name(), names);
|
||||
}
|
||||
//TODO:
|
||||
if (myInitialSetName.length() == 0 && !mySetNames.isEmpty()) {
|
||||
myInitialSetName = (String) mySetNames.get(0);
|
||||
}
|
||||
}
|
||||
|
||||
public ArrayList getValues() {
|
||||
if (AUTO.equals(initialValue())) {
|
||||
if (AUTO_ENCODING == null) {
|
||||
AUTO_ENCODING = new ArrayList();
|
||||
AUTO_ENCODING.add(AUTO);
|
||||
}
|
||||
return AUTO_ENCODING;
|
||||
}
|
||||
return (ArrayList) myValues.get(myInitialSetName);
|
||||
}
|
||||
|
||||
public String initialValue() {
|
||||
if ( myInitialValues.get(myInitialSetName) == null) {
|
||||
myInitialValues.put(myInitialSetName, ((ArrayList) myValues.get(myInitialSetName)).get(0));
|
||||
}
|
||||
return (String) myInitialValues.get(myInitialSetName);
|
||||
}
|
||||
|
||||
public void onAccept(String value) {
|
||||
if (!AUTO.equals(initialValue())) {
|
||||
myEncodingOption.setValue((String) myValueByName.get(value));
|
||||
}
|
||||
}
|
||||
|
||||
public void onValueSelected(int index) {
|
||||
myInitialValues.put(myInitialSetName, getValues().get(index));
|
||||
}
|
||||
}
|
|
@ -1,47 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encodingOption;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.geometerplus.zlibrary.core.dialogs.ZLComboOptionEntry;
|
||||
|
||||
public class EncodingSetEntry extends ZLComboOptionEntry {
|
||||
private EncodingEntry myEncodingEntry;
|
||||
|
||||
public EncodingSetEntry(EncodingEntry encodingEntry) {
|
||||
myEncodingEntry = encodingEntry;
|
||||
}
|
||||
|
||||
public ArrayList getValues() {
|
||||
return myEncodingEntry.mySetNames;
|
||||
}
|
||||
|
||||
public String initialValue() {
|
||||
return myEncodingEntry.myInitialSetName;
|
||||
}
|
||||
|
||||
public void onAccept(String value) {}
|
||||
|
||||
public void onValueSelected(int index) {
|
||||
myEncodingEntry.myInitialSetName = (String) getValues().get(index);
|
||||
myEncodingEntry.resetView();
|
||||
}
|
||||
}
|
|
@ -24,8 +24,6 @@ public interface ActionCode {
|
|||
String SHOW_OPTIONS = "preferences-old";
|
||||
String SHOW_PREFERENCES = "preferences";
|
||||
String SHOW_BOOK_INFO = "bookInfo";
|
||||
String UNDO = "undo";
|
||||
String REDO = "redo";
|
||||
String SHOW_CONTENTS = "toc";
|
||||
String SHOW_BOOKMARKS = "bookmarks";
|
||||
String SEARCH = "search";
|
||||
|
|
|
@ -28,6 +28,10 @@ class BookInfoAction extends FBAction {
|
|||
super(fbreader);
|
||||
}
|
||||
|
||||
public boolean isVisible() {
|
||||
return Reader.Model != null;
|
||||
}
|
||||
|
||||
public void run() {
|
||||
final ZLAndroidDialogManager dialogManager =
|
||||
(ZLAndroidDialogManager)ZLAndroidDialogManager.Instance();
|
||||
|
|
|
@ -33,63 +33,10 @@ import org.geometerplus.zlibrary.text.view.ZLTextPosition;
|
|||
import org.geometerplus.zlibrary.text.view.impl.*;
|
||||
|
||||
public class BookTextView extends FBView {
|
||||
private static final String BUFFER_SIZE = "UndoBufferSize";
|
||||
private static final String POSITION_IN_BUFFER = "PositionInBuffer";
|
||||
private static final String PARAGRAPH_PREFIX = "Paragraph_";
|
||||
private static final String WORD_PREFIX = "Word_";
|
||||
private static final String CHAR_PREFIX = "Char_";
|
||||
// private static final String MODEL_PREFIX = "Model_";
|
||||
|
||||
private static final int MAX_UNDO_STACK_SIZE = 20;
|
||||
|
||||
private ZLIntegerOption myParagraphIndexOption;
|
||||
private ZLIntegerOption myWordIndexOption;
|
||||
private ZLIntegerOption myCharIndexOption;
|
||||
|
||||
private ArrayList<ZLTextPosition> myPositionStack = new ArrayList<ZLTextPosition>();
|
||||
private int myCurrentPointInStack;
|
||||
|
||||
private String myFileName;
|
||||
|
||||
BookTextView(ZLPaintContext context) {
|
||||
super(context);
|
||||
}
|
||||
|
||||
public void setModel(ZLTextModel model, String fileName) {
|
||||
super.setModel(model);
|
||||
|
||||
myFileName = fileName;
|
||||
|
||||
myPositionStack.clear();
|
||||
|
||||
final int stackSize = new ZLIntegerRangeOption(fileName, BUFFER_SIZE, 0, MAX_UNDO_STACK_SIZE, 0).getValue();
|
||||
myCurrentPointInStack = new ZLIntegerRangeOption(fileName, POSITION_IN_BUFFER, 0, (stackSize == 0) ? 0 : (stackSize - 1), 0).getValue();
|
||||
|
||||
if (model != null) {
|
||||
final ZLIntegerOption option = new ZLIntegerOption(fileName, "", 0);
|
||||
for (int i = 0; i < stackSize; ++i) {
|
||||
option.changeName(PARAGRAPH_PREFIX + i);
|
||||
int paragraphIndex = option.getValue();
|
||||
option.changeName(WORD_PREFIX + i);
|
||||
final int wordIndex = option.getValue();
|
||||
option.changeName(CHAR_PREFIX + i);
|
||||
final int charIndex = option.getValue();
|
||||
myPositionStack.add(new ZLTextPosition(paragraphIndex, wordIndex, charIndex));
|
||||
}
|
||||
if (!myPositionStack.isEmpty()) {
|
||||
gotoPosition(myPositionStack.get(myCurrentPointInStack));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected void onPaintInfoPrepared() {
|
||||
if (myPositionStack.isEmpty()) {
|
||||
myPositionStack.add(new ZLTextPosition(getStartCursor()));
|
||||
} else {
|
||||
myPositionStack.get(myCurrentPointInStack).set(getStartCursor());
|
||||
}
|
||||
}
|
||||
|
||||
void scrollToHome() {
|
||||
final ZLTextWordCursor cursor = getStartCursor();
|
||||
if (!cursor.isNull() && cursor.isStartOfParagraph() && cursor.getParagraphCursor().Index == 0) {
|
||||
|
@ -97,9 +44,8 @@ public class BookTextView extends FBView {
|
|||
}
|
||||
final ZLTextPosition position = new ZLTextPosition(cursor);
|
||||
gotoParagraph(0, false);
|
||||
gotoPosition(0, 0, 0);
|
||||
gotoPosition(new ZLTextPosition(0, 0, 0));
|
||||
preparePaintInfo();
|
||||
savePosition(position, getStartCursor());
|
||||
ZLApplication.Instance().repaintView();
|
||||
}
|
||||
|
||||
|
@ -110,7 +56,6 @@ public class BookTextView extends FBView {
|
|||
final ZLTextPosition position = new ZLTextPosition(cursor);
|
||||
gotoParagraph(paragraphIndex, false);
|
||||
preparePaintInfo();
|
||||
savePosition(position, getStartCursor());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -159,76 +104,4 @@ public class BookTextView extends FBView {
|
|||
|
||||
return super.onStylusPress(x, y);
|
||||
}
|
||||
|
||||
public String getFileName() {
|
||||
return this.myFileName;
|
||||
}
|
||||
|
||||
protected void savePosition(ZLTextPosition position) {
|
||||
if (myPositionStack.isEmpty()) {
|
||||
preparePaintInfo();
|
||||
}
|
||||
final ZLTextPosition currentPosition = myPositionStack.get(myCurrentPointInStack);
|
||||
while (myPositionStack.size() > myCurrentPointInStack) {
|
||||
myPositionStack.remove(myPositionStack.size() - 1);
|
||||
}
|
||||
myPositionStack.add(position);
|
||||
myPositionStack.add(currentPosition);
|
||||
while (myPositionStack.size() >= MAX_UNDO_STACK_SIZE) {
|
||||
myPositionStack.remove(0);
|
||||
}
|
||||
myCurrentPointInStack = myPositionStack.size() - 1;
|
||||
}
|
||||
|
||||
void saveState() {
|
||||
new Thread(new Runnable() {
|
||||
public void run() {
|
||||
ZLConfig.Instance().executeAsATransaction(new Runnable() {
|
||||
public void run() {
|
||||
saveStateInternal();
|
||||
}
|
||||
});
|
||||
}
|
||||
}).start();
|
||||
}
|
||||
|
||||
private void saveStateInternal() {
|
||||
if (getModel() == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final String group = getFileName();
|
||||
|
||||
new ZLIntegerOption(group, BUFFER_SIZE, 0).setValue(myPositionStack.size());
|
||||
new ZLIntegerOption(group, POSITION_IN_BUFFER, 0).setValue(myCurrentPointInStack);
|
||||
|
||||
final ZLIntegerOption option = new ZLIntegerOption(group, "", 0);
|
||||
for (int i = 0; i < myPositionStack.size(); ++i) {
|
||||
final ZLTextPosition position = myPositionStack.get(i);
|
||||
option.changeName(PARAGRAPH_PREFIX + i);
|
||||
option.setValue(position.ParagraphIndex);
|
||||
option.changeName(CHAR_PREFIX + i);
|
||||
option.setValue(position.CharIndex);
|
||||
option.changeName(WORD_PREFIX + i);
|
||||
option.setValue(position.WordIndex);
|
||||
}
|
||||
}
|
||||
|
||||
boolean canUndoPageMove() {
|
||||
return myCurrentPointInStack > 0;
|
||||
}
|
||||
|
||||
void undoPageMove() {
|
||||
gotoPosition(myPositionStack.get(--myCurrentPointInStack));
|
||||
ZLApplication.Instance().repaintView();
|
||||
}
|
||||
|
||||
boolean canRedoPageMove() {
|
||||
return myCurrentPointInStack < myPositionStack.size() - 1;
|
||||
}
|
||||
|
||||
void redoPageMove() {
|
||||
gotoPosition(myPositionStack.get(++myCurrentPointInStack));
|
||||
ZLApplication.Instance().repaintView();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -80,9 +80,6 @@ public final class FBReader extends ZLApplication {
|
|||
addAction(ActionCode.QUIT, new QuitAction(this));
|
||||
addAction(ActionCode.ROTATE_SCREEN, new ZLApplication.RotationAction());
|
||||
|
||||
addAction(ActionCode.UNDO, new UndoAction(this));
|
||||
addAction(ActionCode.REDO, new RedoAction(this));
|
||||
|
||||
addAction(ActionCode.INCREASE_FONT, new ChangeFontSizeAction(this, +2));
|
||||
addAction(ActionCode.DECREASE_FONT, new ChangeFontSizeAction(this, -2));
|
||||
|
||||
|
@ -215,23 +212,25 @@ public final class FBReader extends ZLApplication {
|
|||
if (book != null) {
|
||||
onViewChanged();
|
||||
|
||||
BookTextView.saveState();
|
||||
BookTextView.setModel(null, "");
|
||||
if (Model != null) {
|
||||
Model.Book.storePosition(new ZLTextPosition(BookTextView.getStartCursor()));
|
||||
}
|
||||
BookTextView.setModel(null);
|
||||
FootnoteView.setModel(null);
|
||||
|
||||
Model = null;
|
||||
Model = new BookModel(book);
|
||||
System.gc();
|
||||
System.gc();
|
||||
Model = BookModel.createModel(book);
|
||||
if (Model != null) {
|
||||
final String fileName = book.File.getPath();
|
||||
myBookNameOption.setValue(fileName);
|
||||
ZLTextHyphenator.Instance().load(book.getLanguage());
|
||||
BookTextView.setModel(Model.BookTextModel, fileName);
|
||||
BookTextView.setCaption(book.getTitle());
|
||||
if (position != null) {
|
||||
BookTextView.gotoPosition(position);
|
||||
}
|
||||
FootnoteView.setModel(null);
|
||||
FootnoteView.setCaption(book.getTitle());
|
||||
BookTextView.setModel(Model.BookTextModel);
|
||||
BookTextView.gotoPosition((position != null) ? position : book.getStoredPosition());
|
||||
Library.Instance().addBookToRecentList(book);
|
||||
}
|
||||
}
|
||||
repaintView();
|
||||
}
|
||||
|
||||
|
@ -270,8 +269,8 @@ main:
|
|||
}
|
||||
|
||||
public void onWindowClosing() {
|
||||
if (BookTextView != null) {
|
||||
BookTextView.saveState();
|
||||
if ((Model != null) && (BookTextView != null)) {
|
||||
Model.Book.storePosition(new ZLTextPosition(BookTextView.getStartCursor()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -33,8 +33,6 @@ public abstract class FBView extends ZLTextViewImpl {
|
|||
|
||||
private static ZLBooleanOption ourSelectionOption;
|
||||
|
||||
private String myCaption;
|
||||
|
||||
private static ZLIntegerRangeOption createMarginOption(String name, int defaultValue) {
|
||||
return new ZLIntegerRangeOption(
|
||||
"Options", name, 0, 1000, defaultValue
|
||||
|
@ -226,14 +224,6 @@ public abstract class FBView extends ZLTextViewImpl {
|
|||
return getBottomMarginOption().getValue();
|
||||
}
|
||||
|
||||
public String getCaption() {
|
||||
return myCaption;
|
||||
}
|
||||
|
||||
void setCaption(String caption) {
|
||||
myCaption = caption;
|
||||
}
|
||||
|
||||
public static ZLBooleanOption selectionOption() {
|
||||
if (ourSelectionOption == null) {
|
||||
ourSelectionOption = new ZLBooleanOption("Options", "IsSelectionEnabled", true);
|
||||
|
|
|
@ -1,38 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.fbreader;
|
||||
|
||||
class RedoAction extends FBAction {
|
||||
RedoAction(FBReader fbreader) {
|
||||
super(fbreader);
|
||||
}
|
||||
|
||||
public boolean isVisible() {
|
||||
return Reader.getMode() == FBReader.ViewMode.BOOK_TEXT;
|
||||
}
|
||||
|
||||
public boolean isEnabled() {
|
||||
return isVisible() && Reader.BookTextView.canRedoPageMove();
|
||||
}
|
||||
|
||||
public void run() {
|
||||
Reader.BookTextView.redoPageMove();
|
||||
}
|
||||
}
|
|
@ -26,6 +26,10 @@ class SearchAction extends FBAction {
|
|||
super(fbreader);
|
||||
}
|
||||
|
||||
public boolean isVisible() {
|
||||
return Reader.Model != null;
|
||||
}
|
||||
|
||||
public void run() {
|
||||
ZLDialogManager.Instance().startSearch();
|
||||
}
|
||||
|
|
|
@ -1,43 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.fbreader;
|
||||
|
||||
class UndoAction extends FBAction {
|
||||
UndoAction(FBReader fbreader) {
|
||||
super(fbreader);
|
||||
}
|
||||
|
||||
public boolean isVisible() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean isEnabled() {
|
||||
return Reader.getMode() != FBReader.ViewMode.BOOK_TEXT ||
|
||||
Reader.BookTextView.canUndoPageMove();
|
||||
}
|
||||
|
||||
public void run() {
|
||||
if (Reader.getMode() == FBReader.ViewMode.BOOK_TEXT) {
|
||||
Reader.BookTextView.undoPageMove();
|
||||
} else {
|
||||
Reader.restorePreviousMode();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,38 +0,0 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.formats;
|
||||
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingCollection;
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingConverter;
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingConverterInfo;
|
||||
|
||||
public class EncodedTextReader {
|
||||
private ZLEncodingConverter myConverter;
|
||||
//?static
|
||||
public EncodedTextReader(final String encoding) {
|
||||
ZLEncodingCollection collection = ZLEncodingCollection.instance();
|
||||
ZLEncodingConverterInfo info = collection.info(encoding);
|
||||
myConverter = (info != null) ? info.createConverter() : collection.defaultConverter();
|
||||
}
|
||||
|
||||
public ZLEncodingConverter getConverter() {
|
||||
return myConverter;
|
||||
}
|
||||
}
|
|
@ -27,7 +27,7 @@ import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
|||
import org.geometerplus.fbreader.formats.fb2.FB2Plugin;
|
||||
import org.geometerplus.fbreader.formats.html.HtmlPlugin;
|
||||
import org.geometerplus.fbreader.formats.oeb.OEBPlugin;
|
||||
import org.geometerplus.fbreader.formats.plucker.PluckerPlugin;
|
||||
import org.geometerplus.fbreader.formats.pdb.MobipocketPlugin;
|
||||
|
||||
public class PluginCollection {
|
||||
private static PluginCollection ourInstance;
|
||||
|
@ -44,13 +44,12 @@ public class PluginCollection {
|
|||
//ourInstance.myPlugins.add(new PluckerPlugin());
|
||||
//ourInstance->myPlugins.push_back(new DocBookPlugin());
|
||||
//ourInstance.myPlugins.add(new HtmlPlugin());
|
||||
/*ourInstance.myPlugins.add(new TxtPlugin());
|
||||
ourInstance.myPlugins.add(new PalmDocPlugin());
|
||||
//ourInstance.myPlugins.add(new TxtPlugin());
|
||||
//ourInstance.myPlugins.add(new PalmDocPlugin());
|
||||
ourInstance.myPlugins.add(new MobipocketPlugin());
|
||||
ourInstance.myPlugins.add(new ZTXTPlugin());
|
||||
ourInstance.myPlugins.add(new TcrPlugin());
|
||||
ourInstance.myPlugins.add(new CHMPlugin());
|
||||
*/
|
||||
//ourInstance.myPlugins.add(new ZTXTPlugin());
|
||||
//ourInstance.myPlugins.add(new TcrPlugin());
|
||||
//ourInstance.myPlugins.add(new CHMPlugin());
|
||||
ourInstance.myPlugins.add(new OEBPlugin());
|
||||
//ourInstance.myPlugins.add(new RtfPlugin());
|
||||
//ourInstance.myPlugins.add(new OpenReaderPlugin());
|
||||
|
|
|
@ -50,7 +50,6 @@ public abstract class DocDecompressor {
|
|||
|
||||
if (stream.read(sourceBuffer, 0, compressedSize) == compressedSize) {
|
||||
byte token;
|
||||
int shiftedIndex;
|
||||
|
||||
loop:
|
||||
while ((sourceIndex < compressedSize) && (targetIndex < maxUncompressedSize)) {
|
||||
|
@ -79,17 +78,17 @@ loop:
|
|||
if (sourceIndex + 1 > compressedSize) {
|
||||
break loop;
|
||||
}
|
||||
int N = 256 * (token & 0xFF) + (sourceBuffer[sourceIndex++] & 0xFF);
|
||||
int copyLength = (N & 7) + 3;
|
||||
final int N = ((token & 0xFF) << 16) + (sourceBuffer[sourceIndex++] & 0xFF);
|
||||
final int copyLength = (N & 7) + 3;
|
||||
if (targetIndex + copyLength > maxUncompressedSize) {
|
||||
break loop;
|
||||
}
|
||||
shiftedIndex = targetIndex - (N & 0x3fff) / 8;
|
||||
if (shiftedIndex >= 0) {
|
||||
for (int i = 0; i < copyLength; i++) {
|
||||
targetBuffer[targetIndex++] = targetBuffer[shiftedIndex++];
|
||||
}
|
||||
final int srcIndex = targetIndex - (N & 0x3fff) / 8;
|
||||
if (srcIndex < 0) {
|
||||
break;
|
||||
}
|
||||
System.arraycopy(targetBuffer, srcIndex, targetBuffer, targetIndex, copyLength);
|
||||
targetIndex += copyLength;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
128
src/org/geometerplus/fbreader/formats/pdb/MobipocketPlugin.java
Normal file
128
src/org/geometerplus/fbreader/formats/pdb/MobipocketPlugin.java
Normal file
|
@ -0,0 +1,128 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.formats.pdb;
|
||||
|
||||
import java.io.*;
|
||||
|
||||
import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
||||
import org.geometerplus.zlibrary.core.encoding.ZLEncodingCollection;
|
||||
import org.geometerplus.zlibrary.core.util.ZLLanguageUtil;
|
||||
|
||||
import org.geometerplus.fbreader.library.Book;
|
||||
import org.geometerplus.fbreader.bookmodel.BookModel;
|
||||
|
||||
public class MobipocketPlugin extends PdbPlugin {
|
||||
@Override
|
||||
public boolean acceptsFile(ZLFile file) {
|
||||
return super.acceptsFile(file) && (fileType(file) == "BOOKMOBI");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean readMetaInfo(Book book) {
|
||||
InputStream stream = null;
|
||||
try {
|
||||
stream = book.File.getInputStream();
|
||||
final PdbHeader header = new PdbHeader(stream);
|
||||
PdbUtil.skip(stream, header.Offsets[0] + 16 - header.length());
|
||||
if (PdbUtil.readInt(stream) != 0x4D4F4249) /* "MOBI" */ {
|
||||
return false;
|
||||
}
|
||||
final int length = (int)PdbUtil.readInt(stream);
|
||||
PdbUtil.skip(stream, 4);
|
||||
final int encodingCode = (int)PdbUtil.readInt(stream);
|
||||
String encodingName = ZLEncodingCollection.Instance().getEncodingName(encodingCode);
|
||||
book.setEncoding(encodingName);
|
||||
if (encodingName == null) {
|
||||
encodingName = "utf-8";
|
||||
}
|
||||
PdbUtil.skip(stream, 52);
|
||||
final int fullNameOffset = (int)PdbUtil.readInt(stream);
|
||||
final int fullNameLength = (int)PdbUtil.readInt(stream);
|
||||
final int languageCode = (int)PdbUtil.readInt(stream);
|
||||
book.setLanguage(ZLLanguageUtil.languageByCode(languageCode & 0xFF, (languageCode >> 8) & 0xFF));
|
||||
PdbUtil.skip(stream, 32);
|
||||
int offset = 132;
|
||||
if ((PdbUtil.readInt(stream) & 0x40) != 0) {
|
||||
PdbUtil.skip(stream, length - 116);
|
||||
offset = length + 20;
|
||||
if (PdbUtil.readInt(stream) == 0x45585448) /* "EXTH" */ {
|
||||
PdbUtil.skip(stream, 4);
|
||||
final int recordsNumber = (int)PdbUtil.readInt(stream);
|
||||
offset += 8;
|
||||
for (int i = 0; i < recordsNumber; ++i) {
|
||||
final int type = (int)PdbUtil.readInt(stream);
|
||||
final int size = (int)PdbUtil.readInt(stream);
|
||||
offset += size;
|
||||
if (size <= 8) {
|
||||
continue;
|
||||
}
|
||||
switch (type) {
|
||||
default:
|
||||
PdbUtil.skip(stream, size - 8);
|
||||
break;
|
||||
case 100:
|
||||
{
|
||||
final byte[] buffer = new byte[size - 8];
|
||||
stream.read(buffer);
|
||||
String author = new String(buffer, encodingName);
|
||||
final int index = author.indexOf(',');
|
||||
if (index != -1) {
|
||||
author = author.substring(index + 1).trim() +
|
||||
' ' +
|
||||
author.substring(0, index).trim();
|
||||
} else {
|
||||
author = author.trim();
|
||||
}
|
||||
book.addAuthor(author);
|
||||
break;
|
||||
}
|
||||
case 105:
|
||||
{
|
||||
final byte[] buffer = new byte[size - 8];
|
||||
stream.read(buffer);
|
||||
book.addTag(new String(buffer, encodingName));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
PdbUtil.skip(stream, fullNameOffset - offset);
|
||||
final byte[] titleBuffer = new byte[fullNameLength];
|
||||
stream.read(titleBuffer);
|
||||
book.setTitle(new String(titleBuffer, encodingName));
|
||||
return true;
|
||||
} catch (IOException e) {
|
||||
return false;
|
||||
} finally {
|
||||
if (stream != null) {
|
||||
try {
|
||||
stream.close();
|
||||
} catch (IOException e) {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean readModel(BookModel model) {
|
||||
return false;
|
||||
}
|
||||
}
|
|
@ -17,18 +17,37 @@
|
|||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.fbreader.encoding;
|
||||
package org.geometerplus.fbreader.formats.pdb;
|
||||
|
||||
public class MyEncodingConverterProvider extends ZLEncodingConverterProvider {
|
||||
import java.io.IOException;
|
||||
|
||||
public ZLEncodingConverter createConverter(String encoding) {
|
||||
// TODO Auto-generated method stub
|
||||
return null;
|
||||
import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
||||
|
||||
class MobipocketStream extends PdbStream {
|
||||
private final long myFileSize;
|
||||
private final boolean myIsCompressed;
|
||||
|
||||
MobipocketStream(ZLFile file) throws IOException {
|
||||
super(file);
|
||||
myFileSize = file.size();
|
||||
|
||||
final int version = PdbUtil.readShort(myBase);
|
||||
switch (version) {
|
||||
case 1:
|
||||
myIsCompressed = false;
|
||||
break;
|
||||
case 2:
|
||||
myIsCompressed = true;
|
||||
break;
|
||||
default:
|
||||
throw new IOException("Unsupported compression type: " + version);
|
||||
}
|
||||
PdbUtil.skip(myBase, 6);
|
||||
// TODO: implement
|
||||
}
|
||||
|
||||
public boolean providesConverter(String encoding) {
|
||||
// TODO Auto-generated method stub
|
||||
protected boolean fillBuffer() {
|
||||
// TODO: implement
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
|
@ -21,7 +21,6 @@ package org.geometerplus.fbreader.formats.pdb;
|
|||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
|
||||
public class PdbHeader {
|
||||
static public String DocName;
|
||||
|
@ -29,41 +28,36 @@ public class PdbHeader {
|
|||
static public String Id;
|
||||
static public int[] Offsets;
|
||||
|
||||
public boolean read(InputStream stream) throws IOException {
|
||||
public PdbHeader(InputStream stream) throws IOException {
|
||||
final byte[] buffer = new byte[32];
|
||||
if (stream.read(buffer, 0, 32) != 32) {
|
||||
System.err.println("way 0");
|
||||
return false;
|
||||
throw new IOException("PdbHeader: cannot reader document name");
|
||||
}
|
||||
DocName = new String(buffer);
|
||||
Flags = PdbUtil.readShort(stream);
|
||||
|
||||
stream.skip(26);
|
||||
PdbUtil.skip(stream, 26);
|
||||
|
||||
if (stream.read(buffer, 0, 8) != 8) {
|
||||
System.err.println("way 1");
|
||||
return false;
|
||||
throw new IOException("PdbHeader: cannot reader palm id");
|
||||
}
|
||||
Id = new String(buffer, 0, 8);
|
||||
|
||||
stream.skip(8);
|
||||
PdbUtil.skip(stream, 8);
|
||||
|
||||
int numRecords = PdbUtil.readShort(stream);
|
||||
if (numRecords <= 0) {
|
||||
System.err.println(numRecords);
|
||||
System.err.println("way 2");
|
||||
return false;
|
||||
throw new IOException("PdbHeader: record number = " + numRecords);
|
||||
}
|
||||
Offsets = new int[numRecords];
|
||||
|
||||
for (int i = 0; i < numRecords; ++i) {
|
||||
Offsets[i] = PdbUtil.readInt(stream);
|
||||
if (stream.skip(4) != 4) {
|
||||
System.err.println("way 3");
|
||||
return false;
|
||||
Offsets[i] = (int)PdbUtil.readInt(stream);
|
||||
PdbUtil.skip(stream, 4);
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
public final int length() {
|
||||
return 78 + Offsets.length * 8;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -22,25 +22,25 @@ package org.geometerplus.fbreader.formats.pdb;
|
|||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
||||
//import org.geometerplus.fbreader.collection.BookDescriptionUtil;
|
||||
import org.geometerplus.fbreader.formats.FormatPlugin;
|
||||
import org.geometerplus.fbreader.formats.plucker.PluckerTextStream;
|
||||
import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
||||
import org.geometerplus.zlibrary.core.options.ZLStringOption;
|
||||
|
||||
import org.geometerplus.fbreader.formats.FormatPlugin;
|
||||
|
||||
public abstract class PdbPlugin extends FormatPlugin {
|
||||
protected static String fileType(final ZLFile file) {
|
||||
final String extension = file.getExtension().toLowerCase().intern();
|
||||
if ((extension != "prc") && (extension != "pdb") && (extension != "mobi")) {
|
||||
return null;
|
||||
@Override
|
||||
public boolean acceptsFile(ZLFile file) {
|
||||
final String extension = file.getExtension();
|
||||
return (extension == "prc") || (extension == "pdb") || (extension == "mobi");
|
||||
}
|
||||
|
||||
protected static String fileType(final ZLFile file) {
|
||||
ZLFile baseFile = file.getPhysicalFile();
|
||||
boolean upToDate = true;//BookDescriptionUtil.checkInfo(baseFile);
|
||||
|
||||
// TODO: use database instead of option (?)
|
||||
ZLStringOption palmTypeOption = new ZLStringOption(file.getPath(), "PalmType", "");
|
||||
String palmType = palmTypeOption.getValue();
|
||||
if ((palmType.length() != 8) || !upToDate) {
|
||||
if (palmType.length() != 8) {
|
||||
byte[] id = new byte[8];
|
||||
try {
|
||||
final InputStream stream = file.getInputStream();
|
||||
|
@ -48,18 +48,13 @@ public abstract class PdbPlugin extends FormatPlugin {
|
|||
return null;
|
||||
}
|
||||
stream.skip(60);
|
||||
stream.read(id, 0, 8);
|
||||
stream.read(id);
|
||||
stream.close();
|
||||
} catch (IOException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
}
|
||||
palmType = new String(id);
|
||||
if (!upToDate) {
|
||||
//BookDescriptionUtil.saveInfo(baseFile);
|
||||
}
|
||||
palmType = new String(id).intern();
|
||||
palmTypeOption.setValue(palmType);
|
||||
}
|
||||
return palmType;
|
||||
return palmType.intern();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -26,22 +26,28 @@ import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
|||
|
||||
public abstract class PdbStream extends InputStream {
|
||||
protected final InputStream myBase;
|
||||
private int myOffset;
|
||||
public final PdbHeader myHeader = new PdbHeader();
|
||||
public PdbHeader myHeader;
|
||||
protected byte[] myBuffer;
|
||||
|
||||
protected short myBufferLength;
|
||||
protected short myBufferOffset;
|
||||
|
||||
public PdbStream(ZLFile file) {
|
||||
InputStream base;
|
||||
try {
|
||||
base = file.getInputStream();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
base = null;
|
||||
public PdbStream(ZLFile file) throws IOException {
|
||||
myBase = file.getInputStream();
|
||||
|
||||
myHeader = new PdbHeader(myBase);
|
||||
|
||||
myBase.skip(myHeader.Offsets[0] - myHeader.length());
|
||||
|
||||
myBufferLength = 0;
|
||||
myBufferOffset = 0;
|
||||
}
|
||||
myBase = base;
|
||||
|
||||
public int read() {
|
||||
if (!fillBuffer()) {
|
||||
return -1;
|
||||
}
|
||||
return myBuffer[myBufferOffset++];
|
||||
}
|
||||
|
||||
public int read(byte[] buffer,int offset, int maxSize) {
|
||||
|
@ -57,45 +63,8 @@ public abstract class PdbStream extends InputStream {
|
|||
myBufferOffset += size;
|
||||
}
|
||||
}
|
||||
myOffset += realSize;
|
||||
return realSize;
|
||||
}
|
||||
/*public int read(byte[] buffer,int offset, int maxSize) {
|
||||
int realSize = 0;
|
||||
while (realSize < maxSize) {
|
||||
if (!fillBuffer()) {
|
||||
break;
|
||||
}
|
||||
int size = Math.min((maxSize - realSize), (myBufferLength - myBufferOffset));
|
||||
if (size > 0) {
|
||||
if (buffer != null) {
|
||||
for (int i = 0; i < size; i++) {
|
||||
myBuffer[myBufferOffset+i] = buffer[realSize+i];
|
||||
}
|
||||
//memcpy(buffer + realSize, myBuffer + myBufferOffset, size);
|
||||
}
|
||||
realSize += size;
|
||||
myBufferOffset += size;
|
||||
}
|
||||
}
|
||||
myOffset += realSize;
|
||||
return realSize;
|
||||
}*/
|
||||
|
||||
public boolean open() throws IOException {
|
||||
if ((myBase == null) || !myHeader.read(myBase)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
myBase.skip(myHeader.Offsets[0] - 78 - 8 * myHeader.Offsets.length);
|
||||
|
||||
myBufferLength = 0;
|
||||
myBufferOffset = 0;
|
||||
|
||||
myOffset = 0;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public void close() throws IOException {
|
||||
if (myBase != null) {
|
||||
|
@ -109,23 +78,10 @@ public abstract class PdbStream extends InputStream {
|
|||
public void skip(int offset) throws IOException {
|
||||
if (offset > 0) {
|
||||
read(null, 0, offset);
|
||||
} else if (offset < 0) {
|
||||
offset += this.offset();
|
||||
open();
|
||||
if (offset >= 0) {
|
||||
read(null, 0, offset);
|
||||
} else {
|
||||
throw new IOException("Cannot skip: " + offset + " bytes");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public int offset() {
|
||||
return myOffset;
|
||||
}
|
||||
|
||||
public int sizeOfOpened() {
|
||||
// TODO: implement
|
||||
return 0;
|
||||
}
|
||||
|
||||
protected abstract boolean fillBuffer();
|
||||
}
|
||||
|
|
|
@ -21,31 +21,28 @@ package org.geometerplus.fbreader.formats.pdb;
|
|||
|
||||
import java.io.*;
|
||||
|
||||
public class PdbUtil {
|
||||
public static int readShort(InputStream stream) {
|
||||
final byte[] tmp = new byte[2];
|
||||
try {
|
||||
stream.read(tmp, 0, 2);
|
||||
} catch (IOException e) {
|
||||
return -1;
|
||||
public abstract class PdbUtil {
|
||||
public static void skip(InputStream stream, int numBytes) throws IOException {
|
||||
numBytes -= stream.skip(numBytes);
|
||||
for (; numBytes > 0; --numBytes) {
|
||||
if (stream.read() == -1) {
|
||||
throw new IOException("Unexpected end of stream");
|
||||
}
|
||||
}
|
||||
// int i = ((tmp[1] & 0xFF) + ((tmp[0] & 0xFF) << 8));
|
||||
// if (i > Short.MAX_VALUE)
|
||||
// System.out.println("i = " + i);
|
||||
return ((tmp[1] & 0xFF) + ((tmp[0] & 0xFF) << 8));
|
||||
}
|
||||
|
||||
//? long
|
||||
public static int readInt(InputStream stream) {
|
||||
public static int readShort(InputStream stream) throws IOException {
|
||||
final byte[] tmp = new byte[2];
|
||||
stream.read(tmp, 0, 2);
|
||||
return (tmp[1] & 0xFF) + ((tmp[0] & 0xFF) << 8);
|
||||
}
|
||||
|
||||
public static long readInt(InputStream stream) throws IOException {
|
||||
final byte[] tmp = new byte[4];
|
||||
try {
|
||||
stream.read(tmp, 0, 4);
|
||||
} catch (IOException e) {
|
||||
return -1;
|
||||
}
|
||||
return (tmp[0] << 24) +
|
||||
((tmp[1] & 0xFF) << 16) +
|
||||
((tmp[2] & 0xFF) << 8) +
|
||||
(tmp[3] & 0xFF);
|
||||
return (((long)(tmp[0] & 0xFF)) << 24) +
|
||||
+ ((tmp[1] & 0xFF) << 16) +
|
||||
+ ((tmp[2] & 0xFF) << 8) +
|
||||
+ (tmp[3] & 0xFF);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -28,8 +28,6 @@ import org.geometerplus.zlibrary.core.image.*;
|
|||
import org.geometerplus.zlibrary.text.model.*;
|
||||
|
||||
import org.geometerplus.fbreader.bookmodel.*;
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingConverter;
|
||||
import org.geometerplus.fbreader.formats.EncodedTextReader;
|
||||
import org.geometerplus.fbreader.formats.pdb.*;
|
||||
|
||||
public class PluckerBookReader extends BookReader {
|
||||
|
@ -51,11 +49,9 @@ public class PluckerBookReader extends BookReader {
|
|||
private ArrayList/*<Integer, Integer>*/ myParagraphVector = new ArrayList(); //<EFBFBD><EFBFBD> <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
private boolean myParagraphStored;
|
||||
|
||||
private final ZLEncodingConverter myConverter;
|
||||
|
||||
public PluckerBookReader(ZLFile file, BookModel model, String encoding){
|
||||
super(model);
|
||||
myConverter = new EncodedTextReader(encoding).getConverter();
|
||||
//myConverter = new EncodedTextReader(encoding).getConverter();
|
||||
myFile = file;
|
||||
//System.out.println(filePath + " " + encoding);
|
||||
myFont = FontType.FT_REGULAR;
|
||||
|
@ -63,14 +59,11 @@ public class PluckerBookReader extends BookReader {
|
|||
myForcedEntry = null;
|
||||
}
|
||||
|
||||
public boolean readDocument() throws IOException {
|
||||
public boolean readDocument() {
|
||||
try {
|
||||
myStream = new PdbInputStream(myFile);
|
||||
|
||||
PdbHeader header = new PdbHeader();
|
||||
if (!header.read(myStream)) {
|
||||
myStream.close();
|
||||
return false;
|
||||
}
|
||||
PdbHeader header = new PdbHeader(myStream);
|
||||
|
||||
setMainTextModel();
|
||||
myFont = FontType.FT_REGULAR;
|
||||
|
@ -91,6 +84,9 @@ public class PluckerBookReader extends BookReader {
|
|||
readRecord(recordSize);
|
||||
}
|
||||
myStream.close();
|
||||
} catch (IOException e) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (Iterator it = myReferencedParagraphs.iterator(); it.hasNext();) {
|
||||
Pair pair = (Pair)it.next();
|
||||
|
@ -285,7 +281,7 @@ public class PluckerBookReader extends BookReader {
|
|||
if (ptr > textStart) {
|
||||
safeBeginParagraph();
|
||||
// myConvertedTextBuffer = "";//.erase();
|
||||
myConvertedTextBuffer = myConverter.convert(data, textStart, ptr);
|
||||
myConvertedTextBuffer = "";//myConverter.convert(data, textStart, ptr);
|
||||
addData(myConvertedTextBuffer.toCharArray());
|
||||
myBufferIsEmpty = false;
|
||||
}
|
||||
|
@ -315,7 +311,7 @@ public class PluckerBookReader extends BookReader {
|
|||
if (end > textStart) {
|
||||
safeBeginParagraph();
|
||||
// myConvertedTextBuffer = "";//erase();
|
||||
myConvertedTextBuffer = myConverter.convert(data, textStart, end);
|
||||
myConvertedTextBuffer = "";//myConverter.convert(data, textStart, end);
|
||||
addData(myConvertedTextBuffer.toCharArray());
|
||||
myBufferIsEmpty = false;
|
||||
}
|
||||
|
|
|
@ -36,7 +36,7 @@ public class PluckerPlugin extends PdbPlugin {
|
|||
@Override
|
||||
public boolean readMetaInfo(Book book) {
|
||||
try {
|
||||
PdbStream stream = new PluckerTextStream(book.File);
|
||||
PluckerTextStream stream = new PluckerTextStream(book.File);
|
||||
if (stream.open()) {
|
||||
//detectEncodingAndLanguage(book, stream);
|
||||
stream.close();
|
||||
|
@ -53,12 +53,6 @@ public class PluckerPlugin extends PdbPlugin {
|
|||
|
||||
@Override
|
||||
public boolean readModel(BookModel model) {
|
||||
try {
|
||||
return new PluckerBookReader(model.Book.File, model, model.Book.getEncoding()).readDocument();
|
||||
} catch (IOException e) {
|
||||
// TODO Auto-generated catch block
|
||||
e.printStackTrace();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,7 +30,7 @@ public class PluckerTextStream extends PdbStream {
|
|||
private byte[] myFullBuffer;
|
||||
private int myRecordIndex;
|
||||
|
||||
public PluckerTextStream(ZLFile file) {
|
||||
public PluckerTextStream(ZLFile file) throws IOException {
|
||||
super(file);
|
||||
myFullBuffer = null;
|
||||
}
|
||||
|
@ -40,9 +40,9 @@ public class PluckerTextStream extends PdbStream {
|
|||
}
|
||||
|
||||
public boolean open() throws IOException {
|
||||
if (!super.open()) {
|
||||
return false;
|
||||
}
|
||||
//if (!super.open()) {
|
||||
// return false;
|
||||
//}
|
||||
|
||||
myCompressionVersion = (short) PdbUtil.readShort(myBase);
|
||||
|
||||
|
|
|
@ -24,6 +24,8 @@ import java.util.*;
|
|||
import org.geometerplus.zlibrary.core.util.ZLMiscUtil;
|
||||
import org.geometerplus.zlibrary.core.filesystem.*;
|
||||
|
||||
import org.geometerplus.zlibrary.text.view.ZLTextPosition;
|
||||
|
||||
import org.geometerplus.fbreader.formats.*;
|
||||
|
||||
public class Book {
|
||||
|
@ -77,7 +79,11 @@ public class Book {
|
|||
if (book == null) {
|
||||
book = new Book(bookFile);
|
||||
}
|
||||
return book.readMetaInfo() ? book : null;
|
||||
if (book.readMetaInfo()) {
|
||||
book.save();
|
||||
return book;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public final ZLFile File;
|
||||
|
@ -320,4 +326,14 @@ public class Book {
|
|||
myIsSaved = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
public ZLTextPosition getStoredPosition() {
|
||||
return BooksDatabase.Instance().getStoredPosition(myId);
|
||||
}
|
||||
|
||||
public void storePosition(ZLTextPosition position) {
|
||||
if (myId != -1) {
|
||||
BooksDatabase.Instance().storePosition(myId, position);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -34,7 +34,8 @@ public class Bookmark {
|
|||
}
|
||||
|
||||
private long myId;
|
||||
private long myBookId;
|
||||
private final long myBookId;
|
||||
private final String myBookTitle;
|
||||
private String myText;
|
||||
private final Date myCreationDate;
|
||||
private Date myModificationDate;
|
||||
|
@ -45,9 +46,10 @@ public class Bookmark {
|
|||
|
||||
private boolean myIsChanged;
|
||||
|
||||
Bookmark(long id, long bookId, String text, Date creationDate, Date modificationDate, Date accessDate, int accessCount, int paragraphIndex, int wordIndex, int charIndex) {
|
||||
Bookmark(long id, long bookId, String bookTitle, String text, Date creationDate, Date modificationDate, Date accessDate, int accessCount, int paragraphIndex, int wordIndex, int charIndex) {
|
||||
myId = id;
|
||||
myBookId = bookId;
|
||||
myBookTitle = bookTitle;
|
||||
myText = text;
|
||||
myCreationDate = creationDate;
|
||||
myModificationDate = modificationDate;
|
||||
|
@ -66,6 +68,7 @@ public class Bookmark {
|
|||
public Bookmark(Book book, String text, ZLTextPosition position) {
|
||||
myId = -1;
|
||||
myBookId = book.getId();
|
||||
myBookTitle = book.getTitle();
|
||||
myText = text;
|
||||
myCreationDate = new Date();
|
||||
myPosition = position;
|
||||
|
@ -84,6 +87,10 @@ public class Bookmark {
|
|||
return myText;
|
||||
}
|
||||
|
||||
public String getBookTitle() {
|
||||
return myBookTitle;
|
||||
}
|
||||
|
||||
public ZLTextPosition getPosition() {
|
||||
return myPosition;
|
||||
}
|
||||
|
|
|
@ -23,6 +23,8 @@ import java.util.*;
|
|||
|
||||
import org.geometerplus.zlibrary.core.filesystem.ZLFile;
|
||||
|
||||
import org.geometerplus.zlibrary.text.view.ZLTextPosition;
|
||||
|
||||
public abstract class BooksDatabase {
|
||||
private static BooksDatabase ourInstance;
|
||||
|
||||
|
@ -75,12 +77,15 @@ public abstract class BooksDatabase {
|
|||
protected abstract List<Long> listRecentBookIds();
|
||||
protected abstract void saveRecentBookIds(final List<Long> ids);
|
||||
|
||||
protected Bookmark createBookmark(long id, long bookId, String text, Date creationDate, Date modificationDate, Date accessDate, int accessCounter, int paragraphIndex, int wordIndex, int charIndex) {
|
||||
return new Bookmark(id, bookId, text, creationDate, modificationDate, accessDate, accessCounter, paragraphIndex, wordIndex, charIndex);
|
||||
protected Bookmark createBookmark(long id, long bookId, String bookTitle, String text, Date creationDate, Date modificationDate, Date accessDate, int accessCounter, int paragraphIndex, int wordIndex, int charIndex) {
|
||||
return new Bookmark(id, bookId, bookTitle, text, creationDate, modificationDate, accessDate, accessCounter, paragraphIndex, wordIndex, charIndex);
|
||||
}
|
||||
|
||||
protected abstract List<Bookmark> listBookmarks(long bookId);
|
||||
protected abstract List<Bookmark> listAllBookmarks();
|
||||
protected abstract long saveBookmark(Bookmark bookmark);
|
||||
protected abstract void deleteBookmark(Bookmark bookmark);
|
||||
|
||||
protected abstract ZLTextPosition getStoredPosition(long bookId);
|
||||
protected abstract void storePosition(long bookId, ZLTextPosition position);
|
||||
}
|
||||
|
|
|
@ -27,8 +27,6 @@ import org.geometerplus.zlibrary.core.resources.ZLResource;
|
|||
import org.geometerplus.zlibrary.core.view.ZLViewWidget;
|
||||
import org.geometerplus.zlibrary.text.view.style.*;
|
||||
|
||||
import org.geometerplus.fbreader.encoding.ZLEncodingCollection;
|
||||
import org.geometerplus.fbreader.encodingOption.*;
|
||||
import org.geometerplus.fbreader.fbreader.*;
|
||||
import org.geometerplus.fbreader.formats.PluginCollection;
|
||||
|
||||
|
|
|
@ -30,8 +30,6 @@ public abstract class ZLConfig {
|
|||
ourInstance = this;
|
||||
}
|
||||
|
||||
public abstract void executeAsATransaction(Runnable actions);
|
||||
|
||||
public abstract String getValue(String group, String name, String defaultValue);
|
||||
public abstract void setValue(String group, String name, String value);
|
||||
public abstract void unsetValue(String group, String name);
|
||||
|
|
|
@ -0,0 +1,96 @@
|
|||
/*
|
||||
* Copyright (C) 2007-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.zlibrary.core.encoding;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
import org.geometerplus.zlibrary.core.filesystem.ZLResourceFile;
|
||||
import org.geometerplus.zlibrary.core.library.ZLibrary;
|
||||
import org.geometerplus.zlibrary.core.xml.ZLStringMap;
|
||||
import org.geometerplus.zlibrary.core.xml.ZLXMLReaderAdapter;
|
||||
|
||||
public final class ZLEncodingCollection {
|
||||
private static ZLEncodingCollection ourInstance;
|
||||
|
||||
public static ZLEncodingCollection Instance() {
|
||||
if (ourInstance == null) {
|
||||
ourInstance = new ZLEncodingCollection();
|
||||
}
|
||||
return ourInstance;
|
||||
}
|
||||
|
||||
private final HashMap<String,String> myEncodingByAlias = new HashMap<String,String>();
|
||||
|
||||
private ZLEncodingCollection() {
|
||||
new ZLEncodingCollectionReader().read(
|
||||
ZLResourceFile.createResourceFile("data/encodings/Encodings.xml")
|
||||
);
|
||||
}
|
||||
|
||||
public String getEncodingName(String alias) {
|
||||
final String name = myEncodingByAlias.get(alias);
|
||||
return (name != null) ? name : alias;
|
||||
}
|
||||
|
||||
public String getEncodingName(int code) {
|
||||
return myEncodingByAlias.get("" + code);
|
||||
}
|
||||
|
||||
private class ZLEncodingCollectionReader extends ZLXMLReaderAdapter {
|
||||
private String myCurrentEncodingName;
|
||||
|
||||
public ZLEncodingCollectionReader() {
|
||||
}
|
||||
|
||||
public boolean dontCacheAttributeValues() {
|
||||
return true;
|
||||
}
|
||||
|
||||
private static final String ENCODING = "encoding";
|
||||
private static final String NAME = "name";
|
||||
private static final String ALIAS = "alias";
|
||||
private static final String CODE = "code";
|
||||
private static final String NUMBER = "number";
|
||||
|
||||
public boolean startElementHandler(String tag, ZLStringMap attributes) {
|
||||
if (ENCODING == tag) {
|
||||
myCurrentEncodingName = attributes.getValue(NAME);
|
||||
} else if (myCurrentEncodingName != null) {
|
||||
String alias = null;
|
||||
if (ALIAS == tag) {
|
||||
alias = attributes.getValue(NAME);
|
||||
} else if (CODE == tag) {
|
||||
alias = attributes.getValue(NUMBER);
|
||||
}
|
||||
if (alias != null) {
|
||||
myEncodingByAlias.put(alias, myCurrentEncodingName);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean endElementHandler(String tag) {
|
||||
if (ENCODING == tag) {
|
||||
myCurrentEncodingName = null;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -56,18 +56,22 @@ public abstract class ZLArchiveEntryFile extends ZLFile {
|
|||
init();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean exists() {
|
||||
return myParent.exists();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDirectory() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPath() {
|
||||
return myParent.getPath() + ":" + myName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getNameWithExtension() {
|
||||
if (myShortName == null) {
|
||||
final String name = myName;
|
||||
|
@ -81,10 +85,12 @@ public abstract class ZLArchiveEntryFile extends ZLFile {
|
|||
return myShortName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ZLFile getParent() {
|
||||
return myParent;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ZLPhysicalFile getPhysicalFile() {
|
||||
ZLFile ancestor = myParent;
|
||||
while ((ancestor != null) && !(ancestor instanceof ZLPhysicalFile)) {
|
||||
|
|
|
@ -94,6 +94,7 @@ public abstract class ZLFile {
|
|||
return new ZLPhysicalFile(path);
|
||||
}
|
||||
|
||||
public abstract long size();
|
||||
public abstract boolean exists();
|
||||
public abstract boolean isDirectory();
|
||||
public abstract String getPath();
|
||||
|
@ -118,53 +119,6 @@ public abstract class ZLFile {
|
|||
return myExtension;
|
||||
}
|
||||
|
||||
/*
|
||||
public InputStream getInputStream() throws IOException {
|
||||
InputStream stream = null;
|
||||
int index = ZLFSUtil.findArchiveFileNameDelimiter(myPath);
|
||||
if (index == -1) {
|
||||
stream = ZLibrary.Instance().getInputStream(myPath);
|
||||
} else {
|
||||
ZLFile baseFile = new ZLFile(myPath.substring(0, index));
|
||||
InputStream base = baseFile.getInputStream();
|
||||
if (base != null) {
|
||||
if (0 != (baseFile.myArchiveType & ArchiveType.ZIP)) {
|
||||
ZipFile zf = getZipFile(myPath.substring(0, index));
|
||||
/*
|
||||
ZipEntry entry = zf.getEntry(myPath.substring(index+1));
|
||||
stream = zf.getInputStream(entry);
|
||||
* /
|
||||
final String entryName = myPath.substring(index + 1);
|
||||
stream = zf.getInputStream(entryName);
|
||||
/*
|
||||
while (true) {
|
||||
ZipEntry entry = zipStream.getNextEntry();
|
||||
if (entry == null) {
|
||||
break;
|
||||
} else if (entryName.equals(entry.getName())) {
|
||||
stream = zipStream;
|
||||
break;
|
||||
}
|
||||
}
|
||||
* /
|
||||
} else if (0 != (baseFile.myArchiveType & ArchiveType.TAR)) {
|
||||
stream = new ZLTarInputStream(base, myPath.substring(index + 1));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (stream != null) {
|
||||
if (0 != (myArchiveType & ArchiveType.GZIP)) {
|
||||
return new java.util.zip.GZIPInputStream(stream, 8192);
|
||||
}
|
||||
//if (0 != (myArchiveType & ArchiveType.BZIP2)) {
|
||||
//return new ZLBzip2InputStream(stream);
|
||||
//}
|
||||
}
|
||||
return stream;
|
||||
}
|
||||
*/
|
||||
|
||||
protected List<ZLFile> directoryEntries() {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
|
|
|
@ -36,39 +36,46 @@ public final class ZLPhysicalFile extends ZLFile {
|
|||
init();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean exists() {
|
||||
return myFile.exists();
|
||||
}
|
||||
|
||||
@Override
|
||||
public long size() {
|
||||
return myFile.length();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isDirectory() {
|
||||
return myFile.isDirectory();
|
||||
//return myFile.length() == 0;
|
||||
}
|
||||
|
||||
public boolean remove() {
|
||||
return myFile.delete();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPath() {
|
||||
return myFile.getPath();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getNameWithExtension() {
|
||||
return myFile.getName();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ZLFile getParent() {
|
||||
return isDirectory() ? null : new ZLPhysicalFile(myFile.getParent());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ZLPhysicalFile getPhysicalFile() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream getInputStream() throws IOException {
|
||||
return new FileInputStream(myFile);
|
||||
}
|
||||
|
|
|
@ -67,6 +67,12 @@ final class ZLZipEntryFile extends ZLArchiveEntryFile {
|
|||
super(parent, name);
|
||||
}
|
||||
|
||||
@Override
|
||||
public long size() {
|
||||
throw new RuntimeException("Not implemented yet.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream getInputStream() throws IOException {
|
||||
return getZipFile(myParent).getInputStream(myName);
|
||||
}
|
||||
|
|
|
@ -56,11 +56,13 @@ public final class ZLTarEntryFile extends ZLArchiveEntryFile {
|
|||
super(parent, name);
|
||||
}
|
||||
|
||||
@Override
|
||||
public long size() {
|
||||
throw new RuntimeException("Not implemented yet.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream getInputStream() throws IOException {
|
||||
InputStream base = myParent.getInputStream();
|
||||
if (base != null) {
|
||||
return new ZLTarInputStream(base, myName);
|
||||
}
|
||||
return null;
|
||||
return new ZLTarInputStream(myParent.getInputStream(), myName);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -29,11 +29,6 @@ public final class ZLIntegerOption extends ZLOption {
|
|||
myValue = defaultValue;
|
||||
}
|
||||
|
||||
public void changeName(String optionName) {
|
||||
super.changeName(optionName);
|
||||
myValue = myDefaultValue;
|
||||
}
|
||||
|
||||
public int getValue() {
|
||||
if (!myIsSynchronized) {
|
||||
String value = getConfigValue(null);
|
||||
|
|
157
src/org/geometerplus/zlibrary/core/util/ZLLanguageUtil.java
Normal file
157
src/org/geometerplus/zlibrary/core/util/ZLLanguageUtil.java
Normal file
|
@ -0,0 +1,157 @@
|
|||
/*
|
||||
* Copyright (C) 2008-2009 Geometer Plus <contact@geometerplus.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*/
|
||||
|
||||
package org.geometerplus.zlibrary.core.util;
|
||||
|
||||
public abstract class ZLLanguageUtil {
|
||||
public static String languageByCode(int languageCode, int subLanguageCode) {
|
||||
switch (languageCode) {
|
||||
default: return null;
|
||||
case 0x01: return "ar"; // Arabic
|
||||
case 0x02: return "bg"; // Bulgarian
|
||||
case 0x03: return "ca"; // Catalan
|
||||
case 0x04: return "zh"; // Chinese
|
||||
case 0x05: return "cs"; // Czech
|
||||
case 0x06: return "da"; // Danish
|
||||
case 0x07: return "de"; // German
|
||||
case 0x08: return "el"; // Greek
|
||||
case 0x09: return "en"; // English
|
||||
case 0x0A: return "es"; // Spanish
|
||||
case 0x0B: return "fi"; // Finnish
|
||||
case 0x0C: return "fr"; // French
|
||||
case 0x0D: return "he"; // Hebrew
|
||||
case 0x0E: return "hu"; // Hungarian
|
||||
case 0x0F: return "is"; // Icelandic
|
||||
case 0x10: return "it"; // Italian
|
||||
case 0x11: return "ja"; // Japanese
|
||||
case 0x12: return "ko"; // Korean
|
||||
case 0x13: return "nl"; // Dutch
|
||||
case 0x14: return "no"; // Norwegian
|
||||
case 0x15: return "pl"; // Polish
|
||||
case 0x16: return "pt"; // Portuguese
|
||||
case 0x17: return "rm"; // Romansh
|
||||
case 0x18: return "ro"; // Romanian
|
||||
case 0x19: return "ru"; // Russian
|
||||
case 0x1A:
|
||||
switch (subLanguageCode) {
|
||||
default: return "sr"; // Serbian
|
||||
case 0x04:
|
||||
case 0x10: return "hr"; // Croatian
|
||||
case 0x14:
|
||||
case 0x20:
|
||||
case 0x78: return "bs"; // Bosnian
|
||||
}
|
||||
case 0x1B: return "sk"; // Slovak
|
||||
case 0x1C: return "sq"; // Albanian
|
||||
case 0x1D: return "sv"; // Swedish
|
||||
case 0x1E: return "th"; // Thai
|
||||
case 0x1F: return "tr"; // Turkish
|
||||
case 0x20: return "ur"; // Urdu
|
||||
case 0x21: return "id"; // Indonesian
|
||||
case 0x22: return "uk"; // Ukrainian
|
||||
case 0x23: return "be"; // Belarusian
|
||||
case 0x24: return "sl"; // Slovenian
|
||||
case 0x25: return "et"; // Estonian
|
||||
case 0x26: return "lv"; // Latvian
|
||||
case 0x27: return "lt"; // Lithuanian
|
||||
case 0x28: return "tg"; // Tajik
|
||||
case 0x29: return "fa"; // Persian (Farsi)
|
||||
case 0x2A: return "vi"; // Vietnamese
|
||||
case 0x2B: return "hy"; // Armenian
|
||||
case 0x2C: return "az"; // Azeri
|
||||
case 0x2D: return "eu"; // Basque
|
||||
case 0x2E: return (subLanguageCode == 0x08)
|
||||
? "dsb" // Lower Sorbian
|
||||
: "wen"; // Upper Sorbian
|
||||
case 0x2F: return "mk"; // Makedonian
|
||||
case 0x32: return "tn"; // Setswana/Tswana
|
||||
case 0x34: return "xh"; // Xhosa/isiXhosa
|
||||
case 0x35: return "zu"; // Zulu/isiZulu
|
||||
case 0x36: return "af"; // Afrikaans
|
||||
case 0x37: return "ka"; // Georgian
|
||||
case 0x38: return "fo"; // Faeroese
|
||||
case 0x39: return "hi"; // Hindi
|
||||
case 0x3A: return "mt"; // Maltese
|
||||
case 0x3B: return "se"; // Sami
|
||||
case 0x3C: return "ga"; // Irish
|
||||
case 0x3E: return "ms"; // Malay
|
||||
case 0x3F: return "kk"; // Kazak
|
||||
case 0x40: return "ky"; // Kyrgyz
|
||||
case 0x41: return "sw"; // Swahili
|
||||
case 0x42: return "tk"; // Turkmen
|
||||
case 0x43: return "uz"; // Uzbek
|
||||
case 0x44: return "tt"; // Tatar
|
||||
case 0x45: return "bn"; // Bengali
|
||||
case 0x46: return "pa"; // Punjabi
|
||||
case 0x47: return "gu"; // Gujaratu
|
||||
case 0x48: return "or"; // Oriya
|
||||
case 0x49: return "ta"; // Tamil
|
||||
case 0x4A: return "te"; // Telugi
|
||||
case 0x4B: return "kn"; // Kannada
|
||||
case 0x4C: return "ml"; // Malayalam
|
||||
case 0x4D: return "as"; // Assamese
|
||||
case 0x4E: return "mr"; // Marathi
|
||||
case 0x4F: return "sa"; // Sanskrit
|
||||
case 0x50: return "mn"; // Mongolian
|
||||
case 0x51: return "bo"; // Tibetian
|
||||
case 0x52: return "cy"; // Welsh
|
||||
case 0x53: return "kh"; // Khmer
|
||||
case 0x54: return "lo"; // Lao
|
||||
case 0x56: return "gl"; // Galician
|
||||
case 0x57: return "kok"; // Konkani
|
||||
case 0x58: return "mni"; // Manipuri
|
||||
case 0x59: return "sd"; // Sindhi
|
||||
case 0x5A: return "syr"; // Syriac
|
||||
case 0x5B: return "si"; // Sinhala
|
||||
case 0x5D: return "iu"; // Inuktitut
|
||||
case 0x5E: return "am"; // Amharic
|
||||
case 0x5F: return "tzm"; // Tamazight
|
||||
case 0x60: return "ks"; // Kashmiri
|
||||
case 0x61: return "ne"; // Nepali
|
||||
case 0x62: return "fy"; // Frisian
|
||||
case 0x63: return "ps"; // Pashto
|
||||
case 0x64: return "fil"; // Filipino
|
||||
case 0x65: return "dv"; // Divehi
|
||||
case 0x68: return "ha"; // Hausa
|
||||
case 0x6A: return "yo"; // Yoruba
|
||||
case 0x6B: return "quz"; // Quechua
|
||||
case 0x6C: return "ns"; // Northern Sotho
|
||||
case 0x6D: return "ba"; // Bashkir
|
||||
case 0x6E: return "lb"; // Luxemburgish
|
||||
case 0x6F: return "kl"; // Greenlandic
|
||||
case 0x70: return "ig"; // Igbo
|
||||
case 0x73: return "ti"; // Tigrinya
|
||||
case 0x78: return "yi"; // Yi
|
||||
case 0x7A: return "arn"; // Mapudungun
|
||||
case 0x7C: return "moh"; // Mohawk
|
||||
case 0x7E: return "be"; // Breton
|
||||
case 0x80: return "ug"; // Uighur
|
||||
case 0x81: return "mi"; // Maori
|
||||
case 0x82: return "oc"; // Occitan
|
||||
case 0x83: return "co"; // Corsican
|
||||
case 0x84: return "gsw"; // Alsatian
|
||||
case 0x85: return "sah"; // Yakut
|
||||
case 0x86: return "qut"; // K'iche
|
||||
case 0x87: return "rw"; // Kinyarwanda
|
||||
case 0x88: return "wo"; // Wolof
|
||||
case 0x8C: return "prs"; // Dari
|
||||
case 0x8D: return "mg"; // Malagasy
|
||||
}
|
||||
}
|
||||
}
|
|
@ -28,8 +28,6 @@ abstract public class ZLView {
|
|||
Context = context;
|
||||
}
|
||||
|
||||
abstract public String getCaption();
|
||||
|
||||
public static final int PAGE_CENTRAL = 0;
|
||||
public static final int PAGE_LEFT = 1;
|
||||
public static final int PAGE_RIGHT = 2;
|
||||
|
|
|
@ -263,24 +263,10 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
if (myCurrentPage.StartCursor.isNull()) {
|
||||
preparePaintInfo(myCurrentPage);
|
||||
}
|
||||
/* if (!position.equalsToCursor(myCurrentPage.StartCursor)) {
|
||||
savePosition(position);
|
||||
}
|
||||
*/
|
||||
savePosition(position, myCurrentPage.StartCursor);
|
||||
ZLApplication.Instance().repaintView();
|
||||
}
|
||||
}
|
||||
|
||||
protected void savePosition(ZLTextPosition position) {
|
||||
}
|
||||
|
||||
protected final void savePosition(ZLTextPosition position, ZLTextWordCursor cursorToCheck) {
|
||||
if (!position.equalsToCursor(cursorToCheck)) {
|
||||
savePosition(position);
|
||||
}
|
||||
}
|
||||
|
||||
public int search(final String text, boolean ignoreCase, boolean wholeText, boolean backward, boolean thisSectionOnly) {
|
||||
if (text.length() == 0) {
|
||||
return 0;
|
||||
|
@ -383,9 +369,6 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
myNextPage.StartCursor.setCursor(myCurrentPage.EndCursor);
|
||||
myNextPage.PaintState = PaintStateEnum.START_IS_KNOWN;
|
||||
}
|
||||
if (myCurrentPage.PaintState == PaintStateEnum.READY) {
|
||||
onPaintInfoPrepared();
|
||||
}
|
||||
break;
|
||||
}
|
||||
case PAGE_RIGHT:
|
||||
|
@ -401,9 +384,6 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
myCurrentPage.StartCursor.setCursor(myNextPage.EndCursor);
|
||||
myCurrentPage.PaintState = PaintStateEnum.START_IS_KNOWN;
|
||||
}
|
||||
if (myCurrentPage.PaintState == PaintStateEnum.READY) {
|
||||
onPaintInfoPrepared();
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -487,14 +467,14 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
}
|
||||
|
||||
public final int getScrollbarFullSize() {
|
||||
if ((myTextSize == null) || (myTextSize.length == 0)) {
|
||||
if ((myModel == null) || (myTextSize == null) || (myTextSize.length == 0)) {
|
||||
return 1;
|
||||
}
|
||||
return myTextSize[myTextSize.length - 1];
|
||||
}
|
||||
|
||||
public final int getScrollbarThumbPosition(int viewPage) {
|
||||
if ((myTextSize == null) || (myTextSize.length == 0)) {
|
||||
if ((myModel == null) || (myTextSize == null) || (myTextSize.length == 0)) {
|
||||
return 0;
|
||||
}
|
||||
ZLTextPage page = getPage(viewPage);
|
||||
|
@ -503,7 +483,7 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
}
|
||||
|
||||
public final int getScrollbarThumbLength(int viewPage) {
|
||||
if ((myTextSize == null) || (myTextSize.length == 0)) {
|
||||
if ((myModel == null) || (myTextSize == null) || (myTextSize.length == 0)) {
|
||||
return 0;
|
||||
}
|
||||
ZLTextPage page = getPage(viewPage);
|
||||
|
@ -1042,10 +1022,12 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
}
|
||||
|
||||
public final void gotoPosition(ZLTextPosition position) {
|
||||
if (position != null) {
|
||||
gotoPosition(position.ParagraphIndex, position.WordIndex, position.CharIndex);
|
||||
}
|
||||
}
|
||||
|
||||
public final void gotoPosition(int paragraphIndex, int wordIndex, int charIndex) {
|
||||
private void gotoPosition(int paragraphIndex, int wordIndex, int charIndex) {
|
||||
final int maxParagraphIndex = myModel.getParagraphsNumber() - 1;
|
||||
if (paragraphIndex > maxParagraphIndex) {
|
||||
paragraphIndex = maxParagraphIndex;
|
||||
|
@ -1216,13 +1198,9 @@ public abstract class ZLTextViewImpl extends ZLTextView {
|
|||
if (page == myCurrentPage) {
|
||||
myPreviousPage.reset();
|
||||
myNextPage.reset();
|
||||
onPaintInfoPrepared();
|
||||
}
|
||||
}
|
||||
|
||||
protected void onPaintInfoPrepared() {
|
||||
}
|
||||
|
||||
public void clearCaches() {
|
||||
rebuildPaintInfo();
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue