summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTor Andersson <tor.andersson@artifex.com>2017-01-09 13:27:53 +0100
committerTor Andersson <tor.andersson@artifex.com>2017-01-09 17:46:26 +0100
commitc405c2fe7a442a720c869befeaafbeffc0aa3ae6 (patch)
treee3fa87c87d3f9ac886c160d3f0f2d7aa133cfb84
parent9d96d035d3b7af53256ee64b5ddb0ad8bcf8df38 (diff)
downloadmupdf-c405c2fe7a442a720c869befeaafbeffc0aa3ae6.tar.xz
Remove platform/android/viewer directory.
The Android viewer has been moved to its own git repository.
-rw-r--r--platform/android/viewer/.gitignore8
-rw-r--r--platform/android/viewer/AndroidManifest.xml116
-rw-r--r--platform/android/viewer/ClassStructure.txt182
-rw-r--r--platform/android/viewer/Icons.txt2
-rw-r--r--platform/android/viewer/Makefile7
-rw-r--r--platform/android/viewer/ReadMe.txt209
-rw-r--r--platform/android/viewer/build.gradle92
-rw-r--r--platform/android/viewer/build.xml82
-rw-r--r--platform/android/viewer/jni/Android.mk42
-rw-r--r--platform/android/viewer/jni/Application.mk50
-rw-r--r--platform/android/viewer/jni/Core.mk79
-rw-r--r--platform/android/viewer/jni/ThirdParty.mk175
-rw-r--r--platform/android/viewer/jni/mupdf.c2919
-rw-r--r--platform/android/viewer/local.properties.sample5
-rw-r--r--platform/android/viewer/project.properties11
-rw-r--r--platform/android/viewer/res/animator/info.xml20
-rw-r--r--platform/android/viewer/res/drawable-hdpi/icon.pngbin4791 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_annot.pngbin311 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_annotation.pngbin480 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_arrow_left.pngbin204 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_arrow_right.pngbin208 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_cancel.pngbin204 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_check.pngbin213 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_clipboard.pngbin1309 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_dir.pngbin157 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_doc.pngbin1262 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_highlight.pngbin378 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_link.pngbin342 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_list.pngbin2821 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_magnifying_glass.pngbin323 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_more.pngbin533 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_pen.pngbin257 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_print.pngbin1248 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_proof.pngbin1229 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_reflow.pngbin220 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_select.pngbin247 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_share.pngbin313 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_strike.pngbin449 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_trash.pngbin246 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_underline.pngbin403 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/ic_updir.pngbin268 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-ldpi/icon.pngbin2158 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_annot.pngbin418 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_annotation.pngbin601 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_arrow_left.pngbin225 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_arrow_right.pngbin233 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_arrow_up.pngbin297 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_cancel.pngbin224 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_check.pngbin251 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_clipboard.pngbin1345 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_dir.pngbin165 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_doc.pngbin1277 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_highlight.pngbin524 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_link.pngbin374 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_list.pngbin2791 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_magnifying_glass.pngbin386 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_more.pngbin671 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_pen.pngbin282 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_print.pngbin1250 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_proof.pngbin2267 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_reflow.pngbin234 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_select.pngbin280 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_sep.pngbin1098 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_share.pngbin361 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_strike.pngbin622 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_trash.pngbin291 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/ic_underline.pngbin565 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-mdpi/icon.pngbin3009 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable-xhdpi/icon.pngbin6413 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable/busy.xml10
-rw-r--r--platform/android/viewer/res/drawable/button.xml23
-rw-r--r--platform/android/viewer/res/drawable/darkdenim3.pngbin22532 -> 0 bytes
-rw-r--r--platform/android/viewer/res/drawable/page_num.xml9
-rw-r--r--platform/android/viewer/res/drawable/search.xml37
-rw-r--r--platform/android/viewer/res/drawable/seek_progress.xml6
-rw-r--r--platform/android/viewer/res/drawable/seek_thumb.xml7
-rw-r--r--platform/android/viewer/res/drawable/tiled_background.xml4
-rw-r--r--platform/android/viewer/res/layout/buttons.xml408
-rw-r--r--platform/android/viewer/res/layout/main.xml5
-rw-r--r--platform/android/viewer/res/layout/outline_entry.xml27
-rw-r--r--platform/android/viewer/res/layout/picker_entry.xml25
-rw-r--r--platform/android/viewer/res/layout/print_dialog.xml9
-rw-r--r--platform/android/viewer/res/layout/textentry.xml8
-rw-r--r--platform/android/viewer/res/values-ar/strings.xml54
-rw-r--r--platform/android/viewer/res/values-ca/strings.xml54
-rw-r--r--platform/android/viewer/res/values-cs/strings.xml54
-rw-r--r--platform/android/viewer/res/values-da/strings.xml54
-rw-r--r--platform/android/viewer/res/values-de/strings.xml54
-rw-r--r--platform/android/viewer/res/values-el/strings.xml54
-rw-r--r--platform/android/viewer/res/values-es/strings.xml54
-rw-r--r--platform/android/viewer/res/values-et/strings.xml54
-rw-r--r--platform/android/viewer/res/values-fi/strings.xml54
-rw-r--r--platform/android/viewer/res/values-fr/strings.xml54
-rw-r--r--platform/android/viewer/res/values-hi/strings.xml54
-rw-r--r--platform/android/viewer/res/values-hu/strings.xml54
-rw-r--r--platform/android/viewer/res/values-in/strings.xml54
-rw-r--r--platform/android/viewer/res/values-it/strings.xml54
-rw-r--r--platform/android/viewer/res/values-iw/strings.xml54
-rw-r--r--platform/android/viewer/res/values-ja/strings.xml54
-rw-r--r--platform/android/viewer/res/values-ko/strings.xml54
-rw-r--r--platform/android/viewer/res/values-lt/strings.xml54
-rw-r--r--platform/android/viewer/res/values-ms/strings.xml54
-rw-r--r--platform/android/viewer/res/values-nl/strings.xml54
-rw-r--r--platform/android/viewer/res/values-no/strings.xml54
-rw-r--r--platform/android/viewer/res/values-pl/strings.xml54
-rw-r--r--platform/android/viewer/res/values-pt/strings.xml54
-rw-r--r--platform/android/viewer/res/values-ru/strings.xml54
-rw-r--r--platform/android/viewer/res/values-sk/strings.xml54
-rw-r--r--platform/android/viewer/res/values-sv/strings.xml54
-rw-r--r--platform/android/viewer/res/values-th/strings.xml54
-rw-r--r--platform/android/viewer/res/values-tl/strings.xml54
-rw-r--r--platform/android/viewer/res/values-tr/strings.xml54
-rw-r--r--platform/android/viewer/res/values-zh-rTW/strings.xml54
-rw-r--r--platform/android/viewer/res/values-zh/strings.xml54
-rw-r--r--platform/android/viewer/res/values/colors.xml16
-rw-r--r--platform/android/viewer/res/values/strings.xml58
-rw-r--r--platform/android/viewer/res/values/styles.xml5
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/Annotation.java18
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/ArrayDeque.java855
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/AsyncTask.java670
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/CancellableAsyncTask.java83
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/CancellableTaskDefinition.java8
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFActivity.java228
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFAdapter.java66
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFItem.java15
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/Deque.java552
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/FilePicker.java21
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfo.java14
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoExternal.java14
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoInternal.java14
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoRemote.java18
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoVisitor.java7
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFActivity.java1423
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlert.java21
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlertInternal.java30
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCancellableTaskDefinition.java38
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCore.java402
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageAdapter.java87
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageView.java691
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReaderView.java277
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowAdapter.java43
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowView.java182
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFView.java33
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivity.java31
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivityData.java17
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/OutlineAdapter.java46
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/OutlineItem.java14
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/PageView.java697
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/PrintDialogActivity.java145
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/ReaderView.java936
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/SafeAnimatorInflater.java35
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/SearchTask.java128
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/SearchTaskResult.java24
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/Separation.java15
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/Stepper.java42
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/TextChar.java12
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/TextWord.java17
-rw-r--r--platform/android/viewer/src/com/artifex/mupdfdemo/WidgetType.java9
158 files changed, 0 insertions, 14308 deletions
diff --git a/platform/android/viewer/.gitignore b/platform/android/viewer/.gitignore
deleted file mode 100644
index 644037fa..00000000
--- a/platform/android/viewer/.gitignore
+++ /dev/null
@@ -1,8 +0,0 @@
-.gradle
-/local.properties
-.idea
-.DS_Store
-/build
-/captures
-*.iml
-obj
diff --git a/platform/android/viewer/AndroidManifest.xml b/platform/android/viewer/AndroidManifest.xml
deleted file mode 100644
index 36e12b3a..00000000
--- a/platform/android/viewer/AndroidManifest.xml
+++ /dev/null
@@ -1,116 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<manifest xmlns:android="http://schemas.android.com/apk/res/android"
- package="com.artifex.mupdfdemo"
- android:versionCode="50"
- android:versionName="@string/version"
- android:debuggable="false"
- android:installLocation="auto">
- <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
- <uses-permission android:name="android.permission.INTERNET" />
- <supports-screens
- android:smallScreens="true"
- android:normalScreens="true"
- android:largeScreens="true"
- android:anyDensity="true" />
- <uses-sdk android:minSdkVersion="8" android:targetSdkVersion="16"/>
- <application
- android:label="@string/app_name"
- android:icon="@drawable/icon"
- android:hardwareAccelerated="true">
- <activity
- android:name="ChoosePDFActivity"
- android:theme="@android:style/Theme.Light"
- android:label="@string/app_name">
- <intent-filter>
- <action android:name="android.intent.action.MAIN"/>
- <category android:name="android.intent.category.LAUNCHER"/>
- </intent-filter>
- </activity>
- <activity
- android:name="MuPDFActivity"
- android:theme="@style/AppBaseTheme"
- android:label="@string/app_name">
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <data android:mimeType="application/vnd.ms-xpsdocument"/>
- <data android:mimeType="application/xps"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <data android:mimeType="application/pdf"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <data android:mimeType="application/x-cbz"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <data android:mimeType="application/epub+zip"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <data android:mimeType="text/xml"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <category android:name="android.intent.category.BROWSABLE"/>
- <data android:scheme="file"/>
- <data android:mimeType="*/*"/>
- <data android:pathPattern=".*\\.xps"/>
- <data android:host="*"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <category android:name="android.intent.category.BROWSABLE"/>
- <data android:scheme="file"/>
- <data android:mimeType="*/*"/>
- <data android:pathPattern=".*\\.pdf"/>
- <data android:host="*"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <category android:name="android.intent.category.BROWSABLE"/>
- <data android:scheme="file"/>
- <data android:mimeType="*/*"/>
- <data android:pathPattern=".*\\.cbz"/>
- <data android:host="*"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <category android:name="android.intent.category.BROWSABLE"/>
- <data android:scheme="file"/>
- <data android:mimeType="*/*"/>
- <data android:pathPattern=".*\\.epub"/>
- <data android:host="*"/>
- </intent-filter>
- <intent-filter>
- <action android:name="android.intent.action.VIEW"/>
- <category android:name="android.intent.category.DEFAULT"/>
- <category android:name="android.intent.category.BROWSABLE"/>
- <data android:scheme="file"/>
- <data android:mimeType="*/*"/>
- <data android:pathPattern=".*\\.fb2"/>
- <data android:host="*"/>
- </intent-filter>
- </activity>
- <activity
- android:name="OutlineActivity"
- android:theme="@android:style/Theme.Light.NoTitleBar.Fullscreen"
- android:label="@string/outline_title">
- </activity>
- <activity
- android:name="PrintDialogActivity"
- android:theme="@android:style/Theme.Light.NoTitleBar.Fullscreen"
- android:label="@string/print">
- </activity>
- </application>
-</manifest>
diff --git a/platform/android/viewer/ClassStructure.txt b/platform/android/viewer/ClassStructure.txt
deleted file mode 100644
index ff1f9409..00000000
--- a/platform/android/viewer/ClassStructure.txt
+++ /dev/null
@@ -1,182 +0,0 @@
-MuPDFActivity
-~~~~~~~~~~~~~
-
-MuPDFActivity is the main activity used when displaying and interacting with a
-document. This class is responsible for creating the view hierarchy and the
-menus.
-
-Main view classes
-~~~~~~~~~~~~~~~~~
-
-ReaderView
-~~~~~~~~~~
-MuPDF uses Android's standard Adapter/AdapterView paradigm, where a subclass of
-BaseAdapter supplies multiple views that have their motion on screen
-choreographed by a subclass of AdapterView. There are several standard
-AdapterView subclasses, but none support zooming into a specific subview and
-then panning within it, so MuPDF has its own AdapterView subclass, namely
-ReaderView. The class is intended to be general purpose and usable within any
-document-viewing application. During page viewing, ReaderView handles all touch
-events, recognises gestures and positions the displayed document pages
-accordingly. ReaderView needs to handle positioning slightly differently
-depending on whether MuPDF is reflowing text or not, and so it has two slightly
-different modes of operation.
-
-MuPDFReaderView
-~~~~~~~~~~~~~~~
-MuPDFReaderView subclasses ReaderView, so as to provide some of the
-page-positioning behaviour that is specific to MuPDF. It overrides some of the
-gesture recognition methods of ReaderView, so that it can perform special
-handling of (e.g.) tapping on the side of the screen for page progression, and
-tapping on links or form fields. It also handles the disabling of scrolling
-during text-selection and annotation-drawing, and it performs the setup
-operations needed by the individual page views as each newly appears.
-
-MuPDFView
-~~~~~~~~~
-Document viewing uses different View subclasses to display the individual pages
-depending on whether reflowing text or displaying pages unaltered. MuPDFView is
-the common interface to the two view subclasses.
-
-PageView
-~~~~~~~~
-PageView is the main View class used for non-reflow display of a page. Like
-ReaderView, it is intended to be, as much as is possible, independent of the
-specifics of MuPDF and usable in general document display apps. It is a
-subclass of ViewGroup because page displays are built from several layers. The
-lowest layer is a rendering of the page at a resolution that matches the screen
-exactly when maximally zoomed out so that the page fits the screen. As the user
-zooms in, this layer maintains a visible appearance of the page, but one that
-becomes more blurred as zooming in progresses. A second layer provides a higher
-resolution rendering of just the area of the page that is visible on screen,
-and at a resolution that matches the screen. As the user pans, this layer is
-updated on a background thread, so parts of the blurred layer will temporarily
-become visible, but only momentarily later to be replaced by the high-quality
-rendering. There is one further layer that is used to draw transparent shapes
-for highlighting and the like.
-
-MuPDFPageView
-~~~~~~~~~~~~~
-MuPDFPageView is a subclass of PageView, which handles some of the specifics of
-MuPDF's behaviour, such as taps on links and form fields, text selection, and
-annotation drawing. It also handles its parent class's bitmap rendering calls.
-This is the class used to display pages in non-reflow mode. It implements the
-MuPDFView interface.
-
-MuPDFReflowView
-~~~~~~~~~~~~~~~
-This is the class used to display pages in reflow mode. Like MuPDFPageView it
-implements the MuPDFView interface. It is a subclass of WebView, and achieves
-reflowing by loading an HTML version of the page, which the MuPDF core
-constructs.
-
-MuPDFPageAdapter and MuPDFReflowAdapter
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-As with any AdapterView subclass, ReaderView needs an Adapter subclass to
-supply, on demand, the subviews for the pages currently displayed. These are
-the two Adapter subclasses, supplying the subviews as MuPDFPageView and
-MuPDFReflowView objects respectively. The former is a little more complex than
-the latter, since it caches the sizes of the pages corresponding to the views
-it supplies. It does so, so that page views, on their second and subsequent
-appearances, can take on their correct size immediately. (The determining of
-page size is not a completely trivial operation and is performed on a
-background thread, as is all interaction with the core MuPDF library).
-
-C library wrapper
-~~~~~~~~~~~~~~~~~
-
-MuPDFCore
-~~~~~~~~~
-This class is the interface to the MuPDF C library. It is used to render bitmap
-versions of the page for display in the view classes mentioned above. It also
-provides for interaction with objects within the page, such as the individual
-text objects and annotations. Many of the methods take too long an execution
-time to be run on the UI thread, hence they need to be run in the background,
-and because even the fast methods have to be synchronised with the slower
-methods, (almost) all methods should be called in the background. There are a
-few non synchronised ones that have special purposes.
-
-Link handling
-~~~~~~~~~~~~~
-There are three types of PDF links, each entailing different information and
-requiring different handling. There are five classes involved in their
-representation.
-
-LinkInfo is the base class representing any one of the three
-
-LinkInfoExternal, LinkInfoInternal and LinkInfoRemote are the three subclasses
-representing the specific cases.
-
-LinkInfoVisitor is a class implementing a common Java paradigm which allows
-case analysis on the three different types of link, executing different methods
-for each.
-
-BitmapHolder
-~~~~~~~~~~~~
-BitmapHolder is the solution to a problem in allocating the Bitmaps to which
-rendering is performed by background tasks. Renderings for the purpose of
-update have to be passed a Bitmap with the current page state. During frenetic
-page flicking a large number of rendering tasks can be queued, each holding
-reference to a Bitmap. Rather than pass the Bitmap directly, we pass a
-BitmapHolder containing a reference to the Bitmap. When a page view transitions
-off screen, the BitmapHolder's reference to the Bitmap can be nulled to release
-it.
-
-SearchTask and SearchTaskResult
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-SearchTask encapsulates the process of searching for a text string within a
-document. The class uses an AsyncTask internally to perform the search in the
-background and reports the result by calling onTextFound. A SearchTaskResult
-object is used to return the result of the search.
-
-SafeAnimatorInflator
-~~~~~~~~~~~~~~~~~~~~
-This class is a simple wrapper around AnimatorInflator. AnimatorInflator
-doesn't exist in some of the Android API levels MuPDF supports, and the wrapper
-allows for a test of API-level before the point at which the class would be
-loaded.
-
-MuPDFAlert and MuPDFAlertInternal
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-This class represents the information issued by a javascript app.alert call.
-MuPDFAlertInternal represents the same information, but with Java enums
-replaced by ints, which are easier to return from JNI code.
-
-TextChar and TextWord
-~~~~~~~~~~~~~~~~~~~~~
-TextChar is used when processing the individual characters of the page. Each
-TextChar object contains the character and the rectangular area of the page at
-which it appears. TextWord is used to gather TextChars into words.
-
-Annotation
-~~~~~~~~~~
-This class represents the type and position on page of a PDF annotation.
-
-Other activities
-~~~~~~~~~~~~~~~~
-The app has three activities other than document-viewing.
-
-ChoosePDFActivity
-~~~~~~~~~~~~~~~~~
-ChoosePDFActivity allows the user to navigate local disc directories and view a
-list of loadable files, from which one can be chosen. It derives off
-ListActivity, and so displays the files in a standard ListView. ChoosePDFItem
-represents the various types of list entry: up-one, directory or file.
-ChoosePDFAdapter populates the list view.
-
-OutlineActivity
-~~~~~~~~~~~~~~~
-OutlineActivity displays a PDF document's outline as a list of selectable
-section titles. OutlineActivityData represents the current state of the
-activity. OutlineItem represents the individual items, and OutlineAdapter
-populates the list view.
-
-PrintDialogActivity
-~~~~~~~~~~~~~~~~~~~
-This activity allows the user to print documents via Google Cloud Print.
-
-Copied system classes
-~~~~~~~~~~~~~~~~~~~~~
-AsyncTask has had improvements made to it since issuing at the lowest android
-API level we support, and so we include the improved version as part of the
-MuPDF app. We also include Deque and ArrayDeque, which are used my AsyncTask.
diff --git a/platform/android/viewer/Icons.txt b/platform/android/viewer/Icons.txt
deleted file mode 100644
index 9d0082bf..00000000
--- a/platform/android/viewer/Icons.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-The icons are from http://somerandomdude.com/work/iconic/
-They are covered by the CC-BY-SA license: http://creativecommons.org/licenses/by-sa/3.0/us/
diff --git a/platform/android/viewer/Makefile b/platform/android/viewer/Makefile
deleted file mode 100644
index cc557b85..00000000
--- a/platform/android/viewer/Makefile
+++ /dev/null
@@ -1,7 +0,0 @@
-default:
- ndk-build
- ant debug
-
-install:
- ndk-build
- ant debug install
diff --git a/platform/android/viewer/ReadMe.txt b/platform/android/viewer/ReadMe.txt
deleted file mode 100644
index b2e5eb1e..00000000
--- a/platform/android/viewer/ReadMe.txt
+++ /dev/null
@@ -1,209 +0,0 @@
-To build/debug android viewer.
-
-NOTE: Using Android Studio.
-
-The easiest way to get the required SDK and NDK tools is to download
-and install Android Studio. While this build process does not make
-use of Android Studio directly, it does neatly package the tools you
-need into one easily maintainable installation. Our intention is to
-move further toward Android Studio integration in the future.
-
-1) You will need the android SDK and NDK.
-
-The easiest way to get this is to download and install Android Studio
-(see note above). If you prefer, then you can probably use a direct
-download of the SDK/NDK instead.
-
-Within Android Studio, choose: 'Configure' then 'SDK Manager' then
-'Appearance and Behaviour', 'System Settings', 'Android SDK'. This
-will show you the install location.
-
-The Android Studio SDK unpacked as:
-
- C:\Users\UserName\AppData\Local\Android\sdk
-
-on Windows. On MacOS it installed in:
-
- /Users/UserName/Library/Android/sdk
-
-In the 'SDK Plaforms' tab, ensure that at least API 16 is
-downloaded. I have a selection of later APIs too (17, 19, 22),
-but these may not be required.
-
-In the 'SDK Tools' tab, ensure that 'Android NDK' has been
-selected.
-
-Allow the system to update to ensure that everything is downloaded
-correctly.
-
-Whatever directory it unpacks to, ensure that the 'tools',
-'platform-tools' and 'ndk-bundle' directories inside it have been
-added to your PATH.
-
-If you use a direct download of the ndk, then it's important that
-you use the correct NDK for the target platform. If you're
-targeting a 32-bit platform (such as "ARM EABI v7a" or "Intel x86
-Arm") then you MUST use the 32-bit target NDK. If you get
-UnsatisfiedLinkError when opening a document in MuPDF, then you've
-tried to use the 64-bit target NDK with a 32-bit target!
-
-Similary, with a direct download, it is very important that you
-should unpack it to a directory with no spaces in the name! (Don't
-be tempted to put it in C:\Program Files etc)
-
-2) Previous versions of the ndk have required Cygwin to work on
-windows. If you try to use a non Android Studio version, you will
-need to install Cygwin 1.7 or greater now.
-
-3) In version r5 of the ndk, when running under cygwin, there were
-bugs to do with the automatic conversion of dependencies from DOS
-format paths to cygwin format paths. The 2 fixes can be found in:
-
- <http://groups.google.com/group/android-ndk/msg/b385e47e1484c2d4>
-
-Use the version that comes with Android Studio, and there should
-not be a problem.
-
-4) To test builds, you will either a real physical device, or
-an emulated device. The SDK includes an emulator with various
-different images. If you do not wish to set up an emulator,
-skip this step.
-
-From Android Studios 'Android SDK' configuration pane (see section
-1 above), there is a "Launch Standalone SDK Manager" link. In
-standalone sdk/ndk installations this can be reached by running
-'android' from the command line. This opens the SDK configuration GUI.
-
-In new versions of the GUI there is a 'Tools' menu from which you can
-select 'Manage AVDs...'. In old versions, go to the Virtual Devices entry
-on the right hand side. You need to create yourself an emulator image to
-use. Click 'New...' on the right hand side and a window will appear. Fill
-in the entries as follows:
-
- Name: FroyoEm
- Target: Android 2.2 - API Level 8
- CPU/ABI: ARM (armeabi) (If this option exists)
- SD card: Size: 1024MiB
- Skin: Resolution: 480x756 (756 just fits my macbook screen, but 800 may
- be 'more standard')
-
-Click 'Create AVD' (on old versions you may have to wait for a minute or
-so while it is prepared. Now you can exit the GUI.
-
-5) You will need a copy of the JDK installed. See
-<http://www.oracle.com/technetwork/java/javase/downloads/>. When this
-installs, ensure that JAVA_HOME is set to point to the installation
-directory.
-
-6) You will need a copy of Apache ANT installed.
-See <http://ant.apache.org/>. Ensure that ANT_HOME is set to point to
-the top level directory, and that ANT_HOME/bin is on the PATH.
-
-7) Now we are ready to build mupdf viewer for Android. Check out a copy
-of MuPDF (but you've done that already, cos you're reading this, right?).
-
-8) You will also need a copy of mupdf's thirdparty libraries. If you are
-using git, make sure to do a git submodule update --init from the top of
-the build tree. Older versions packaged this source code in a .zip-file
-(see the source code link on http://mupdf.com/). Unpack the contents of
-this into a 'thirdparty' directory created within the mupdf directory
-(i.e. at the same level as fitz, pdf, android etc).
-
-9) Read step 10 of these instructions carefully. This is where
-people skim reading invariably have problems because they skip it.
-
-10) Finally, you will need a copy of a 'generated' directory. This is not
-currently available to download.
-
-The normal mupdf build process involves running some code on the host
-(the machine on which you are compiling), rather than the target (the
-machine/device on which you eventually want to run mupdf). This code
-repacks various bits of information (fonts, CMAPs etc) into a more
-compact and usable form.
-
-Unfortunately, the android SDK does not provide a compiler for the host
-machine, so we cannot run this step automatically as part of the android
-viewer build. You will need to generate it by running a different build, such
-as the windows or linux native builds.
-
-We do not make a snapshot of the generated directory available to
-download as the contents of this directory change frequently, and we'd
-have to keep multiple versions on the website. We assume that anyone
-capable of building for android is capable of doing a normal hosted
-build.
-
-On linux/macos, this can be as simple as running 'make generate' in the
-top level directory. On Windows it's a matter of running the visual
-studio solution, or of using msys or cygwin.
-
-11) Change into mupdf's platform/android/viewer directory. Copy:
-
- platform/android/viewer/local.properties.sample
-
-to be:
-
- platform/android/viewer/local.properties
-
-and change the sdk path there as appropriate. This should be the only
-bit of localisation you need to do.
-
-12) Change into the platform/android/viewer directory (note,
-the platform/android/viewer directory, NOT the
-platform/android/viewer/jni directory!), and execute:
-
- ndk-build
-
-This should build the native code portion.
-
-If this dies with an error in thirdparty/jbig2/os_types.h load this
-file into an editor, and change line 43 from:
-
- #else
-
-to
-
- #elif !defined(HAVE_STDINT_H)
-
-and this should solve the problem.
-
-13) Then execute:
-
- ant debug
-
-or on windows under cygwin:
-
- ant.bat debug
-
-This should build the java wrapper.
-
-14) Now, either attach your physical device, or start the emulator
-by executing:
-
- emulator -avd FroyoEm
-
-The emulator will take a while to start up fully (be patient).
-
-15) We now need to give the demo file something to chew on, so let's
-copy a file into the SD card image of the device (this should only
-need to be done once). With the device attached (or emulator
-running) type:
-
- adb push ../../MyTests/pdf_reference17.pdf /mnt/sdcard/Download/test.pdf
-
-(where obviously ../../MyTests/pdf_reference17.pdf is altered for your
-machine, and under Windows, should start c:/ even if invoked from cygwin)
-(adb lives in <sdk>/platform-tools if it's not on your path).
-
-16) With the emulator running (see step 14), execute
-
- ant debug install
-
-('ant.bat debug install' on Windows) and that will copy MuPDF into the
-emulator where you can run it from the launchpad screen.
-
-17) To see debug messages from the device (physical or emulated)
-(including stdout/stderr from our app), execute:
-
- adb logcat
-
-Good luck!
diff --git a/platform/android/viewer/build.gradle b/platform/android/viewer/build.gradle
deleted file mode 100644
index 3d8088d2..00000000
--- a/platform/android/viewer/build.gradle
+++ /dev/null
@@ -1,92 +0,0 @@
-buildscript {
- repositories {
- jcenter()
- }
- dependencies {
- classpath 'com.android.tools.build:gradle:1.2.3'
- }
-}
-
-allprojects {
- repositories {
- jcenter()
- }
-}
-
-apply plugin: 'com.android.application'
-
-dependencies {
- compile fileTree(dir: 'libs', include: '*.so')
-}
-
-android {
- compileSdkVersion 17
- buildToolsVersion '21.1.2'
-
- /* this stops gradle from making it's own Android.mk file */
- sourceSets.main.jni.srcDirs = []
-
- sourceSets {
- main {
- manifest {
- srcFile 'AndroidManifest.xml'
- }
- java {
- srcDir 'src'
- exclude 'com/artifex/mupdf/fitz/AndroidDrawDevice.java'
- }
- res {
- srcDir 'res'
- }
- assets {
- srcDir 'assets'
- }
- resources {
- srcDir 'src'
- }
- jniLibs {
- srcDir 'libs'
- }
- }
- }
-
- /* This is important, it will run lint checks but won't abort build */
- lintOptions {
- abortOnError false
- }
-}
-
-// This defines the path to Android's ndk-build.
-import org.apache.tools.ant.taskdefs.condition.Os
-def ndkBuildPath = plugins.getPlugin('com.android.application').sdkHandler.getNdkFolder().absolutePath + File.separator + 'ndk-build'
-if (Os.isFamily(Os.FAMILY_WINDOWS)) {
- ndkBuildPath +='.cmd'
-}
-
-// This task builds the native part
-// To build with experimental proofing enabled, define FZ_ENABLE_GPRF,
-// as shown below, and put a copy of libgs.so in the
-// JNI folder before building.
-
-task buildNative(type: Exec,description: 'Compile JNI source via NDK') {
- println('executing buildNative')
-// commandLine ndkBuildPath, '-C', file('.').absolutePath, ' FZ_ENABLE_GPRF=1'
- commandLine ndkBuildPath, '-C', file('.').absolutePath
-}
-
-// This task cleans the native part
-
-task cleanNative(type: Exec, description: 'Clean JNI object files') {
- println('executing cleanNative')
- commandLine ndkBuildPath, '-C', file('.').absolutePath, 'clean'
-}
-
-// cleaning should also include cleaning native
-
-clean.dependsOn 'cleanNative'
-
-// building should include native
-
-tasks.withType(JavaCompile) {
- compileTask -> compileTask.dependsOn buildNative
-}
diff --git a/platform/android/viewer/build.xml b/platform/android/viewer/build.xml
deleted file mode 100644
index 627346bc..00000000
--- a/platform/android/viewer/build.xml
+++ /dev/null
@@ -1,82 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<project name="MuPDF" default="help">
-
- <!--
- The local.properties file is created and updated by the 'android' tool.
- It contains the path to the SDK. It should *NOT* be checked into
- Version Control Systems.
- -->
- <loadproperties srcFile="local.properties" />
-
- <!--
- The ant.properties file can be created by you. It is only edited by the
- 'android' tool to add properties to it.
- This is the place to change some Ant specific build properties.
- Here are some properties you may want to change/update:
-
- source.dir
- The name of the source directory. Default is 'src'.
- out.dir
- The name of the output directory. Default is 'bin'.
-
- For other overridable properties, look at the beginning of the rules
- files in the SDK, at tools/ant/build.xml
-
- Properties related to the SDK location or the project target should
- be updated using the 'android' tool with the 'update' action.
-
- This file is an integral part of the build system for your
- application and should be checked into Version Control Systems.
- -->
- <property file="ant.properties" />
-
- <!--
- The project.properties file is created and updated by the 'android'
- tool, as well as ADT.
-
- This contains project specific properties such as project target, and library
- dependencies. Lower level build properties are stored in ant.properties
- (or in .classpath for Eclipse projects).
-
- This file is an integral part of the build system for your
- application and should be checked into Version Control Systems.
- -->
- <loadproperties srcFile="project.properties" />
-
- <!-- quick check on sdk.dir -->
- <fail
- message="sdk.dir is missing. Make sure to generate local.properties using 'android update project'"
- unless="sdk.dir"
- />
-
-<!-- extension targets. Uncomment the ones where you want to do custom work in between standard targets -->
-<!--
- <target name="-pre-build">
- </target>
- <target name="-pre-compile">
- </target>
- <target name="-post-compile">
- </target>
--->
-
- <!-- Import the actual build file.
-
- To customize existing targets, there are two options:
- - Customize only one target:
- - copy/paste the target into this file, *before* the <import> task.
- - customize it to your needs.
- - Customize the whole content of build.xml
- - copy/paste the content of the rules files (minus the top node)
- into this file, replacing the <import> task.
- - customize to your needs.
-
- ***********************
- ****** IMPORTANT ******
- ***********************
- In all cases you must update the value of version-tag below to read 'custom' instead of an integer,
- in order to avoid having your file be overridden by tools such as "android update project"
- -->
- <!-- version-tag: 1 -->
- <import file="${sdk.dir}/tools/ant/build.xml" />
-
-</project>
diff --git a/platform/android/viewer/jni/Android.mk b/platform/android/viewer/jni/Android.mk
deleted file mode 100644
index 857c9ba1..00000000
--- a/platform/android/viewer/jni/Android.mk
+++ /dev/null
@@ -1,42 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-TOP_LOCAL_PATH := $(LOCAL_PATH)
-
-MUPDF_ROOT := ../../..
-
-ifdef NDK_PROFILER
-include android-ndk-profiler.mk
-endif
-
-include $(TOP_LOCAL_PATH)/Core.mk
-include $(TOP_LOCAL_PATH)/ThirdParty.mk
-
-include $(CLEAR_VARS)
-
-LOCAL_C_INCLUDES := \
- jni/andprof \
- $(MUPDF_ROOT)/include \
- $(MUPDF_ROOT)/source/fitz \
- $(MUPDF_ROOT)/source/pdf \
- $(MUPDF_ROOT)/platform/java
-LOCAL_CFLAGS := -DHAVE_ANDROID
-LOCAL_MODULE := mupdf_java32
-
-LOCAL_SRC_FILES := \
- mupdf.c \
- $(MUPDF_ROOT)/../platform/java/mupdf_native.c
-
-LOCAL_STATIC_LIBRARIES := mupdfcore mupdfthirdparty
-ifdef NDK_PROFILER
-LOCAL_CFLAGS += -pg -DNDK_PROFILER
-LOCAL_STATIC_LIBRARIES += andprof
-endif
-ifdef FZ_ENABLE_GPRF
-LOCAL_CFLAGS += -DFZ_ENABLE_GPRF
-endif
-
-LOCAL_LDLIBS := -lm -llog -ljnigraphics
-ifdef CRYPTO_BUILD
-LOCAL_LDLIBS += -L$(MUPDF_ROOT)/thirdparty/openssl/android -lcrypto
-endif
-
-include $(BUILD_SHARED_LIBRARY)
diff --git a/platform/android/viewer/jni/Application.mk b/platform/android/viewer/jni/Application.mk
deleted file mode 100644
index d0c02018..00000000
--- a/platform/android/viewer/jni/Application.mk
+++ /dev/null
@@ -1,50 +0,0 @@
-# When we build for google play, we build 4 different apk's, each with
-# a different version, by uncommenting one of the pairs of lines below.
-# Suppose our base version is X:
-
-# Version X: armeabi
-#APP_PLATFORM=android-8
-#APP_ABI := armeabi
-
-# Version X+1: armeabi-v7a (Much faster due to the availability of hardware
-# FP, but cannot be run in the emulator).
-APP_PLATFORM=android-8
-APP_ABI := armeabi-v7a
-
-# Version X+2: x86 (Requires android-9, so a change needs to be made in
-# AndroidManifest.xml too)
-#APP_PLATFORM=android-9
-#APP_ABI := x86
-
-# Version X+3: mips (Requires android-9, so a change needs to be made in
-# AndroidManifest.xml too)
-#APP_PLATFORM=android-9
-#APP_ABI := mips
-
-ifdef NDK_PROFILER
-# The profiler doesn't seem to receive ticks when run on release code.
-# Accordingly, we need to build as debug - but this turns optimisations
-# off, which is less than ideal.
-APP_OPTIM := debug
-APP_CFLAGS := -O2
-else
-ifdef DEBUG
-APP_OPTIM := debug
-APP_CFLAGS := -DDEBUG
-else
-APP_OPTIM := release
-endif
-endif
-ifdef V8_BUILD
-APP_STL := stlport_static
-endif
-ifdef MEMENTO
-APP_CFLAGS += -DMEMENTO -DMEMENTO_LEAKONLY
-APP_STL = gnustl_static
-endif
-
-# If the ndk is r8b then workaround bug by uncommenting the following line
-#NDK_TOOLCHAIN_VERSION=4.4.3
-
-# If the ndk is newer than r8c, try using clang.
-#NDK_TOOLCHAIN_VERSION=clang3.1
diff --git a/platform/android/viewer/jni/Core.mk b/platform/android/viewer/jni/Core.mk
deleted file mode 100644
index 9f11aa5a..00000000
--- a/platform/android/viewer/jni/Core.mk
+++ /dev/null
@@ -1,79 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-
-ifdef FZ_ENABLE_GPRF
-include $(CLEAR_VARS)
-LOCAL_MODULE := gsso
-LOCAL_SRC_FILES := libgs.so
-include $(PREBUILT_SHARED_LIBRARY)
-endif
-
-include $(CLEAR_VARS)
-
-MY_ROOT := ../../..
-
-LOCAL_CFLAGS += -Wall -Wno-uninitialized
-
-ifeq ($(TARGET_ARCH),arm)
-LOCAL_CFLAGS += -DARCH_ARM -DARCH_THUMB -DARCH_ARM_CAN_LOAD_UNALIGNED
-ifdef NDK_PROFILER
-LOCAL_CFLAGS += -pg -DNDK_PROFILER
-endif
-endif
-ifdef FZ_ENABLE_GPRF
-LOCAL_CFLAGS += -DFZ_ENABLE_GPRF
-endif
-LOCAL_CFLAGS += -DAA_BITS=8
-ifdef MEMENTO
-LOCAL_CFLAGS += -DMEMENTO -DMEMENTO_LEAKONLY
-endif
-ifdef CRYPTO_BUILD
-LOCAL_CFLAGS += -DHAVE_LIBCRYPTO
-endif
-
-LOCAL_C_INCLUDES := \
- $(MY_ROOT)/thirdparty/harfbuzz/src \
- $(MY_ROOT)/thirdparty/jbig2dec \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2 \
- $(MY_ROOT)/thirdparty/jpeg \
- $(MY_ROOT)/thirdparty/mujs \
- $(MY_ROOT)/thirdparty/zlib \
- $(MY_ROOT)/thirdparty/freetype/include \
- $(MY_ROOT)/source/fitz \
- $(MY_ROOT)/source/pdf \
- $(MY_ROOT)/source/xps \
- $(MY_ROOT)/source/svg \
- $(MY_ROOT)/source/cbz \
- $(MY_ROOT)/source/img \
- $(MY_ROOT)/source/tiff \
- $(MY_ROOT)/scripts/freetype \
- $(MY_ROOT)/scripts/jpeg \
- $(MY_ROOT)/generated \
- $(MY_ROOT)/resources \
- $(MY_ROOT)/include \
- $(MY_ROOT)
-ifdef V8_BUILD
-LOCAL_C_INCLUDES += $(MY_ROOT)/thirdparty/$(V8)/include
-endif
-ifdef CRYPTO_BUILD
-LOCAL_C_INCLUDES += $(MY_ROOT)/thirdparty/openssl/include
-endif
-
-LOCAL_MODULE := mupdfcore
-LOCAL_SRC_FILES := \
- $(wildcard $(MY_ROOT)/source/fitz/*.c) \
- $(wildcard $(MY_ROOT)/source/pdf/*.c) \
- $(wildcard $(MY_ROOT)/source/xps/*.c) \
- $(wildcard $(MY_ROOT)/source/svg/*.c) \
- $(wildcard $(MY_ROOT)/source/cbz/*.c) \
- $(wildcard $(MY_ROOT)/source/gprf/*.c) \
- $(wildcard $(MY_ROOT)/source/html/*.c) \
- $(wildcard $(MY_ROOT)/generated/*.c)
-
-ifdef FZ_ENABLE_GPRF
-LOCAL_SHARED_LIBRARIES := gsso
-endif
-LOCAL_LDLIBS := -lm -llog -ljnigraphics
-
-LOCAL_SRC_FILES := $(addprefix ../, $(LOCAL_SRC_FILES))
-
-include $(BUILD_STATIC_LIBRARY)
diff --git a/platform/android/viewer/jni/ThirdParty.mk b/platform/android/viewer/jni/ThirdParty.mk
deleted file mode 100644
index 450dc776..00000000
--- a/platform/android/viewer/jni/ThirdParty.mk
+++ /dev/null
@@ -1,175 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-MY_ROOT := ../../..
-
-LOCAL_C_INCLUDES := \
- $(MY_ROOT)/include/ \
- $(MY_ROOT)/thirdparty/harfbuzz/src \
- $(MY_ROOT)/thirdparty/jbig2dec \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2 \
- $(MY_ROOT)/thirdparty/jpeg \
- $(MY_ROOT)/thirdparty/mujs \
- $(MY_ROOT)/thirdparty/zlib \
- $(MY_ROOT)/thirdparty/freetype/include \
- $(MY_ROOT)/scripts/freetype \
- $(MY_ROOT)/scripts/jpeg
-
-LOCAL_CFLAGS := \
- -DFT2_BUILD_LIBRARY -DDARWIN_NO_CARBON -DHAVE_STDINT_H \
- -DOPJ_HAVE_STDINT_H -DOPJ_HAVE_INTTYPES_H -DUSE_JPIP \
- '-DFT_CONFIG_MODULES_H="slimftmodules.h"' \
- '-DFT_CONFIG_OPTIONS_H="slimftoptions.h"' \
- -Dhb_malloc_impl=hb_malloc -Dhb_calloc_impl=hb_calloc \
- -Dhb_realloc_impl=hb_realloc -Dhb_free_impl=hb_free \
- -DHAVE_OT -DHAVE_UCDN -DHB_NO_MT
-ifdef NDK_PROFILER
-LOCAL_CFLAGS += -pg -DNDK_PROFILER -O2
-endif
-ifdef MEMENTO
-LOCAL_CFLAGS += -DMEMENTO -DMEMENTO_LEAKONLY
-endif
-
-LOCAL_CPP_EXTENSION := .cc
-
-LOCAL_MODULE := mupdfthirdparty
-LOCAL_SRC_FILES := \
- $(MY_ROOT)/thirdparty/mujs/one.c \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-blob.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-buffer.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-buffer-serialize.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-common.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-face.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-fallback-shape.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-font.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ft.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-font.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-layout.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-map.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-arabic.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-default.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-hangul.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-hebrew.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-indic-table.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-indic.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-myanmar.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-thai.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-tibetan.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-use-table.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-complex-use.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-fallback.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape-normalize.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-shape.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ot-tag.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-set.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-shape-plan.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-shape.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-shaper.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-ucdn.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-unicode.cc \
- $(MY_ROOT)/thirdparty/harfbuzz/src/hb-warning.cc \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_arith.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_arith_iaid.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_arith_int.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_generic.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_halftone.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_huffman.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_image.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_metadata.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_mmr.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_page.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_refinement.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_segment.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_symbol_dict.c \
- $(MY_ROOT)/thirdparty/jbig2dec/jbig2_text.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/bio.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/cidx_manager.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/cio.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/dwt.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/event.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/function_list.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/image.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/invert.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/j2k.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/jp2.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/mct.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/mqc.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/openjpeg.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/phix_manager.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/pi.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/ppix_manager.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/raw.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/t1.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/t2.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/tcd.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/tgt.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/thix_manager.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/thread.c \
- $(MY_ROOT)/thirdparty/openjpeg/src/lib/openjp2/tpix_manager.c \
- $(MY_ROOT)/thirdparty/jpeg/jaricom.c \
- $(MY_ROOT)/thirdparty/jpeg/jcomapi.c \
- $(MY_ROOT)/thirdparty/jpeg/jdapimin.c \
- $(MY_ROOT)/thirdparty/jpeg/jdapistd.c \
- $(MY_ROOT)/thirdparty/jpeg/jdarith.c \
- $(MY_ROOT)/thirdparty/jpeg/jdatadst.c \
- $(MY_ROOT)/thirdparty/jpeg/jdatasrc.c \
- $(MY_ROOT)/thirdparty/jpeg/jdcoefct.c \
- $(MY_ROOT)/thirdparty/jpeg/jdcolor.c \
- $(MY_ROOT)/thirdparty/jpeg/jddctmgr.c \
- $(MY_ROOT)/thirdparty/jpeg/jdhuff.c \
- $(MY_ROOT)/thirdparty/jpeg/jdinput.c \
- $(MY_ROOT)/thirdparty/jpeg/jdmainct.c \
- $(MY_ROOT)/thirdparty/jpeg/jdmarker.c \
- $(MY_ROOT)/thirdparty/jpeg/jdmaster.c \
- $(MY_ROOT)/thirdparty/jpeg/jdmerge.c \
- $(MY_ROOT)/thirdparty/jpeg/jdpostct.c \
- $(MY_ROOT)/thirdparty/jpeg/jdsample.c \
- $(MY_ROOT)/thirdparty/jpeg/jdtrans.c \
- $(MY_ROOT)/thirdparty/jpeg/jerror.c \
- $(MY_ROOT)/thirdparty/jpeg/jfdctflt.c \
- $(MY_ROOT)/thirdparty/jpeg/jfdctfst.c \
- $(MY_ROOT)/thirdparty/jpeg/jfdctint.c \
- $(MY_ROOT)/thirdparty/jpeg/jidctflt.c \
- $(MY_ROOT)/thirdparty/jpeg/jidctfst.c \
- $(MY_ROOT)/thirdparty/jpeg/jidctint.c \
- $(MY_ROOT)/thirdparty/jpeg/jmemmgr.c \
- $(MY_ROOT)/thirdparty/jpeg/jquant1.c \
- $(MY_ROOT)/thirdparty/jpeg/jquant2.c \
- $(MY_ROOT)/thirdparty/jpeg/jutils.c \
- $(MY_ROOT)/thirdparty/zlib/adler32.c \
- $(MY_ROOT)/thirdparty/zlib/compress.c \
- $(MY_ROOT)/thirdparty/zlib/crc32.c \
- $(MY_ROOT)/thirdparty/zlib/deflate.c \
- $(MY_ROOT)/thirdparty/zlib/inffast.c \
- $(MY_ROOT)/thirdparty/zlib/inflate.c \
- $(MY_ROOT)/thirdparty/zlib/inftrees.c \
- $(MY_ROOT)/thirdparty/zlib/trees.c \
- $(MY_ROOT)/thirdparty/zlib/uncompr.c \
- $(MY_ROOT)/thirdparty/zlib/zutil.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftbase.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftbbox.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftbitmap.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftfntfmt.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftgasp.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftglyph.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftinit.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftstroke.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftsynth.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/ftsystem.c \
- $(MY_ROOT)/thirdparty/freetype/src/base/fttype1.c \
- $(MY_ROOT)/thirdparty/freetype/src/cff/cff.c \
- $(MY_ROOT)/thirdparty/freetype/src/cid/type1cid.c \
- $(MY_ROOT)/thirdparty/freetype/src/psaux/psaux.c \
- $(MY_ROOT)/thirdparty/freetype/src/pshinter/pshinter.c \
- $(MY_ROOT)/thirdparty/freetype/src/psnames/psnames.c \
- $(MY_ROOT)/thirdparty/freetype/src/raster/raster.c \
- $(MY_ROOT)/thirdparty/freetype/src/smooth/smooth.c \
- $(MY_ROOT)/thirdparty/freetype/src/sfnt/sfnt.c \
- $(MY_ROOT)/thirdparty/freetype/src/truetype/truetype.c \
- $(MY_ROOT)/thirdparty/freetype/src/type1/type1.c
-
-LOCAL_SRC_FILES := $(addprefix ../, $(LOCAL_SRC_FILES))
-
-include $(BUILD_STATIC_LIBRARY)
diff --git a/platform/android/viewer/jni/mupdf.c b/platform/android/viewer/jni/mupdf.c
deleted file mode 100644
index 71477b32..00000000
--- a/platform/android/viewer/jni/mupdf.c
+++ /dev/null
@@ -1,2919 +0,0 @@
-#include <jni.h>
-#include <time.h>
-#include <pthread.h>
-#include <android/log.h>
-#include <android/bitmap.h>
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <math.h>
-
-#ifdef NDK_PROFILER
-#include "prof.h"
-#endif
-
-#include "mupdf/fitz.h"
-#include "mupdf/pdf.h"
-
-#define JNI_FN(A) Java_com_artifex_mupdfdemo_ ## A
-#define PACKAGENAME "com/artifex/mupdfdemo"
-
-#define LOG_TAG "libmupdf"
-#define LOGI(...) __android_log_print(ANDROID_LOG_INFO,LOG_TAG,__VA_ARGS__)
-#define LOGT(...) __android_log_print(ANDROID_LOG_INFO,"alert",__VA_ARGS__)
-#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR,LOG_TAG,__VA_ARGS__)
-
-/* Enable to log rendering times (render each frame 100 times and time) */
-#undef TIME_DISPLAY_LIST
-
-#define MAX_SEARCH_HITS (500)
-#define NUM_CACHE (3)
-#define STRIKE_HEIGHT (0.375f)
-#define UNDERLINE_HEIGHT (0.075f)
-#define LINE_THICKNESS (0.07f)
-#define INK_THICKNESS (4.0f)
-#define SMALL_FLOAT (0.00001)
-#define PROOF_RESOLUTION (300)
-
-enum
-{
- NONE,
- TEXT,
- LISTBOX,
- COMBOBOX,
- SIGNATURE
-};
-
-typedef struct rect_node_s rect_node;
-
-struct rect_node_s
-{
- fz_rect rect;
- rect_node *next;
-};
-
-typedef struct
-{
- int number;
- int width;
- int height;
- fz_rect media_box;
- fz_page *page;
- rect_node *changed_rects;
- rect_node *hq_changed_rects;
- fz_display_list *page_list;
- fz_display_list *annot_list;
-} page_cache;
-
-typedef struct globals_s globals;
-
-struct globals_s
-{
- fz_colorspace *colorspace;
- fz_document *doc;
- int resolution;
- fz_context *ctx;
- fz_rect *hit_bbox;
- int current;
- char *current_path;
-
- page_cache pages[NUM_CACHE];
-
- int alerts_initialised;
- // fin_lock and fin_lock2 are used during shutdown. The two waiting tasks
- // show_alert and waitForAlertInternal respectively take these locks while
- // waiting. During shutdown, the conditions are signaled and then the fin_locks
- // are taken momentarily to ensure the blocked threads leave the controlled
- // area of code before the mutexes and condition variables are destroyed.
- pthread_mutex_t fin_lock;
- pthread_mutex_t fin_lock2;
- // alert_lock is the main lock guarding the variables directly below.
- pthread_mutex_t alert_lock;
- // Flag indicating if the alert system is active. When not active, both
- // show_alert and waitForAlertInternal return immediately.
- int alerts_active;
- // Pointer to the alert struct passed in by show_alert, and valid while
- // show_alert is blocked.
- pdf_alert_event *current_alert;
- // Flag and condition varibles to signal a request is present and a reply
- // is present, respectively. The condition variables alone are not sufficient
- // because of the pthreads permit spurious signals.
- int alert_request;
- int alert_reply;
- pthread_cond_t alert_request_cond;
- pthread_cond_t alert_reply_cond;
-
- // For the buffer reading mode, we need to implement stream reading, which
- // needs access to the following.
- JNIEnv *env;
- jclass thiz;
-};
-
-static jfieldID global_fid;
-static jfieldID buffer_fid;
-
-// Do our best to avoid casting warnings.
-#define CAST(type, var) (type)pointer_cast(var)
-
-static inline void *pointer_cast(jlong l)
-{
- return (void *)(intptr_t)l;
-}
-
-static inline jlong jlong_cast(void *p)
-{
- return (jlong)(intptr_t)p;
-}
-
-static void drop_changed_rects(fz_context *ctx, rect_node **nodePtr)
-{
- rect_node *node = *nodePtr;
- while (node)
- {
- rect_node *tnode = node;
- node = node->next;
- fz_free(ctx, tnode);
- }
-
- *nodePtr = NULL;
-}
-
-static void drop_page_cache(globals *glo, page_cache *pc)
-{
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
-
- LOGI("Drop page %d", pc->number);
- fz_drop_display_list(ctx, pc->page_list);
- pc->page_list = NULL;
- fz_drop_display_list(ctx, pc->annot_list);
- pc->annot_list = NULL;
- fz_drop_page(ctx, pc->page);
- pc->page = NULL;
- drop_changed_rects(ctx, &pc->changed_rects);
- drop_changed_rects(ctx, &pc->hq_changed_rects);
-}
-
-static void dump_annotation_display_lists(globals *glo)
-{
- fz_context *ctx = glo->ctx;
- int i;
-
- for (i = 0; i < NUM_CACHE; i++) {
- fz_drop_display_list(ctx, glo->pages[i].annot_list);
- glo->pages[i].annot_list = NULL;
- }
-}
-
-static void show_alert(globals *glo, pdf_alert_event *alert)
-{
- pthread_mutex_lock(&glo->fin_lock2);
- pthread_mutex_lock(&glo->alert_lock);
-
- LOGT("Enter show_alert: %s", alert->title);
- alert->button_pressed = 0;
-
- if (glo->alerts_active)
- {
- glo->current_alert = alert;
- glo->alert_request = 1;
- pthread_cond_signal(&glo->alert_request_cond);
-
- while (glo->alerts_active && !glo->alert_reply)
- pthread_cond_wait(&glo->alert_reply_cond, &glo->alert_lock);
- glo->alert_reply = 0;
- glo->current_alert = NULL;
- }
-
- LOGT("Exit show_alert");
-
- pthread_mutex_unlock(&glo->alert_lock);
- pthread_mutex_unlock(&glo->fin_lock2);
-}
-
-static void event_cb(fz_context *ctx, pdf_document *doc, pdf_doc_event *event, void *data)
-{
- globals *glo = (globals *)data;
-
- switch (event->type)
- {
- case PDF_DOCUMENT_EVENT_ALERT:
- show_alert(glo, pdf_access_alert_event(ctx, event));
- break;
- }
-}
-
-static void alerts_init(globals *glo)
-{
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
-
- if (!idoc || glo->alerts_initialised)
- return;
-
- if (idoc)
- pdf_enable_js(ctx, idoc);
-
- glo->alerts_active = 0;
- glo->alert_request = 0;
- glo->alert_reply = 0;
- pthread_mutex_init(&glo->fin_lock, NULL);
- pthread_mutex_init(&glo->fin_lock2, NULL);
- pthread_mutex_init(&glo->alert_lock, NULL);
- pthread_cond_init(&glo->alert_request_cond, NULL);
- pthread_cond_init(&glo->alert_reply_cond, NULL);
-
- pdf_set_doc_event_callback(ctx, idoc, event_cb, glo);
- LOGT("alert_init");
- glo->alerts_initialised = 1;
-}
-
-static void alerts_fin(globals *glo)
-{
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- if (!glo->alerts_initialised)
- return;
-
- LOGT("Enter alerts_fin");
- if (idoc)
- pdf_set_doc_event_callback(ctx, idoc, NULL, NULL);
-
- // Set alerts_active false and wake up show_alert and waitForAlertInternal,
- pthread_mutex_lock(&glo->alert_lock);
- glo->current_alert = NULL;
- glo->alerts_active = 0;
- pthread_cond_signal(&glo->alert_request_cond);
- pthread_cond_signal(&glo->alert_reply_cond);
- pthread_mutex_unlock(&glo->alert_lock);
-
- // Wait for the fin_locks.
- pthread_mutex_lock(&glo->fin_lock);
- pthread_mutex_unlock(&glo->fin_lock);
- pthread_mutex_lock(&glo->fin_lock2);
- pthread_mutex_unlock(&glo->fin_lock2);
-
- pthread_cond_destroy(&glo->alert_reply_cond);
- pthread_cond_destroy(&glo->alert_request_cond);
- pthread_mutex_destroy(&glo->alert_lock);
- pthread_mutex_destroy(&glo->fin_lock2);
- pthread_mutex_destroy(&glo->fin_lock);
- LOGT("Exit alerts_fin");
- glo->alerts_initialised = 0;
-}
-
-// Should only be called from the single background AsyncTask thread
-static globals *get_globals(JNIEnv *env, jobject thiz)
-{
- globals *glo = CAST(globals *, (*env)->GetLongField(env, thiz, global_fid));
- if (glo != NULL)
- {
- glo->env = env;
- glo->thiz = thiz;
- }
- return glo;
-}
-
-// May be called from any thread, provided the values of glo->env and glo->thiz
-// are not used.
-static globals *get_globals_any_thread(JNIEnv *env, jobject thiz)
-{
- return (globals *)(intptr_t)((*env)->GetLongField(env, thiz, global_fid));
-}
-
-JNIEXPORT jlong JNICALL
-JNI_FN(MuPDFCore_openFile)(JNIEnv * env, jobject thiz, jstring jfilename)
-{
- const char *filename;
- globals *glo;
- fz_context *ctx;
- jclass clazz;
-
-#ifdef NDK_PROFILER
- monstartup("libmupdf_java32.so");
-#endif
-
- clazz = (*env)->GetObjectClass(env, thiz);
- global_fid = (*env)->GetFieldID(env, clazz, "globals", "J");
-
- glo = calloc(1, sizeof(*glo));
- if (glo == NULL)
- return 0;
- glo->resolution = 160;
- glo->alerts_initialised = 0;
-
-#ifdef DEBUG
- /* Try and send stdout/stderr to file in debug builds. This
- * path may not work on all platforms, but it works on the
- * LG G3, and it's no worse than not redirecting it anywhere
- * on anything else. */
- freopen("/storage/emulated/0/Download/stdout.txt", "a", stdout);
- freopen("/storage/emulated/0/Download/stderr.txt", "a", stderr);
-#endif
-
- filename = (*env)->GetStringUTFChars(env, jfilename, NULL);
- if (filename == NULL)
- {
- LOGE("Failed to get filename");
- free(glo);
- return 0;
- }
-
- /* 128 MB store for low memory devices. Tweak as necessary. */
- glo->ctx = ctx = fz_new_context(NULL, NULL, 128 << 20);
- if (!ctx)
- {
- LOGE("Failed to initialise context");
- (*env)->ReleaseStringUTFChars(env, jfilename, filename);
- free(glo);
- return 0;
- }
-
- fz_register_document_handlers(ctx);
-
- glo->doc = NULL;
- fz_try(ctx)
- {
- glo->colorspace = fz_device_rgb(ctx);
-
- LOGI("Opening document...");
- fz_try(ctx)
- {
- glo->current_path = fz_strdup(ctx, (char *)filename);
- glo->doc = fz_open_document(ctx, (char *)filename);
- alerts_init(glo);
- }
- fz_catch(ctx)
- {
- fz_throw(ctx, FZ_ERROR_GENERIC, "Cannot open document: '%s'", filename);
- }
- LOGI("Done!");
- }
- fz_catch(ctx)
- {
- LOGE("Failed: %s", ctx->error->message);
- fz_drop_document(ctx, glo->doc);
- glo->doc = NULL;
- fz_drop_context(ctx);
- glo->ctx = NULL;
- free(glo);
- glo = NULL;
- }
-
- (*env)->ReleaseStringUTFChars(env, jfilename, filename);
-
- return jlong_cast(glo);
-}
-
-typedef struct buffer_state_s
-{
- globals *globals;
- jbyte buffer[4096];
-}
-buffer_state;
-
-static int bufferStreamNext(fz_context *ctx, fz_stream *stream, size_t max)
-{
- buffer_state *bs = (buffer_state *)stream->state;
- globals *glo = bs->globals;
- JNIEnv *env = glo->env;
- jbyteArray array = (jbyteArray)(void *)((*env)->GetObjectField(env, glo->thiz, buffer_fid));
- int arrayLength = (*env)->GetArrayLength(env, array);
- int len = sizeof(bs->buffer);
-
- if (stream->pos > arrayLength)
- stream->pos = arrayLength;
- if (stream->pos < 0)
- stream->pos = 0;
- if (len + stream->pos > arrayLength)
- len = arrayLength - stream->pos;
-
- (*env)->GetByteArrayRegion(env, array, stream->pos, len, bs->buffer);
- (*env)->DeleteLocalRef(env, array);
-
- stream->rp = (unsigned char *)bs->buffer;
- stream->wp = stream->rp + len;
- stream->pos += len;
- if (len == 0)
- return EOF;
-
- return *stream->rp++;
-}
-
-static void bufferStreamClose(fz_context *ctx, void *state)
-{
- fz_free(ctx, state);
-}
-
-static void bufferStreamSeek(fz_context *ctx, fz_stream *stream, int offset, int whence)
-{
- buffer_state *bs = (buffer_state *)stream->state;
- globals *glo = bs->globals;
- JNIEnv *env = glo->env;
- jbyteArray array = (jbyteArray)(void *)((*env)->GetObjectField(env, glo->thiz, buffer_fid));
- int arrayLength = (*env)->GetArrayLength(env, array);
-
- (*env)->DeleteLocalRef(env, array);
-
- if (whence == 0) /* SEEK_SET */
- stream->pos = offset;
- else if (whence == 1) /* SEEK_CUR */
- stream->pos += offset;
- else if (whence == 2) /* SEEK_END */
- stream->pos = arrayLength + offset;
-
- if (stream->pos > arrayLength)
- stream->pos = arrayLength;
- if (stream->pos < 0)
- stream->pos = 0;
-
- stream->wp = stream->rp;
-}
-
-JNIEXPORT jlong JNICALL
-JNI_FN(MuPDFCore_openBuffer)(JNIEnv * env, jobject thiz, jstring jmagic)
-{
- globals *glo;
- fz_context *ctx;
- jclass clazz;
- fz_stream *stream = NULL;
- buffer_state *bs;
- const char *magic;
-
-#ifdef NDK_PROFILER
- monstartup("libmupdf_java32.so");
-#endif
-
- clazz = (*env)->GetObjectClass(env, thiz);
- global_fid = (*env)->GetFieldID(env, clazz, "globals", "J");
-
- glo = calloc(1, sizeof(*glo));
- if (glo == NULL)
- return 0;
- glo->resolution = 160;
- glo->alerts_initialised = 0;
- glo->env = env;
- glo->thiz = thiz;
- buffer_fid = (*env)->GetFieldID(env, clazz, "fileBuffer", "[B");
-
- magic = (*env)->GetStringUTFChars(env, jmagic, NULL);
- if (magic == NULL)
- {
- LOGE("Failed to get magic");
- free(glo);
- return 0;
- }
-
- /* 128 MB store for low memory devices. Tweak as necessary. */
- glo->ctx = ctx = fz_new_context(NULL, NULL, 128 << 20);
- if (!ctx)
- {
- LOGE("Failed to initialise context");
- (*env)->ReleaseStringUTFChars(env, jmagic, magic);
- free(glo);
- return 0;
- }
-
- fz_register_document_handlers(ctx);
- fz_var(stream);
-
- glo->doc = NULL;
- fz_try(ctx)
- {
- bs = fz_malloc_struct(ctx, buffer_state);
- bs->globals = glo;
- stream = fz_new_stream(ctx, bs, bufferStreamNext, bufferStreamClose);
- stream->seek = bufferStreamSeek;
-
- glo->colorspace = fz_device_rgb(ctx);
-
- LOGI("Opening document...");
- fz_try(ctx)
- {
- glo->current_path = NULL;
- glo->doc = fz_open_document_with_stream(ctx, magic, stream);
- alerts_init(glo);
- }
- fz_catch(ctx)
- {
- fz_throw(ctx, FZ_ERROR_GENERIC, "Cannot open memory document");
- }
- LOGI("Done!");
- }
- fz_always(ctx)
- {
- fz_drop_stream(ctx, stream);
- }
- fz_catch(ctx)
- {
- LOGE("Failed: %s", ctx->error->message);
- fz_drop_document(ctx, glo->doc);
- glo->doc = NULL;
- fz_drop_context(ctx);
- glo->ctx = NULL;
- free(glo);
- glo = NULL;
- }
-
- (*env)->ReleaseStringUTFChars(env, jmagic, magic);
-
- return jlong_cast(glo);
-}
-
-JNIEXPORT int JNICALL
-JNI_FN(MuPDFCore_countPagesInternal)(JNIEnv *env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- int count = 0;
-
- fz_try(ctx)
- {
- count = fz_count_pages(ctx, glo->doc);
- }
- fz_catch(ctx)
- {
- LOGE("exception while counting pages: %s", ctx->error->message);
- }
- return count;
-}
-
-JNIEXPORT jstring JNICALL
-JNI_FN(MuPDFCore_fileFormatInternal)(JNIEnv * env, jobject thiz)
-{
- char info[64];
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
-
- fz_lookup_metadata(ctx, glo->doc, FZ_META_FORMAT, info, sizeof(info));
-
- return (*env)->NewStringUTF(env, info);
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_isUnencryptedPDFInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals_any_thread(env, thiz);
- if (glo == NULL)
- return JNI_FALSE;
-
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- if (idoc == NULL)
- return JNI_FALSE; // Not a PDF
-
- int cryptVer = pdf_crypt_version(ctx, idoc);
- return (cryptVer == 0) ? JNI_TRUE : JNI_FALSE;
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_gotoPageInternal)(JNIEnv *env, jobject thiz, int page)
-{
- int i;
- int furthest;
- int furthest_dist = -1;
- float zoom;
- fz_matrix ctm;
- fz_irect bbox;
- page_cache *pc;
- globals *glo = get_globals(env, thiz);
- if (glo == NULL)
- return;
- fz_context *ctx = glo->ctx;
-
- for (i = 0; i < NUM_CACHE; i++)
- {
- if (glo->pages[i].page != NULL && glo->pages[i].number == page)
- {
- /* The page is already cached */
- glo->current = i;
- return;
- }
-
- if (glo->pages[i].page == NULL)
- {
- /* cache record unused, and so a good one to use */
- furthest = i;
- furthest_dist = INT_MAX;
- }
- else
- {
- int dist = abs(glo->pages[i].number - page);
-
- /* Further away - less likely to be needed again */
- if (dist > furthest_dist)
- {
- furthest_dist = dist;
- furthest = i;
- }
- }
- }
-
- glo->current = furthest;
- pc = &glo->pages[glo->current];
-
- drop_page_cache(glo, pc);
-
- /* In the event of an error, ensure we give a non-empty page */
- pc->width = 100;
- pc->height = 100;
-
- pc->number = page;
- LOGI("Goto page %d...", page);
- fz_try(ctx)
- {
- fz_rect rect;
- LOGI("Load page %d", pc->number);
- pc->page = fz_load_page(ctx, glo->doc, pc->number);
- zoom = glo->resolution / 72;
- fz_bound_page(ctx, pc->page, &pc->media_box);
- fz_scale(&ctm, zoom, zoom);
- rect = pc->media_box;
- fz_round_rect(&bbox, fz_transform_rect(&rect, &ctm));
- pc->width = bbox.x1-bbox.x0;
- pc->height = bbox.y1-bbox.y0;
- }
- fz_catch(ctx)
- {
- LOGE("cannot make displaylist from page %d", pc->number);
- }
-}
-
-JNIEXPORT float JNICALL
-JNI_FN(MuPDFCore_getPageWidth)(JNIEnv *env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- LOGI("PageWidth=%d", glo->pages[glo->current].width);
- return glo->pages[glo->current].width;
-}
-
-JNIEXPORT float JNICALL
-JNI_FN(MuPDFCore_getPageHeight)(JNIEnv *env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- LOGI("PageHeight=%d", glo->pages[glo->current].height);
- return glo->pages[glo->current].height;
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_javascriptSupported)(JNIEnv *env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- if (idoc)
- return pdf_js_supported(ctx, idoc);
- return 0;
-}
-
-static void update_changed_rects(globals *glo, page_cache *pc, pdf_document *idoc)
-{
- fz_context *ctx = glo->ctx;
- pdf_page *ppage = (pdf_page*)pc->page;
- pdf_annot *pannot;
-
- pdf_update_page(ctx, ppage);
- for (pannot = pdf_first_annot(ctx, ppage); pannot; pannot = pdf_next_annot(ctx, pannot))
- {
- if (pannot->changed)
- {
- fz_annot *annot = (fz_annot*)pannot;
- fz_rect bounds;
- rect_node *node;
-
- fz_bound_annot(ctx, annot, &bounds);
-
- node = fz_malloc_struct(ctx, rect_node);
- node->rect = bounds;
- node->next = pc->changed_rects;
- pc->changed_rects = node;
-
- node = fz_malloc_struct(ctx, rect_node);
- node->rect = bounds;
- node->next = pc->hq_changed_rects;
- pc->hq_changed_rects = node;
-
- pannot->changed = 0;
- }
- }
-}
-
-static void update_changed_rects_all_page(globals *glo, page_cache *pc, pdf_document *idoc)
-{
- fz_context *ctx = glo->ctx;
- fz_page *page = pc->page;
- fz_rect bounds;
- rect_node *node;
-
- fz_bound_page(ctx, page, &node->rect);
-
- drop_changed_rects(ctx, &pc->hq_changed_rects);
- drop_changed_rects(ctx, &pc->changed_rects);
-
- node = fz_malloc_struct(ctx, rect_node);
- node->rect = bounds;
- node->next = pc->changed_rects;
- pc->changed_rects = node;
-
- node = fz_malloc_struct(ctx, rect_node);
- node->rect = bounds;
- node->next = pc->hq_changed_rects;
- pc->hq_changed_rects = node;
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_drawPage)(JNIEnv *env, jobject thiz, jobject bitmap,
- int pageW, int pageH, int patchX, int patchY, int patchW, int patchH, jlong cookiePtr)
-{
- AndroidBitmapInfo info;
- void *pixels;
- int ret;
- fz_device *dev = NULL;
- float zoom;
- fz_matrix ctm;
- fz_irect bbox;
- fz_rect rect;
- fz_pixmap *pix = NULL;
- float xscale, yscale;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- page_cache *pc = &glo->pages[glo->current];
- int hq = (patchW < pageW || patchH < pageH);
- fz_matrix scale;
- fz_cookie *cookie = (fz_cookie *)(intptr_t)cookiePtr;
-
- if (pc->page == NULL)
- return 0;
-
- fz_var(pix);
- fz_var(dev);
-
- LOGI("In native method\n");
- if ((ret = AndroidBitmap_getInfo(env, bitmap, &info)) < 0) {
- LOGE("AndroidBitmap_getInfo() failed ! error=%d", ret);
- return 0;
- }
-
- LOGI("Checking format\n");
- if (info.format != ANDROID_BITMAP_FORMAT_RGBA_8888) {
- LOGE("Bitmap format is not RGBA_8888 !");
- return 0;
- }
-
- LOGI("locking pixels\n");
- if ((ret = AndroidBitmap_lockPixels(env, bitmap, &pixels)) < 0) {
- LOGE("AndroidBitmap_lockPixels() failed ! error=%d", ret);
- return 0;
- }
-
- /* Call mupdf to render display list to screen */
- LOGI("Rendering page(%d)=%dx%d patch=[%d,%d,%d,%d]",
- pc->number, pageW, pageH, patchX, patchY, patchW, patchH);
-
- fz_try(ctx)
- {
- fz_irect pixbbox;
- pdf_document *idoc = pdf_specifics(ctx, doc);
-
- if (idoc)
- {
- /* Update the changed-rects for both hq patch and main bitmap */
- update_changed_rects(glo, pc, idoc);
-
- /* Then drop the changed-rects for the bitmap we're about to
- render because we are rendering the entire area */
- drop_changed_rects(ctx, hq ? &pc->hq_changed_rects : &pc->changed_rects);
- }
-
- if (pc->page_list == NULL)
- {
- /* Render to list */
- pc->page_list = fz_new_display_list(ctx, NULL);
- dev = fz_new_list_device(ctx, pc->page_list);
- fz_run_page_contents(ctx, pc->page, dev, &fz_identity, cookie);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
- if (cookie != NULL && cookie->abort)
- {
- fz_drop_display_list(ctx, pc->page_list);
- pc->page_list = NULL;
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
- }
- }
-
- if (pc->annot_list == NULL)
- {
- fz_annot *annot;
- pc->annot_list = fz_new_display_list(ctx, NULL);
- dev = fz_new_list_device(ctx, pc->annot_list);
- for (annot = fz_first_annot(ctx, pc->page); annot; annot = fz_next_annot(ctx, annot))
- fz_run_annot(ctx, annot, dev, &fz_identity, cookie);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
- if (cookie != NULL && cookie->abort)
- {
- fz_drop_display_list(ctx, pc->annot_list);
- pc->annot_list = NULL;
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
- }
- }
-
- bbox.x0 = patchX;
- bbox.y0 = patchY;
- bbox.x1 = patchX + patchW;
- bbox.y1 = patchY + patchH;
- pixbbox = bbox;
- pixbbox.x1 = pixbbox.x0 + info.width;
- /* pixmaps cannot handle right-edge padding, so the bbox must be expanded to match the pixels data */
- pix = fz_new_pixmap_with_bbox_and_data(ctx, glo->colorspace, &pixbbox, 1, pixels);
- if (pc->page_list == NULL && pc->annot_list == NULL)
- {
- fz_clear_pixmap_with_value(ctx, pix, 0xd0);
- break;
- }
- fz_clear_pixmap_with_value(ctx, pix, 0xff);
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
- rect = pc->media_box;
- fz_round_rect(&bbox, fz_transform_rect(&rect, &ctm));
- /* Now, adjust ctm so that it would give the correct page width heights. */
- xscale = (float)pageW/(float)(bbox.x1-bbox.x0);
- yscale = (float)pageH/(float)(bbox.y1-bbox.y0);
- fz_concat(&ctm, &ctm, fz_scale(&scale, xscale, yscale));
- rect = pc->media_box;
- fz_transform_rect(&rect, &ctm);
-
- dev = fz_new_draw_device(ctx, NULL, pix);
-#ifdef TIME_DISPLAY_LIST
- {
- clock_t time;
- int i;
-
- LOGI("Executing display list");
- time = clock();
- for (i=0; i<100;i++) {
-#endif
- if (pc->page_list)
- fz_run_display_list(ctx, pc->page_list, dev, &ctm, &rect, cookie);
- if (cookie != NULL && cookie->abort)
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
-
- if (pc->annot_list)
- fz_run_display_list(ctx, pc->annot_list, dev, &ctm, &rect, cookie);
- if (cookie != NULL && cookie->abort)
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
-
-#ifdef TIME_DISPLAY_LIST
- }
- time = clock() - time;
- LOGI("100 renders in %d (%d per sec)", time, CLOCKS_PER_SEC);
- }
-#endif
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
- fz_drop_pixmap(ctx, pix);
- LOGI("Rendered");
- }
- fz_always(ctx)
- {
- fz_drop_device(ctx, dev);
- dev = NULL;
- }
- fz_catch(ctx)
- {
- LOGE("Render failed");
- }
-
- AndroidBitmap_unlockPixels(env, bitmap);
-
- return 1;
-}
-
-static char *widget_type_string(int t)
-{
- switch(t)
- {
- case PDF_WIDGET_TYPE_PUSHBUTTON: return "pushbutton";
- case PDF_WIDGET_TYPE_CHECKBOX: return "checkbox";
- case PDF_WIDGET_TYPE_RADIOBUTTON: return "radiobutton";
- case PDF_WIDGET_TYPE_TEXT: return "text";
- case PDF_WIDGET_TYPE_LISTBOX: return "listbox";
- case PDF_WIDGET_TYPE_COMBOBOX: return "combobox";
- case PDF_WIDGET_TYPE_SIGNATURE: return "signature";
- default: return "non-widget";
- }
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_updatePageInternal)(JNIEnv *env, jobject thiz, jobject bitmap, int page,
- int pageW, int pageH, int patchX, int patchY, int patchW, int patchH, jlong cookiePtr)
-{
- AndroidBitmapInfo info;
- void *pixels;
- int ret;
- fz_device *dev = NULL;
- float zoom;
- fz_matrix ctm;
- fz_irect bbox;
- fz_rect rect;
- fz_pixmap *pix = NULL;
- float xscale, yscale;
- pdf_document *idoc;
- page_cache *pc = NULL;
- int hq = (patchW < pageW || patchH < pageH);
- int i;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- rect_node *crect;
- fz_matrix scale;
- fz_cookie *cookie = (fz_cookie *)(intptr_t)cookiePtr;
-
- for (i = 0; i < NUM_CACHE; i++)
- {
- if (glo->pages[i].page != NULL && glo->pages[i].number == page)
- {
- pc = &glo->pages[i];
- break;
- }
- }
-
- if (pc == NULL)
- {
- /* Without a cached page object we cannot perform a partial update so
- render the entire bitmap instead */
- JNI_FN(MuPDFCore_gotoPageInternal)(env, thiz, page);
- return JNI_FN(MuPDFCore_drawPage)(env, thiz, bitmap, pageW, pageH, patchX, patchY, patchW, patchH, (jlong)(intptr_t)cookie);
- }
-
- idoc = pdf_specifics(ctx, doc);
-
- fz_var(pix);
- fz_var(dev);
-
- LOGI("In native method\n");
- if ((ret = AndroidBitmap_getInfo(env, bitmap, &info)) < 0) {
- LOGE("AndroidBitmap_getInfo() failed ! error=%d", ret);
- return 0;
- }
-
- LOGI("Checking format\n");
- if (info.format != ANDROID_BITMAP_FORMAT_RGBA_8888) {
- LOGE("Bitmap format is not RGBA_8888 !");
- return 0;
- }
-
- LOGI("locking pixels\n");
- if ((ret = AndroidBitmap_lockPixels(env, bitmap, &pixels)) < 0) {
- LOGE("AndroidBitmap_lockPixels() failed ! error=%d", ret);
- return 0;
- }
-
- /* Call mupdf to render display list to screen */
- LOGI("Rendering page(%d)=%dx%d patch=[%d,%d,%d,%d]",
- pc->number, pageW, pageH, patchX, patchY, patchW, patchH);
-
- fz_try(ctx)
- {
- fz_annot *annot;
- fz_irect pixbbox;
-
- if (idoc)
- {
- /* Update the changed-rects for both hq patch and main bitmap */
- update_changed_rects(glo, pc, idoc);
- }
-
- if (pc->page_list == NULL)
- {
- /* Render to list */
- pc->page_list = fz_new_display_list(ctx, NULL);
- dev = fz_new_list_device(ctx, pc->page_list);
- fz_run_page_contents(ctx, pc->page, dev, &fz_identity, cookie);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
- if (cookie != NULL && cookie->abort)
- {
- fz_drop_display_list(ctx, pc->page_list);
- pc->page_list = NULL;
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
- }
- }
-
- if (pc->annot_list == NULL) {
- pc->annot_list = fz_new_display_list(ctx, NULL);
- dev = fz_new_list_device(ctx, pc->annot_list);
- for (annot = fz_first_annot(ctx, pc->page); annot; annot = fz_next_annot(ctx, annot))
- fz_run_annot(ctx, annot, dev, &fz_identity, cookie);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
- if (cookie != NULL && cookie->abort)
- {
- fz_drop_display_list(ctx, pc->annot_list);
- pc->annot_list = NULL;
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
- }
- }
-
- bbox.x0 = patchX;
- bbox.y0 = patchY;
- bbox.x1 = patchX + patchW;
- bbox.y1 = patchY + patchH;
- pixbbox = bbox;
- pixbbox.x1 = pixbbox.x0 + info.width;
- /* pixmaps cannot handle right-edge padding, so the bbox must be expanded to
- * match the pixels data */
- pix = fz_new_pixmap_with_bbox_and_data(ctx, glo->colorspace, &pixbbox, 1, pixels);
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
- rect = pc->media_box;
- fz_round_rect(&bbox, fz_transform_rect(&rect, &ctm));
- /* Now, adjust ctm so that it would give the correct page width
- * heights. */
- xscale = (float)pageW/(float)(bbox.x1-bbox.x0);
- yscale = (float)pageH/(float)(bbox.y1-bbox.y0);
- fz_concat(&ctm, &ctm, fz_scale(&scale, xscale, yscale));
- rect = pc->media_box;
- fz_transform_rect(&rect, &ctm);
-
- LOGI("Start partial update");
- for (crect = hq ? pc->hq_changed_rects : pc->changed_rects; crect; crect = crect->next)
- {
- fz_irect abox;
- fz_rect arect = crect->rect;
- fz_intersect_rect(fz_transform_rect(&arect, &ctm), &rect);
- fz_round_rect(&abox, &arect);
-
- LOGI("Update rectangle (%d, %d, %d, %d)", abox.x0, abox.y0, abox.x1, abox.y1);
- if (!fz_is_empty_irect(&abox))
- {
- LOGI("And it isn't empty");
- fz_clear_pixmap_rect_with_value(ctx, pix, 0xff, &abox);
- dev = fz_new_draw_device_with_bbox(ctx, NULL, pix, &abox);
- if (pc->page_list)
- fz_run_display_list(ctx, pc->page_list, dev, &ctm, &arect, cookie);
- if (cookie != NULL && cookie->abort)
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
-
- if (pc->annot_list)
- fz_run_display_list(ctx, pc->annot_list, dev, &ctm, &arect, cookie);
- if (cookie != NULL && cookie->abort)
- fz_throw(ctx, FZ_ERROR_GENERIC, "Render aborted");
-
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
- }
- }
- LOGI("End partial update");
-
- /* Drop the changed rects we've just rendered */
- drop_changed_rects(ctx, hq ? &pc->hq_changed_rects : &pc->changed_rects);
-
- LOGI("Rendered");
- }
- fz_always(ctx)
- {
- fz_drop_device(ctx, dev);
- dev = NULL;
- }
- fz_catch(ctx)
- {
- LOGE("Render failed");
- }
-
- fz_drop_pixmap(ctx, pix);
- AndroidBitmap_unlockPixels(env, bitmap);
-
- return 1;
-}
-
-static int
-charat(fz_context *ctx, fz_stext_page *page, int idx)
-{
- fz_char_and_box cab;
- return fz_stext_char_at(ctx, &cab, page, idx)->c;
-}
-
-static fz_rect
-bboxcharat(fz_context *ctx, fz_stext_page *page, int idx)
-{
- fz_char_and_box cab;
- return fz_stext_char_at(ctx, &cab, page, idx)->bbox;
-}
-
-static int
-textlen(fz_stext_page *page)
-{
- int len = 0;
- int block_num;
-
- for (block_num = 0; block_num < page->len; block_num++)
- {
- fz_stext_block *block;
- fz_stext_line *line;
-
- if (page->blocks[block_num].type != FZ_PAGE_BLOCK_TEXT)
- continue;
- block = page->blocks[block_num].u.text;
- for (line = block->lines; line < block->lines + block->len; line++)
- {
- fz_stext_span *span;
-
- for (span = line->first_span; span; span = span->next)
- {
- len += span->len;
- }
- len++; /* pseudo-newline */
- }
- }
- return len;
-}
-
-static int
-countOutlineItems(fz_outline *outline)
-{
- int count = 0;
-
- while (outline)
- {
- if (outline->page >= 0 && outline->title)
- count++;
-
- count += countOutlineItems(outline->down);
- outline = outline->next;
- }
-
- return count;
-}
-
-static int
-fillInOutlineItems(JNIEnv * env, jclass olClass, jmethodID ctor, jobjectArray arr, int pos, fz_outline *outline, int level)
-{
- while (outline)
- {
- int page = outline->page;
- if (page >= 0 && outline->title)
- {
- jobject ol;
- jstring title = (*env)->NewStringUTF(env, outline->title);
- if (title == NULL) return -1;
- ol = (*env)->NewObject(env, olClass, ctor, level, title, page);
- if (ol == NULL) return -1;
- (*env)->SetObjectArrayElement(env, arr, pos, ol);
- (*env)->DeleteLocalRef(env, ol);
- (*env)->DeleteLocalRef(env, title);
- pos++;
- }
- pos = fillInOutlineItems(env, olClass, ctor, arr, pos, outline->down, level+1);
- if (pos < 0) return -1;
- outline = outline->next;
- }
-
- return pos;
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_needsPasswordInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
-
- return fz_needs_password(ctx, glo->doc) ? JNI_TRUE : JNI_FALSE;
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_authenticatePasswordInternal)(JNIEnv *env, jobject thiz, jstring password)
-{
- const char *pw;
- int result;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
-
- pw = (*env)->GetStringUTFChars(env, password, NULL);
- if (pw == NULL)
- return JNI_FALSE;
-
- result = fz_authenticate_password(ctx, glo->doc, (char *)pw);
- (*env)->ReleaseStringUTFChars(env, password, pw);
- return result;
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_hasOutlineInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_outline *outline;
- fz_try(ctx)
- outline = fz_load_outline(ctx, glo->doc);
- fz_catch(ctx)
- outline = NULL;
-
- fz_drop_outline(glo->ctx, outline);
- return (outline == NULL) ? JNI_FALSE : JNI_TRUE;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_getOutlineInternal)(JNIEnv * env, jobject thiz)
-{
- jclass olClass;
- jmethodID ctor;
- jobjectArray arr;
- jobject ol;
- fz_outline *outline;
- int nItems;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- jobjectArray ret;
-
- olClass = (*env)->FindClass(env, PACKAGENAME "/OutlineItem");
- if (olClass == NULL) return NULL;
- ctor = (*env)->GetMethodID(env, olClass, "<init>", "(ILjava/lang/String;I)V");
- if (ctor == NULL) return NULL;
-
- fz_try(ctx)
- outline = fz_load_outline(ctx, glo->doc);
- fz_catch(ctx)
- outline = NULL;
- nItems = countOutlineItems(outline);
-
- arr = (*env)->NewObjectArray(env,
- nItems,
- olClass,
- NULL);
- if (arr == NULL) return NULL;
-
- ret = fillInOutlineItems(env, olClass, ctor, arr, 0, outline, 0) > 0
- ? arr
- :NULL;
- fz_drop_outline(glo->ctx, outline);
- return ret;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_searchPage)(JNIEnv * env, jobject thiz, jstring jtext)
-{
- jclass rectClass;
- jmethodID ctor;
- jobjectArray arr;
- jobject rect;
- fz_stext_sheet *sheet = NULL;
- fz_stext_page *text = NULL;
- fz_device *dev = NULL;
- float zoom;
- fz_matrix ctm;
- int pos;
- int len;
- int i, n;
- int hit_count = 0;
- const char *str;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- page_cache *pc = &glo->pages[glo->current];
-
- rectClass = (*env)->FindClass(env, "android/graphics/RectF");
- if (rectClass == NULL) return NULL;
- ctor = (*env)->GetMethodID(env, rectClass, "<init>", "(FFFF)V");
- if (ctor == NULL) return NULL;
- str = (*env)->GetStringUTFChars(env, jtext, NULL);
- if (str == NULL) return NULL;
-
- fz_var(sheet);
- fz_var(text);
- fz_var(dev);
-
- fz_try(ctx)
- {
- fz_rect mediabox;
-
- if (glo->hit_bbox == NULL)
- glo->hit_bbox = fz_malloc_array(ctx, MAX_SEARCH_HITS, sizeof(*glo->hit_bbox));
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
- sheet = fz_new_stext_sheet(ctx);
- text = fz_new_stext_page(ctx, fz_bound_page(ctx, pc->page, &mediabox));
- dev = fz_new_stext_device(ctx, sheet, text, NULL);
- fz_run_page(ctx, pc->page, dev, &ctm, NULL);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
-
- hit_count = fz_search_stext_page(ctx, text, str, glo->hit_bbox, MAX_SEARCH_HITS);
- }
- fz_always(ctx)
- {
- fz_drop_stext_page(ctx, text);
- fz_drop_stext_sheet(ctx, sheet);
- fz_drop_device(ctx, dev);
- }
- fz_catch(ctx)
- {
- jclass cls;
- (*env)->ReleaseStringUTFChars(env, jtext, str);
- cls = (*env)->FindClass(env, "java/lang/OutOfMemoryError");
- if (cls != NULL)
- (*env)->ThrowNew(env, cls, "Out of memory in MuPDFCore_searchPage");
- (*env)->DeleteLocalRef(env, cls);
-
- return NULL;
- }
-
- (*env)->ReleaseStringUTFChars(env, jtext, str);
-
- arr = (*env)->NewObjectArray(env,
- hit_count,
- rectClass,
- NULL);
- if (arr == NULL) return NULL;
-
- for (i = 0; i < hit_count; i++) {
- rect = (*env)->NewObject(env, rectClass, ctor,
- (float) (glo->hit_bbox[i].x0),
- (float) (glo->hit_bbox[i].y0),
- (float) (glo->hit_bbox[i].x1),
- (float) (glo->hit_bbox[i].y1));
- if (rect == NULL)
- return NULL;
- (*env)->SetObjectArrayElement(env, arr, i, rect);
- (*env)->DeleteLocalRef(env, rect);
- }
-
- return arr;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_text)(JNIEnv * env, jobject thiz)
-{
- jclass textCharClass;
- jclass textSpanClass;
- jclass textLineClass;
- jclass textBlockClass;
- jmethodID ctor;
- jobjectArray barr = NULL;
- fz_stext_sheet *sheet = NULL;
- fz_stext_page *text = NULL;
- fz_device *dev = NULL;
- float zoom;
- fz_matrix ctm;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- page_cache *pc = &glo->pages[glo->current];
-
- textCharClass = (*env)->FindClass(env, PACKAGENAME "/TextChar");
- if (textCharClass == NULL) return NULL;
- textSpanClass = (*env)->FindClass(env, "[L" PACKAGENAME "/TextChar;");
- if (textSpanClass == NULL) return NULL;
- textLineClass = (*env)->FindClass(env, "[[L" PACKAGENAME "/TextChar;");
- if (textLineClass == NULL) return NULL;
- textBlockClass = (*env)->FindClass(env, "[[[L" PACKAGENAME "/TextChar;");
- if (textBlockClass == NULL) return NULL;
- ctor = (*env)->GetMethodID(env, textCharClass, "<init>", "(FFFFC)V");
- if (ctor == NULL) return NULL;
-
- fz_var(sheet);
- fz_var(text);
- fz_var(dev);
-
- fz_try(ctx)
- {
- fz_rect mediabox;
- int b, l, s, c;
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
- sheet = fz_new_stext_sheet(ctx);
- text = fz_new_stext_page(ctx, fz_bound_page(ctx, pc->page, &mediabox));
- dev = fz_new_stext_device(ctx, sheet, text, NULL);
- fz_run_page(ctx, pc->page, dev, &ctm, NULL);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
-
- barr = (*env)->NewObjectArray(env, text->len, textBlockClass, NULL);
- if (barr == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "NewObjectArray failed");
-
- for (b = 0; b < text->len; b++)
- {
- fz_stext_block *block;
- jobjectArray *larr;
-
- if (text->blocks[b].type != FZ_PAGE_BLOCK_TEXT)
- continue;
- block = text->blocks[b].u.text;
- larr = (*env)->NewObjectArray(env, block->len, textLineClass, NULL);
- if (larr == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "NewObjectArray failed");
-
- for (l = 0; l < block->len; l++)
- {
- fz_stext_line *line = &block->lines[l];
- jobjectArray *sarr;
- fz_stext_span *span;
- int len = 0;
-
- for (span = line->first_span; span; span = span->next)
- len++;
-
- sarr = (*env)->NewObjectArray(env, len, textSpanClass, NULL);
- if (sarr == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "NewObjectArray failed");
-
- for (s=0, span = line->first_span; span; s++, span = span->next)
- {
- jobjectArray *carr = (*env)->NewObjectArray(env, span->len, textCharClass, NULL);
- if (carr == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "NewObjectArray failed");
-
- for (c = 0; c < span->len; c++)
- {
- fz_stext_char *ch = &span->text[c];
- fz_rect bbox;
- fz_stext_char_bbox(ctx, &bbox, span, c);
- jobject cobj = (*env)->NewObject(env, textCharClass, ctor, bbox.x0, bbox.y0, bbox.x1, bbox.y1, ch->c);
- if (cobj == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "NewObjectfailed");
-
- (*env)->SetObjectArrayElement(env, carr, c, cobj);
- (*env)->DeleteLocalRef(env, cobj);
- }
-
- (*env)->SetObjectArrayElement(env, sarr, s, carr);
- (*env)->DeleteLocalRef(env, carr);
- }
-
- (*env)->SetObjectArrayElement(env, larr, l, sarr);
- (*env)->DeleteLocalRef(env, sarr);
- }
-
- (*env)->SetObjectArrayElement(env, barr, b, larr);
- (*env)->DeleteLocalRef(env, larr);
- }
- }
- fz_always(ctx)
- {
- fz_drop_stext_page(ctx, text);
- fz_drop_stext_sheet(ctx, sheet);
- fz_drop_device(ctx, dev);
- }
- fz_catch(ctx)
- {
- jclass cls = (*env)->FindClass(env, "java/lang/OutOfMemoryError");
- if (cls != NULL)
- (*env)->ThrowNew(env, cls, "Out of memory in MuPDFCore_text");
- (*env)->DeleteLocalRef(env, cls);
-
- return NULL;
- }
-
- return barr;
-}
-
-JNIEXPORT jbyteArray JNICALL
-JNI_FN(MuPDFCore_textAsHtml)(JNIEnv * env, jobject thiz)
-{
- fz_stext_sheet *sheet = NULL;
- fz_stext_page *text = NULL;
- fz_device *dev = NULL;
- fz_matrix ctm;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- page_cache *pc = &glo->pages[glo->current];
- jbyteArray bArray = NULL;
- fz_buffer *buf = NULL;
- fz_output *out = NULL;
- size_t len;
- unsigned char *data;
-
- fz_var(sheet);
- fz_var(text);
- fz_var(dev);
- fz_var(buf);
- fz_var(out);
-
- fz_try(ctx)
- {
- fz_rect mediabox;
- int b, l, s, c;
-
- ctm = fz_identity;
- sheet = fz_new_stext_sheet(ctx);
- text = fz_new_stext_page(ctx, fz_bound_page(ctx, pc->page, &mediabox));
- dev = fz_new_stext_device(ctx, sheet, text, NULL);
- fz_run_page(ctx, pc->page, dev, &ctm, NULL);
- fz_close_device(ctx, dev);
- fz_drop_device(ctx, dev);
- dev = NULL;
-
- fz_analyze_text(ctx, sheet, text);
-
- buf = fz_new_buffer(ctx, 256);
- out = fz_new_output_with_buffer(ctx, buf);
- fz_printf(ctx, out, "<html>\n");
- fz_printf(ctx, out, "<style>\n");
- fz_printf(ctx, out, "body{margin:0;}\n");
- fz_printf(ctx, out, "div.page{background-color:white;}\n");
- fz_printf(ctx, out, "div.block{margin:0pt;padding:0pt;}\n");
- fz_printf(ctx, out, "div.metaline{display:table;width:100%%}\n");
- fz_printf(ctx, out, "div.line{display:table-row;}\n");
- fz_printf(ctx, out, "div.cell{display:table-cell;padding-left:0.25em;padding-right:0.25em}\n");
- //fz_printf(ctx, out, "p{margin:0;padding:0;}\n");
- fz_printf(ctx, out, "</style>\n");
- fz_printf(ctx, out, "<body style=\"margin:0\"><div style=\"padding:10px\" id=\"content\">");
- fz_print_stext_page_html(ctx, out, text);
- fz_printf(ctx, out, "</div></body>\n");
- fz_printf(ctx, out, "<style>\n");
- fz_print_stext_sheet(ctx, out, sheet);
- fz_printf(ctx, out, "</style>\n</html>\n");
- fz_drop_output(ctx, out);
- out = NULL;
-
- len = fz_buffer_storage(ctx, buf, &data);
- bArray = (*env)->NewByteArray(env, len);
- if (bArray == NULL)
- fz_throw(ctx, FZ_ERROR_GENERIC, "Failed to make byteArray");
- (*env)->SetByteArrayRegion(env, bArray, 0, len, (const jbyte *)data);
- }
- fz_always(ctx)
- {
- fz_drop_stext_page(ctx, text);
- fz_drop_stext_sheet(ctx, sheet);
- fz_drop_device(ctx, dev);
- fz_drop_output(ctx, out);
- fz_drop_buffer(ctx, buf);
- }
- fz_catch(ctx)
- {
- jclass cls = (*env)->FindClass(env, "java/lang/OutOfMemoryError");
- if (cls != NULL)
- (*env)->ThrowNew(env, cls, "Out of memory in MuPDFCore_textAsHtml");
- (*env)->DeleteLocalRef(env, cls);
-
- return NULL;
- }
-
- return bArray;
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_addMarkupAnnotationInternal)(JNIEnv * env, jobject thiz, jobjectArray points, fz_annot_type type)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- pdf_document *idoc = pdf_specifics(ctx, doc);
- page_cache *pc = &glo->pages[glo->current];
- jclass pt_cls;
- jfieldID x_fid, y_fid;
- int i, n;
- float *pts = NULL;
- float color[3];
- float alpha;
- float line_height;
- float line_thickness;
-
- if (idoc == NULL)
- return;
-
- switch (type)
- {
- case PDF_ANNOT_HIGHLIGHT:
- color[0] = 1.0;
- color[1] = 1.0;
- color[2] = 0.0;
- alpha = 0.5;
- line_thickness = 1.0;
- line_height = 0.5;
- break;
- case PDF_ANNOT_UNDERLINE:
- color[0] = 0.0;
- color[1] = 0.0;
- color[2] = 1.0;
- alpha = 1.0;
- line_thickness = LINE_THICKNESS;
- line_height = UNDERLINE_HEIGHT;
- break;
- case PDF_ANNOT_STRIKE_OUT:
- color[0] = 1.0;
- color[1] = 0.0;
- color[2] = 0.0;
- alpha = 1.0;
- line_thickness = LINE_THICKNESS;
- line_height = STRIKE_HEIGHT;
- break;
- default:
- return;
- }
-
- fz_var(pts);
- fz_try(ctx)
- {
- fz_annot *annot;
- fz_matrix ctm;
-
- float zoom = glo->resolution / 72;
- zoom = 1.0 / zoom;
- fz_scale(&ctm, zoom, zoom);
- pt_cls = (*env)->FindClass(env, "android/graphics/PointF");
- if (pt_cls == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "FindClass");
- x_fid = (*env)->GetFieldID(env, pt_cls, "x", "F");
- if (x_fid == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "GetFieldID(x)");
- y_fid = (*env)->GetFieldID(env, pt_cls, "y", "F");
- if (y_fid == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "GetFieldID(y)");
-
- n = (*env)->GetArrayLength(env, points);
-
- pts = fz_malloc_array(ctx, n * 2, sizeof(float));
-
- for (i = 0; i < n; i++)
- {
- fz_point pt;
- jobject opt = (*env)->GetObjectArrayElement(env, points, i);
- pt.x = opt ? (*env)->GetFloatField(env, opt, x_fid) : 0.0f;
- pt.y = opt ? (*env)->GetFloatField(env, opt, y_fid) : 0.0f;
- fz_transform_point(&pt, &ctm);
- pts[i*2+0] = pt.x;
- pts[i*2+1] = pt.y;
- }
-
- annot = (fz_annot *)pdf_create_annot(ctx, (pdf_page *)pc->page, type);
-
- pdf_set_annot_quad_points(ctx, (pdf_annot *)annot, n / 4, pts);
- pdf_set_markup_appearance(ctx, idoc, (pdf_annot *)annot, color, alpha, line_thickness, line_height);
-
- dump_annotation_display_lists(glo);
- }
- fz_always(ctx)
- {
- fz_free(ctx, pts);
- }
- fz_catch(ctx)
- {
- LOGE("addStrikeOutAnnotation: %s failed", ctx->error->message);
- jclass cls = (*env)->FindClass(env, "java/lang/OutOfMemoryError");
- if (cls != NULL)
- (*env)->ThrowNew(env, cls, "Out of memory in MuPDFCore_searchPage");
- (*env)->DeleteLocalRef(env, cls);
- }
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_addInkAnnotationInternal)(JNIEnv * env, jobject thiz, jobjectArray arcs)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- pdf_document *idoc = pdf_specifics(ctx, doc);
- page_cache *pc = &glo->pages[glo->current];
- jclass pt_cls;
- jfieldID x_fid, y_fid;
- int i, j, k, n;
- float *pts = NULL;
- int *counts = NULL;
- int total = 0;
- float color[4];
-
- if (idoc == NULL)
- return;
-
- color[0] = 1.0;
- color[1] = 0.0;
- color[2] = 0.0;
- color[3] = 0.0;
-
- fz_var(pts);
- fz_var(counts);
- fz_try(ctx)
- {
- pdf_annot *annot;
- fz_matrix ctm;
-
- float zoom = glo->resolution / 72;
- zoom = 1.0 / zoom;
- fz_scale(&ctm, zoom, zoom);
- pt_cls = (*env)->FindClass(env, "android/graphics/PointF");
- if (pt_cls == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "FindClass");
- x_fid = (*env)->GetFieldID(env, pt_cls, "x", "F");
- if (x_fid == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "GetFieldID(x)");
- y_fid = (*env)->GetFieldID(env, pt_cls, "y", "F");
- if (y_fid == NULL) fz_throw(ctx, FZ_ERROR_GENERIC, "GetFieldID(y)");
-
- n = (*env)->GetArrayLength(env, arcs);
-
- counts = fz_malloc_array(ctx, n, sizeof(int));
-
- for (i = 0; i < n; i++)
- {
- jobjectArray arc = (jobjectArray)(*env)->GetObjectArrayElement(env, arcs, i);
- int count = (*env)->GetArrayLength(env, arc);
-
- counts[i] = count;
- total += count;
- }
-
- pts = fz_malloc_array(ctx, total * 2, sizeof(float));
-
- k = 0;
- for (i = 0; i < n; i++)
- {
- jobjectArray arc = (jobjectArray)(*env)->GetObjectArrayElement(env, arcs, i);
- int count = counts[i];
-
- for (j = 0; j < count; j++)
- {
- jobject jpt = (*env)->GetObjectArrayElement(env, arc, j);
- fz_point pt;
- pt.x = jpt ? (*env)->GetFloatField(env, jpt, x_fid) : 0.0f;
- pt.y = jpt ? (*env)->GetFloatField(env, jpt, y_fid) : 0.0f;
- (*env)->DeleteLocalRef(env, jpt);
- fz_transform_point(&pt, &ctm);
- pts[k++] = pt.x;
- pts[k++] = pt.y;
- }
- (*env)->DeleteLocalRef(env, arc);
- }
-
- annot = pdf_create_annot(ctx, (pdf_page *)pc->page, PDF_ANNOT_INK);
-
- pdf_set_annot_border(ctx, annot, INK_THICKNESS);
- pdf_set_annot_color(ctx, annot, 3, color);
- pdf_set_annot_ink_list(ctx, annot, n, counts, pts);
-
- dump_annotation_display_lists(glo);
- }
- fz_always(ctx)
- {
- fz_free(ctx, pts);
- fz_free(ctx, counts);
- }
- fz_catch(ctx)
- {
- LOGE("addInkAnnotation: %s failed", ctx->error->message);
- jclass cls = (*env)->FindClass(env, "java/lang/OutOfMemoryError");
- if (cls != NULL)
- (*env)->ThrowNew(env, cls, "Out of memory in MuPDFCore_searchPage");
- (*env)->DeleteLocalRef(env, cls);
- }
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_deleteAnnotationInternal)(JNIEnv * env, jobject thiz, int annot_index)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_document *doc = glo->doc;
- pdf_document *idoc = pdf_specifics(ctx, doc);
- page_cache *pc = &glo->pages[glo->current];
- fz_annot *annot;
- int i;
-
- if (idoc == NULL)
- return;
-
- fz_try(ctx)
- {
- annot = fz_first_annot(ctx, pc->page);
- for (i = 0; i < annot_index && annot; i++)
- annot = fz_next_annot(ctx, annot);
-
- if (annot)
- {
- pdf_delete_annot(ctx, (pdf_page *)pc->page, (pdf_annot *)annot);
- update_changed_rects_all_page(glo, pc, idoc);
- dump_annotation_display_lists(glo);
- }
- }
- fz_catch(ctx)
- {
- LOGE("deleteAnnotationInternal: %s", ctx->error->message);
- }
-}
-
-/* Close the document, at least enough to be able to save over it. This
- * may be called again later, so must be idempotent. */
-static void close_doc(globals *glo)
-{
- int i;
-
- fz_free(glo->ctx, glo->hit_bbox);
- glo->hit_bbox = NULL;
-
- for (i = 0; i < NUM_CACHE; i++)
- drop_page_cache(glo, &glo->pages[i]);
-
- alerts_fin(glo);
-
- fz_drop_document(glo->ctx, glo->doc);
- glo->doc = NULL;
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_destroying)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
-
- if (glo == NULL)
- return;
- LOGI("Destroying");
- fz_free(glo->ctx, glo->current_path);
- glo->current_path = NULL;
- close_doc(glo);
- fz_drop_context(glo->ctx);
- glo->ctx = NULL;
- free(glo);
-#ifdef MEMENTO
- LOGI("Destroying dump start");
- Memento_fin();
- LOGI("Destroying dump end");
-#endif
-#ifdef NDK_PROFILER
- // Apparently we should really be writing to whatever path we get
- // from calling getFilesDir() in the java part, which supposedly
- // gives /sdcard/data/data/com.artifex.MuPDF/gmon.out, but that's
- // unfriendly.
- setenv("CPUPROFILE", "/sdcard/gmon.out", 1);
- moncleanup();
-#endif
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_getPageLinksInternal)(JNIEnv * env, jobject thiz, int pageNumber)
-{
- jclass linkInfoClass;
- jclass linkInfoInternalClass;
- jclass linkInfoExternalClass;
- jclass linkInfoRemoteClass;
- jmethodID ctorInternal;
- jmethodID ctorExternal;
- jmethodID ctorRemote;
- jobjectArray arr;
- jobject linkInfo;
- fz_matrix ctm;
- float zoom;
- fz_link *list;
- fz_link *link;
- int count;
- page_cache *pc;
- globals *glo = get_globals(env, thiz);
-
- linkInfoClass = (*env)->FindClass(env, PACKAGENAME "/LinkInfo");
- if (linkInfoClass == NULL) return NULL;
- linkInfoInternalClass = (*env)->FindClass(env, PACKAGENAME "/LinkInfoInternal");
- if (linkInfoInternalClass == NULL) return NULL;
- linkInfoExternalClass = (*env)->FindClass(env, PACKAGENAME "/LinkInfoExternal");
- if (linkInfoExternalClass == NULL) return NULL;
- linkInfoRemoteClass = (*env)->FindClass(env, PACKAGENAME "/LinkInfoRemote");
- if (linkInfoRemoteClass == NULL) return NULL;
- ctorInternal = (*env)->GetMethodID(env, linkInfoInternalClass, "<init>", "(FFFFI)V");
- if (ctorInternal == NULL) return NULL;
- ctorExternal = (*env)->GetMethodID(env, linkInfoExternalClass, "<init>", "(FFFFLjava/lang/String;)V");
- if (ctorExternal == NULL) return NULL;
- ctorRemote = (*env)->GetMethodID(env, linkInfoRemoteClass, "<init>", "(FFFFLjava/lang/String;IZ)V");
- if (ctorRemote == NULL) return NULL;
-
- JNI_FN(MuPDFCore_gotoPageInternal)(env, thiz, pageNumber);
- pc = &glo->pages[glo->current];
- if (pc->page == NULL || pc->number != pageNumber)
- return NULL;
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
-
- list = fz_load_links(glo->ctx, pc->page);
- count = 0;
- for (link = list; link; link = link->next)
- {
- if (link->uri)
- count++ ;
- }
-
- arr = (*env)->NewObjectArray(env, count, linkInfoClass, NULL);
- if (arr == NULL)
- {
- fz_drop_link(glo->ctx, list);
- return NULL;
- }
-
- count = 0;
- for (link = list; link; link = link->next)
- {
- fz_rect rect = link->rect;
- fz_transform_rect(&rect, &ctm);
-
- if (!fz_is_external_link(glo->ctx, link->uri))
- {
- linkInfo = (*env)->NewObject(env, linkInfoInternalClass, ctorInternal,
- (float)rect.x0, (float)rect.y0, (float)rect.x1, (float)rect.y1,
- fz_resolve_link(glo->ctx, link->doc, link->uri, NULL, NULL));
- }
- else
- {
- jstring juri = (*env)->NewStringUTF(env, link->uri);
- linkInfo = (*env)->NewObject(env, linkInfoExternalClass, ctorExternal,
- (float)rect.x0, (float)rect.y0, (float)rect.x1, (float)rect.y1,
- juri);
- }
-
- if (linkInfo == NULL)
- {
- fz_drop_link(glo->ctx, list);
- return NULL;
- }
- (*env)->SetObjectArrayElement(env, arr, count, linkInfo);
- (*env)->DeleteLocalRef(env, linkInfo);
- count++;
- }
- fz_drop_link(glo->ctx, list);
-
- return arr;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_getWidgetAreasInternal)(JNIEnv * env, jobject thiz, int pageNumber)
-{
- jclass rectFClass;
- jmethodID ctor;
- jobjectArray arr;
- jobject rectF;
- pdf_document *idoc;
- pdf_widget *widget;
- fz_matrix ctm;
- float zoom;
- int count;
- page_cache *pc;
- globals *glo = get_globals(env, thiz);
- if (glo == NULL)
- return NULL;
- fz_context *ctx = glo->ctx;
-
- rectFClass = (*env)->FindClass(env, "android/graphics/RectF");
- if (rectFClass == NULL) return NULL;
- ctor = (*env)->GetMethodID(env, rectFClass, "<init>", "(FFFF)V");
- if (ctor == NULL) return NULL;
-
- JNI_FN(MuPDFCore_gotoPageInternal)(env, thiz, pageNumber);
- pc = &glo->pages[glo->current];
- if (pc->number != pageNumber || pc->page == NULL)
- return NULL;
-
- idoc = pdf_specifics(ctx, glo->doc);
- if (idoc == NULL)
- return NULL;
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
-
- count = 0;
- for (widget = pdf_first_widget(ctx, idoc, (pdf_page *)pc->page); widget; widget = pdf_next_widget(ctx, widget))
- count ++;
-
- arr = (*env)->NewObjectArray(env, count, rectFClass, NULL);
- if (arr == NULL) return NULL;
-
- count = 0;
- for (widget = pdf_first_widget(ctx, idoc, (pdf_page *)pc->page); widget; widget = pdf_next_widget(ctx, widget))
- {
- fz_rect rect;
- pdf_bound_widget(ctx, widget, &rect);
- fz_transform_rect(&rect, &ctm);
-
- rectF = (*env)->NewObject(env, rectFClass, ctor,
- (float)rect.x0, (float)rect.y0, (float)rect.x1, (float)rect.y1);
- if (rectF == NULL) return NULL;
- (*env)->SetObjectArrayElement(env, arr, count, rectF);
- (*env)->DeleteLocalRef(env, rectF);
-
- count ++;
- }
-
- return arr;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_getAnnotationsInternal)(JNIEnv * env, jobject thiz, int pageNumber)
-{
- jclass annotClass;
- jmethodID ctor;
- jobjectArray arr;
- jobject jannot;
- fz_annot *annot;
- fz_matrix ctm;
- float zoom;
- int count;
- page_cache *pc;
- globals *glo = get_globals(env, thiz);
- if (glo == NULL)
- return NULL;
- fz_context *ctx = glo->ctx;
-
- annotClass = (*env)->FindClass(env, PACKAGENAME "/Annotation");
- if (annotClass == NULL) return NULL;
- ctor = (*env)->GetMethodID(env, annotClass, "<init>", "(FFFFI)V");
- if (ctor == NULL) return NULL;
-
- JNI_FN(MuPDFCore_gotoPageInternal)(env, thiz, pageNumber);
- pc = &glo->pages[glo->current];
- if (pc->number != pageNumber || pc->page == NULL)
- return NULL;
-
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
-
- count = 0;
- for (annot = fz_first_annot(ctx, pc->page); annot; annot = fz_next_annot(ctx, annot))
- count ++;
-
- arr = (*env)->NewObjectArray(env, count, annotClass, NULL);
- if (arr == NULL) return NULL;
-
- count = 0;
- for (annot = fz_first_annot(ctx, pc->page); annot; annot = fz_next_annot(ctx, annot))
- {
- fz_rect rect;
- fz_annot_type type = pdf_annot_type(ctx, (pdf_annot *)annot);
- fz_bound_annot(ctx, annot, &rect);
- fz_transform_rect(&rect, &ctm);
-
- jannot = (*env)->NewObject(env, annotClass, ctor,
- (float)rect.x0, (float)rect.y0, (float)rect.x1, (float)rect.y1, type);
- if (jannot == NULL) return NULL;
- (*env)->SetObjectArrayElement(env, arr, count, jannot);
- (*env)->DeleteLocalRef(env, jannot);
-
- count ++;
- }
-
- return arr;
-}
-
-JNIEXPORT int JNICALL
-JNI_FN(MuPDFCore_passClickEventInternal)(JNIEnv * env, jobject thiz, int pageNumber, float x, float y)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- fz_matrix ctm;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- float zoom;
- fz_point p;
- pdf_ui_event event;
- int changed = 0;
- page_cache *pc;
-
- if (idoc == NULL)
- return 0;
-
- JNI_FN(MuPDFCore_gotoPageInternal)(env, thiz, pageNumber);
- pc = &glo->pages[glo->current];
- if (pc->number != pageNumber || pc->page == NULL)
- return 0;
-
- p.x = x;
- p.y = y;
-
- /* Ultimately we should probably return a pointer to a java structure
- * with the link details in, but for now, page number will suffice.
- */
- zoom = glo->resolution / 72;
- fz_scale(&ctm, zoom, zoom);
- fz_invert_matrix(&ctm, &ctm);
-
- fz_transform_point(&p, &ctm);
-
- fz_try(ctx)
- {
- event.etype = PDF_EVENT_TYPE_POINTER;
- event.event.pointer.pt = p;
- event.event.pointer.ptype = PDF_POINTER_DOWN;
- changed = pdf_pass_event(ctx, idoc, (pdf_page *)pc->page, &event);
- event.event.pointer.ptype = PDF_POINTER_UP;
- changed |= pdf_pass_event(ctx, idoc, (pdf_page *)pc->page, &event);
- if (changed) {
- dump_annotation_display_lists(glo);
- }
- }
- fz_catch(ctx)
- {
- LOGE("passClickEvent: %s", ctx->error->message);
- }
-
- return changed;
-}
-
-JNIEXPORT jstring JNICALL
-JNI_FN(MuPDFCore_getFocusedWidgetTextInternal)(JNIEnv * env, jobject thiz)
-{
- char *text = "";
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
-
- fz_try(ctx)
- {
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
-
- if (idoc)
- {
- pdf_widget *focus = pdf_focused_widget(ctx, idoc);
-
- if (focus)
- text = pdf_text_widget_text(ctx, idoc, focus);
- }
- }
- fz_catch(ctx)
- {
- LOGE("getFocusedWidgetText failed: %s", ctx->error->message);
- }
-
- return (*env)->NewStringUTF(env, text);
-}
-
-JNIEXPORT int JNICALL
-JNI_FN(MuPDFCore_setFocusedWidgetTextInternal)(JNIEnv * env, jobject thiz, jstring jtext)
-{
- const char *text;
- int result = 0;
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
-
- text = (*env)->GetStringUTFChars(env, jtext, NULL);
- if (text == NULL)
- {
- LOGE("Failed to get text");
- return 0;
- }
-
- fz_try(ctx)
- {
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
-
- if (idoc)
- {
- pdf_widget *focus = pdf_focused_widget(ctx, idoc);
-
- if (focus)
- {
- result = pdf_text_widget_set_text(ctx, idoc, focus, (char *)text);
- dump_annotation_display_lists(glo);
- }
- }
- }
- fz_catch(ctx)
- {
- LOGE("setFocusedWidgetText failed: %s", ctx->error->message);
- }
-
- (*env)->ReleaseStringUTFChars(env, jtext, text);
-
- return result;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_getFocusedWidgetChoiceOptions)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
- int type;
- int nopts, i;
- char **opts = NULL;
- jclass stringClass;
- jobjectArray arr;
-
- if (idoc == NULL)
- return NULL;
-
- focus = pdf_focused_widget(ctx, idoc);
- if (focus == NULL)
- return NULL;
-
- type = pdf_widget_type(ctx, focus);
- if (type != PDF_WIDGET_TYPE_LISTBOX && type != PDF_WIDGET_TYPE_COMBOBOX)
- return NULL;
-
- fz_var(opts);
- fz_try(ctx)
- {
- nopts = pdf_choice_widget_options(ctx, idoc, focus, 0, NULL);
- opts = fz_malloc(ctx, nopts * sizeof(*opts));
- (void)pdf_choice_widget_options(ctx, idoc, focus, 0, opts);
- }
- fz_catch(ctx)
- {
- fz_free(ctx, opts);
- LOGE("Failed in getFocuseedWidgetChoiceOptions");
- return NULL;
- }
-
- stringClass = (*env)->FindClass(env, "java/lang/String");
-
- arr = (*env)->NewObjectArray(env, nopts, stringClass, NULL);
-
- for (i = 0; i < nopts; i++)
- {
- jstring s = (*env)->NewStringUTF(env, opts[i]);
- if (s != NULL)
- (*env)->SetObjectArrayElement(env, arr, i, s);
-
- (*env)->DeleteLocalRef(env, s);
- }
-
- fz_free(ctx, opts);
-
- return arr;
-}
-
-JNIEXPORT jobjectArray JNICALL
-JNI_FN(MuPDFCore_getFocusedWidgetChoiceSelected)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
- int type;
- int nsel, i;
- char **sel = NULL;
- jclass stringClass;
- jobjectArray arr;
-
- if (idoc == NULL)
- return NULL;
-
- focus = pdf_focused_widget(ctx, idoc);
- if (focus == NULL)
- return NULL;
-
- type = pdf_widget_type(ctx, focus);
- if (type != PDF_WIDGET_TYPE_LISTBOX && type != PDF_WIDGET_TYPE_COMBOBOX)
- return NULL;
-
- fz_var(sel);
- fz_try(ctx)
- {
- nsel = pdf_choice_widget_value(ctx, idoc, focus, NULL);
- sel = fz_malloc(ctx, nsel * sizeof(*sel));
- (void)pdf_choice_widget_value(ctx, idoc, focus, sel);
- }
- fz_catch(ctx)
- {
- fz_free(ctx, sel);
- LOGE("Failed in getFocuseedWidgetChoiceOptions");
- return NULL;
- }
-
- stringClass = (*env)->FindClass(env, "java/lang/String");
-
- arr = (*env)->NewObjectArray(env, nsel, stringClass, NULL);
-
- for (i = 0; i < nsel; i++)
- {
- jstring s = (*env)->NewStringUTF(env, sel[i]);
- if (s != NULL)
- (*env)->SetObjectArrayElement(env, arr, i, s);
-
- (*env)->DeleteLocalRef(env, s);
- }
-
- fz_free(ctx, sel);
-
- return arr;
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_setFocusedWidgetChoiceSelectedInternal)(JNIEnv * env, jobject thiz, jobjectArray arr)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
- int type;
- int nsel, i;
- char **sel = NULL;
- jstring *objs = NULL;
-
- if (idoc == NULL)
- return;
-
- focus = pdf_focused_widget(ctx, idoc);
- if (focus == NULL)
- return;
-
- type = pdf_widget_type(ctx, focus);
- if (type != PDF_WIDGET_TYPE_LISTBOX && type != PDF_WIDGET_TYPE_COMBOBOX)
- return;
-
- nsel = (*env)->GetArrayLength(env, arr);
-
- sel = calloc(nsel, sizeof(*sel));
- objs = calloc(nsel, sizeof(*objs));
- if (objs == NULL || sel == NULL)
- {
- free(sel);
- free(objs);
- LOGE("Failed in setFocusWidgetChoiceSelected");
- return;
- }
-
- for (i = 0; i < nsel; i++)
- {
- objs[i] = (jstring)(*env)->GetObjectArrayElement(env, arr, i);
- sel[i] = (char *)(*env)->GetStringUTFChars(env, objs[i], NULL);
- }
-
- fz_try(ctx)
- {
- pdf_choice_widget_set_value(ctx, idoc, focus, nsel, sel);
- dump_annotation_display_lists(glo);
- }
- fz_catch(ctx)
- {
- LOGE("Failed in setFocusWidgetChoiceSelected");
- }
-
- for (i = 0; i < nsel; i++)
- (*env)->ReleaseStringUTFChars(env, objs[i], sel[i]);
-
- free(sel);
- free(objs);
-}
-
-JNIEXPORT int JNICALL
-JNI_FN(MuPDFCore_getFocusedWidgetTypeInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
-
- if (ctx == NULL || idoc == NULL)
- return NONE;
-
- focus = pdf_focused_widget(ctx, idoc);
-
- if (focus == NULL)
- return NONE;
-
- switch (pdf_widget_type(ctx, focus))
- {
- case PDF_WIDGET_TYPE_TEXT: return TEXT;
- case PDF_WIDGET_TYPE_LISTBOX: return LISTBOX;
- case PDF_WIDGET_TYPE_COMBOBOX: return COMBOBOX;
- case PDF_WIDGET_TYPE_SIGNATURE: return SIGNATURE;
- }
-
- return NONE;
-}
-
-/* This enum should be kept in line with SignatureState in MuPDFPageView.java */
-enum
-{
- Signature_NoSupport,
- Signature_Unsigned,
- Signature_Signed
-};
-
-JNIEXPORT int JNICALL
-JNI_FN(MuPDFCore_getFocusedWidgetSignatureState)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
-
- if (ctx == NULL || idoc == NULL)
- return Signature_NoSupport;
-
- focus = pdf_focused_widget(ctx, idoc);
-
- if (focus == NULL)
- return Signature_NoSupport;
-
- if (!pdf_signatures_supported(ctx))
- return Signature_NoSupport;
-
- return pdf_dict_get(ctx, ((pdf_annot *)focus)->obj, PDF_NAME_V) ? Signature_Signed : Signature_Unsigned;
-}
-
-JNIEXPORT jstring JNICALL
-JNI_FN(MuPDFCore_checkFocusedSignatureInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
- char ebuf[256] = "Failed";
-
- if (idoc == NULL)
- goto exit;
-
- focus = pdf_focused_widget(ctx, idoc);
-
- if (focus == NULL)
- goto exit;
-
- if (pdf_check_signature(ctx, idoc, focus, glo->current_path, ebuf, sizeof(ebuf)))
- {
- strcpy(ebuf, "Signature is valid");
- }
-
-exit:
- return (*env)->NewStringUTF(env, ebuf);
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_signFocusedSignatureInternal)(JNIEnv * env, jobject thiz, jstring jkeyfile, jstring jpassword)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
- pdf_widget *focus;
- const char *keyfile;
- const char *password;
- jboolean res;
-
- if (idoc == NULL)
- return JNI_FALSE;
-
- focus = pdf_focused_widget(ctx, idoc);
-
- if (focus == NULL)
- return JNI_FALSE;
-
- keyfile = (*env)->GetStringUTFChars(env, jkeyfile, NULL);
- password = (*env)->GetStringUTFChars(env, jpassword, NULL);
- if (keyfile == NULL || password == NULL)
- return JNI_FALSE;
-
- fz_var(res);
- fz_try(ctx)
- {
- pdf_sign_signature(ctx, idoc, focus, keyfile, password);
- dump_annotation_display_lists(glo);
- res = JNI_TRUE;
- }
- fz_catch(ctx)
- {
- res = JNI_FALSE;
- }
-
- return res;
-}
-
-JNIEXPORT jobject JNICALL
-JNI_FN(MuPDFCore_waitForAlertInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- jclass alertClass;
- jmethodID ctor;
- jstring title;
- jstring message;
- int alert_present;
- pdf_alert_event alert;
-
- LOGT("Enter waitForAlert");
- pthread_mutex_lock(&glo->fin_lock);
- pthread_mutex_lock(&glo->alert_lock);
-
- while (glo->alerts_active && !glo->alert_request)
- pthread_cond_wait(&glo->alert_request_cond, &glo->alert_lock);
- glo->alert_request = 0;
-
- alert_present = (glo->alerts_active && glo->current_alert);
-
- if (alert_present)
- alert = *glo->current_alert;
-
- pthread_mutex_unlock(&glo->alert_lock);
- pthread_mutex_unlock(&glo->fin_lock);
- LOGT("Exit waitForAlert %d", alert_present);
-
- if (!alert_present)
- return NULL;
-
- alertClass = (*env)->FindClass(env, PACKAGENAME "/MuPDFAlertInternal");
- if (alertClass == NULL)
- return NULL;
-
- ctor = (*env)->GetMethodID(env, alertClass, "<init>", "(Ljava/lang/String;IILjava/lang/String;I)V");
- if (ctor == NULL)
- return NULL;
-
- title = (*env)->NewStringUTF(env, alert.title);
- if (title == NULL)
- return NULL;
-
- message = (*env)->NewStringUTF(env, alert.message);
- if (message == NULL)
- return NULL;
-
- return (*env)->NewObject(env, alertClass, ctor, message, alert.icon_type, alert.button_group_type, title, alert.button_pressed);
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_replyToAlertInternal)(JNIEnv * env, jobject thiz, jobject alert)
-{
- globals *glo = get_globals(env, thiz);
- jclass alertClass;
- jfieldID field;
- int button_pressed;
-
- alertClass = (*env)->FindClass(env, PACKAGENAME "/MuPDFAlertInternal");
- if (alertClass == NULL)
- return;
-
- field = (*env)->GetFieldID(env, alertClass, "buttonPressed", "I");
- if (field == NULL)
- return;
-
- button_pressed = (*env)->GetIntField(env, alert, field);
-
- LOGT("Enter replyToAlert");
- pthread_mutex_lock(&glo->alert_lock);
-
- if (glo->alerts_active && glo->current_alert)
- {
- // Fill in button_pressed and signal reply received.
- glo->current_alert->button_pressed = button_pressed;
- glo->alert_reply = 1;
- pthread_cond_signal(&glo->alert_reply_cond);
- }
-
- pthread_mutex_unlock(&glo->alert_lock);
- LOGT("Exit replyToAlert");
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_startAlertsInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
-
- if (!glo->alerts_initialised)
- return;
-
- LOGT("Enter startAlerts");
- pthread_mutex_lock(&glo->alert_lock);
-
- glo->alert_reply = 0;
- glo->alert_request = 0;
- glo->alerts_active = 1;
- glo->current_alert = NULL;
-
- pthread_mutex_unlock(&glo->alert_lock);
- LOGT("Exit startAlerts");
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_stopAlertsInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
-
- if (!glo->alerts_initialised)
- return;
-
- LOGT("Enter stopAlerts");
- pthread_mutex_lock(&glo->alert_lock);
-
- glo->alert_reply = 0;
- glo->alert_request = 0;
- glo->alerts_active = 0;
- glo->current_alert = NULL;
- pthread_cond_signal(&glo->alert_reply_cond);
- pthread_cond_signal(&glo->alert_request_cond);
-
- pthread_mutex_unlock(&glo->alert_lock);
- LOGT("Exit stopAleerts");
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_hasChangesInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
-
- return (idoc && pdf_has_unsaved_changes(ctx, idoc)) ? JNI_TRUE : JNI_FALSE;
-}
-
-static char *tmp_path(char *path)
-{
- int f;
- char *buf = malloc(strlen(path) + 6 + 1);
- if (!buf)
- return NULL;
-
- strcpy(buf, path);
- strcat(buf, "XXXXXX");
-
- f = mkstemp(buf);
-
- if (f >= 0)
- {
- close(f);
- return buf;
- }
- else
- {
- free(buf);
- return NULL;
- }
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_saveInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- pdf_document *idoc = pdf_specifics(ctx, glo->doc);
-
- if (idoc && glo->current_path)
- {
- char *tmp;
- pdf_write_options opts = { 0 };
-
- opts.do_incremental = pdf_can_be_saved_incrementally(ctx, idoc);
-
- tmp = tmp_path(glo->current_path);
- if (tmp)
- {
- int written = 0;
-
- fz_var(written);
- fz_try(ctx)
- {
- FILE *fin = fopen(glo->current_path, "rb");
- FILE *fout = fopen(tmp, "wb");
- char buf[256];
- int n, err = 1;
-
- if (fin && fout)
- {
- while ((n = fread(buf, 1, sizeof(buf), fin)) > 0)
- fwrite(buf, 1, n, fout);
- err = (ferror(fin) || ferror(fout));
- }
-
- if (fin)
- fclose(fin);
- if (fout)
- fclose(fout);
-
- if (!err)
- {
- pdf_save_document(ctx, idoc, tmp, &opts);
- written = 1;
- }
- }
- fz_catch(ctx)
- {
- written = 0;
- }
-
- if (written)
- {
- close_doc(glo);
- rename(tmp, glo->current_path);
- }
-
- free(tmp);
- }
- }
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_dumpMemoryInternal)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
-
-#ifdef MEMENTO
- LOGE("dumpMemoryInternal start");
- Memento_listNewBlocks();
- Memento_stats();
- LOGE("dumpMemoryInternal end");
-#endif
-}
-
-JNIEXPORT jlong JNICALL
-JNI_FN(MuPDFCore_createCookie)(JNIEnv * env, jobject thiz)
-{
- globals *glo = get_globals_any_thread(env, thiz);
- if (glo == NULL)
- return 0;
- fz_context *ctx = glo->ctx;
-
- return (jlong) (intptr_t) fz_calloc_no_throw(ctx,1, sizeof(fz_cookie));
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_destroyCookie)(JNIEnv * env, jobject thiz, jlong cookiePtr)
-{
- fz_cookie *cookie = (fz_cookie *) (intptr_t) cookiePtr;
- globals *glo = get_globals_any_thread(env, thiz);
- if (glo == NULL)
- return;
- fz_context *ctx = glo->ctx;
-
- fz_free(ctx, cookie);
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_abortCookie)(JNIEnv * env, jobject thiz, jlong cookiePtr)
-{
- fz_cookie *cookie = (fz_cookie *) (intptr_t) cookiePtr;
- if (cookie != NULL)
- cookie->abort = 1;
-}
-
-static char *tmp_gproof_path(char *path)
-{
- FILE *f;
- int i;
- char *buf = malloc(strlen(path) + 20 + 1);
- if (!buf)
- return NULL;
-
- for (i = 0; i < 10000; i++)
- {
- sprintf(buf, "%s.%d.gproof", path, i);
-
- LOGE("Trying for %s\n", buf);
- f = fopen(buf, "r");
- if (f != NULL)
- {
- fclose(f);
- continue;
- }
-
- f = fopen(buf, "w");
- if (f != NULL)
- {
- fclose(f);
- break;
- }
- }
- if (i == 10000)
- {
- LOGE("Failed to find temp gproof name");
- free(buf);
- return NULL;
- }
-
- LOGE("Rewritten to %s\n", buf);
- return buf;
-}
-
-JNIEXPORT jstring JNICALL
-JNI_FN(MuPDFCore_startProofInternal)(JNIEnv * env, jobject thiz, int inResolution)
-{
-#ifdef FZ_ENABLE_GPRF
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- char *tmp;
- jstring ret;
-
- if (!glo->doc || !glo->current_path)
- return NULL;
-
- tmp = tmp_gproof_path(glo->current_path);
- if (!tmp)
- return NULL;
-
- int theResolution = PROOF_RESOLUTION;
- if (inResolution != 0)
- theResolution = inResolution;
-
- fz_try(ctx)
- {
- fz_save_gproof(ctx, glo->current_path, glo->doc, tmp, theResolution, "", "");
-
- LOGE("Creating %s\n", tmp);
- ret = (*env)->NewStringUTF(env, tmp);
- }
- fz_always(ctx)
- {
- free(tmp);
- }
- fz_catch(ctx)
- {
- ret = NULL;
- }
- return ret;
-#else
- return NULL;
-#endif
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_endProofInternal)(JNIEnv * env, jobject thiz, jstring jfilename)
-{
-#ifdef FZ_ENABLE_GPRF
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- const char *tmp;
-
- if (!glo->doc || !glo->current_path || jfilename == NULL)
- return;
-
- tmp = (*env)->GetStringUTFChars(env, jfilename, NULL);
- if (tmp)
- {
- LOGE("Deleting %s\n", tmp);
-
- unlink(tmp);
- (*env)->ReleaseStringUTFChars(env, jfilename, tmp);
- }
-#endif
-}
-
-JNIEXPORT jboolean JNICALL
-JNI_FN(MuPDFCore_gprfSupportedInternal)(JNIEnv * env)
-{
-#ifdef FZ_ENABLE_GPRF
- return JNI_TRUE;
-#else
- return JNI_FALSE;
-#endif
-}
-
-JNIEXPORT int JNICALL
-JNI_FN(MuPDFCore_getNumSepsOnPageInternal)(JNIEnv *env, jobject thiz, int page)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- int i;
-
- for (i = 0; i < NUM_CACHE; i++)
- {
- if (glo->pages[i].page != NULL && glo->pages[i].number == page)
- break;
- }
- if (i == NUM_CACHE)
- return 0;
-
- LOGE("Counting seps on page %d", page);
-
- return fz_count_separations_on_page(ctx, glo->pages[i].page);
-}
-
-JNIEXPORT void JNICALL
-JNI_FN(MuPDFCore_controlSepOnPageInternal)(JNIEnv *env, jobject thiz, int page, int sep, jboolean disable)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- int i;
-
- for (i = 0; i < NUM_CACHE; i++)
- {
- if (glo->pages[i].page != NULL && glo->pages[i].number == page)
- break;
- }
- if (i == NUM_CACHE)
- return;
-
- fz_control_separation_on_page(ctx, glo->pages[i].page, sep, disable);
-}
-
-JNIEXPORT jobject JNICALL
-JNI_FN(MuPDFCore_getSepInternal)(JNIEnv *env, jobject thiz, int page, int sep)
-{
- globals *glo = get_globals(env, thiz);
- fz_context *ctx = glo->ctx;
- const char *name;
- char rgba[4];
- unsigned int bgra;
- unsigned int cmyk;
- jobject jname;
- jclass sepClass;
- jmethodID ctor;
- int i;
-
- for (i = 0; i < NUM_CACHE; i++)
- {
- if (glo->pages[i].page != NULL && glo->pages[i].number == page)
- break;
- }
- if (i == NUM_CACHE)
- return NULL;
-
- /* MuPDF returns RGBA as bytes. Android wants a packed BGRA int. */
- name = fz_get_separation_on_page(ctx, glo->pages[i].page, sep, (unsigned int *)(&rgba[0]), &cmyk);
- bgra = (rgba[0] << 16) | (rgba[1]<<8) | rgba[2] | (rgba[3]<<24);
- jname = name ? (*env)->NewStringUTF(env, name) : NULL;
-
- sepClass = (*env)->FindClass(env, PACKAGENAME "/Separation");
- if (sepClass == NULL)
- return NULL;
-
- ctor = (*env)->GetMethodID(env, sepClass, "<init>", "(Ljava/lang/String;II)V");
- if (ctor == NULL)
- return NULL;
-
- return (*env)->NewObject(env, sepClass, ctor, jname, bgra, cmyk);
-}
diff --git a/platform/android/viewer/local.properties.sample b/platform/android/viewer/local.properties.sample
deleted file mode 100644
index bc40e6ef..00000000
--- a/platform/android/viewer/local.properties.sample
+++ /dev/null
@@ -1,5 +0,0 @@
-# Uncomment and edit the appropriate line below.
-# Resave this file as local.properties.
-
-sdk.dir=/path/to/android/sdk
-ndk.dir=/path/to/android/ndk
diff --git a/platform/android/viewer/project.properties b/platform/android/viewer/project.properties
deleted file mode 100644
index 895c9ce2..00000000
--- a/platform/android/viewer/project.properties
+++ /dev/null
@@ -1,11 +0,0 @@
-# This file is automatically generated by Android Tools.
-# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
-#
-# This file must be checked in Version Control Systems.
-#
-# To customize properties used by the Ant build system use,
-# "ant.properties", and override values to adapt the script to your
-# project structure.
-
-# Project target.
-target=android-16
diff --git a/platform/android/viewer/res/animator/info.xml b/platform/android/viewer/res/animator/info.xml
deleted file mode 100644
index 9085a9ee..00000000
--- a/platform/android/viewer/res/animator/info.xml
+++ /dev/null
@@ -1,20 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<set xmlns:android="http://schemas.android.com/apk/res/android"
- android:ordering="sequentially" >
-
- <objectAnimator
- android:propertyName="alpha"
- android:valueFrom="0.0"
- android:valueTo="1.0"
- android:duration="200" />
-
- <objectAnimator
- android:propertyName="alpha"
- android:valueTo="1.0"
- android:duration="800" />
-
- <objectAnimator
- android:propertyName="alpha"
- android:valueTo="0.0"
- android:duration="400" />
-</set>
diff --git a/platform/android/viewer/res/drawable-hdpi/icon.png b/platform/android/viewer/res/drawable-hdpi/icon.png
deleted file mode 100644
index 4f47347d..00000000
--- a/platform/android/viewer/res/drawable-hdpi/icon.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_annot.png b/platform/android/viewer/res/drawable-ldpi/ic_annot.png
deleted file mode 100644
index c4f1df07..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_annot.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_annotation.png b/platform/android/viewer/res/drawable-ldpi/ic_annotation.png
deleted file mode 100644
index 1f4e6d48..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_annotation.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_arrow_left.png b/platform/android/viewer/res/drawable-ldpi/ic_arrow_left.png
deleted file mode 100644
index d49c7438..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_arrow_left.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_arrow_right.png b/platform/android/viewer/res/drawable-ldpi/ic_arrow_right.png
deleted file mode 100644
index e76d0cb0..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_arrow_right.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_cancel.png b/platform/android/viewer/res/drawable-ldpi/ic_cancel.png
deleted file mode 100644
index 6912e1ed..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_cancel.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_check.png b/platform/android/viewer/res/drawable-ldpi/ic_check.png
deleted file mode 100644
index fb789c8d..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_check.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_clipboard.png b/platform/android/viewer/res/drawable-ldpi/ic_clipboard.png
deleted file mode 100644
index 3023c6eb..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_clipboard.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_dir.png b/platform/android/viewer/res/drawable-ldpi/ic_dir.png
deleted file mode 100644
index 2236f2f8..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_dir.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_doc.png b/platform/android/viewer/res/drawable-ldpi/ic_doc.png
deleted file mode 100644
index 407ed5d4..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_doc.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_highlight.png b/platform/android/viewer/res/drawable-ldpi/ic_highlight.png
deleted file mode 100644
index 3d6d29b9..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_highlight.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_link.png b/platform/android/viewer/res/drawable-ldpi/ic_link.png
deleted file mode 100644
index a447b87d..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_link.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_list.png b/platform/android/viewer/res/drawable-ldpi/ic_list.png
deleted file mode 100644
index 4a2dde6d..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_list.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_magnifying_glass.png b/platform/android/viewer/res/drawable-ldpi/ic_magnifying_glass.png
deleted file mode 100644
index a3c8f598..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_magnifying_glass.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_more.png b/platform/android/viewer/res/drawable-ldpi/ic_more.png
deleted file mode 100644
index 68988a56..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_more.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_pen.png b/platform/android/viewer/res/drawable-ldpi/ic_pen.png
deleted file mode 100644
index 7b7de296..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_pen.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_print.png b/platform/android/viewer/res/drawable-ldpi/ic_print.png
deleted file mode 100644
index f191fc85..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_print.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_proof.png b/platform/android/viewer/res/drawable-ldpi/ic_proof.png
deleted file mode 100644
index fee26a7b..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_proof.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_reflow.png b/platform/android/viewer/res/drawable-ldpi/ic_reflow.png
deleted file mode 100644
index e9e8b052..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_reflow.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_select.png b/platform/android/viewer/res/drawable-ldpi/ic_select.png
deleted file mode 100644
index 81af6738..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_select.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_share.png b/platform/android/viewer/res/drawable-ldpi/ic_share.png
deleted file mode 100644
index 05fbe31a..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_share.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_strike.png b/platform/android/viewer/res/drawable-ldpi/ic_strike.png
deleted file mode 100644
index fc39409f..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_strike.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_trash.png b/platform/android/viewer/res/drawable-ldpi/ic_trash.png
deleted file mode 100644
index 465d1245..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_trash.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_underline.png b/platform/android/viewer/res/drawable-ldpi/ic_underline.png
deleted file mode 100644
index 0a5be3d4..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_underline.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/ic_updir.png b/platform/android/viewer/res/drawable-ldpi/ic_updir.png
deleted file mode 100644
index b923e429..00000000
--- a/platform/android/viewer/res/drawable-ldpi/ic_updir.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-ldpi/icon.png b/platform/android/viewer/res/drawable-ldpi/icon.png
deleted file mode 100644
index 82655e72..00000000
--- a/platform/android/viewer/res/drawable-ldpi/icon.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_annot.png b/platform/android/viewer/res/drawable-mdpi/ic_annot.png
deleted file mode 100644
index 0b4bfd92..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_annot.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_annotation.png b/platform/android/viewer/res/drawable-mdpi/ic_annotation.png
deleted file mode 100644
index 6f81c4a0..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_annotation.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_arrow_left.png b/platform/android/viewer/res/drawable-mdpi/ic_arrow_left.png
deleted file mode 100644
index 16a31b21..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_arrow_left.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_arrow_right.png b/platform/android/viewer/res/drawable-mdpi/ic_arrow_right.png
deleted file mode 100644
index cc34067e..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_arrow_right.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_arrow_up.png b/platform/android/viewer/res/drawable-mdpi/ic_arrow_up.png
deleted file mode 100644
index de2726ce..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_arrow_up.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_cancel.png b/platform/android/viewer/res/drawable-mdpi/ic_cancel.png
deleted file mode 100644
index 0b794b4d..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_cancel.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_check.png b/platform/android/viewer/res/drawable-mdpi/ic_check.png
deleted file mode 100644
index 527aaeb9..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_check.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_clipboard.png b/platform/android/viewer/res/drawable-mdpi/ic_clipboard.png
deleted file mode 100644
index c05deffd..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_clipboard.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_dir.png b/platform/android/viewer/res/drawable-mdpi/ic_dir.png
deleted file mode 100644
index e15200c5..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_dir.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_doc.png b/platform/android/viewer/res/drawable-mdpi/ic_doc.png
deleted file mode 100644
index 1eb722be..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_doc.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_highlight.png b/platform/android/viewer/res/drawable-mdpi/ic_highlight.png
deleted file mode 100644
index 2a8fe4db..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_highlight.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_link.png b/platform/android/viewer/res/drawable-mdpi/ic_link.png
deleted file mode 100644
index 7f7ac170..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_link.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_list.png b/platform/android/viewer/res/drawable-mdpi/ic_list.png
deleted file mode 100644
index e4f3164c..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_list.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_magnifying_glass.png b/platform/android/viewer/res/drawable-mdpi/ic_magnifying_glass.png
deleted file mode 100644
index 389cebd5..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_magnifying_glass.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_more.png b/platform/android/viewer/res/drawable-mdpi/ic_more.png
deleted file mode 100644
index 2b662ab3..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_more.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_pen.png b/platform/android/viewer/res/drawable-mdpi/ic_pen.png
deleted file mode 100644
index db805373..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_pen.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_print.png b/platform/android/viewer/res/drawable-mdpi/ic_print.png
deleted file mode 100644
index 58105463..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_print.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_proof.png b/platform/android/viewer/res/drawable-mdpi/ic_proof.png
deleted file mode 100644
index cbda8721..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_proof.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_reflow.png b/platform/android/viewer/res/drawable-mdpi/ic_reflow.png
deleted file mode 100644
index 84bd5418..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_reflow.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_select.png b/platform/android/viewer/res/drawable-mdpi/ic_select.png
deleted file mode 100644
index 9eaf6924..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_select.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_sep.png b/platform/android/viewer/res/drawable-mdpi/ic_sep.png
deleted file mode 100644
index 2167be2e..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_sep.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_share.png b/platform/android/viewer/res/drawable-mdpi/ic_share.png
deleted file mode 100644
index cae51b69..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_share.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_strike.png b/platform/android/viewer/res/drawable-mdpi/ic_strike.png
deleted file mode 100644
index b15e9324..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_strike.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_trash.png b/platform/android/viewer/res/drawable-mdpi/ic_trash.png
deleted file mode 100644
index 3006fec3..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_trash.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/ic_underline.png b/platform/android/viewer/res/drawable-mdpi/ic_underline.png
deleted file mode 100644
index 5d4dd5a4..00000000
--- a/platform/android/viewer/res/drawable-mdpi/ic_underline.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-mdpi/icon.png b/platform/android/viewer/res/drawable-mdpi/icon.png
deleted file mode 100644
index e05de27c..00000000
--- a/platform/android/viewer/res/drawable-mdpi/icon.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable-xhdpi/icon.png b/platform/android/viewer/res/drawable-xhdpi/icon.png
deleted file mode 100644
index 0995b78e..00000000
--- a/platform/android/viewer/res/drawable-xhdpi/icon.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable/busy.xml b/platform/android/viewer/res/drawable/busy.xml
deleted file mode 100644
index f7f42a44..00000000
--- a/platform/android/viewer/res/drawable/busy.xml
+++ /dev/null
@@ -1,10 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<shape xmlns:android="http://schemas.android.com/apk/res/android"
- android:shape="rectangle">
- <corners android:radius="12dp" />
- <padding android:left="16dp"
- android:right="16dp"
- android:top="16dp"
- android:bottom="16dp" />
- <solid android:color="@color/busy_indicator" />
-</shape>
diff --git a/platform/android/viewer/res/drawable/button.xml b/platform/android/viewer/res/drawable/button.xml
deleted file mode 100644
index 0a9bcd51..00000000
--- a/platform/android/viewer/res/drawable/button.xml
+++ /dev/null
@@ -1,23 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<selector xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:state_pressed="true">
- <shape>
- <solid android:color="@color/button_pressed" />
- <padding android:left="8dp" android:top="8dp" android:right="8dp" android:bottom="8dp" />
- </shape>
- </item>
- <item android:state_focused="true">
- <shape>
- <solid android:color="@color/button_normal" />
- <stroke android:width="4dp" android:color="@color/button_pressed" />
- <padding android:left="8dp" android:top="8dp" android:right="8dp" android:bottom="8dp" />
- </shape>
- </item>
- <item>
- <shape>
- <solid android:color="@color/button_normal" />
- <padding android:left="8dp" android:top="8dp" android:right="8dp" android:bottom="8dp" />
- </shape>
- </item>
-</selector>
diff --git a/platform/android/viewer/res/drawable/darkdenim3.png b/platform/android/viewer/res/drawable/darkdenim3.png
deleted file mode 100644
index be532f6d..00000000
--- a/platform/android/viewer/res/drawable/darkdenim3.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/viewer/res/drawable/page_num.xml b/platform/android/viewer/res/drawable/page_num.xml
deleted file mode 100644
index 8d50df85..00000000
--- a/platform/android/viewer/res/drawable/page_num.xml
+++ /dev/null
@@ -1,9 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<shape xmlns:android="http://schemas.android.com/apk/res/android"
- android:shape="rectangle">
- <padding android:left="8dp"
- android:right="8dp"
- android:top="1dp"
- android:bottom="2dp" />
- <solid android:color="@color/page_indicator" />
-</shape>
diff --git a/platform/android/viewer/res/drawable/search.xml b/platform/android/viewer/res/drawable/search.xml
deleted file mode 100644
index 4fc58830..00000000
--- a/platform/android/viewer/res/drawable/search.xml
+++ /dev/null
@@ -1,37 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<selector xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:state_pressed="true">
- <shape android:shape="rectangle">
- <solid android:color="@color/text_pressed" />
- <stroke android:width="4dp" android:color="@color/text_border_pressed" />
- <padding
- android:left="12dp"
- android:right="12dp"
- android:top="8dp"
- android:bottom="8dp" />
- </shape>
- </item>
- <item android:state_focused="true">
- <shape>
- <solid android:color="@color/text_normal" />
- <stroke android:width="4dp" android:color="@color/text_border_focused" />
- <padding
- android:left="12dp"
- android:right="12dp"
- android:top="8dp"
- android:bottom="8dp" />
- </shape>
- </item>
- <item>
- <shape>
- <solid android:color="@color/text_normal" />
- <stroke android:width="4dp" android:color="@color/text_border_normal" />
- <padding
- android:left="12dp"
- android:right="12dp"
- android:top="8dp"
- android:bottom="8dp" />
- </shape>
- </item>
-</selector>
diff --git a/platform/android/viewer/res/drawable/seek_progress.xml b/platform/android/viewer/res/drawable/seek_progress.xml
deleted file mode 100644
index 328139c2..00000000
--- a/platform/android/viewer/res/drawable/seek_progress.xml
+++ /dev/null
@@ -1,6 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<shape xmlns:android="http://schemas.android.com/apk/res/android"
- android:shape="line" >
- <stroke android:width="6dp" android:color="@color/seek_progress" />
-</shape>
diff --git a/platform/android/viewer/res/drawable/seek_thumb.xml b/platform/android/viewer/res/drawable/seek_thumb.xml
deleted file mode 100644
index e3a9bad4..00000000
--- a/platform/android/viewer/res/drawable/seek_thumb.xml
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<shape xmlns:android="http://schemas.android.com/apk/res/android"
- android:shape="oval" >
- <size android:width="28dp" android:height="28dp" />
- <solid android:color="@color/seek_thumb" />
-</shape>
diff --git a/platform/android/viewer/res/drawable/tiled_background.xml b/platform/android/viewer/res/drawable/tiled_background.xml
deleted file mode 100644
index 60e08f3c..00000000
--- a/platform/android/viewer/res/drawable/tiled_background.xml
+++ /dev/null
@@ -1,4 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<bitmap xmlns:android="http://schemas.android.com/apk/res/android"
- android:src="@drawable/darkdenim3"
- android:tileMode="repeat" />
diff --git a/platform/android/viewer/res/layout/buttons.xml b/platform/android/viewer/res/layout/buttons.xml
deleted file mode 100644
index 6c1620ba..00000000
--- a/platform/android/viewer/res/layout/buttons.xml
+++ /dev/null
@@ -1,408 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="match_parent" >
-
- <ViewAnimator
- android:id="@+id/switcher"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_alignParentTop="true"
- android:layout_centerHorizontal="true" >
-
- <RelativeLayout
- android:id="@+id/topBar0Main"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@color/toolbar" >
-
- <TextView
- android:id="@+id/docNameText"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/linkButton"
- android:layout_alignParentLeft="true"
- android:paddingLeft="16dp"
- android:singleLine="true"
- android:textColor="#FFFFFF"
- android:textStyle="bold"
- android:textAppearance="?android:attr/textAppearanceMedium" />
-
- <ImageButton
- android:id="@+id/sepsButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="Separations"
- android:background="@drawable/button"
- android:onClick="OnSepsButtonClick"
- android:src="@drawable/ic_sep" />
-
- <ImageButton
- android:id="@+id/linkButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/reflowButton"
- android:contentDescription="@string/toggle_links"
- android:background="@drawable/button"
- android:src="@drawable/ic_link" />
-
- <ImageButton
- android:id="@+id/reflowButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/outlineButton"
- android:contentDescription="@string/toggle_reflow_mode"
- android:background="@drawable/button"
- android:src="@drawable/ic_reflow" />
-
- <ImageButton
- android:id="@+id/outlineButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/searchButton"
- android:contentDescription="@string/outline_title"
- android:background="@drawable/button"
- android:src="@drawable/ic_list" />
-
- <ImageButton
- android:id="@+id/searchButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/moreButton"
- android:contentDescription="@string/search_document"
- android:background="@drawable/button"
- android:src="@drawable/ic_magnifying_glass" />
-
- <ImageButton
- android:id="@+id/moreButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="@string/more"
- android:background="@drawable/button"
- android:onClick="OnMoreButtonClick"
- android:src="@drawable/ic_more" />
-
- </RelativeLayout>
-
- <RelativeLayout
- android:id="@+id/topBar1Search"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@color/toolbar" >
-
- <ImageButton
- android:id="@+id/cancelSearch"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentLeft="true"
- android:contentDescription="@string/cancel"
- android:background="@drawable/button"
- android:onClick="OnCancelSearchButtonClick"
- android:src="@drawable/ic_cancel" />
-
- <EditText
- android:id="@+id/searchText"
- android:background="@drawable/search"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toRightOf="@+id/cancelSearch"
- android:layout_toLeftOf="@+id/searchBack"
- android:inputType="text"
- android:hint="@string/search"
- android:singleLine="true" />
-
- <ImageButton
- android:id="@+id/searchBack"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/searchForward"
- android:contentDescription="@string/search_backwards"
- android:background="@drawable/button"
- android:src="@drawable/ic_arrow_left" />
-
- <ImageButton
- android:id="@+id/searchForward"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="@string/search_forwards"
- android:background="@drawable/button"
- android:src="@drawable/ic_arrow_right" />
-
- </RelativeLayout>
-
- <RelativeLayout
- android:id="@+id/topBar2Annot"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@color/toolbar" >
-
- <ImageButton
- android:id="@+id/cancelAnnotButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentLeft="true"
- android:contentDescription="@string/cancel"
- android:background="@drawable/button"
- android:onClick="OnCancelAnnotButtonClick"
- android:src="@drawable/ic_cancel" />
-
- <ImageButton
- android:id="@+id/highlightButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/underlineButton"
- android:contentDescription="@string/highlight"
- android:background="@drawable/button"
- android:onClick="OnHighlightButtonClick"
- android:src="@drawable/ic_highlight" />
-
- <ImageButton
- android:id="@+id/underlineButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/strikeOutButton"
- android:contentDescription="@string/underline"
- android:background="@drawable/button"
- android:onClick="OnUnderlineButtonClick"
- android:src="@drawable/ic_underline" />
-
- <ImageButton
- android:id="@+id/strikeOutButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/inkButton"
- android:contentDescription="@string/strike_out"
- android:background="@drawable/button"
- android:onClick="OnStrikeOutButtonClick"
- android:src="@drawable/ic_strike" />
-
- <ImageButton
- android:id="@+id/inkButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="@string/ink"
- android:background="@drawable/button"
- android:onClick="OnInkButtonClick"
- android:src="@drawable/ic_pen" />
-
- </RelativeLayout>
-
- <RelativeLayout
- android:id="@+id/topBar3Delete"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@color/toolbar" >
-
- <ImageButton
- android:id="@+id/cancelDeleteButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentLeft="true"
- android:contentDescription="@string/cancel"
- android:background="@drawable/button"
- android:onClick="OnCancelDeleteButtonClick"
- android:src="@drawable/ic_cancel" />
-
- <TextView
- android:id="@+id/deleteLabel"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toRightOf="@+id/cancelDeleteButton"
- android:layout_toLeftOf="@+id/deleteButton"
- android:gravity="center"
- android:singleLine="true"
- android:textColor="#FFFFFF"
- android:textStyle="bold"
- android:text="@string/delete"
- android:textAppearance="?android:attr/textAppearanceMedium" />
-
- <ImageButton
- android:id="@+id/deleteButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="@string/delete"
- android:background="@drawable/button"
- android:onClick="OnDeleteButtonClick"
- android:src="@drawable/ic_trash" />
-
- </RelativeLayout>
-
- <RelativeLayout
- android:id="@+id/topBar4More"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@color/toolbar" >
-
- <ImageButton
- android:id="@+id/cancelMoreButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentLeft="true"
- android:contentDescription="@string/cancel"
- android:background="@drawable/button"
- android:onClick="OnCancelMoreButtonClick"
- android:src="@drawable/ic_cancel" />
-
- <ImageButton
- android:id="@+id/proofButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/printButton"
- android:contentDescription="@string/proof"
- android:background="@drawable/button"
- android:onClick="OnProofButtonClick"
- android:src="@drawable/ic_proof" />
-
- <ImageButton
- android:id="@+id/printButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/copyTextButton"
- android:contentDescription="@string/print"
- android:background="@drawable/button"
- android:onClick="OnPrintButtonClick"
- android:src="@drawable/ic_print" />
-
- <ImageButton
- android:id="@+id/copyTextButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toLeftOf="@+id/editAnnotButton"
- android:layout_alignWithParentIfMissing="true"
- android:contentDescription="@string/copy_text_to_the_clipboard"
- android:background="@drawable/button"
- android:onClick="OnCopyTextButtonClick"
- android:src="@drawable/ic_clipboard" />
-
- <ImageButton
- android:id="@+id/editAnnotButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="@string/edit_annotations"
- android:background="@drawable/button"
- android:onClick="OnEditAnnotButtonClick"
- android:src="@drawable/ic_annotation" />
- </RelativeLayout>
-
- <RelativeLayout
- android:id="@+id/topBar5Accept"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@color/toolbar" >
-
- <ImageButton
- android:id="@+id/cancelAcceptButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentLeft="true"
- android:contentDescription="@string/cancel"
- android:background="@drawable/button"
- android:onClick="OnCancelAcceptButtonClick"
- android:src="@drawable/ic_cancel" />
-
- <TextView
- android:id="@+id/annotType"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_toRightOf="@+id/cancelAcceptButton"
- android:layout_toLeftOf="@+id/acceptButton"
- android:gravity="center"
- android:singleLine="true"
- android:textColor="#FFFFFF"
- android:textStyle="bold"
- android:textAppearance="?android:attr/textAppearanceMedium" />
-
- <ImageButton
- android:id="@+id/acceptButton"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentRight="true"
- android:contentDescription="@string/accept"
- android:background="@drawable/button"
- android:onClick="OnAcceptButtonClick"
- android:src="@drawable/ic_check" />
- </RelativeLayout>
- </ViewAnimator>
-
- <RelativeLayout
- android:id="@+id/lowerButtons"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_alignParentBottom="true"
- android:layout_centerHorizontal="true" >
-
- <SeekBar
- android:id="@+id/pageSlider"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_alignParentBottom="true"
- android:layout_centerHorizontal="true"
- android:layout_margin="0dp"
- android:thumb="@drawable/seek_thumb"
- android:progressDrawable="@drawable/seek_progress"
- android:paddingLeft="16dp"
- android:paddingRight="16dp"
- android:paddingTop="12dp"
- android:paddingBottom="8dp"
- android:background="@color/toolbar"
- />
-
- <TextView
- android:id="@+id/pageNumber"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_above="@+id/pageSlider"
- android:layout_centerHorizontal="true"
- android:layout_marginBottom="16dp"
- android:background="@drawable/page_num"
- android:textColor="#FFFFFF"
- android:textAppearance="?android:attr/textAppearanceMedium" />
-
- </RelativeLayout>
-
- <TextView
- android:id="@+id/info"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_above="@+id/pageSlider"
- android:layout_centerHorizontal="true"
- android:layout_centerVertical="true"
- android:background="@drawable/page_num"
- android:textAppearance="?android:attr/textAppearanceMedium"
- android:textColor="#FFFFFF" />
-
-</RelativeLayout>
diff --git a/platform/android/viewer/res/layout/main.xml b/platform/android/viewer/res/layout/main.xml
deleted file mode 100644
index 50b4746b..00000000
--- a/platform/android/viewer/res/layout/main.xml
+++ /dev/null
@@ -1,5 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:orientation="vertical"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent" />
diff --git a/platform/android/viewer/res/layout/outline_entry.xml b/platform/android/viewer/res/layout/outline_entry.xml
deleted file mode 100644
index ea7912e4..00000000
--- a/platform/android/viewer/res/layout/outline_entry.xml
+++ /dev/null
@@ -1,27 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" >
-
- <TextView
- android:id="@+id/title"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_alignParentLeft="true"
- android:layout_toLeftOf="@+id/page"
- android:singleLine="true"
- android:layout_centerVertical="true"
- android:paddingLeft="8dp"
- android:textAppearance="?android:attr/textAppearanceMedium" />
-
- <TextView
- android:id="@+id/page"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_alignBaseline="@+id/title"
- android:layout_alignBottom="@+id/title"
- android:layout_alignParentRight="true"
- android:paddingRight="8dp"
- android:textAppearance="?android:attr/textAppearanceMedium" />
-
-</RelativeLayout>
diff --git a/platform/android/viewer/res/layout/picker_entry.xml b/platform/android/viewer/res/layout/picker_entry.xml
deleted file mode 100644
index 673a4724..00000000
--- a/platform/android/viewer/res/layout/picker_entry.xml
+++ /dev/null
@@ -1,25 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:paddingLeft="8dp" >
-
- <ImageView
- android:id="@+id/icon"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_centerVertical="true"
- android:layout_alignParentLeft="true" />
-
- <TextView
- android:id="@+id/name"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_toRightOf="@+id/icon"
- android:paddingBottom="8dp"
- android:paddingLeft="12dp"
- android:paddingRight="12dp"
- android:paddingTop="8dp"
- android:textAppearance="?android:attr/textAppearanceLarge" />
-
-</RelativeLayout>
diff --git a/platform/android/viewer/res/layout/print_dialog.xml b/platform/android/viewer/res/layout/print_dialog.xml
deleted file mode 100644
index 1d54d22f..00000000
--- a/platform/android/viewer/res/layout/print_dialog.xml
+++ /dev/null
@@ -1,9 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent">
- <WebView android:id="@+id/webview"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent"/>
-</RelativeLayout>
diff --git a/platform/android/viewer/res/layout/textentry.xml b/platform/android/viewer/res/layout/textentry.xml
deleted file mode 100644
index 08823df8..00000000
--- a/platform/android/viewer/res/layout/textentry.xml
+++ /dev/null
@@ -1,8 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<EditText xmlns:android="http://schemas.android.com/apk/res/android"
- android:singleLine="false"
- android:minLines="3"
- android:inputType="textMultiLine"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" >
-</EditText>
diff --git a/platform/android/viewer/res/values-ar/strings.xml b/platform/android/viewer/res/values-ar/strings.xml
deleted file mode 100644
index f16d5ba9..00000000
--- a/platform/android/viewer/res/values-ar/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">قبول</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">إلغاء</string>
- <string name="cannot_open_buffer">تعذر فتح المخزن المؤقت</string>
- <string name="cannot_open_document">تعذر فتح المستند</string>
- <string name="cannot_open_document_Reason">تعذر فتح المستند: %1$s</string>
- <string name="cannot_open_file_Path">تعذر فتح الملف: %1$s</string>
- <string name="choose_value">اختر قيمة</string>
- <string name="copied_to_clipboard">تم النسخ إلى الحافظة</string>
- <string name="copy">نسخ</string>
- <string name="copy_text">نسخ النص</string>
- <string name="copy_text_to_the_clipboard">نسخ النص إلى الحافظة</string>
- <string name="delete">حذف</string>
- <string name="dismiss">تجاهل</string>
- <string name="document_has_changes_save_them_">يحتوي المستند على تغييرات. هل تريد حفظها؟</string>
- <string name="draw_annotation">سحب تعليق توضيحي</string>
- <string name="edit_annotations">تعديل التعليقات التوضيحية</string>
- <string name="enter_password">أدخل كلمة المرور</string>
- <string name="entering_reflow_mode">دخول إلى وضع إعادة التدفق</string>
- <string name="fill_out_text_field">تعبئة حقل النص</string>
- <string name="format_currently_not_supported">التنسيق غير مدعوم حاليًا</string>
- <string name="highlight">تظليل</string>
- <string name="ink">حبر</string>
- <string name="leaving_reflow_mode">خروج من وضع إعادة التدفق</string>
- <string name="more">المزيد</string>
- <string name="no">لا</string>
- <string name="no_further_occurrences_found">لم يتم العثور على متكررات أخرى</string>
- <string name="no_media_hint">مشاركة وسائط التخزين مع حاسوب شخصي قد يمنع الوصول إليها</string>
- <string name="no_media_warning">وسائط التخزين غير موجودة</string>
- <string name="no_text_selected">لم يتم تحديد نص</string>
- <string name="not_supported">غير مدعوم</string>
- <string name="nothing_to_save">لا يوجد شيء لحفظه</string>
- <string name="okay">موافق</string>
- <string name="outline_title">جدول المحتويات</string>
- <string name="parent_directory">[أعلى مستوى واحد]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">طباعة</string>
- <string name="print_failed">فشلت الطباعة</string>
- <string name="save">حفظ</string>
- <string name="search">بحث</string>
- <string name="search_backwards">بحث إلى الخلف</string>
- <string name="search_document">بحث في المستند</string>
- <string name="search_forwards">بحث إلى الأمام</string>
- <string name="searching_">جاري البحث في&amp;#8230;</string>
- <string name="select">تحديد</string>
- <string name="select_text">تحديد النص</string>
- <string name="strike_out">شطب</string>
- <string name="text_not_found">لم يتم العثور على النص</string>
- <string name="toggle_links">تظليل وتمكين الروابط</string>
- <string name="underline">تسطير</string>
- <string name="yes">نعم</string>
-</resources>
diff --git a/platform/android/viewer/res/values-ca/strings.xml b/platform/android/viewer/res/values-ca/strings.xml
deleted file mode 100644
index ef72886e..00000000
--- a/platform/android/viewer/res/values-ca/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Acceptar</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Cancel·lar</string>
- <string name="cannot_open_buffer">No es pot obrir el buffer</string>
- <string name="cannot_open_document">No es pot obrir el document</string>
- <string name="cannot_open_document_Reason">No es pot obrir el document: %1$s</string>
- <string name="cannot_open_file_Path">No es pot obrir l\'arxiu: %1$s</string>
- <string name="choose_value">Tria el valor</string>
- <string name="copied_to_clipboard">Copiat al portapapers</string>
- <string name="copy">Copiar</string>
- <string name="copy_text">copiar text</string>
- <string name="copy_text_to_the_clipboard">Copiar text al portapapers</string>
- <string name="delete">Esborrar</string>
- <string name="dismiss">Descartar</string>
- <string name="document_has_changes_save_them_">El document té canvis. Desar?</string>
- <string name="draw_annotation">Dibuixar anotació</string>
- <string name="edit_annotations">Editar anotacions</string>
- <string name="enter_password">Introduir contrasenya</string>
- <string name="entering_reflow_mode">Entrant en modo de reflux</string>
- <string name="fill_out_text_field">Emplena el camp de text</string>
- <string name="format_currently_not_supported">Format no suportat actualment</string>
- <string name="highlight">Destacar</string>
- <string name="ink">Tinta</string>
- <string name="leaving_reflow_mode">Abandonant modo de reflux</string>
- <string name="more">Més</string>
- <string name="no">No</string>
- <string name="no_further_occurrences_found">No hi ha més coincidències</string>
- <string name="no_media_hint">Compartir el mitjà d\'emmagatzematge amb un PC pot fer que sigui inaccessible</string>
- <string name="no_media_warning">Mitjà d\'emmagatzematge no present</string>
- <string name="no_text_selected">No s\'ha seleccionat text</string>
- <string name="not_supported">No compatible</string>
- <string name="nothing_to_save">No hi ha gens que guardar</string>
- <string name="okay">Acceptar</string>
- <string name="outline_title">Índex</string>
- <string name="parent_directory">[Pujar un nivell]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Imprimir</string>
- <string name="print_failed">Fallada al imprimir</string>
- <string name="save">Desar</string>
- <string name="search">Buscar</string>
- <string name="search_backwards">Buscar cap a enrere</string>
- <string name="search_document">Buscar document</string>
- <string name="search_forwards">Buscar cap a davant</string>
- <string name="searching_">Buscant…</string>
- <string name="select">Seleccionar</string>
- <string name="select_text">Seleccionar text</string>
- <string name="strike_out">Ratllat</string>
- <string name="text_not_found">Text no trobat</string>
- <string name="toggle_links">Ressaltar i habilitar enllaços</string>
- <string name="underline">Subratllat</string>
- <string name="yes">Sí</string>
-</resources>
diff --git a/platform/android/viewer/res/values-cs/strings.xml b/platform/android/viewer/res/values-cs/strings.xml
deleted file mode 100644
index 6c870391..00000000
--- a/platform/android/viewer/res/values-cs/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Přijmout</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Zrušit</string>
- <string name="cannot_open_buffer">Nelze otevřít vyrovnávací paměť</string>
- <string name="cannot_open_document">Nelze otevřít dokument</string>
- <string name="cannot_open_document_Reason">Nelze otevřít dokument: %1$s</string>
- <string name="cannot_open_file_Path">Nelze otevřít soubor: %1$s</string>
- <string name="choose_value">Zvolte hodnotu</string>
- <string name="copied_to_clipboard">Kopírováno do schránky</string>
- <string name="copy">Kopírovat</string>
- <string name="copy_text">kopírovat text</string>
- <string name="copy_text_to_the_clipboard">Kopírovat text do schránky</string>
- <string name="delete">Smazat</string>
- <string name="dismiss">Odmítnout</string>
- <string name="document_has_changes_save_them_">Dokument byl změněn. Uložit?</string>
- <string name="draw_annotation">Vložit anotaci</string>
- <string name="edit_annotations">Upravit anotace</string>
- <string name="enter_password">Zadat heslo</string>
- <string name="entering_reflow_mode">Vstup do režimu přeformátování řádků</string>
- <string name="fill_out_text_field">Vyplnit textové pole</string>
- <string name="format_currently_not_supported">Formát aktuálně nepodporován</string>
- <string name="highlight">Zvýraznit</string>
- <string name="ink">Inkoust</string>
- <string name="leaving_reflow_mode">Odchod z režimu přeformátování řádků</string>
- <string name="more">Více</string>
- <string name="no">Ne</string>
- <string name="no_further_occurrences_found">Nenalezeny další výskyty</string>
- <string name="no_media_hint">Při sdílení s PC může být paměťové médium nedostupné</string>
- <string name="no_media_warning">Paměťové médim nenalezeno</string>
- <string name="no_text_selected">Nevybrán žádný text</string>
- <string name="not_supported">Nepodporováno</string>
- <string name="nothing_to_save">Nic k uložení</string>
- <string name="okay">OK</string>
- <string name="outline_title">Obsah</string>
- <string name="parent_directory">[Nahoru o jednu úroveň]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Tisk</string>
- <string name="print_failed">Tisk selhal</string>
- <string name="save">Uložit</string>
- <string name="search">Hledat</string>
- <string name="search_backwards">Hledat zpět</string>
- <string name="search_document">Prohledat dokument</string>
- <string name="search_forwards">Hledat vpřed</string>
- <string name="searching_">Hledání&amp;#8230;</string>
- <string name="select">Vybrat</string>
- <string name="select_text">Vybrat text</string>
- <string name="strike_out">Přeškrtnout</string>
- <string name="text_not_found">Text nenalezen</string>
- <string name="toggle_links">Zvýraznit a aktivovat odkazy</string>
- <string name="underline">Podtrhnout</string>
- <string name="yes">Ano</string>
-</resources>
diff --git a/platform/android/viewer/res/values-da/strings.xml b/platform/android/viewer/res/values-da/strings.xml
deleted file mode 100644
index b7de1fdc..00000000
--- a/platform/android/viewer/res/values-da/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Accepter</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Annuller</string>
- <string name="cannot_open_buffer">Buffer kan ikke åbnes</string>
- <string name="cannot_open_document">Dokument kan ikke åbnes</string>
- <string name="cannot_open_document_Reason">Kan ikke åbne dokumentet: %1$s</string>
- <string name="cannot_open_file_Path">Kan ikke åbne filen: %1$s</string>
- <string name="choose_value">Vælg værdi</string>
- <string name="copied_to_clipboard">Kopieret til udklipsholder</string>
- <string name="copy">Kopier</string>
- <string name="copy_text">kopier tekst</string>
- <string name="copy_text_to_the_clipboard">kopier tekst til udklipsholder</string>
- <string name="delete">Slet</string>
- <string name="dismiss">Afvis</string>
- <string name="document_has_changes_save_them_">Dokumentet er ændret. Gem ændringer?</string>
- <string name="draw_annotation">Lav anmærkning</string>
- <string name="edit_annotations">Rediger anmærkninger</string>
- <string name="enter_password">Indtast adgangskode</string>
- <string name="entering_reflow_mode">Går over til konverteringstilstand</string>
- <string name="fill_out_text_field">Udfyld tekstfelt</string>
- <string name="format_currently_not_supported">Format ikke understøttet i øjeblikket</string>
- <string name="highlight">Fremhæv</string>
- <string name="ink">Ink</string>
- <string name="leaving_reflow_mode">Forlader konverteringstilstand</string>
- <string name="more">Mere</string>
- <string name="no">Nej</string>
- <string name="no_further_occurrences_found">Der blev ikke fundet flere tilfælde</string>
- <string name="no_media_hint">Deles lagermediet med en PC, kan det gøre det utilgængeligt</string>
- <string name="no_media_warning">Lagermedie ikke fundet</string>
- <string name="no_text_selected">Ingen tekst valgt</string>
- <string name="not_supported">Ikke understøttet</string>
- <string name="nothing_to_save">Intet at gemme</string>
- <string name="okay">Okay</string>
- <string name="outline_title">Indholdsfortegnelse</string>
- <string name="parent_directory">[Et niveau op]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Udskriv</string>
- <string name="print_failed">Udskrivning mislykket</string>
- <string name="save">Gem</string>
- <string name="search">Søg</string>
- <string name="search_backwards">Søg bagud</string>
- <string name="search_document">Søg i dokument</string>
- <string name="search_forwards">Søg fremad</string>
- <string name="searching_">Søger&amp;#8230;</string>
- <string name="select">Vælg</string>
- <string name="select_text">Vælg tekst</string>
- <string name="strike_out">Gennemstreget</string>
- <string name="text_not_found">Tekst ikke fundet</string>
- <string name="toggle_links">Fremhæv og aktiver links</string>
- <string name="underline">Understreg</string>
- <string name="yes">Ja</string>
-</resources>
diff --git a/platform/android/viewer/res/values-de/strings.xml b/platform/android/viewer/res/values-de/strings.xml
deleted file mode 100644
index 2e69d369..00000000
--- a/platform/android/viewer/res/values-de/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Akzeptieren</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Abbrechen</string>
- <string name="cannot_open_buffer">Zwischenspeicher kann nicht geöffnet werden</string>
- <string name="cannot_open_document">Dokument kann nicht geöffnet werden</string>
- <string name="cannot_open_document_Reason">Dokument kann nicht geöffnet werden: %1$s</string>
- <string name="cannot_open_file_Path">Datei kann nicht geöffnet werden: %1$s</string>
- <string name="choose_value">Wert auswählen</string>
- <string name="copied_to_clipboard">In die Zwischenanlage kopiert</string>
- <string name="copy">Kopieren</string>
- <string name="copy_text">Text kopieren</string>
- <string name="copy_text_to_the_clipboard">Text in Zwischenablage kopieren</string>
- <string name="delete">Entfernen</string>
- <string name="dismiss">Verwerfen</string>
- <string name="document_has_changes_save_them_">Das Dokument wurde verändert. Sollen die Änderungen gespeichert werden?</string>
- <string name="draw_annotation">Kommentar einfügen</string>
- <string name="edit_annotations">Kommentar bearbeiten</string>
- <string name="enter_password">Passwort eingeben</string>
- <string name="entering_reflow_mode">Anpassungsmodus wird gestartet</string>
- <string name="fill_out_text_field">Textfeld ausfüllen</string>
- <string name="format_currently_not_supported">Format wird momentan nicht unterstützt</string>
- <string name="highlight">Markieren</string>
- <string name="ink">Farbe</string>
- <string name="leaving_reflow_mode">Anpassungsmodus wird beendet</string>
- <string name="more">Mehr</string>
- <string name="no">Nein</string>
- <string name="no_further_occurrences_found">Keine weiteren Treffer</string>
- <string name="no_media_hint">Die Freigabe des Speichermediums für einen PC kann es unzugänglich machen</string>
- <string name="no_media_warning">Speichermedium nicht vorhanden</string>
- <string name="no_text_selected">Kein Text ausgewählt</string>
- <string name="not_supported">Nicht unterstützt</string>
- <string name="nothing_to_save">Nichts zum Speichern</string>
- <string name="okay">OK</string>
- <string name="outline_title">Inhaltsverzeichnis</string>
- <string name="parent_directory">[Eine Ebene nach oben]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Drucken</string>
- <string name="print_failed">Fehler beim Drucken</string>
- <string name="save">Speichern</string>
- <string name="search">Suchen</string>
- <string name="search_backwards">Rückwärts suchen</string>
- <string name="search_document">Dokument durchsuchen</string>
- <string name="search_forwards">Vorwärts suchen</string>
- <string name="searching_">Suche…</string>
- <string name="select">Auswählen</string>
- <string name="select_text">Text auswählen</string>
- <string name="strike_out">Durchstreichen</string>
- <string name="text_not_found">Text konnte nicht gefunden werden</string>
- <string name="toggle_links">Markiere und aktiviere Verknüpfungen</string>
- <string name="underline">Unterstreichen</string>
- <string name="yes">Ja</string>
-</resources>
diff --git a/platform/android/viewer/res/values-el/strings.xml b/platform/android/viewer/res/values-el/strings.xml
deleted file mode 100644
index f994f287..00000000
--- a/platform/android/viewer/res/values-el/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Αποδοχή</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Ακύρωση</string>
- <string name="cannot_open_buffer">Αδυναμία ανοίγματος buffer </string>
- <string name="cannot_open_document">Αδυναμία ανοίγματος εγγράφου</string>
- <string name="cannot_open_document_Reason">Αδυναμία ανοίγματος εγγράφου: %1$s</string>
- <string name="cannot_open_file_Path">Αδυναμία ανοίγματος αρχείου: %1$s</string>
- <string name="choose_value">Επιλογή τιμής</string>
- <string name="copied_to_clipboard">Αντιγράφηκε στο πρόχειρο</string>
- <string name="copy">Αντιγραφή</string>
- <string name="copy_text">αντιγραφή κειμένου</string>
- <string name="copy_text_to_the_clipboard">Αντιγραφή κειμένου στο πρόχειρο</string>
- <string name="delete">Διαγραφή</string>
- <string name="dismiss">Ματαίωση</string>
- <string name="document_has_changes_save_them_">Το έγγραφο έχει αλλαγές. Να αποθηκευτούν;</string>
- <string name="draw_annotation">Σχεδίαση σχολίου</string>
- <string name="edit_annotations">Επεξεργασία σχολίων</string>
- <string name="enter_password">Πληκτρολογήστε κωδικό πρόσβασης</string>
- <string name="entering_reflow_mode">Είσοδος σε λειτουργία δυναμικής προσαρμογής</string>
- <string name="fill_out_text_field">Συμπλήρωση πεδίου κειμένου</string>
- <string name="format_currently_not_supported">Αυτή η μορφή δεν υποστηρίζεται τη δεδομένη στιγμή</string>
- <string name="highlight">Επισήμανση</string>
- <string name="ink">Γραφή</string>
- <string name="leaving_reflow_mode">Έξοδος από λειτουργία δυναμικής προσαρμογής</string>
- <string name="more">Περισσότερο</string>
- <string name="no">Όχι</string>
- <string name="no_further_occurrences_found">Δεν βρέθηκαν άλλες εμφανίσεις</string>
- <string name="no_media_hint">Η κοινή χρήση του αποθηκευτικού μέσου με έναν υπολογιστή μπορεί να το καταστήσει μη προσβάσιμο</string>
- <string name="no_media_warning">Δεν υπάρχει αποθηκευτικό μέσο</string>
- <string name="no_text_selected">Δεν έχει επιλεγεί κείμενο</string>
- <string name="not_supported">Δεν υποστηρίζεται</string>
- <string name="nothing_to_save">Δεν υπάρχει περιεχόμενο για αποθήκευση</string>
- <string name="okay">ΟΚ</string>
- <string name="outline_title">Πίνακας περιεχομένων</string>
- <string name="parent_directory">[Ένα επίπεδο επάνω]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Εκτύπωση</string>
- <string name="print_failed">Η εκτύπωση απέτυχε</string>
- <string name="save">Αποθήκευση</string>
- <string name="search">Αναζήτηση</string>
- <string name="search_backwards">Αναζήτηση προς τα πίσω</string>
- <string name="search_document">Αναζήτηση εγγράφου</string>
- <string name="search_forwards">Αναζήτηση προς τα μπροστά</string>
- <string name="searching_">Αναζήτηση&amp;#8230;</string>
- <string name="select">Επιλογή</string>
- <string name="select_text">Επιλογή κειμένου</string>
- <string name="strike_out">Διακριτή διαγραφή</string>
- <string name="text_not_found">Δεν βρέθηκε το κείμενο</string>
- <string name="toggle_links">Επισήμανση και ενεργοποίηση συνδέσεων</string>
- <string name="underline">Υπογράμμιση</string>
- <string name="yes">Ναι</string>
-</resources>
diff --git a/platform/android/viewer/res/values-es/strings.xml b/platform/android/viewer/res/values-es/strings.xml
deleted file mode 100644
index 0e28a909..00000000
--- a/platform/android/viewer/res/values-es/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Aceptar</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Cancelar</string>
- <string name="cannot_open_buffer">No se puede abrir el búfer</string>
- <string name="cannot_open_document">No se puede abrir el documento</string>
- <string name="cannot_open_document_Reason">No se puede abrir el documento:%1$s</string>
- <string name="cannot_open_file_Path">No se puede abrir el archivo: %1$s</string>
- <string name="choose_value">Elegir valor</string>
- <string name="copied_to_clipboard">Copiado al portapapeles</string>
- <string name="copy">Copiar</string>
- <string name="copy_text">copiar texto</string>
- <string name="copy_text_to_the_clipboard">Copiar texto al portapapeles</string>
- <string name="delete">Borrar</string>
- <string name="dismiss">Ignorar</string>
- <string name="document_has_changes_save_them_">El documento tiene cambios. ¿Guardar?</string>
- <string name="draw_annotation">Dibujar anotación</string>
- <string name="edit_annotations">Editar anotaicones</string>
- <string name="enter_password">Introducir contraseña</string>
- <string name="entering_reflow_mode">Entrando en el modo de redistribución</string>
- <string name="fill_out_text_field">Rellenar el campo de texto</string>
- <string name="format_currently_not_supported">Formato actualmente no soportado</string>
- <string name="highlight">Resaltar</string>
- <string name="ink">Tinta</string>
- <string name="leaving_reflow_mode">Saliendo del modo de redistribución</string>
- <string name="more">Más</string>
- <string name="no">No</string>
- <string name="no_further_occurrences_found">No se han encontrado más casos</string>
- <string name="no_media_hint">Compartir el medio de almacenamiento con un PC puede hacerlo inaccesible</string>
- <string name="no_media_warning">Medio de almacenimiento no presente</string>
- <string name="no_text_selected">Texto no seleccionado</string>
- <string name="not_supported">No aceptado</string>
- <string name="nothing_to_save">Nada que guardar</string>
- <string name="okay">OK</string>
- <string name="outline_title">Tabla de contenidos</string>
- <string name="parent_directory">[Subir un nivel]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Imprimir</string>
- <string name="print_failed">No se ha imprimido</string>
- <string name="save">Guardar</string>
- <string name="search">Buscar</string>
- <string name="search_backwards">Buscar hacia atrás</string>
- <string name="search_document">Buscar documento</string>
- <string name="search_forwards">Buscar hacia adelante</string>
- <string name="searching_">Buscando&amp;#8230;</string>
- <string name="select">Seleccionar</string>
- <string name="select_text">Seleccionar texto</string>
- <string name="strike_out">Tachar</string>
- <string name="text_not_found">Texto no encontrado</string>
- <string name="toggle_links">Resaltar y activar</string>
- <string name="underline">Subrayar</string>
- <string name="yes">Sí</string>
-</resources>
diff --git a/platform/android/viewer/res/values-et/strings.xml b/platform/android/viewer/res/values-et/strings.xml
deleted file mode 100644
index fddd25a8..00000000
--- a/platform/android/viewer/res/values-et/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Nõustu</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Tühista</string>
- <string name="cannot_open_buffer">Ei saa avada puhvrit</string>
- <string name="cannot_open_document">Ei saa avada dokumenti</string>
- <string name="cannot_open_document_Reason">Ei saa avada dokumenti: %1$s</string>
- <string name="cannot_open_file_Path">Ei saa avada faili: %1$s</string>
- <string name="choose_value">Vali väärtus</string>
- <string name="copied_to_clipboard">Kopeeritud lõikelauale</string>
- <string name="copy">Kopeeri</string>
- <string name="copy_text">kopeeri tekst</string>
- <string name="copy_text_to_the_clipboard">Kopeeri tekst lõikelauale</string>
- <string name="delete">Kustuta</string>
- <string name="dismiss">Lõpeta</string>
- <string name="document_has_changes_save_them_">Dokumendis on tehtud muudatusi. Kas salvestada need?</string>
- <string name="draw_annotation">Tee marginaal</string>
- <string name="edit_annotations">Redigeeri marginaale</string>
- <string name="enter_password">Sisesta salasõna</string>
- <string name="entering_reflow_mode">Sisenen ümberpaigutamise režiimi</string>
- <string name="fill_out_text_field">Täida tekstiväli</string>
- <string name="format_currently_not_supported">Vormingul puudub hetkel tugi</string>
- <string name="highlight">Tõsta esile</string>
- <string name="ink">Tint</string>
- <string name="leaving_reflow_mode">Lahkun ümberpaigutamise režiimist</string>
- <string name="more">Veel</string>
- <string name="no">Ei</string>
- <string name="no_further_occurrences_found">Ei leitud rohkem juhtumeid</string>
- <string name="no_media_hint">Salvestuskandja jagamine arvutiga võib selle juurdepääsmatuks muuta</string>
- <string name="no_media_warning">Salvestuskandja puudub</string>
- <string name="no_text_selected">Teksti ei ole valitud</string>
- <string name="not_supported">Puudub tugi</string>
- <string name="nothing_to_save">Ei ole midagi salvestada</string>
- <string name="okay">OK</string>
- <string name="outline_title">Sisukord</string>
- <string name="parent_directory">[Taseme võrra üles]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s%3$s</string>
- <string name="print">Prindi</string>
- <string name="print_failed">Printimine ebaõnnestus</string>
- <string name="save">Salvesta</string>
- <string name="search">Otsi</string>
- <string name="search_backwards">Otsi tagasisuunas</string>
- <string name="search_document">Otsi dokumendist</string>
- <string name="search_forwards">Otsi edasisuunas</string>
- <string name="searching_">Otsin&amp;#8230;</string>
- <string name="select">Vali</string>
- <string name="select_text">Vali tekst</string>
- <string name="strike_out">Läbikriipsutus</string>
- <string name="text_not_found">Teksti ei leitud</string>
- <string name="toggle_links">Tõsta lingid esile ja luba need</string>
- <string name="underline">Jooni alla</string>
- <string name="yes">Jah</string>
-</resources>
diff --git a/platform/android/viewer/res/values-fi/strings.xml b/platform/android/viewer/res/values-fi/strings.xml
deleted file mode 100644
index ae13e724..00000000
--- a/platform/android/viewer/res/values-fi/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Hyväksy</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Peruuta</string>
- <string name="cannot_open_buffer">Puskuria ei voi avata</string>
- <string name="cannot_open_document">Tiedostoa ei voi avata</string>
- <string name="cannot_open_document_Reason">Ei voi avata tiedostoa: %1$s</string>
- <string name="cannot_open_file_Path">Ei voi avata tiedostoa: %1$s</string>
- <string name="choose_value">Valitse arvo</string>
- <string name="copied_to_clipboard">Kopioitu leikepöydälle</string>
- <string name="copy">Kopioi</string>
- <string name="copy_text">kopio teksti</string>
- <string name="copy_text_to_the_clipboard">Kopioi teksti leikepöydälle</string>
- <string name="delete">Poista</string>
- <string name="dismiss">Hylkää</string>
- <string name="document_has_changes_save_them_">Tiedostossa on muutoksia. Haluatko tallentaa muutokset?</string>
- <string name="draw_annotation">Piirrä huomautus</string>
- <string name="edit_annotations">Muokkaa huomautuksia</string>
- <string name="enter_password">Anna salasana</string>
- <string name="entering_reflow_mode">Siirrytään takaisinmuuntotilaan</string>
- <string name="fill_out_text_field">Täytä tekstikenttä</string>
- <string name="format_currently_not_supported">Muotoa ei tällä hetkellä tueta</string>
- <string name="highlight">Korosta</string>
- <string name="ink">Muste</string>
- <string name="leaving_reflow_mode">Poistutaan takaisinmuuntotilasta</string>
- <string name="more">Lisää</string>
- <string name="no">Ei</string>
- <string name="no_further_occurrences_found">Muita esiintymiä ei löydy</string>
- <string name="no_media_hint">Tallennustietovälineen jakaminen tietokoneen kanssa voi estää sen käyttämisen</string>
- <string name="no_media_warning">Tallennustietoväline ei ole käytössä</string>
- <string name="no_text_selected">Ei valittua tekstiä</string>
- <string name="not_supported">Ei tuettu</string>
- <string name="nothing_to_save">Ei mitään tallennettavaa</string>
- <string name="okay">OK</string>
- <string name="outline_title">Sisällys</string>
- <string name="parent_directory">[Yksi taso ylöspäin]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Tulosta</string>
- <string name="print_failed">Tulostus ei onnistunut</string>
- <string name="save">Tallenna</string>
- <string name="search">Haku</string>
- <string name="search_backwards">Hae taaksepäin</string>
- <string name="search_document">Hae tiedostosta</string>
- <string name="search_forwards">Hae eteenpäin</string>
- <string name="searching_">Haetaan &amp;#8230;</string>
- <string name="select">Valitse</string>
- <string name="select_text">Valitse teksti</string>
- <string name="strike_out">Yliviivaa</string>
- <string name="text_not_found">Tekstiä ei löydy</string>
- <string name="toggle_links">Korosta ja ota käyttöön linkit</string>
- <string name="underline">Alleviivaa</string>
- <string name="yes">Kyllä</string>
-</resources>
diff --git a/platform/android/viewer/res/values-fr/strings.xml b/platform/android/viewer/res/values-fr/strings.xml
deleted file mode 100644
index 967707b9..00000000
--- a/platform/android/viewer/res/values-fr/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Accepter</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Annuler</string>
- <string name="cannot_open_buffer">Impossible d\'ouvrir le buffer</string>
- <string name="cannot_open_document">Impossible d\'ouvrir le document</string>
- <string name="cannot_open_document_Reason">Impossible d\'ouvrir le document : %1$s</string>
- <string name="cannot_open_file_Path">Impossible d\'ouvrir le fichier : %1$s</string>
- <string name="choose_value">Choisir la valeur</string>
- <string name="copied_to_clipboard">Copié dans le presse-papier</string>
- <string name="copy">Copier</string>
- <string name="copy_text">copier le texte</string>
- <string name="copy_text_to_the_clipboard">Copier le texte sur le presse-papier</string>
- <string name="delete">Supprimer</string>
- <string name="dismiss">Ignorer</string>
- <string name="document_has_changes_save_them_">Des modifications ont été effectuées au document. Les sauvegarder ?</string>
- <string name="draw_annotation">Dessiner une note</string>
- <string name="edit_annotations">Éditer une note</string>
- <string name="enter_password">Introduire le mot de passe</string>
- <string name="entering_reflow_mode">Entrer en mode refusion</string>
- <string name="fill_out_text_field">Remplir le champ du texte</string>
- <string name="format_currently_not_supported">Format non compatible pour l\'instant</string>
- <string name="highlight">Surligner</string>
- <string name="ink">Encre</string>
- <string name="leaving_reflow_mode">Quitter le mode refusion</string>
- <string name="more">Plus</string>
- <string name="no">Non</string>
- <string name="no_further_occurrences_found">Aucune occurrence trouvée</string>
- <string name="no_media_hint">Sauvegarder le support de stockage avec un PC peut le rendre inaccessible</string>
- <string name="no_media_warning">Support de stockage absent</string>
- <string name="no_text_selected">Aucun texte sélectionné</string>
- <string name="not_supported">Non compatible</string>
- <string name="nothing_to_save">Rien à sauvegarder</string>
- <string name="okay">OK</string>
- <string name="outline_title">Table des matières</string>
- <string name="parent_directory">[Niveau supérieur]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s : %3$s</string>
- <string name="print">Imprimer</string>
- <string name="print_failed">L\'impression a échoué</string>
- <string name="save">Sauvegarder</string>
- <string name="search">Rechercher</string>
- <string name="search_backwards">Rechercher en arrière</string>
- <string name="search_document">Rechercher document</string>
- <string name="search_forwards">Rechercher en avant</string>
- <string name="searching_">Chercher&amp;#8230 ;</string>
- <string name="select">Sélectionner</string>
- <string name="select_text">Sélectionner le texte</string>
- <string name="strike_out">Rayer</string>
- <string name="text_not_found">Texte introuvable</string>
- <string name="toggle_links">Surligner et autoriser les liens</string>
- <string name="underline">Souligner</string>
- <string name="yes">Oui</string>
-</resources>
diff --git a/platform/android/viewer/res/values-hi/strings.xml b/platform/android/viewer/res/values-hi/strings.xml
deleted file mode 100644
index 4d09a972..00000000
--- a/platform/android/viewer/res/values-hi/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">स्वीकार करें</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">रद्द करें</string>
- <string name="cannot_open_buffer">बफ़र खोल नहीं सके</string>
- <string name="cannot_open_document">दस्तावेज़ खोल नहीं सके</string>
- <string name="cannot_open_document_Reason">दस्तावेज़ नहीं खोल सके: %1$s</string>
- <string name="cannot_open_file_Path">फ़ाइल खोल नहीं सके: %1$s</string>
- <string name="choose_value">मान चुनें</string>
- <string name="copied_to_clipboard">क्लिपबोर्ड में कॉप कर दिया गया</string>
- <string name="copy">कॉपी करें</string>
- <string name="copy_text">पाठ कॉपी करें</string>
- <string name="copy_text_to_the_clipboard">पाठ को क्लिपबोर्ड में कॉपी करें</string>
- <string name="delete">हटाएँ</string>
- <string name="dismiss">खारिज करें</string>
- <string name="document_has_changes_save_them_">दस्तावेज़ में परिवर्तन हैं। उन्हें सहेजें?</string>
- <string name="draw_annotation">एनोटेशन बनाएँ</string>
- <string name="edit_annotations">एनोटेशनों को संपादित करें</string>
- <string name="enter_password">पासवर्ड दर्ज करें</string>
- <string name="entering_reflow_mode">रीफ़्लो मोड में प्रवेश कर रहे हैं</string>
- <string name="fill_out_text_field">पाठ फ़ील्ड को भरें</string>
- <string name="format_currently_not_supported">इस समय इस फ़ॉर्मेट को समर्थन नहीं प्राप्त है</string>
- <string name="highlight">हाइलाइट करें</string>
- <string name="ink">स्याही</string>
- <string name="leaving_reflow_mode">रीफ़्लो मोड को छोड़ रहे हैं</string>
- <string name="more">और भी</string>
- <string name="no">नहीं</string>
- <string name="no_further_occurrences_found">यह और कहीं नहीं मिला</string>
- <string name="no_media_hint">संग्रह माध्यम को पीसी के साथ साझा करने से उस तक पहुँचना मुश्किल हो सकता है</string>
- <string name="no_media_warning">संग्रह माध्यम मौजूद नहीं है</string>
- <string name="no_text_selected">कोई भी पाठ नहीं चुना गया है</string>
- <string name="not_supported">असमर्थित</string>
- <string name="nothing_to_save">सहेजने के लिए कुछ नहीं है</string>
- <string name="okay">ठीक है</string>
- <string name="outline_title">विषय सूची</string>
- <string name="parent_directory">[एक स्तर ऊपर]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s:%3$s</string>
- <string name="print">मुद्रित करें</string>
- <string name="print_failed">मुद्रण विफल हुआ</string>
- <string name="save">सहेजें</string>
- <string name="search">खोजें</string>
- <string name="search_backwards">पीछे की ओर खोजें</string>
- <string name="search_document">दस्तावेज़ में खोजें</string>
- <string name="search_forwards">आगे की ओर खोजें</string>
- <string name="searching_">&amp;#8230 को खोज रहे हैं;</string>
- <string name="select">चुनें</string>
- <string name="select_text">पाठ चुनें</string>
- <string name="strike_out">काटें</string>
- <string name="text_not_found">पाठ नहीं मिला</string>
- <string name="toggle_links">लिंकों को हाइलाइट और सक्षम करें</string>
- <string name="underline">रेखांकित करें</string>
- <string name="yes">हाँ</string>
-</resources>
diff --git a/platform/android/viewer/res/values-hu/strings.xml b/platform/android/viewer/res/values-hu/strings.xml
deleted file mode 100644
index 1533b65a..00000000
--- a/platform/android/viewer/res/values-hu/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Elfogadás</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Mégse</string>
- <string name="cannot_open_buffer">A puffert nem lehet megnyitni</string>
- <string name="cannot_open_document">A dokumentumot nem lehet megnyitni</string>
- <string name="cannot_open_document_Reason">A dokumentumot nem lehet megnyitni: %1$s</string>
- <string name="cannot_open_file_Path">A fájlt nem lehet megnyitni: %1$s</string>
- <string name="choose_value">Érték kiválasztása</string>
- <string name="copied_to_clipboard">A vágólapra másolva</string>
- <string name="copy">Másolás</string>
- <string name="copy_text">szöveg másolása</string>
- <string name="copy_text_to_the_clipboard">Szöveg másolása a vágólapra</string>
- <string name="delete">Törlés</string>
- <string name="dismiss">Bezárás</string>
- <string name="document_has_changes_save_them_">A dokumentum módosítva lett. Menti a változtatásokat?</string>
- <string name="draw_annotation">Jegyzet rajzolása</string>
- <string name="edit_annotations">Jegyzetek szerkesztése</string>
- <string name="enter_password">Jelszó megadása</string>
- <string name="entering_reflow_mode">Belépés az újrarendezési módba</string>
- <string name="fill_out_text_field">Szövegmező kitöltése</string>
- <string name="format_currently_not_supported">A formátum jelenleg nem támogatott</string>
- <string name="highlight">Kiemelés</string>
- <string name="ink">Kézírás</string>
- <string name="leaving_reflow_mode">Kilépés az újrarendezési módból</string>
- <string name="more">Több</string>
- <string name="no">Nem</string>
- <string name="no_further_occurrences_found">Nincsenek további találatok</string>
- <string name="no_media_hint">Az adathordozó a PC-vel való megosztás esetén elérhetetlenné válhat</string>
- <string name="no_media_warning">Nincs jelen adathordozó</string>
- <string name="no_text_selected">Nincs kijelölt szöveg</string>
- <string name="not_supported">Nem támogatott</string>
- <string name="nothing_to_save">Nem kell semmit menteni</string>
- <string name="okay">OK</string>
- <string name="outline_title">Tartalomjegyzék</string>
- <string name="parent_directory">[Egy szinttel feljebb]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Nyomtatás</string>
- <string name="print_failed">Nyomtatás sikertelen</string>
- <string name="save">Mentés</string>
- <string name="search">Keresés</string>
- <string name="search_backwards">Keresés visszafelé</string>
- <string name="search_document">Dokumentum keresése</string>
- <string name="search_forwards">Keresés előrefelé</string>
- <string name="searching_">Keresés:&amp;#8230;</string>
- <string name="select">Kijelölés</string>
- <string name="select_text">Szöveg kijelölése</string>
- <string name="strike_out">Áthúzás</string>
- <string name="text_not_found">Szöveg nem található</string>
- <string name="toggle_links">Kiemelés és linkek engedélyezése</string>
- <string name="underline">Aláhúzás</string>
- <string name="yes">Igen</string>
-</resources>
diff --git a/platform/android/viewer/res/values-in/strings.xml b/platform/android/viewer/res/values-in/strings.xml
deleted file mode 100644
index f90d1b3b..00000000
--- a/platform/android/viewer/res/values-in/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Terima</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Batal</string>
- <string name="cannot_open_buffer">Tidak bisa membuka penyangga</string>
- <string name="cannot_open_document">Tidak bisa membuka dokumen</string>
- <string name="cannot_open_document_Reason">Tidak bisa membuka dokumen: %1$s</string>
- <string name="cannot_open_file_Path">Tidak bisa membuka berkas: %1$s</string>
- <string name="choose_value">Pilih nilai</string>
- <string name="copied_to_clipboard">Disalin ke papan klip</string>
- <string name="copy">Salin</string>
- <string name="copy_text">Salin teks</string>
- <string name="copy_text_to_the_clipboard">Salin teks ke papan klip</string>
- <string name="delete">Hapus</string>
- <string name="dismiss">Hilangkan</string>
- <string name="document_has_changes_save_them_">Dokumen telah berubah. Simpan perubahan?</string>
- <string name="draw_annotation">Gambar anotasi</string>
- <string name="edit_annotations">Sunting anotasi</string>
- <string name="enter_password">Masukkan kata sandi</string>
- <string name="entering_reflow_mode">Masuk mode alir-ulang</string>
- <string name="fill_out_text_field">Isi bidang teks</string>
- <string name="format_currently_not_supported">Format ini tidak didukung</string>
- <string name="highlight">Sorotan</string>
- <string name="ink">Tinta</string>
- <string name="leaving_reflow_mode">Tinggalkan mode alir-ulang</string>
- <string name="more">Selengkapnya</string>
- <string name="no">Tidak</string>
- <string name="no_further_occurrences_found">Tidak ditemukan kejadian lain</string>
- <string name="no_media_hint">Berbagi media penyimpanan dengan PC dapat membuatnya tidak bisa diakses</string>
- <string name="no_media_warning">Media penyimpanan tidak ada</string>
- <string name="no_text_selected">Tidak ada teks yang dipilih</string>
- <string name="not_supported">Tidak didukung</string>
- <string name="nothing_to_save">Tidak ada yang disimpan</string>
- <string name="okay">Oke</string>
- <string name="outline_title">Daftar Isi</string>
- <string name="parent_directory">[Naik satu tingkat]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Cetak</string>
- <string name="print_failed">Pencetakan gagal</string>
- <string name="save">Simpan</string>
- <string name="search">Cari</string>
- <string name="search_backwards">Cari mundur</string>
- <string name="search_document">Cari dokumen</string>
- <string name="search_forwards">Cari maju</string>
- <string name="searching_">Mencari…</string>
- <string name="select">Pilih</string>
- <string name="select_text">Pilih teks</string>
- <string name="strike_out">Gagal</string>
- <string name="text_not_found">Teks tidak ditemukan</string>
- <string name="toggle_links">Sorot dan aktifkan tautan</string>
- <string name="underline">Garis bawah</string>
- <string name="yes">Ya</string>
-</resources>
diff --git a/platform/android/viewer/res/values-it/strings.xml b/platform/android/viewer/res/values-it/strings.xml
deleted file mode 100644
index 25cf56dd..00000000
--- a/platform/android/viewer/res/values-it/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Accetta</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Annulla</string>
- <string name="cannot_open_buffer">Impossibile aprire buffering</string>
- <string name="cannot_open_document">Impossibile aprire documento</string>
- <string name="cannot_open_document_Reason">Impossibile aprire documento: %1$s</string>
- <string name="cannot_open_file_Path">Impossibile aprire file: %1$s</string>
- <string name="choose_value">Scegli valore</string>
- <string name="copied_to_clipboard">Copiato negli appunti</string>
- <string name="copy">Copia</string>
- <string name="copy_text">copia testo</string>
- <string name="copy_text_to_the_clipboard">Copia testo negli appunti</string>
- <string name="delete">Elimina</string>
- <string name="dismiss">Ignora</string>
- <string name="document_has_changes_save_them_">Il documento contiene modifiche. Salvare?</string>
- <string name="draw_annotation">Disegna annotazione</string>
- <string name="edit_annotations">Modifica annotazione</string>
- <string name="enter_password">Inserisci password</string>
- <string name="entering_reflow_mode">Inserimento modalità di adattamento dinamico del contenuto</string>
- <string name="fill_out_text_field">Riempi il campo di testo</string>
- <string name="format_currently_not_supported">Formato attualmente non supportato</string>
- <string name="highlight">Evidenzia</string>
- <string name="ink">Inchiostro</string>
- <string name="leaving_reflow_mode">Abbandono della modalità di adattamento dinamico del contenuto</string>
- <string name="more">Altro</string>
- <string name="no">No</string>
- <string name="no_further_occurrences_found">Nessun\'altra occorrenza trovata</string>
- <string name="no_media_hint">La condivisione del supporto di archiviazione con un PC può renderlo inaccessibile</string>
- <string name="no_media_warning">Supporto di archiviazione non presente</string>
- <string name="no_text_selected">Nessun testo selezionato</string>
- <string name="not_supported">Non supportato</string>
- <string name="nothing_to_save">Niente da salvare</string>
- <string name="okay">Ok</string>
- <string name="outline_title">Sommario</string>
- <string name="parent_directory">[Su di un livello]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Stampa</string>
- <string name="print_failed">Stampa non riuscita</string>
- <string name="save">Salva</string>
- <string name="search">Cerca</string>
- <string name="search_backwards">Cerca indietro</string>
- <string name="search_document">Cerca documento</string>
- <string name="search_forwards">Cerca avanti</string>
- <string name="searching_">Ricerca...</string>
- <string name="select">Seleziona</string>
- <string name="select_text">Seleziona testo</string>
- <string name="strike_out">Barrato</string>
- <string name="text_not_found">Testo non trovato</string>
- <string name="toggle_links">Evidenzia e abilita link</string>
- <string name="underline">Sottolinea</string>
- <string name="yes">Sì</string>
-</resources>
diff --git a/platform/android/viewer/res/values-iw/strings.xml b/platform/android/viewer/res/values-iw/strings.xml
deleted file mode 100644
index d259ae76..00000000
--- a/platform/android/viewer/res/values-iw/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">קבל</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">בטל</string>
- <string name="cannot_open_buffer">אין אפשרות לפתוח מאגר</string>
- <string name="cannot_open_document">אין אפשרות לפתוח מסמך</string>
- <string name="cannot_open_document_Reason">אין אפשרות לפתוח מסמך: %1$s</string>
- <string name="cannot_open_file_Path">אין אפשרות לפתוח קובץ: %1$s</string>
- <string name="choose_value">בחר ערך</string>
- <string name="copied_to_clipboard">הועתק ללוח</string>
- <string name="copy">העתק</string>
- <string name="copy_text">העתק טקסט</string>
- <string name="copy_text_to_the_clipboard">העתק טקסט ללוח</string>
- <string name="delete">מחק</string>
- <string name="dismiss">התעלם</string>
- <string name="document_has_changes_save_them_">קיימים שינויים במסמך. לשמור אותם?</string>
- <string name="draw_annotation">רשום ביאור</string>
- <string name="edit_annotations">ערוך ביאורים</string>
- <string name="enter_password">הזן סיסמה</string>
- <string name="entering_reflow_mode">כניסה למצב הזרמה מחדש</string>
- <string name="fill_out_text_field">מלא את שדה הטקסט</string>
- <string name="format_currently_not_supported">תבנית לא נתמכת כעת</string>
- <string name="highlight">הבלטה</string>
- <string name="ink">דיו</string>
- <string name="leaving_reflow_mode">יציאה ממצב הזרמה מחדש</string>
- <string name="more">עוד</string>
- <string name="no">לא</string>
- <string name="no_further_occurrences_found">לא עוד</string>
- <string name="no_media_hint">שיתוף מדיית האחסון עם מחשב עשויה להפוך אותה לבלתי נגישה</string>
- <string name="no_media_warning">מדיית אחסון לא קיימת</string>
- <string name="no_text_selected">לא נבחר טקסט</string>
- <string name="not_supported">לא נתמך</string>
- <string name="nothing_to_save">אין מה לשמור</string>
- <string name="okay">בסדר</string>
- <string name="outline_title">תוכן העניינים</string>
- <string name="parent_directory">[למעלה ברמה אחת]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">הדפס</string>
- <string name="print_failed">ההדפסה נכשלה</string>
- <string name="save">שמור</string>
- <string name="search">חפש</string>
- <string name="search_backwards">חפש אחורה</string>
- <string name="search_document">חפש במסמך</string>
- <string name="search_forwards">חפש קדימה</string>
- <string name="searching_">מחפש&amp;#8230;</string>
- <string name="select">בחר ערך</string>
- <string name="select_text">בחר טקסט</string>
- <string name="strike_out">הדגש</string>
- <string name="text_not_found">לא נמצא טקסט</string>
- <string name="toggle_links">הבלט ואפשר קישורים</string>
- <string name="underline">קו תחתון</string>
- <string name="yes">כן</string>
-</resources>
diff --git a/platform/android/viewer/res/values-ja/strings.xml b/platform/android/viewer/res/values-ja/strings.xml
deleted file mode 100644
index 8ceb5e09..00000000
--- a/platform/android/viewer/res/values-ja/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">承諾する</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">キャンセル</string>
- <string name="cannot_open_buffer">バッファーを開けません</string>
- <string name="cannot_open_document">ドキュメントを開けません</string>
- <string name="cannot_open_document_Reason">次のドキュメントを開けません:%1$s</string>
- <string name="cannot_open_file_Path">次のファイルを開けません: %1$s</string>
- <string name="choose_value">バリューを選択してください</string>
- <string name="copied_to_clipboard">クリップボードにコピーされました</string>
- <string name="copy">コピー</string>
- <string name="copy_text">テキストをコピー</string>
- <string name="copy_text_to_the_clipboard">テキストをクリップボードにコピー</string>
- <string name="delete">削除</string>
- <string name="dismiss">却下</string>
- <string name="document_has_changes_save_them_">ドキュメントは変更されました。保存しますか?</string>
- <string name="draw_annotation">注釈を挿入する</string>
- <string name="edit_annotations">注釈を編集する</string>
- <string name="enter_password">パスワードを入力する</string>
- <string name="entering_reflow_mode">リフローモードを開始する</string>
- <string name="fill_out_text_field">テキストフィールドに書き込む</string>
- <string name="format_currently_not_supported">このフォーマットは現在サポートされていません</string>
- <string name="highlight">ハイライト</string>
- <string name="ink">インク</string>
- <string name="leaving_reflow_mode">リフローモードを終了する</string>
- <string name="more">もっと</string>
- <string name="no">いいえ</string>
- <string name="no_further_occurrences_found">他にオカレンスは見つかりませんでした</string>
- <string name="no_media_hint">記憶媒体をPCとシェアするとアクセスできなくなる可能性があります</string>
- <string name="no_media_warning">記憶媒体が見つかりません</string>
- <string name="no_text_selected">テキストが選択されていません</string>
- <string name="not_supported">サポートされていません</string>
- <string name="nothing_to_save">保存するものがありません</string>
- <string name="okay">了解</string>
- <string name="outline_title">目次</string>
- <string name="parent_directory">[一つ上位のレベル]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">印刷</string>
- <string name="print_failed">印刷に失敗しました</string>
- <string name="save">保存</string>
- <string name="search">検索</string>
- <string name="search_backwards">逆方向検索</string>
- <string name="search_document">ドキュメントを検索する</string>
- <string name="search_forwards">順方向検索</string>
- <string name="searching_">検索中</string>
- <string name="select">選択</string>
- <string name="select_text">テキストを選択する</string>
- <string name="strike_out">取り消し線を引く</string>
- <string name="text_not_found">テキストが見つかりません</string>
- <string name="toggle_links">ハイライトしてリンクを有効にする</string>
- <string name="underline">下線を引く</string>
- <string name="yes">はい</string>
-</resources>
diff --git a/platform/android/viewer/res/values-ko/strings.xml b/platform/android/viewer/res/values-ko/strings.xml
deleted file mode 100644
index b52a2f5a..00000000
--- a/platform/android/viewer/res/values-ko/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">수락</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">취소</string>
- <string name="cannot_open_buffer">버퍼 열 수 없음</string>
- <string name="cannot_open_document">문서 열 수 없음</string>
- <string name="cannot_open_document_Reason">문서 열 수 없음: %1$s</string>
- <string name="cannot_open_file_Path">파일 열 수 없음: %1$s</string>
- <string name="choose_value">값 선택</string>
- <string name="copied_to_clipboard">클립보드로 복사됨</string>
- <string name="copy">복사</string>
- <string name="copy_text">텍스트 복사</string>
- <string name="copy_text_to_the_clipboard">클립보드로 텍스트 복사</string>
- <string name="delete">삭제</string>
- <string name="dismiss">무시</string>
- <string name="document_has_changes_save_them_">문서에 변경사항이 있습니다. 저장?</string>
- <string name="draw_annotation">주석달기</string>
- <string name="edit_annotations">주석 편집</string>
- <string name="enter_password">패스워드 입력</string>
- <string name="entering_reflow_mode">리플로우 모드 시작</string>
- <string name="fill_out_text_field">텍스트 입력란에 기입하십시오.</string>
- <string name="format_currently_not_supported">현재 지원되지 않는 포맷</string>
- <string name="highlight">주요기능</string>
- <string name="ink">잉크</string>
- <string name="leaving_reflow_mode">리플로우 모드 해제</string>
- <string name="more">기타</string>
- <string name="no">아니오</string>
- <string name="no_further_occurrences_found">발견된 추가 발생 없음</string>
- <string name="no_media_hint">PC와 스토리지 미디어를 공유하면 액세스할 수 없습니다.</string>
- <string name="no_media_warning">스토리지 미디어 없음</string>
- <string name="no_text_selected">선택된 텍스트 없음</string>
- <string name="not_supported">지원 안됨</string>
- <string name="nothing_to_save">저장 대상 없음</string>
- <string name="okay">확인</string>
- <string name="outline_title">목차</string>
- <string name="parent_directory">[레벨 한 단계 상승]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">인쇄</string>
- <string name="print_failed">인쇄 실패</string>
- <string name="save">저장</string>
- <string name="search">검색</string>
- <string name="search_backwards">뒤로 검색</string>
- <string name="search_document">문서 검색</string>
- <string name="search_forwards">앞으로 검색</string>
- <string name="searching_">검색 중&amp;#8230;</string>
- <string name="select">선택</string>
- <string name="select_text">텍스트 선택</string>
- <string name="strike_out">삭제</string>
- <string name="text_not_found">발견된 텍스트 없음</string>
- <string name="toggle_links">하이라이트 및 링크 활성화</string>
- <string name="underline">밑줄</string>
- <string name="yes">예</string>
-</resources>
diff --git a/platform/android/viewer/res/values-lt/strings.xml b/platform/android/viewer/res/values-lt/strings.xml
deleted file mode 100644
index f66ba305..00000000
--- a/platform/android/viewer/res/values-lt/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Priimti</string>
- <string name="app_name">„MuPDF“</string>
- <string name="cancel">Atšaukti</string>
- <string name="cannot_open_buffer">Nepavyksta atverti buferinės atmintinės</string>
- <string name="cannot_open_document">Nepavyksta atverti dokumento</string>
- <string name="cannot_open_document_Reason">Nepavyksta atverti dokumento: %1$s</string>
- <string name="cannot_open_file_Path">Nepavyksta atverti failo: %1$s</string>
- <string name="choose_value">Pasirinkti vertę</string>
- <string name="copied_to_clipboard">Nukopijuota į iškarpinę</string>
- <string name="copy">Kopijuoti</string>
- <string name="copy_text">kopijuoti tekstą</string>
- <string name="copy_text_to_the_clipboard">Kopijuoti tekstą į iškarpinę</string>
- <string name="delete">Naikinti</string>
- <string name="dismiss">Atmesti</string>
- <string name="document_has_changes_save_them_">Dokumente yra pakeitimų. Ar juos įrašyti?</string>
- <string name="draw_annotation">Braižyti anotaciją</string>
- <string name="edit_annotations">Redaguoti anotacijas</string>
- <string name="enter_password">Įvesti slaptažodį</string>
- <string name="entering_reflow_mode">Pereinama į pertvarkymo režimą</string>
- <string name="fill_out_text_field">Užpildyti teksto lauką</string>
- <string name="format_currently_not_supported">Formatas šiuo metu nedera</string>
- <string name="highlight">Pažymėti</string>
- <string name="ink">Rašalas</string>
- <string name="leaving_reflow_mode">Išeinama iš pertvarkymo režimo</string>
- <string name="more">Daugiau</string>
- <string name="no">Ne</string>
- <string name="no_further_occurrences_found">Daugiau įrašų nerasta</string>
- <string name="no_media_hint">Pabendrinus laikmeną su kompiuteriu, ji gali tapti nebepasiekiama</string>
- <string name="no_media_warning">Laikmenos nėra</string>
- <string name="no_text_selected">Neparinktas tekstas</string>
- <string name="not_supported">Nedera</string>
- <string name="nothing_to_save">Nėra ką įrašyti</string>
- <string name="okay">Gerai</string>
- <string name="outline_title">Turinys</string>
- <string name="parent_directory">[Vienu lygiu aukštyn]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Spausdinti</string>
- <string name="print_failed">Išspausdinti nepavyko</string>
- <string name="save">Įrašyti</string>
- <string name="search">Ieškoti</string>
- <string name="search_backwards">Ieškoti atgal</string>
- <string name="search_document">Ieškoti dokumente</string>
- <string name="search_forwards">Ieškoti pirmyn</string>
- <string name="searching_">Ieškoma&amp;#8230;</string>
- <string name="select">Pasirinkti</string>
- <string name="select_text">Pasirinkti tekstą</string>
- <string name="strike_out">Išbraukti</string>
- <string name="text_not_found">Teksto nerasta</string>
- <string name="toggle_links">Pažymėti ir įjungti nuorodas</string>
- <string name="underline">Pabraukti</string>
- <string name="yes">Taip</string>
-</resources>
diff --git a/platform/android/viewer/res/values-ms/strings.xml b/platform/android/viewer/res/values-ms/strings.xml
deleted file mode 100644
index 64541e6f..00000000
--- a/platform/android/viewer/res/values-ms/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Terima</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Batal</string>
- <string name="cannot_open_buffer">Tidak boleh membuka penimbal</string>
- <string name="cannot_open_document">Tidak boleh membuka dokumen</string>
- <string name="cannot_open_document_Reason">Tidak boleh membuka dokumen: %1$s</string>
- <string name="cannot_open_file_Path">Tidak boleh membuka fail: %1$s</string>
- <string name="choose_value">Pilih nilai</string>
- <string name="copied_to_clipboard">Disalin ke papan klip</string>
- <string name="copy">Salin</string>
- <string name="copy_text">salin teks</string>
- <string name="copy_text_to_the_clipboard">Salin teks ke papan klip</string>
- <string name="delete">Padam</string>
- <string name="dismiss">Singkir</string>
- <string name="document_has_changes_save_them_">Dokumen mempunyai perubahan. Simpankannya?</string>
- <string name="draw_annotation">Lakarkan catatan</string>
- <string name="edit_annotations">Suntingkan catatan</string>
- <string name="enter_password">Masukkan kata laluan</string>
- <string name="entering_reflow_mode">Memasuki mod penyusunan semula</string>
- <string name="fill_out_text_field">Mengisi medan teks</string>
- <string name="format_currently_not_supported">Format buat masa ini tidak disokong</string>
- <string name="highlight">Serlahkan</string>
- <string name="ink">Dakwat</string>
- <string name="leaving_reflow_mode">Meninggalkan mod penyusunan semula</string>
- <string name="more">Lagi</string>
- <string name="no">Tidak</string>
- <string name="no_further_occurrences_found">Tiada kejadian lanjut ditemui</string>
- <string name="no_media_hint">Berkongsi media storan dengan PC boleh menjadikannya tidak dapat dicapai</string>
- <string name="no_media_warning">Media storan tidak wujud</string>
- <string name="no_text_selected">Tiada teks dipilih</string>
- <string name="not_supported">Tidak disokong</string>
- <string name="nothing_to_save">Tiada apa untuk disimpan</string>
- <string name="okay">Okey</string>
- <string name="outline_title">Jadual Kandungan</string>
- <string name="parent_directory">[Naik satu tahap]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Cetak</string>
- <string name="print_failed">Gagal dicetak</string>
- <string name="save">Simpan</string>
- <string name="search">Carian</string>
- <string name="search_backwards">Carian ke belakang</string>
- <string name="search_document">Carian dokumen</string>
- <string name="search_forwards">Carian ke depan</string>
- <string name="searching_">Mencari&amp;#8230;</string>
- <string name="select">Pilih</string>
- <string name="select_text">Pilih teks</string>
- <string name="strike_out">Mansuhkan</string>
- <string name="text_not_found">Teks tidak ditemui</string>
- <string name="toggle_links">Serlahkan dan dayakan pautan</string>
- <string name="underline">Gariskan</string>
- <string name="yes">Ya</string>
-</resources>
diff --git a/platform/android/viewer/res/values-nl/strings.xml b/platform/android/viewer/res/values-nl/strings.xml
deleted file mode 100644
index 21945c86..00000000
--- a/platform/android/viewer/res/values-nl/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Accepteren</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Annuleren</string>
- <string name="cannot_open_buffer">Buffer kan niet geopend worden</string>
- <string name="cannot_open_document">Document kan niet geopend worden</string>
- <string name="cannot_open_document_Reason">Document kan niet geopend worden: %1$s</string>
- <string name="cannot_open_file_Path">Bestand kan niet geopend worden : %1$s</string>
- <string name="choose_value">Kies waarde</string>
- <string name="copied_to_clipboard">Gekopieerd naar klembord</string>
- <string name="copy">Kopiëren</string>
- <string name="copy_text">tekst kopiëren</string>
- <string name="copy_text_to_the_clipboard">Tekst kopiëren naar klembord</string>
- <string name="delete">Verwijderen</string>
- <string name="dismiss">Afwijzen</string>
- <string name="document_has_changes_save_them_">Het document is gewijzigd. Opslaan?</string>
- <string name="draw_annotation">Opmerking tekenen</string>
- <string name="edit_annotations">Opmerkingen bewerken</string>
- <string name="enter_password">Voer wachtwoord in</string>
- <string name="entering_reflow_mode">Conversiemodus wordt geopend</string>
- <string name="fill_out_text_field">Vul het tekstveld in</string>
- <string name="format_currently_not_supported">Formaat wordt momenteel niet ondersteund</string>
- <string name="highlight">Markeren</string>
- <string name="ink">Inkten</string>
- <string name="leaving_reflow_mode">Conversiemodus wordt beëindigd</string>
- <string name="more">Meer</string>
- <string name="no">Nee</string>
- <string name="no_further_occurrences_found">Geen andere resultaten gevonden</string>
- <string name="no_media_hint">Het opslagmedium kan ontoegankelijk worden als het met een pc wordt gedeeld</string>
- <string name="no_media_warning">Geen opslagmedium aanwezig</string>
- <string name="no_text_selected">Geen tekst geselecteerd</string>
- <string name="not_supported">Niet ondersteund</string>
- <string name="nothing_to_save">Niets om op te slaan</string>
- <string name="okay">Oké</string>
- <string name="outline_title">Inhoudsopgave</string>
- <string name="parent_directory">[Een niveau hoger]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Afdrukken</string>
- <string name="print_failed">Afdrukken mislukt</string>
- <string name="save">Opslaan</string>
- <string name="search">Zoeken</string>
- <string name="search_backwards">Achterstevoren zoeken</string>
- <string name="search_document">Document doorzoeken</string>
- <string name="search_forwards">Vooruit zoeken</string>
- <string name="searching_">Aan het zoeken …</string>
- <string name="select">Selecteren</string>
- <string name="select_text">Tekst selecteren</string>
- <string name="strike_out">Doorhalen</string>
- <string name="text_not_found">Tekst niet gevonden</string>
- <string name="toggle_links">Markeren en koppelingen inschakelen</string>
- <string name="underline">Onderstrepen</string>
- <string name="yes">Ja</string>
-</resources>
diff --git a/platform/android/viewer/res/values-no/strings.xml b/platform/android/viewer/res/values-no/strings.xml
deleted file mode 100644
index 31bd6bf0..00000000
--- a/platform/android/viewer/res/values-no/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Aksepter</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Avbryt</string>
- <string name="cannot_open_buffer">Kan ikke åpne buffer</string>
- <string name="cannot_open_document">Kan ikke åpne dukumentet</string>
- <string name="cannot_open_document_Reason">Kan ikke åpne dokumentet: %1$s</string>
- <string name="cannot_open_file_Path">Kan ikke åpne filen: %1$s</string>
- <string name="choose_value">Velg verdi</string>
- <string name="copied_to_clipboard">Kopiert til utklippstavlen</string>
- <string name="copy">Kopier</string>
- <string name="copy_text">kopier tekst</string>
- <string name="copy_text_to_the_clipboard">Kopier teksten til utklippstavlen</string>
- <string name="delete">Slett</string>
- <string name="dismiss">Avvis</string>
- <string name="document_has_changes_save_them_">Det er endringer i dokumentet. Lagre dem?</string>
- <string name="draw_annotation">Lag merknad</string>
- <string name="edit_annotations">Rediger merknader</string>
- <string name="enter_password">Skriv inn passord</string>
- <string name="entering_reflow_mode">Bytter til konverteringsmodus</string>
- <string name="fill_out_text_field">Fyll ut tekstfeltet</string>
- <string name="format_currently_not_supported">Formatet er ikke støttet for øyeblikket</string>
- <string name="highlight">Uthev</string>
- <string name="ink">Håndskrift</string>
- <string name="leaving_reflow_mode">Går ut av konverteringsmodus</string>
- <string name="more">Mer</string>
- <string name="no">Nei</string>
- <string name="no_further_occurrences_found">Ingen flere hendelser funnet</string>
- <string name="no_media_hint">Deling av lagringsmedia med en PC kan gjøre det utilgjengelig</string>
- <string name="no_media_warning">Lagringsmedia ikke til stede</string>
- <string name="no_text_selected">Ingen tekst er valgt</string>
- <string name="not_supported">Ikke støttet</string>
- <string name="nothing_to_save">Ingenting å lagre</string>
- <string name="okay">Ok</string>
- <string name="outline_title">Innholdsfortegnelse</string>
- <string name="parent_directory">[OPP ett nivå]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s%3$s</string>
- <string name="print">Skriv ut</string>
- <string name="print_failed">Kunne ikke skrive ut</string>
- <string name="save">Lagre</string>
- <string name="search">Søk</string>
- <string name="search_backwards">Søk bakover</string>
- <string name="search_document">Søk i dokument</string>
- <string name="search_forwards">Søk framover</string>
- <string name="searching_">Søker&amp;#8230;</string>
- <string name="select">Velg</string>
- <string name="select_text">Valgt tekst</string>
- <string name="strike_out">Gjennomstreking</string>
- <string name="text_not_found">Teksten ble ikke funnet</string>
- <string name="toggle_links">Uthev og aktiver koblinger</string>
- <string name="underline">Understrek</string>
- <string name="yes">Ja</string>
-</resources>
diff --git a/platform/android/viewer/res/values-pl/strings.xml b/platform/android/viewer/res/values-pl/strings.xml
deleted file mode 100644
index 42511e42..00000000
--- a/platform/android/viewer/res/values-pl/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Zaakceptuj</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Anuluj</string>
- <string name="cannot_open_buffer">Nie można otworzyć bufora</string>
- <string name="cannot_open_document">Nie można otworzyć dokumentu</string>
- <string name="cannot_open_document_Reason">Nie można otworzyć dokumentu: %1$s</string>
- <string name="cannot_open_file_Path">Nie można otworzyć pliku: %1$s</string>
- <string name="choose_value">Wybierz wartość</string>
- <string name="copied_to_clipboard">Skopiowano do schowka</string>
- <string name="copy">Kopiuj</string>
- <string name="copy_text">kopiuj tekst</string>
- <string name="copy_text_to_the_clipboard">Kopiuj tekst do schowka</string>
- <string name="delete">Usuń</string>
- <string name="dismiss">Odrzuć</string>
- <string name="document_has_changes_save_them_">W dokumencie dokonano zmian. Czy chcesz je zapisać?</string>
- <string name="draw_annotation">Sporządź notatkę</string>
- <string name="edit_annotations">Edytuj notatki</string>
- <string name="enter_password">Wprowadź hasło</string>
- <string name="entering_reflow_mode">Włączanie trybu zawijania tekstu</string>
- <string name="fill_out_text_field">Wypełnij pole tekstowe</string>
- <string name="format_currently_not_supported">Format obecnie nieobsługiwany</string>
- <string name="highlight">Podświetl</string>
- <string name="ink">Atrament</string>
- <string name="leaving_reflow_mode">Wyłączanie trybu zawijania tekstu</string>
- <string name="more">Więcej</string>
- <string name="no">Nie</string>
- <string name="no_further_occurrences_found">Nie znaleziono więcej wystąpień</string>
- <string name="no_media_hint">Współdzielenie nośnika danych z komputerem PC może sprawić, że będzie niedostępny</string>
- <string name="no_media_warning">Nośnik danych niedostępny</string>
- <string name="no_text_selected">Nie wybrano tekstu</string>
- <string name="not_supported">Nieobsługiwany</string>
- <string name="nothing_to_save">Nie ma nic do zapisania</string>
- <string name="okay">OK</string>
- <string name="outline_title">Spis treści</string>
- <string name="parent_directory">[W górę o jeden poziom]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Drukuj</string>
- <string name="print_failed">Drukowanie nieudane</string>
- <string name="save">Zapisz</string>
- <string name="search">Szukaj</string>
- <string name="search_backwards">Szukaj z tyłu</string>
- <string name="search_document">Szukaj w dokumencie</string>
- <string name="search_forwards">Szukaj z przodu</string>
- <string name="searching_">Wyszukiwanie&amp;#8230;</string>
- <string name="select">Wybierz</string>
- <string name="select_text">Wybierz tekst</string>
- <string name="strike_out">Przekreślenie</string>
- <string name="text_not_found">Nie znaleziono tekstu</string>
- <string name="toggle_links">Podświetl i aktywuj linki</string>
- <string name="underline">Podkreślenie</string>
- <string name="yes">Tak</string>
-</resources>
diff --git a/platform/android/viewer/res/values-pt/strings.xml b/platform/android/viewer/res/values-pt/strings.xml
deleted file mode 100644
index 15f86283..00000000
--- a/platform/android/viewer/res/values-pt/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Aceitar</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Cancelar</string>
- <string name="cannot_open_buffer">Não é possível abrir a memória intermédia</string>
- <string name="cannot_open_document">Não é possível abrir o documento</string>
- <string name="cannot_open_document_Reason">Não é possível abrir o documento: %1$s</string>
- <string name="cannot_open_file_Path">Não é possível abrir o ficheiro: %1$s</string>
- <string name="choose_value">Escolha um valor</string>
- <string name="copied_to_clipboard">Copiado para a área de transferência</string>
- <string name="copy">Copiar</string>
- <string name="copy_text">copiar o texto</string>
- <string name="copy_text_to_the_clipboard">Copiar o texto para a área de transferência</string>
- <string name="delete">Eliminar</string>
- <string name="dismiss">Desistir</string>
- <string name="document_has_changes_save_them_">Há alterações ao documento. Deseja guardá-las?</string>
- <string name="draw_annotation">Adicionar anotação</string>
- <string name="edit_annotations">Editar anotações</string>
- <string name="enter_password">Escrever a palavra-passe</string>
- <string name="entering_reflow_mode">A entrar no modo de refluxo</string>
- <string name="fill_out_text_field">Preencher o campo de texto</string>
- <string name="format_currently_not_supported">Esse formato não é atualmente suportado</string>
- <string name="highlight">Destacar</string>
- <string name="ink">Tinta</string>
- <string name="leaving_reflow_mode">A sair do modo de refluxo</string>
- <string name="more">Mais</string>
- <string name="no">Não</string>
- <string name="no_further_occurrences_found">Não foram encontradas mais ocorrências</string>
- <string name="no_media_hint">Partilhar o dispositivo de armazenamento com um PC poderá torná-lo inacessível</string>
- <string name="no_media_warning">O dispositivo de armazenamento não está presente</string>
- <string name="no_text_selected">Não há texto selecionado</string>
- <string name="not_supported">Não suportado</string>
- <string name="nothing_to_save">Não há nada para guardar</string>
- <string name="okay">Okay</string>
- <string name="outline_title">Índice</string>
- <string name="parent_directory">[subir um nível]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s: %3$s</string>
- <string name="print">Imprimir</string>
- <string name="print_failed">Falha na Impressão</string>
- <string name="save">Guardar</string>
- <string name="search">Pesquisar</string>
- <string name="search_backwards">Pesquisar para trás</string>
- <string name="search_document">Pesquisar no documento</string>
- <string name="search_forwards">Pesquisar para a frente</string>
- <string name="searching_">A pesquisar&amp;#8230;</string>
- <string name="select">Selecionar</string>
- <string name="select_text">Selecionar o texto</string>
- <string name="strike_out">Rasurado</string>
- <string name="text_not_found">Texto não encontrado</string>
- <string name="toggle_links">Destacar e permitir links</string>
- <string name="underline">Sublinhado</string>
- <string name="yes">Sim</string>
-</resources>
diff --git a/platform/android/viewer/res/values-ru/strings.xml b/platform/android/viewer/res/values-ru/strings.xml
deleted file mode 100644
index 7cc35187..00000000
--- a/platform/android/viewer/res/values-ru/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Принять</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Отмена</string>
- <string name="cannot_open_buffer">Невозможно открыть буфер</string>
- <string name="cannot_open_document">Невозможно открыть документ</string>
- <string name="cannot_open_document_Reason">Невозможно открыть документ: %1$s</string>
- <string name="cannot_open_file_Path">Невозможно открыть файл: %1$s</string>
- <string name="choose_value">Выберите значение</string>
- <string name="copied_to_clipboard">Скопировано в буфер</string>
- <string name="copy">Копировать</string>
- <string name="copy_text">копировать текст</string>
- <string name="copy_text_to_the_clipboard">Копировать текст в буфер</string>
- <string name="delete">Удалить</string>
- <string name="dismiss">Пропустить</string>
- <string name="document_has_changes_save_them_">Документ был изменен. Сохранить изменения?</string>
- <string name="draw_annotation">Создать аннтоацию</string>
- <string name="edit_annotations">Редактировать аннотации</string>
- <string name="enter_password">Введите пароль</string>
- <string name="entering_reflow_mode">Переход в режим Reflow</string>
- <string name="fill_out_text_field">Заполните текстовое поле</string>
- <string name="format_currently_not_supported">Формат не поддерживается</string>
- <string name="highlight">Выделить</string>
- <string name="ink">Чернила</string>
- <string name="leaving_reflow_mode">Выход из режима Reflow</string>
- <string name="more">Еще</string>
- <string name="no">Нет</string>
- <string name="no_further_occurrences_found">Других ошибок не зафиксировано</string>
- <string name="no_media_hint">Подключение компьютеров к хранилищу данных может привести к потере доступа к хранилищу</string>
- <string name="no_media_warning">Хранилище данных отсутствует</string>
- <string name="no_text_selected">Текст не выбран</string>
- <string name="not_supported">Не поддерживается</string>
- <string name="nothing_to_save">Не выбраны файлы для сохранения</string>
- <string name="okay">ОК</string>
- <string name="outline_title">Содержание</string>
- <string name="parent_directory">[Вверх на один уровень]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Печать</string>
- <string name="print_failed">Печать не выполнена</string>
- <string name="save">Сохранить</string>
- <string name="search">Поиск</string>
- <string name="search_backwards">Искать в предыдущей части документа</string>
- <string name="search_document">Искать в документе</string>
- <string name="search_forwards">Искать в остальной части документа</string>
- <string name="searching_">Поиск&amp;#8230;</string>
- <string name="select">Выбор</string>
- <string name="select_text">Выбрать текст</string>
- <string name="strike_out">Зачеркнуть</string>
- <string name="text_not_found">Текст не найден</string>
- <string name="toggle_links">Выделить и включить ссылки</string>
- <string name="underline">Подчеркнуть</string>
- <string name="yes">Да</string>
-</resources>
diff --git a/platform/android/viewer/res/values-sk/strings.xml b/platform/android/viewer/res/values-sk/strings.xml
deleted file mode 100644
index e11737ef..00000000
--- a/platform/android/viewer/res/values-sk/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Prijať</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Zrušiť</string>
- <string name="cannot_open_buffer">Buffer sa nedá otvoriť</string>
- <string name="cannot_open_document">Dokument sa nedá otvoriť</string>
- <string name="cannot_open_document_Reason">Nedá sa otvoriť dokument: %1$s</string>
- <string name="cannot_open_file_Path">Nedá sa otvoriť súbor: %1$s</string>
- <string name="choose_value">Vyberte si hodnotu</string>
- <string name="copied_to_clipboard">Skopírované do vyrovnávacej pamäti</string>
- <string name="copy">Kopírovať</string>
- <string name="copy_text">kopírovať text</string>
- <string name="copy_text_to_the_clipboard">Kopírovať text do vyrovnávacej pamäti</string>
- <string name="delete">Zmazať</string>
- <string name="dismiss">Zrušiť</string>
- <string name="document_has_changes_save_them_">Dokument bol zmený. Uložiť zmeny?</string>
- <string name="draw_annotation">Zostaviť anotáciu</string>
- <string name="edit_annotations">Upraviť anotácie</string>
- <string name="enter_password">Zadať heslo</string>
- <string name="entering_reflow_mode">Vstupujem do režimu opätovného nalievania</string>
- <string name="fill_out_text_field">Vyplniť textové pole</string>
- <string name="format_currently_not_supported">Tento formát momentálne nepodporujem</string>
- <string name="highlight">Zvýrazniť</string>
- <string name="ink">Atrament</string>
- <string name="leaving_reflow_mode">Vystupujem z režimu opätovného nalievania</string>
- <string name="more">Viac</string>
- <string name="no">Nie</string>
- <string name="no_further_occurrences_found">Viac príkladov sa nenašlo</string>
- <string name="no_media_hint">Zdieľanie úložného média s PC môže znemožniť prístup</string>
- <string name="no_media_warning">Nie je tu úložné médium</string>
- <string name="no_text_selected">Žiadny text nie je vybraný</string>
- <string name="not_supported">Nepodporované</string>
- <string name="nothing_to_save">Niet čo uložiť</string>
- <string name="okay">Dobre</string>
- <string name="outline_title">Obsah</string>
- <string name="parent_directory">[O úroveň vyššie]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Tlačiť</string>
- <string name="print_failed">Tlačenie zlyhalo</string>
- <string name="save">Uložiť</string>
- <string name="search">Hľadať</string>
- <string name="search_backwards">Hľadať spätne</string>
- <string name="search_document">Hľadať v dokumente</string>
- <string name="search_forwards">Hľadať dopredu</string>
- <string name="searching_">Hľadám&amp;#8230;</string>
- <string name="select">Vybrať</string>
- <string name="select_text">Vybrať text</string>
- <string name="strike_out">Preškrtnúť</string>
- <string name="text_not_found">Text sa nenašiel</string>
- <string name="toggle_links">Zvýrazniť a zapnúť linky</string>
- <string name="underline">Podčiarknúť</string>
- <string name="yes">Áno</string>
-</resources>
diff --git a/platform/android/viewer/res/values-sv/strings.xml b/platform/android/viewer/res/values-sv/strings.xml
deleted file mode 100644
index 61d14d05..00000000
--- a/platform/android/viewer/res/values-sv/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Acceptera</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Avbryt</string>
- <string name="cannot_open_buffer">Kan inte öppna buffer</string>
- <string name="cannot_open_document">Kan inte öppna dokument</string>
- <string name="cannot_open_document_Reason">Kan inte öppna dokument: %1$s</string>
- <string name="cannot_open_file_Path">Kan inte öppna fil: %1$s</string>
- <string name="choose_value">Välj värde</string>
- <string name="copied_to_clipboard">Kopierat till klippbordet</string>
- <string name="copy">Kopiera</string>
- <string name="copy_text">kopiera text</string>
- <string name="copy_text_to_the_clipboard">Kopiera text till klippbordet</string>
- <string name="delete">Ta bort</string>
- <string name="dismiss">Avfärda</string>
- <string name="document_has_changes_save_them_">Dokumentet har ändrats. Spara ändringar?</string>
- <string name="draw_annotation">Rita annotation</string>
- <string name="edit_annotations">Ändra annotation</string>
- <string name="enter_password">Fyll i lösenord</string>
- <string name="entering_reflow_mode">Aktiverar reflow-läge</string>
- <string name="fill_out_text_field">Fyll i textfält</string>
- <string name="format_currently_not_supported">Formatat stöds inte för närvarande</string>
- <string name="highlight">Markera</string>
- <string name="ink">Bläck</string>
- <string name="leaving_reflow_mode">Lämnar reflow-läge</string>
- <string name="more">Mer</string>
- <string name="no">Nej</string>
- <string name="no_further_occurrences_found">Inga flera förekomster hittades</string>
- <string name="no_media_hint">Att dela lagringsmediet med en PC kan göra den oåtkomlig</string>
- <string name="no_media_warning">Lagringsmedia finns inte</string>
- <string name="no_text_selected">Ingen text har valts</string>
- <string name="not_supported">Stöds ej</string>
- <string name="nothing_to_save">Inget att spara</string>
- <string name="okay">OK</string>
- <string name="outline_title">Innehållsförteckning</string>
- <string name="parent_directory">[Upp en nivå]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Skriv ut</string>
- <string name="print_failed">Utskrift misslyckades</string>
- <string name="save">Spara</string>
- <string name="search">Sök</string>
- <string name="search_backwards">Sök bakåt</string>
- <string name="search_document">Sök dokument</string>
- <string name="search_forwards">Sök framåt</string>
- <string name="searching_">Letar&amp;#8230;</string>
- <string name="select">Välj</string>
- <string name="select_text">Välj text</string>
- <string name="strike_out">Stryk</string>
- <string name="text_not_found">Text hittades ej</string>
- <string name="toggle_links">Markera och aktivera länkar</string>
- <string name="underline">Understryk</string>
- <string name="yes">Ja</string>
-</resources>
diff --git a/platform/android/viewer/res/values-th/strings.xml b/platform/android/viewer/res/values-th/strings.xml
deleted file mode 100644
index e6827125..00000000
--- a/platform/android/viewer/res/values-th/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">ยอมรับ</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">ยกเลิก</string>
- <string name="cannot_open_buffer">ไม่สามารถเปิดบัฟเฟอร์</string>
- <string name="cannot_open_document">ไม่สามารถเปิดเอกสาร</string>
- <string name="cannot_open_document_Reason">ไม่สามารถเปิดเอกสาร: %1$s</string>
- <string name="cannot_open_file_Path">ไม่สามารถเปิดไฟล์: %1$s</string>
- <string name="choose_value">เลือกค่า</string>
- <string name="copied_to_clipboard">คัดลอกไปที่คลิปบอร์ดแล้ว</string>
- <string name="copy">คัดลอก</string>
- <string name="copy_text">คัดลอกข้อความ</string>
- <string name="copy_text_to_the_clipboard">คัดลอกข้อความไปที่คลิปบอร์ด</string>
- <string name="delete">ลบ</string>
- <string name="dismiss">เลิกใช้</string>
- <string name="document_has_changes_save_them_">เอกสารมีการเปลี่ยนแปลง ต้องการบันทึกหรือไม่</string>
- <string name="draw_annotation">เขียนคำอธิบายประกอบ</string>
- <string name="edit_annotations">แก้ไขคำอธิบายประกอบ</string>
- <string name="enter_password">ป้อนรหัสผ่าน</string>
- <string name="entering_reflow_mode">เข้าสู่โหมดเรียงหน้ากระดาษใหม่</string>
- <string name="fill_out_text_field">เติมในช่องข้อความ</string>
- <string name="format_currently_not_supported">ไม่รองรับรูปแบบในขณะนี้</string>
- <string name="highlight">ไฮไลท์</string>
- <string name="ink">หมึก</string>
- <string name="leaving_reflow_mode">ออกจากโหมดเรียงหน้ากระดาษใหม่</string>
- <string name="more">เพิ่มเติม</string>
- <string name="no">ไม่</string>
- <string name="no_further_occurrences_found">ไม่พบเหตุการณ์ที่เกิดขึ้นเพิ่มเติม</string>
- <string name="no_media_hint">การแบ่งปันสื่อจัดเก็บข้อมูลกับพีซีสามารถทำให้สื่อจัดเก็บข้อมูลไม่สามารถเข้าถึงได้</string>
- <string name="no_media_warning">สื่อเก็บข้อมูลไม่ปรากฏ</string>
- <string name="no_text_selected">ไม่มีข้อความที่เลือก</string>
- <string name="not_supported">ไม่รองรับ</string>
- <string name="nothing_to_save">ไม่มีอะไรให้บันทึก</string>
- <string name="okay">ตกลง</string>
- <string name="outline_title">สารบัญ</string>
- <string name="parent_directory">[ขึ้นหนึ่งระดับ]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">พิมพ์</string>
- <string name="print_failed">พิมพ์ล้มเหลว</string>
- <string name="save">บันทึก</string>
- <string name="search">ค้นหา</string>
- <string name="search_backwards">ค้นหาย้อนกลับ</string>
- <string name="search_document">ค้นหาเอกสาร</string>
- <string name="search_forwards">ค้นหาไปข้างหน้า</string>
- <string name="searching_">กำลังค้นหา&amp;#8230;</string>
- <string name="select">เลือก</string>
- <string name="select_text">เลือกข้อความ</string>
- <string name="strike_out">ขีดทับ</string>
- <string name="text_not_found">ไม่พบข้อความ</string>
- <string name="toggle_links">ไฮไลท์และเปิดใช้งานลิงก์</string>
- <string name="underline">ขีดเส้นใต้</string>
- <string name="yes">ใช่</string>
-</resources>
diff --git a/platform/android/viewer/res/values-tl/strings.xml b/platform/android/viewer/res/values-tl/strings.xml
deleted file mode 100644
index 39611fcb..00000000
--- a/platform/android/viewer/res/values-tl/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Tanggapin</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">Kanselahin</string>
- <string name="cannot_open_buffer">Hindi mabuksan ang buffer</string>
- <string name="cannot_open_document">Hindi mabuksan ang dokumento</string>
- <string name="cannot_open_document_Reason">Hindi mabuksan ang dokumentong: %1$s</string>
- <string name="cannot_open_file_Path">Hindi mabuksan ang file na: %1$s</string>
- <string name="choose_value">Pumili ng halaga</string>
- <string name="copied_to_clipboard">Kinopya sa clipboard</string>
- <string name="copy">Kopyahin</string>
- <string name="copy_text">kopyahin ang teksto</string>
- <string name="copy_text_to_the_clipboard">Kopyahin ang teksto sa clipboard</string>
- <string name="delete">Alisin</string>
- <string name="dismiss">Umalis</string>
- <string name="document_has_changes_save_them_">May mga pagbabago sa dokumento. I-save ang mga ito?</string>
- <string name="draw_annotation">Gumuhit ng anotasyon</string>
- <string name="edit_annotations">I-edit ang mga anotasyon</string>
- <string name="enter_password">Ilagay ang password</string>
- <string name="entering_reflow_mode">Pumapasok sa reflow mode</string>
- <string name="fill_out_text_field">Punan ang puwang para sa teksto</string>
- <string name="format_currently_not_supported">Ang format ay kasalukuyang hindi gumagana dito</string>
- <string name="highlight">I-highlight</string>
- <string name="ink">Lagdaan (Ink)</string>
- <string name="leaving_reflow_mode">Umaalis sa reflow mode</string>
- <string name="more">Higit pa</string>
- <string name="no">Hindi</string>
- <string name="no_further_occurrences_found">Walang nahanap na karagdagang paglitaw</string>
- <string name="no_media_hint">Ang pagbabahagi ng storage media sa isang PC ay gagawin itong hindi magagamit</string>
- <string name="no_media_warning">Walang storage media</string>
- <string name="no_text_selected">Walang piniling teksto</string>
- <string name="not_supported">Hindi gumagana dito</string>
- <string name="nothing_to_save">Walang ise-save</string>
- <string name="okay">Okay</string>
- <string name="outline_title">Talaan ng Nilalaman</string>
- <string name="parent_directory">[Umakyat ng isang antas]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">I-print</string>
- <string name="print_failed">Hindi nai-print</string>
- <string name="save">I-save</string>
- <string name="search">Maghanap</string>
- <string name="search_backwards">Maghanap pabalik</string>
- <string name="search_document">Maghanap sa dokumento</string>
- <string name="search_forwards">Maghanap nang pasulong</string>
- <string name="searching_">Hinahanap ang&amp;#8230;</string>
- <string name="select">Piliin</string>
- <string name="select_text">Piliin ang teksto</string>
- <string name="strike_out">Guhitan ang teksto (strike-out)</string>
- <string name="text_not_found">Hindi nahanap ang teksto</string>
- <string name="toggle_links">I-highlight at paganahin ang mga link</string>
- <string name="underline">Guhitan</string>
- <string name="yes">Oo</string>
-</resources>
diff --git a/platform/android/viewer/res/values-tr/strings.xml b/platform/android/viewer/res/values-tr/strings.xml
deleted file mode 100644
index c64ab7ce..00000000
--- a/platform/android/viewer/res/values-tr/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">Kabul et</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">İptal et</string>
- <string name="cannot_open_buffer">Arabellek açılamıyor</string>
- <string name="cannot_open_document">Belge açılamıyor</string>
- <string name="cannot_open_document_Reason">Belge açılamıyor: %1$s</string>
- <string name="cannot_open_file_Path">Dosya açılamıyor: %1$s</string>
- <string name="choose_value">Değeri seç</string>
- <string name="copied_to_clipboard">Panoya kopyalandı</string>
- <string name="copy">Kopyala</string>
- <string name="copy_text">metni kopyala</string>
- <string name="copy_text_to_the_clipboard">Metni panoya kopyala</string>
- <string name="delete">Sil</string>
- <string name="dismiss">Bırak</string>
- <string name="document_has_changes_save_them_">Belgede değişiklikler var. Kaydetmek istiyor musunuz?</string>
- <string name="draw_annotation">Ek açıklama çiz</string>
- <string name="edit_annotations">Ek açıklamalar düzenle</string>
- <string name="enter_password">Şifreyi gir</string>
- <string name="entering_reflow_mode">Yeniden akma moduna giriyor</string>
- <string name="fill_out_text_field">Metin alanını doldurun</string>
- <string name="format_currently_not_supported">Bu format şu an için desteklenmiyor</string>
- <string name="highlight">Vurgula</string>
- <string name="ink">Mürekkep</string>
- <string name="leaving_reflow_mode">Yeniden akma modundan çıkılıyor</string>
- <string name="more">Daha fazla</string>
- <string name="no">Hayır</string>
- <string name="no_further_occurrences_found">Daha fazla öğe bulunamadı</string>
- <string name="no_media_hint">Depolama ortamının bilgisayar ile paylaşımı onu erişilmez yapabilir</string>
- <string name="no_media_warning">Depolama ortamı bulunmuyor</string>
- <string name="no_text_selected">Seçili metin bulunmuyor</string>
- <string name="not_supported">Desteklenmiyor</string>
- <string name="nothing_to_save">Kaydedecek bir şey yok</string>
- <string name="okay">Tamam</string>
- <string name="outline_title">İçindekiler Tablosu</string>
- <string name="parent_directory">[Bir seviye üste çık]</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="print">Yazdır</string>
- <string name="print_failed">Yazdırma başarısız oldu</string>
- <string name="save">Kaydet</string>
- <string name="search">Ara</string>
- <string name="search_backwards">Geriye doğru ara</string>
- <string name="search_document">Belge ara</string>
- <string name="search_forwards">İleriye doğru ara</string>
- <string name="searching_">Aranıyor&amp;#8230;</string>
- <string name="select">Seç</string>
- <string name="select_text">Metin seç</string>
- <string name="strike_out">Üstünü çiz</string>
- <string name="text_not_found">Metin bulunamadı</string>
- <string name="toggle_links">Bağlantıları vurgula ve etkinleştir</string>
- <string name="underline">Altını çiz</string>
- <string name="yes">Evet</string>
-</resources>
diff --git a/platform/android/viewer/res/values-zh-rTW/strings.xml b/platform/android/viewer/res/values-zh-rTW/strings.xml
deleted file mode 100644
index 4cd89709..00000000
--- a/platform/android/viewer/res/values-zh-rTW/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">同意</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">取消</string>
- <string name="cannot_open_buffer">未能開啟緩衝</string>
- <string name="cannot_open_document">未能開啟文件</string>
- <string name="cannot_open_document_Reason">未能開啟文件: %1$s</string>
- <string name="cannot_open_file_Path">未能開啟檔案%1$s</string>
- <string name="choose_value">選擇數值</string>
- <string name="copied_to_clipboard">複製至剪貼簿</string>
- <string name="copy">複製</string>
- <string name="copy_text">複製文字</string>
- <string name="copy_text_to_the_clipboard">複製文字至剪貼簿</string>
- <string name="delete">刪除</string>
- <string name="dismiss">取消</string>
- <string name="document_has_changes_save_them_">你需要儲存已編輯的文件嗎?</string>
- <string name="draw_annotation">繪畫註釋</string>
- <string name="edit_annotations">編輯註釋</string>
- <string name="enter_password">輸入密碼</string>
- <string name="entering_reflow_mode">根據螢幕大小顯示</string>
- <string name="fill_out_text_field">填寫文字欄</string>
- <string name="format_currently_not_supported">暫時不支援此格式</string>
- <string name="highlight">標示重點</string>
- <string name="ink">墨水</string>
- <string name="leaving_reflow_mode">不根據螢幕大小顯示</string>
- <string name="more">更多</string>
- <string name="no">沒有</string>
- <string name="no_further_occurrences_found">沒有相符項目</string>
- <string name="no_media_hint">未能與電腦分享存放裝置</string>
- <string name="no_media_warning">沒有存放裝置</string>
- <string name="no_text_selected">沒有選擇文字</string>
- <string name="not_supported">不支援</string>
- <string name="nothing_to_save">沒有資料儲存</string>
- <string name="okay">完成</string>
- <string name="outline_title">目錄</string>
- <string name="parent_directory">[升一級]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s%3$s</string>
- <string name="print">列印</string>
- <string name="print_failed">列印失敗</string>
- <string name="save">儲存</string>
- <string name="search">搜尋</string>
- <string name="search_backwards">往後搜尋</string>
- <string name="search_document">搜尋文件</string>
- <string name="search_forwards">往前搜尋</string>
- <string name="searching_">搜尋中&amp;#8230;</string>
- <string name="select">選擇</string>
- <string name="select_text">選擇文字</string>
- <string name="strike_out">刪除線</string>
- <string name="text_not_found">未能找到文字</string>
- <string name="toggle_links">標示及允許連結</string>
- <string name="underline">在下面劃線</string>
- <string name="yes">是</string>
-</resources>
diff --git a/platform/android/viewer/res/values-zh/strings.xml b/platform/android/viewer/res/values-zh/strings.xml
deleted file mode 100644
index 60fcbb82..00000000
--- a/platform/android/viewer/res/values-zh/strings.xml
+++ /dev/null
@@ -1,54 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="accept">接受</string>
- <string name="app_name">MuPDF</string>
- <string name="cancel">取消</string>
- <string name="cannot_open_buffer">无法打开缓冲器</string>
- <string name="cannot_open_document">无法打开文档</string>
- <string name="cannot_open_document_Reason">无法打开文档: %1$s</string>
- <string name="cannot_open_file_Path">无法打开文件:%1$s</string>
- <string name="choose_value">选择值</string>
- <string name="copied_to_clipboard">已复制到剪贴板</string>
- <string name="copy">复制</string>
- <string name="copy_text">复制文本</string>
- <string name="copy_text_to_the_clipboard">将文本复制到剪贴板</string>
- <string name="delete">删除</string>
- <string name="dismiss">解除</string>
- <string name="document_has_changes_save_them_">文档已变更,保存变更吗?</string>
- <string name="draw_annotation">作批注</string>
- <string name="edit_annotations">编辑批注</string>
- <string name="enter_password">输入密码</string>
- <string name="entering_reflow_mode">输入重排模式</string>
- <string name="fill_out_text_field">填充文本字段</string>
- <string name="format_currently_not_supported">当前不支持此格式</string>
- <string name="highlight">高亮</string>
- <string name="ink">墨迹</string>
- <string name="leaving_reflow_mode">正在离开重排模式</string>
- <string name="more">更多</string>
- <string name="no">否</string>
- <string name="no_further_occurrences_found">未发现更多实例。</string>
- <string name="no_media_hint">存储介质在设备和 PC 上共同使用,会导致该存储介质在设备上无法被访问</string>
- <string name="no_media_warning">没有存储介质</string>
- <string name="no_text_selected">未选择文本</string>
- <string name="not_supported">不被支持</string>
- <string name="nothing_to_save">没有要保存的内容</string>
- <string name="okay">确定</string>
- <string name="outline_title">目录</string>
- <string name="parent_directory">[向上一级]</string>
- <string name="picker_title_App_Ver_Dir">%1$s%2$s:%3$s</string>
- <string name="print">打印</string>
- <string name="print_failed">未能打印</string>
- <string name="save">保存</string>
- <string name="search">搜索</string>
- <string name="search_backwards">向后搜索</string>
- <string name="search_document">搜索文档</string>
- <string name="search_forwards">向前搜索</string>
- <string name="searching_">正在搜索…</string>
- <string name="select">选择</string>
- <string name="select_text">选择文本</string>
- <string name="strike_out">删除线</string>
- <string name="text_not_found">未发现文本</string>
- <string name="toggle_links">高亮并启用墨迹</string>
- <string name="underline">下划线</string>
- <string name="yes">是</string>
-</resources>
diff --git a/platform/android/viewer/res/values/colors.xml b/platform/android/viewer/res/values/colors.xml
deleted file mode 100644
index ecd1519d..00000000
--- a/platform/android/viewer/res/values/colors.xml
+++ /dev/null
@@ -1,16 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <color name="canvas">#404040</color>
- <color name="toolbar">#C0000000</color>
- <color name="page_indicator">#C0202020</color>
- <color name="busy_indicator">#C0202020</color>
- <color name="button_normal">#00000000</color>
- <color name="button_pressed">#FF2572AC</color>
- <color name="text_normal">#FFFFFF</color>
- <color name="text_pressed">#FFFFFF</color>
- <color name="text_border_normal">#000000</color>
- <color name="text_border_pressed">#2572AC</color>
- <color name="text_border_focused">#000000</color>
- <color name="seek_thumb">#2572AC</color>
- <color name="seek_progress">#FFFFFF</color>
-</resources>
diff --git a/platform/android/viewer/res/values/strings.xml b/platform/android/viewer/res/values/strings.xml
deleted file mode 100644
index 134f6cf2..00000000
--- a/platform/android/viewer/res/values/strings.xml
+++ /dev/null
@@ -1,58 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="app_name">MuPDF</string>
- <string name="version">1.10a (git build)</string>
- <string name="no_media_warning">Storage media not present</string>
- <string name="no_media_hint">Sharing the storage media with a PC can make it inaccessible</string>
- <string name="cancel">Cancel</string>
- <string name="search_backwards">Search backwards</string>
- <string name="search_forwards">Search forwards</string>
- <string name="search_document">Search document</string>
- <string name="picker_title_App_Ver_Dir">%1$s %2$s: %3$s</string>
- <string name="outline_title">Table of Contents</string>
- <string name="enter_password">Enter password</string>
- <string name="text_not_found">Text not found</string>
- <string name="searching_">Searching&#8230;</string>
- <string name="toggle_links">Highlight and enable links</string>
- <string name="no_further_occurrences_found">No further occurrences found</string>
- <string name="select">Select</string>
- <string name="search">Search</string>
- <string name="copy">Copy</string>
- <string name="strike_out">Strike-out</string>
- <string name="delete">Delete</string>
- <string name="highlight">Highlight</string>
- <string name="underline">Underline</string>
- <string name="edit_annotations">Edit annotations</string>
- <string name="ink">Ink</string>
- <string name="save">Save</string>
- <string name="proof">Proof</string>
- <string name="separation">Separation</string>
- <string name="print">Print</string>
- <string name="dismiss">Dismiss</string>
- <string name="parent_directory">[Up one level]</string>
- <string name="yes">Yes</string>
- <string name="no">No</string>
- <string name="entering_reflow_mode">Entering reflow mode</string>
- <string name="leaving_reflow_mode">Leaving reflow mode</string>
- <string name="print_failed">Print failed</string>
- <string name="select_text">Select text</string>
- <string name="copied_to_clipboard">Copied to clipboard</string>
- <string name="no_text_selected">No text selected</string>
- <string name="draw_annotation">Draw annotation</string>
- <string name="nothing_to_save">Nothing to save</string>
- <string name="document_has_changes_save_them_">Document has changes. Save them?</string>
- <string name="cannot_open_document">Cannot open document</string>
- <string name="cannot_open_document_Reason">Cannot open document: %1$s</string>
- <string name="cannot_open_file_Path">Cannot open file: %1$s</string>
- <string name="cannot_open_buffer">Cannot open buffer</string>
- <string name="fill_out_text_field">Fill out text field</string>
- <string name="okay">Okay</string>
- <string name="choose_value">Choose value</string>
- <string name="not_supported">Not supported</string>
- <string name="copy_text_to_the_clipboard">Copy text to the clipboard</string>
- <string name="more">More</string>
- <string name="accept">Accept</string>
- <string name="copy_text">copy text</string>
- <string name="format_currently_not_supported">Format currently not supported</string>
- <string name="toggle_reflow_mode">Toggle reflow mode</string>
-</resources>
diff --git a/platform/android/viewer/res/values/styles.xml b/platform/android/viewer/res/values/styles.xml
deleted file mode 100644
index e1d118a9..00000000
--- a/platform/android/viewer/res/values/styles.xml
+++ /dev/null
@@ -1,5 +0,0 @@
-<resources>
- <style name="AppBaseTheme" parent="@android:style/Theme.NoTitleBar.Fullscreen">
- <item name="android:windowBackground">@drawable/tiled_background</item>
- </style>
-</resources>
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/Annotation.java b/platform/android/viewer/src/com/artifex/mupdfdemo/Annotation.java
deleted file mode 100644
index cf915524..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/Annotation.java
+++ /dev/null
@@ -1,18 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.graphics.RectF;
-
-public class Annotation extends RectF {
- enum Type {
- TEXT, LINK, FREETEXT, LINE, SQUARE, CIRCLE, POLYGON, POLYLINE, HIGHLIGHT,
- UNDERLINE, SQUIGGLY, STRIKEOUT, STAMP, CARET, INK, POPUP, FILEATTACHMENT,
- SOUND, MOVIE, WIDGET, SCREEN, PRINTERMARK, TRAPNET, WATERMARK, A3D, UNKNOWN
- }
-
- public final Type type;
-
- public Annotation(float x0, float y0, float x1, float y1, int _type) {
- super(x0, y0, x1, y1);
- type = _type == -1 ? Type.UNKNOWN : Type.values()[_type];
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/ArrayDeque.java b/platform/android/viewer/src/com/artifex/mupdfdemo/ArrayDeque.java
deleted file mode 100644
index c8549058..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/ArrayDeque.java
+++ /dev/null
@@ -1,855 +0,0 @@
-/*
- * Written by Josh Bloch of Google Inc. and released to the public domain,
- * as explained at http://creativecommons.org/publicdomain/zero/1.0/.
- */
-
-package com.artifex.mupdfdemo;
-
-import java.util.AbstractCollection;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.ConcurrentModificationException;
-import java.util.Iterator;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.NoSuchElementException;
-import java.util.Queue;
-import java.util.Stack;
-
-// BEGIN android-note
-// removed link to collections framework docs
-// END android-note
-
-/**
- * Resizable-array implementation of the {@link Deque} interface. Array
- * deques have no capacity restrictions; they grow as necessary to support
- * usage. They are not thread-safe; in the absence of external
- * synchronization, they do not support concurrent access by multiple threads.
- * Null elements are prohibited. This class is likely to be faster than
- * {@link Stack} when used as a stack, and faster than {@link LinkedList}
- * when used as a queue.
- *
- * <p>Most <tt>ArrayDeque</tt> operations run in amortized constant time.
- * Exceptions include {@link #remove(Object) remove}, {@link
- * #removeFirstOccurrence removeFirstOccurrence}, {@link #removeLastOccurrence
- * removeLastOccurrence}, {@link #contains contains}, {@link #iterator
- * iterator.remove()}, and the bulk operations, all of which run in linear
- * time.
- *
- * <p>The iterators returned by this class's <tt>iterator</tt> method are
- * <i>fail-fast</i>: If the deque is modified at any time after the iterator
- * is created, in any way except through the iterator's own <tt>remove</tt>
- * method, the iterator will generally throw a {@link
- * ConcurrentModificationException}. Thus, in the face of concurrent
- * modification, the iterator fails quickly and cleanly, rather than risking
- * arbitrary, non-deterministic behavior at an undetermined time in the
- * future.
- *
- * <p>Note that the fail-fast behavior of an iterator cannot be guaranteed
- * as it is, generally speaking, impossible to make any hard guarantees in the
- * presence of unsynchronized concurrent modification. Fail-fast iterators
- * throw <tt>ConcurrentModificationException</tt> on a best-effort basis.
- * Therefore, it would be wrong to write a program that depended on this
- * exception for its correctness: <i>the fail-fast behavior of iterators
- * should be used only to detect bugs.</i>
- *
- * <p>This class and its iterator implement all of the
- * <em>optional</em> methods of the {@link Collection} and {@link
- * Iterator} interfaces.
- *
- * @author Josh Bloch and Doug Lea
- * @since 1.6
- * @param <E> the type of elements held in this collection
- */
-public class ArrayDeque<E> extends AbstractCollection<E>
- implements Deque<E>, Cloneable, java.io.Serializable
-{
- /**
- * The array in which the elements of the deque are stored.
- * The capacity of the deque is the length of this array, which is
- * always a power of two. The array is never allowed to become
- * full, except transiently within an addX method where it is
- * resized (see doubleCapacity) immediately upon becoming full,
- * thus avoiding head and tail wrapping around to equal each
- * other. We also guarantee that all array cells not holding
- * deque elements are always null.
- */
- private transient Object[] elements;
-
- /**
- * The index of the element at the head of the deque (which is the
- * element that would be removed by remove() or pop()); or an
- * arbitrary number equal to tail if the deque is empty.
- */
- private transient int head;
-
- /**
- * The index at which the next element would be added to the tail
- * of the deque (via addLast(E), add(E), or push(E)).
- */
- private transient int tail;
-
- /**
- * The minimum capacity that we'll use for a newly created deque.
- * Must be a power of 2.
- */
- private static final int MIN_INITIAL_CAPACITY = 8;
-
- // ****** Array allocation and resizing utilities ******
-
- /**
- * Allocate empty array to hold the given number of elements.
- *
- * @param numElements the number of elements to hold
- */
- private void allocateElements(int numElements) {
- int initialCapacity = MIN_INITIAL_CAPACITY;
- // Find the best power of two to hold elements.
- // Tests "<=" because arrays aren't kept full.
- if (numElements >= initialCapacity) {
- initialCapacity = numElements;
- initialCapacity |= (initialCapacity >>> 1);
- initialCapacity |= (initialCapacity >>> 2);
- initialCapacity |= (initialCapacity >>> 4);
- initialCapacity |= (initialCapacity >>> 8);
- initialCapacity |= (initialCapacity >>> 16);
- initialCapacity++;
-
- if (initialCapacity < 0) // Too many elements, must back off
- initialCapacity >>>= 1; // Good luck allocating 2 ^ 30 elements
- }
- elements = new Object[initialCapacity];
- }
-
- /**
- * Double the capacity of this deque. Call only when full, i.e.,
- * when head and tail have wrapped around to become equal.
- */
- private void doubleCapacity() {
- // assert head == tail;
- int p = head;
- int n = elements.length;
- int r = n - p; // number of elements to the right of p
- int newCapacity = n << 1;
- if (newCapacity < 0)
- throw new IllegalStateException("Sorry, deque too big");
- Object[] a = new Object[newCapacity];
- System.arraycopy(elements, p, a, 0, r);
- System.arraycopy(elements, 0, a, r, p);
- elements = a;
- head = 0;
- tail = n;
- }
-
- /**
- * Copies the elements from our element array into the specified array,
- * in order (from first to last element in the deque). It is assumed
- * that the array is large enough to hold all elements in the deque.
- *
- * @return its argument
- */
- private <T> T[] copyElements(T[] a) {
- if (head < tail) {
- System.arraycopy(elements, head, a, 0, size());
- } else if (head > tail) {
- int headPortionLen = elements.length - head;
- System.arraycopy(elements, head, a, 0, headPortionLen);
- System.arraycopy(elements, 0, a, headPortionLen, tail);
- }
- return a;
- }
-
- /**
- * Constructs an empty array deque with an initial capacity
- * sufficient to hold 16 elements.
- */
- public ArrayDeque() {
- elements = new Object[16];
- }
-
- /**
- * Constructs an empty array deque with an initial capacity
- * sufficient to hold the specified number of elements.
- *
- * @param numElements lower bound on initial capacity of the deque
- */
- public ArrayDeque(int numElements) {
- allocateElements(numElements);
- }
-
- /**
- * Constructs a deque containing the elements of the specified
- * collection, in the order they are returned by the collection's
- * iterator. (The first element returned by the collection's
- * iterator becomes the first element, or <i>front</i> of the
- * deque.)
- *
- * @param c the collection whose elements are to be placed into the deque
- * @throws NullPointerException if the specified collection is null
- */
- public ArrayDeque(Collection<? extends E> c) {
- allocateElements(c.size());
- addAll(c);
- }
-
- // The main insertion and extraction methods are addFirst,
- // addLast, pollFirst, pollLast. The other methods are defined in
- // terms of these.
-
- /**
- * Inserts the specified element at the front of this deque.
- *
- * @param e the element to add
- * @throws NullPointerException if the specified element is null
- */
- public void addFirst(E e) {
- if (e == null)
- throw new NullPointerException("e == null");
- elements[head = (head - 1) & (elements.length - 1)] = e;
- if (head == tail)
- doubleCapacity();
- }
-
- /**
- * Inserts the specified element at the end of this deque.
- *
- * <p>This method is equivalent to {@link #add}.
- *
- * @param e the element to add
- * @throws NullPointerException if the specified element is null
- */
- public void addLast(E e) {
- if (e == null)
- throw new NullPointerException("e == null");
- elements[tail] = e;
- if ( (tail = (tail + 1) & (elements.length - 1)) == head)
- doubleCapacity();
- }
-
- /**
- * Inserts the specified element at the front of this deque.
- *
- * @param e the element to add
- * @return <tt>true</tt> (as specified by {@link Deque#offerFirst})
- * @throws NullPointerException if the specified element is null
- */
- public boolean offerFirst(E e) {
- addFirst(e);
- return true;
- }
-
- /**
- * Inserts the specified element at the end of this deque.
- *
- * @param e the element to add
- * @return <tt>true</tt> (as specified by {@link Deque#offerLast})
- * @throws NullPointerException if the specified element is null
- */
- public boolean offerLast(E e) {
- addLast(e);
- return true;
- }
-
- /**
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E removeFirst() {
- E x = pollFirst();
- if (x == null)
- throw new NoSuchElementException();
- return x;
- }
-
- /**
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E removeLast() {
- E x = pollLast();
- if (x == null)
- throw new NoSuchElementException();
- return x;
- }
-
- public E pollFirst() {
- int h = head;
- @SuppressWarnings("unchecked") E result = (E) elements[h];
- // Element is null if deque empty
- if (result == null)
- return null;
- elements[h] = null; // Must null out slot
- head = (h + 1) & (elements.length - 1);
- return result;
- }
-
- public E pollLast() {
- int t = (tail - 1) & (elements.length - 1);
- @SuppressWarnings("unchecked") E result = (E) elements[t];
- if (result == null)
- return null;
- elements[t] = null;
- tail = t;
- return result;
- }
-
- /**
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E getFirst() {
- @SuppressWarnings("unchecked") E result = (E) elements[head];
- if (result == null)
- throw new NoSuchElementException();
- return result;
- }
-
- /**
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E getLast() {
- @SuppressWarnings("unchecked")
- E result = (E) elements[(tail - 1) & (elements.length - 1)];
- if (result == null)
- throw new NoSuchElementException();
- return result;
- }
-
- public E peekFirst() {
- @SuppressWarnings("unchecked") E result = (E) elements[head];
- // elements[head] is null if deque empty
- return result;
- }
-
- public E peekLast() {
- @SuppressWarnings("unchecked")
- E result = (E) elements[(tail - 1) & (elements.length - 1)];
- return result;
- }
-
- /**
- * Removes the first occurrence of the specified element in this
- * deque (when traversing the deque from head to tail).
- * If the deque does not contain the element, it is unchanged.
- * More formally, removes the first element <tt>e</tt> such that
- * <tt>o.equals(e)</tt> (if such an element exists).
- * Returns <tt>true</tt> if this deque contained the specified element
- * (or equivalently, if this deque changed as a result of the call).
- *
- * @param o element to be removed from this deque, if present
- * @return <tt>true</tt> if the deque contained the specified element
- */
- public boolean removeFirstOccurrence(Object o) {
- if (o == null)
- return false;
- int mask = elements.length - 1;
- int i = head;
- Object x;
- while ( (x = elements[i]) != null) {
- if (o.equals(x)) {
- delete(i);
- return true;
- }
- i = (i + 1) & mask;
- }
- return false;
- }
-
- /**
- * Removes the last occurrence of the specified element in this
- * deque (when traversing the deque from head to tail).
- * If the deque does not contain the element, it is unchanged.
- * More formally, removes the last element <tt>e</tt> such that
- * <tt>o.equals(e)</tt> (if such an element exists).
- * Returns <tt>true</tt> if this deque contained the specified element
- * (or equivalently, if this deque changed as a result of the call).
- *
- * @param o element to be removed from this deque, if present
- * @return <tt>true</tt> if the deque contained the specified element
- */
- public boolean removeLastOccurrence(Object o) {
- if (o == null)
- return false;
- int mask = elements.length - 1;
- int i = (tail - 1) & mask;
- Object x;
- while ( (x = elements[i]) != null) {
- if (o.equals(x)) {
- delete(i);
- return true;
- }
- i = (i - 1) & mask;
- }
- return false;
- }
-
- // *** Queue methods ***
-
- /**
- * Inserts the specified element at the end of this deque.
- *
- * <p>This method is equivalent to {@link #addLast}.
- *
- * @param e the element to add
- * @return <tt>true</tt> (as specified by {@link Collection#add})
- * @throws NullPointerException if the specified element is null
- */
- public boolean add(E e) {
- addLast(e);
- return true;
- }
-
- /**
- * Inserts the specified element at the end of this deque.
- *
- * <p>This method is equivalent to {@link #offerLast}.
- *
- * @param e the element to add
- * @return <tt>true</tt> (as specified by {@link Queue#offer})
- * @throws NullPointerException if the specified element is null
- */
- public boolean offer(E e) {
- return offerLast(e);
- }
-
- /**
- * Retrieves and removes the head of the queue represented by this deque.
- *
- * This method differs from {@link #poll poll} only in that it throws an
- * exception if this deque is empty.
- *
- * <p>This method is equivalent to {@link #removeFirst}.
- *
- * @return the head of the queue represented by this deque
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E remove() {
- return removeFirst();
- }
-
- /**
- * Retrieves and removes the head of the queue represented by this deque
- * (in other words, the first element of this deque), or returns
- * <tt>null</tt> if this deque is empty.
- *
- * <p>This method is equivalent to {@link #pollFirst}.
- *
- * @return the head of the queue represented by this deque, or
- * <tt>null</tt> if this deque is empty
- */
- public E poll() {
- return pollFirst();
- }
-
- /**
- * Retrieves, but does not remove, the head of the queue represented by
- * this deque. This method differs from {@link #peek peek} only in
- * that it throws an exception if this deque is empty.
- *
- * <p>This method is equivalent to {@link #getFirst}.
- *
- * @return the head of the queue represented by this deque
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E element() {
- return getFirst();
- }
-
- /**
- * Retrieves, but does not remove, the head of the queue represented by
- * this deque, or returns <tt>null</tt> if this deque is empty.
- *
- * <p>This method is equivalent to {@link #peekFirst}.
- *
- * @return the head of the queue represented by this deque, or
- * <tt>null</tt> if this deque is empty
- */
- public E peek() {
- return peekFirst();
- }
-
- // *** Stack methods ***
-
- /**
- * Pushes an element onto the stack represented by this deque. In other
- * words, inserts the element at the front of this deque.
- *
- * <p>This method is equivalent to {@link #addFirst}.
- *
- * @param e the element to push
- * @throws NullPointerException if the specified element is null
- */
- public void push(E e) {
- addFirst(e);
- }
-
- /**
- * Pops an element from the stack represented by this deque. In other
- * words, removes and returns the first element of this deque.
- *
- * <p>This method is equivalent to {@link #removeFirst()}.
- *
- * @return the element at the front of this deque (which is the top
- * of the stack represented by this deque)
- * @throws NoSuchElementException {@inheritDoc}
- */
- public E pop() {
- return removeFirst();
- }
-
- private void checkInvariants() {
- // assert elements[tail] == null;
- // assert head == tail ? elements[head] == null :
- // (elements[head] != null &&
- // elements[(tail - 1) & (elements.length - 1)] != null);
- // assert elements[(head - 1) & (elements.length - 1)] == null;
- }
-
- /**
- * Removes the element at the specified position in the elements array,
- * adjusting head and tail as necessary. This can result in motion of
- * elements backwards or forwards in the array.
- *
- * <p>This method is called delete rather than remove to emphasize
- * that its semantics differ from those of {@link List#remove(int)}.
- *
- * @return true if elements moved backwards
- */
- private boolean delete(int i) {
- //checkInvariants();
- final Object[] elements = this.elements;
- final int mask = elements.length - 1;
- final int h = head;
- final int t = tail;
- final int front = (i - h) & mask;
- final int back = (t - i) & mask;
-
- // Invariant: head <= i < tail mod circularity
- if (front >= ((t - h) & mask))
- throw new ConcurrentModificationException();
-
- // Optimize for least element motion
- if (front < back) {
- if (h <= i) {
- System.arraycopy(elements, h, elements, h + 1, front);
- } else { // Wrap around
- System.arraycopy(elements, 0, elements, 1, i);
- elements[0] = elements[mask];
- System.arraycopy(elements, h, elements, h + 1, mask - h);
- }
- elements[h] = null;
- head = (h + 1) & mask;
- return false;
- } else {
- if (i < t) { // Copy the null tail as well
- System.arraycopy(elements, i + 1, elements, i, back);
- tail = t - 1;
- } else { // Wrap around
- System.arraycopy(elements, i + 1, elements, i, mask - i);
- elements[mask] = elements[0];
- System.arraycopy(elements, 1, elements, 0, t);
- tail = (t - 1) & mask;
- }
- return true;
- }
- }
-
- // *** Collection Methods ***
-
- /**
- * Returns the number of elements in this deque.
- *
- * @return the number of elements in this deque
- */
- public int size() {
- return (tail - head) & (elements.length - 1);
- }
-
- /**
- * Returns <tt>true</tt> if this deque contains no elements.
- *
- * @return <tt>true</tt> if this deque contains no elements
- */
- public boolean isEmpty() {
- return head == tail;
- }
-
- /**
- * Returns an iterator over the elements in this deque. The elements
- * will be ordered from first (head) to last (tail). This is the same
- * order that elements would be dequeued (via successive calls to
- * {@link #remove} or popped (via successive calls to {@link #pop}).
- *
- * @return an iterator over the elements in this deque
- */
- public Iterator<E> iterator() {
- return new DeqIterator();
- }
-
- public Iterator<E> descendingIterator() {
- return new DescendingIterator();
- }
-
- private class DeqIterator implements Iterator<E> {
- /**
- * Index of element to be returned by subsequent call to next.
- */
- private int cursor = head;
-
- /**
- * Tail recorded at construction (also in remove), to stop
- * iterator and also to check for comodification.
- */
- private int fence = tail;
-
- /**
- * Index of element returned by most recent call to next.
- * Reset to -1 if element is deleted by a call to remove.
- */
- private int lastRet = -1;
-
- public boolean hasNext() {
- return cursor != fence;
- }
-
- public E next() {
- if (cursor == fence)
- throw new NoSuchElementException();
- @SuppressWarnings("unchecked") E result = (E) elements[cursor];
- // This check doesn't catch all possible comodifications,
- // but does catch the ones that corrupt traversal
- if (tail != fence || result == null)
- throw new ConcurrentModificationException();
- lastRet = cursor;
- cursor = (cursor + 1) & (elements.length - 1);
- return result;
- }
-
- public void remove() {
- if (lastRet < 0)
- throw new IllegalStateException();
- if (delete(lastRet)) { // if left-shifted, undo increment in next()
- cursor = (cursor - 1) & (elements.length - 1);
- fence = tail;
- }
- lastRet = -1;
- }
- }
-
- private class DescendingIterator implements Iterator<E> {
- /*
- * This class is nearly a mirror-image of DeqIterator, using
- * tail instead of head for initial cursor, and head instead of
- * tail for fence.
- */
- private int cursor = tail;
- private int fence = head;
- private int lastRet = -1;
-
- public boolean hasNext() {
- return cursor != fence;
- }
-
- public E next() {
- if (cursor == fence)
- throw new NoSuchElementException();
- cursor = (cursor - 1) & (elements.length - 1);
- @SuppressWarnings("unchecked") E result = (E) elements[cursor];
- if (head != fence || result == null)
- throw new ConcurrentModificationException();
- lastRet = cursor;
- return result;
- }
-
- public void remove() {
- if (lastRet < 0)
- throw new IllegalStateException();
- if (!delete(lastRet)) {
- cursor = (cursor + 1) & (elements.length - 1);
- fence = head;
- }
- lastRet = -1;
- }
- }
-
- /**
- * Returns <tt>true</tt> if this deque contains the specified element.
- * More formally, returns <tt>true</tt> if and only if this deque contains
- * at least one element <tt>e</tt> such that <tt>o.equals(e)</tt>.
- *
- * @param o object to be checked for containment in this deque
- * @return <tt>true</tt> if this deque contains the specified element
- */
- public boolean contains(Object o) {
- if (o == null)
- return false;
- int mask = elements.length - 1;
- int i = head;
- Object x;
- while ( (x = elements[i]) != null) {
- if (o.equals(x))
- return true;
- i = (i + 1) & mask;
- }
- return false;
- }
-
- /**
- * Removes a single instance of the specified element from this deque.
- * If the deque does not contain the element, it is unchanged.
- * More formally, removes the first element <tt>e</tt> such that
- * <tt>o.equals(e)</tt> (if such an element exists).
- * Returns <tt>true</tt> if this deque contained the specified element
- * (or equivalently, if this deque changed as a result of the call).
- *
- * <p>This method is equivalent to {@link #removeFirstOccurrence}.
- *
- * @param o element to be removed from this deque, if present
- * @return <tt>true</tt> if this deque contained the specified element
- */
- public boolean remove(Object o) {
- return removeFirstOccurrence(o);
- }
-
- /**
- * Removes all of the elements from this deque.
- * The deque will be empty after this call returns.
- */
- public void clear() {
- int h = head;
- int t = tail;
- if (h != t) { // clear all cells
- head = tail = 0;
- int i = h;
- int mask = elements.length - 1;
- do {
- elements[i] = null;
- i = (i + 1) & mask;
- } while (i != t);
- }
- }
-
- /**
- * Returns an array containing all of the elements in this deque
- * in proper sequence (from first to last element).
- *
- * <p>The returned array will be "safe" in that no references to it are
- * maintained by this deque. (In other words, this method must allocate
- * a new array). The caller is thus free to modify the returned array.
- *
- * <p>This method acts as bridge between array-based and collection-based
- * APIs.
- *
- * @return an array containing all of the elements in this deque
- */
- public Object[] toArray() {
- return copyElements(new Object[size()]);
- }
-
- /**
- * Returns an array containing all of the elements in this deque in
- * proper sequence (from first to last element); the runtime type of the
- * returned array is that of the specified array. If the deque fits in
- * the specified array, it is returned therein. Otherwise, a new array
- * is allocated with the runtime type of the specified array and the
- * size of this deque.
- *
- * <p>If this deque fits in the specified array with room to spare
- * (i.e., the array has more elements than this deque), the element in
- * the array immediately following the end of the deque is set to
- * <tt>null</tt>.
- *
- * <p>Like the {@link #toArray()} method, this method acts as bridge between
- * array-based and collection-based APIs. Further, this method allows
- * precise control over the runtime type of the output array, and may,
- * under certain circumstances, be used to save allocation costs.
- *
- * <p>Suppose <tt>x</tt> is a deque known to contain only strings.
- * The following code can be used to dump the deque into a newly
- * allocated array of <tt>String</tt>:
- *
- * <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
- *
- * Note that <tt>toArray(new Object[0])</tt> is identical in function to
- * <tt>toArray()</tt>.
- *
- * @param a the array into which the elements of the deque are to
- * be stored, if it is big enough; otherwise, a new array of the
- * same runtime type is allocated for this purpose
- * @return an array containing all of the elements in this deque
- * @throws ArrayStoreException if the runtime type of the specified array
- * is not a supertype of the runtime type of every element in
- * this deque
- * @throws NullPointerException if the specified array is null
- */
- @SuppressWarnings("unchecked")
- public <T> T[] toArray(T[] a) {
- int size = size();
- if (a.length < size)
- a = (T[])java.lang.reflect.Array.newInstance(
- a.getClass().getComponentType(), size);
- copyElements(a);
- if (a.length > size)
- a[size] = null;
- return a;
- }
-
- // *** Object methods ***
-
- /**
- * Returns a copy of this deque.
- *
- * @return a copy of this deque
- */
- public ArrayDeque<E> clone() {
- try {
- @SuppressWarnings("unchecked")
- ArrayDeque<E> result = (ArrayDeque<E>) super.clone();
- result.elements = Arrays.copyOf(elements, elements.length);
- return result;
-
- } catch (CloneNotSupportedException e) {
- throw new AssertionError();
- }
- }
-
- /**
- * Appease the serialization gods.
- */
- private static final long serialVersionUID = 2340985798034038923L;
-
- /**
- * Serialize this deque.
- *
- * @serialData The current size (<tt>int</tt>) of the deque,
- * followed by all of its elements (each an object reference) in
- * first-to-last order.
- */
- private void writeObject(java.io.ObjectOutputStream s)
- throws java.io.IOException {
- s.defaultWriteObject();
-
- // Write out size
- s.writeInt(size());
-
- // Write out elements in order.
- int mask = elements.length - 1;
- for (int i = head; i != tail; i = (i + 1) & mask)
- s.writeObject(elements[i]);
- }
-
- /**
- * Deserialize this deque.
- */
- private void readObject(java.io.ObjectInputStream s)
- throws java.io.IOException, ClassNotFoundException {
- s.defaultReadObject();
-
- // Read in size and allocate array
- int size = s.readInt();
- allocateElements(size);
- head = 0;
- tail = size;
-
- // Read in all elements in the proper order.
- for (int i = 0; i < size; i++)
- elements[i] = s.readObject();
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/AsyncTask.java b/platform/android/viewer/src/com/artifex/mupdfdemo/AsyncTask.java
deleted file mode 100644
index f2dcf70a..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/AsyncTask.java
+++ /dev/null
@@ -1,670 +0,0 @@
-/*
- * Copyright (C) 2008 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.artifex.mupdfdemo;
-
-import java.util.concurrent.BlockingQueue;
-import java.util.concurrent.Callable;
-import java.util.concurrent.CancellationException;
-import java.util.concurrent.ExecutionException;
-import java.util.concurrent.Executor;
-import java.util.concurrent.FutureTask;
-import java.util.concurrent.LinkedBlockingQueue;
-import java.util.concurrent.ThreadFactory;
-import java.util.concurrent.ThreadPoolExecutor;
-import java.util.concurrent.TimeUnit;
-import java.util.concurrent.TimeoutException;
-import java.util.concurrent.atomic.AtomicBoolean;
-import java.util.concurrent.atomic.AtomicInteger;
-
-import android.os.Process;
-import android.os.Handler;
-import android.os.Message;
-
-/**
- * <p>AsyncTask enables proper and easy use of the UI thread. This class allows to
- * perform background operations and publish results on the UI thread without
- * having to manipulate threads and/or handlers.</p>
- *
- * <p>AsyncTask is designed to be a helper class around {@link Thread} and {@link Handler}
- * and does not constitute a generic threading framework. AsyncTasks should ideally be
- * used for short operations (a few seconds at the most.) If you need to keep threads
- * running for long periods of time, it is highly recommended you use the various APIs
- * provided by the <code>java.util.concurrent</code> pacakge such as {@link Executor},
- * {@link ThreadPoolExecutor} and {@link FutureTask}.</p>
- *
- * <p>An asynchronous task is defined by a computation that runs on a background thread and
- * whose result is published on the UI thread. An asynchronous task is defined by 3 generic
- * types, called <code>Params</code>, <code>Progress</code> and <code>Result</code>,
- * and 4 steps, called <code>onPreExecute</code>, <code>doInBackground</code>,
- * <code>onProgressUpdate</code> and <code>onPostExecute</code>.</p>
- *
- * <div class="special reference">
- * <h3>Developer Guides</h3>
- * <p>For more information about using tasks and threads, read the
- * <a href="{@docRoot}guide/topics/fundamentals/processes-and-threads.html">Processes and
- * Threads</a> developer guide.</p>
- * </div>
- *
- * <h2>Usage</h2>
- * <p>AsyncTask must be subclassed to be used. The subclass will override at least
- * one method ({@link #doInBackground}), and most often will override a
- * second one ({@link #onPostExecute}.)</p>
- *
- * <p>Here is an example of subclassing:</p>
- * <pre class="prettyprint">
- * private class DownloadFilesTask extends AsyncTask&lt;URL, Integer, Long&gt; {
- * protected Long doInBackground(URL... urls) {
- * int count = urls.length;
- * long totalSize = 0;
- * for (int i = 0; i < count; i++) {
- * totalSize += Downloader.downloadFile(urls[i]);
- * publishProgress((int) ((i / (float) count) * 100));
- * // Escape early if cancel() is called
- * if (isCancelled()) break;
- * }
- * return totalSize;
- * }
- *
- * protected void onProgressUpdate(Integer... progress) {
- * setProgressPercent(progress[0]);
- * }
- *
- * protected void onPostExecute(Long result) {
- * showDialog("Downloaded " + result + " bytes");
- * }
- * }
- * </pre>
- *
- * <p>Once created, a task is executed very simply:</p>
- * <pre class="prettyprint">
- * new DownloadFilesTask().execute(url1, url2, url3);
- * </pre>
- *
- * <h2>AsyncTask's generic types</h2>
- * <p>The three types used by an asynchronous task are the following:</p>
- * <ol>
- * <li><code>Params</code>, the type of the parameters sent to the task upon
- * execution.</li>
- * <li><code>Progress</code>, the type of the progress units published during
- * the background computation.</li>
- * <li><code>Result</code>, the type of the result of the background
- * computation.</li>
- * </ol>
- * <p>Not all types are always used by an asynchronous task. To mark a type as unused,
- * simply use the type {@link Void}:</p>
- * <pre>
- * private class MyTask extends AsyncTask&lt;Void, Void, Void&gt; { ... }
- * </pre>
- *
- * <h2>The 4 steps</h2>
- * <p>When an asynchronous task is executed, the task goes through 4 steps:</p>
- * <ol>
- * <li>{@link #onPreExecute()}, invoked on the UI thread before the task
- * is executed. This step is normally used to setup the task, for instance by
- * showing a progress bar in the user interface.</li>
- * <li>{@link #doInBackground}, invoked on the background thread
- * immediately after {@link #onPreExecute()} finishes executing. This step is used
- * to perform background computation that can take a long time. The parameters
- * of the asynchronous task are passed to this step. The result of the computation must
- * be returned by this step and will be passed back to the last step. This step
- * can also use {@link #publishProgress} to publish one or more units
- * of progress. These values are published on the UI thread, in the
- * {@link #onProgressUpdate} step.</li>
- * <li>{@link #onProgressUpdate}, invoked on the UI thread after a
- * call to {@link #publishProgress}. The timing of the execution is
- * undefined. This method is used to display any form of progress in the user
- * interface while the background computation is still executing. For instance,
- * it can be used to animate a progress bar or show logs in a text field.</li>
- * <li>{@link #onPostExecute}, invoked on the UI thread after the background
- * computation finishes. The result of the background computation is passed to
- * this step as a parameter.</li>
- * </ol>
- *
- * <h2>Cancelling a task</h2>
- * <p>A task can be cancelled at any time by invoking {@link #cancel(boolean)}. Invoking
- * this method will cause subsequent calls to {@link #isCancelled()} to return true.
- * After invoking this method, {@link #onCancelled(Object)}, instead of
- * {@link #onPostExecute(Object)} will be invoked after {@link #doInBackground(Object[])}
- * returns. To ensure that a task is cancelled as quickly as possible, you should always
- * check the return value of {@link #isCancelled()} periodically from
- * {@link #doInBackground(Object[])}, if possible (inside a loop for instance.)</p>
- *
- * <h2>Threading rules</h2>
- * <p>There are a few threading rules that must be followed for this class to
- * work properly:</p>
- * <ul>
- * <li>The AsyncTask class must be loaded on the UI thread. This is done
- * automatically as of {@link android.os.Build.VERSION_CODES#JELLY_BEAN}.</li>
- * <li>The task instance must be created on the UI thread.</li>
- * <li>{@link #execute} must be invoked on the UI thread.</li>
- * <li>Do not call {@link #onPreExecute()}, {@link #onPostExecute},
- * {@link #doInBackground}, {@link #onProgressUpdate} manually.</li>
- * <li>The task can be executed only once (an exception will be thrown if
- * a second execution is attempted.)</li>
- * </ul>
- *
- * <h2>Memory observability</h2>
- * <p>AsyncTask guarantees that all callback calls are synchronized in such a way that the following
- * operations are safe without explicit synchronizations.</p>
- * <ul>
- * <li>Set member fields in the constructor or {@link #onPreExecute}, and refer to them
- * in {@link #doInBackground}.
- * <li>Set member fields in {@link #doInBackground}, and refer to them in
- * {@link #onProgressUpdate} and {@link #onPostExecute}.
- * </ul>
- *
- * <h2>Order of execution</h2>
- * <p>When first introduced, AsyncTasks were executed serially on a single background
- * thread. Starting with {@link android.os.Build.VERSION_CODES#DONUT}, this was changed
- * to a pool of threads allowing multiple tasks to operate in parallel. Starting with
- * {@link android.os.Build.VERSION_CODES#HONEYCOMB}, tasks are executed on a single
- * thread to avoid common application errors caused by parallel execution.</p>
- * <p>If you truly want parallel execution, you can invoke
- * {@link #executeOnExecutor(java.util.concurrent.Executor, Object[])} with
- * {@link #THREAD_POOL_EXECUTOR}.</p>
- */
-public abstract class AsyncTask<Params, Progress, Result> {
- private static final String LOG_TAG = "AsyncTask";
-
- private static final int CORE_POOL_SIZE = 5;
- private static final int MAXIMUM_POOL_SIZE = 128;
- private static final int KEEP_ALIVE = 1;
-
- private static final ThreadFactory sThreadFactory = new ThreadFactory() {
- private final AtomicInteger mCount = new AtomicInteger(1);
-
- public Thread newThread(Runnable r) {
- return new Thread(r, "AsyncTask #" + mCount.getAndIncrement());
- }
- };
-
- private static final BlockingQueue<Runnable> sPoolWorkQueue =
- new LinkedBlockingQueue<Runnable>(10);
-
- /**
- * An {@link Executor} that can be used to execute tasks in parallel.
- */
- public static final Executor THREAD_POOL_EXECUTOR
- = new ThreadPoolExecutor(CORE_POOL_SIZE, MAXIMUM_POOL_SIZE, KEEP_ALIVE,
- TimeUnit.SECONDS, sPoolWorkQueue, sThreadFactory);
-
- /**
- * An {@link Executor} that executes tasks one at a time in serial
- * order. This serialization is global to a particular process.
- */
- public static final Executor SERIAL_EXECUTOR = new SerialExecutor();
-
- private static final int MESSAGE_POST_RESULT = 0x1;
- private static final int MESSAGE_POST_PROGRESS = 0x2;
-
- private static final InternalHandler sHandler = new InternalHandler();
-
- private static volatile Executor sDefaultExecutor = SERIAL_EXECUTOR;
- private final WorkerRunnable<Params, Result> mWorker;
- private final FutureTask<Result> mFuture;
-
- private volatile Status mStatus = Status.PENDING;
-
- private final AtomicBoolean mCancelled = new AtomicBoolean();
- private final AtomicBoolean mTaskInvoked = new AtomicBoolean();
-
- private static class SerialExecutor implements Executor {
- final ArrayDeque<Runnable> mTasks = new ArrayDeque<Runnable>();
- Runnable mActive;
-
- public synchronized void execute(final Runnable r) {
- mTasks.offer(new Runnable() {
- public void run() {
- try {
- r.run();
- } finally {
- scheduleNext();
- }
- }
- });
- if (mActive == null) {
- scheduleNext();
- }
- }
-
- protected synchronized void scheduleNext() {
- if ((mActive = mTasks.poll()) != null) {
- THREAD_POOL_EXECUTOR.execute(mActive);
- }
- }
- }
-
- /**
- * Indicates the current status of the task. Each status will be set only once
- * during the lifetime of a task.
- */
- public enum Status {
- /**
- * Indicates that the task has not been executed yet.
- */
- PENDING,
- /**
- * Indicates that the task is running.
- */
- RUNNING,
- /**
- * Indicates that {@link AsyncTask#onPostExecute} has finished.
- */
- FINISHED,
- }
-
- /** @hide Used to force static handler to be created. */
- public static void init() {
- sHandler.getLooper();
- }
-
- /** @hide */
- public static void setDefaultExecutor(Executor exec) {
- sDefaultExecutor = exec;
- }
-
- /**
- * Creates a new asynchronous task. This constructor must be invoked on the UI thread.
- */
- public AsyncTask() {
- mWorker = new WorkerRunnable<Params, Result>() {
- public Result call() throws Exception {
- mTaskInvoked.set(true);
-
- Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
- //noinspection unchecked
- return postResult(doInBackground(mParams));
- }
- };
-
- mFuture = new FutureTask<Result>(mWorker) {
- @Override
- protected void done() {
- try {
- postResultIfNotInvoked(get());
- } catch (InterruptedException e) {
- android.util.Log.w(LOG_TAG, e);
- } catch (ExecutionException e) {
- throw new RuntimeException("An error occured while executing doInBackground()",
- e.getCause());
- } catch (CancellationException e) {
- postResultIfNotInvoked(null);
- }
- }
- };
- }
-
- private void postResultIfNotInvoked(Result result) {
- final boolean wasTaskInvoked = mTaskInvoked.get();
- if (!wasTaskInvoked) {
- postResult(result);
- }
- }
-
- private Result postResult(Result result) {
- @SuppressWarnings("unchecked")
- Message message = sHandler.obtainMessage(MESSAGE_POST_RESULT,
- new AsyncTaskResult<Result>(this, result));
- message.sendToTarget();
- return result;
- }
-
- /**
- * Returns the current status of this task.
- *
- * @return The current status.
- */
- public final Status getStatus() {
- return mStatus;
- }
-
- /**
- * Override this method to perform a computation on a background thread. The
- * specified parameters are the parameters passed to {@link #execute}
- * by the caller of this task.
- *
- * This method can call {@link #publishProgress} to publish updates
- * on the UI thread.
- *
- * @param params The parameters of the task.
- *
- * @return A result, defined by the subclass of this task.
- *
- * @see #onPreExecute()
- * @see #onPostExecute
- * @see #publishProgress
- */
- protected abstract Result doInBackground(Params... params);
-
- /**
- * Runs on the UI thread before {@link #doInBackground}.
- *
- * @see #onPostExecute
- * @see #doInBackground
- */
- protected void onPreExecute() {
- }
-
- /**
- * <p>Runs on the UI thread after {@link #doInBackground}. The
- * specified result is the value returned by {@link #doInBackground}.</p>
- *
- * <p>This method won't be invoked if the task was cancelled.</p>
- *
- * @param result The result of the operation computed by {@link #doInBackground}.
- *
- * @see #onPreExecute
- * @see #doInBackground
- * @see #onCancelled(Object)
- */
- @SuppressWarnings({"UnusedDeclaration"})
- protected void onPostExecute(Result result) {
- }
-
- /**
- * Runs on the UI thread after {@link #publishProgress} is invoked.
- * The specified values are the values passed to {@link #publishProgress}.
- *
- * @param values The values indicating progress.
- *
- * @see #publishProgress
- * @see #doInBackground
- */
- @SuppressWarnings({"UnusedDeclaration"})
- protected void onProgressUpdate(Progress... values) {
- }
-
- /**
- * <p>Runs on the UI thread after {@link #cancel(boolean)} is invoked and
- * {@link #doInBackground(Object[])} has finished.</p>
- *
- * <p>The default implementation simply invokes {@link #onCancelled()} and
- * ignores the result. If you write your own implementation, do not call
- * <code>super.onCancelled(result)</code>.</p>
- *
- * @param result The result, if any, computed in
- * {@link #doInBackground(Object[])}, can be null
- *
- * @see #cancel(boolean)
- * @see #isCancelled()
- */
- @SuppressWarnings({"UnusedParameters"})
- protected void onCancelled(Result result) {
- onCancelled();
- }
-
- /**
- * <p>Applications should preferably override {@link #onCancelled(Object)}.
- * This method is invoked by the default implementation of
- * {@link #onCancelled(Object)}.</p>
- *
- * <p>Runs on the UI thread after {@link #cancel(boolean)} is invoked and
- * {@link #doInBackground(Object[])} has finished.</p>
- *
- * @see #onCancelled(Object)
- * @see #cancel(boolean)
- * @see #isCancelled()
- */
- protected void onCancelled() {
- }
-
- /**
- * Returns <tt>true</tt> if this task was cancelled before it completed
- * normally. If you are calling {@link #cancel(boolean)} on the task,
- * the value returned by this method should be checked periodically from
- * {@link #doInBackground(Object[])} to end the task as soon as possible.
- *
- * @return <tt>true</tt> if task was cancelled before it completed
- *
- * @see #cancel(boolean)
- */
- public final boolean isCancelled() {
- return mCancelled.get();
- }
-
- /**
- * <p>Attempts to cancel execution of this task. This attempt will
- * fail if the task has already completed, already been cancelled,
- * or could not be cancelled for some other reason. If successful,
- * and this task has not started when <tt>cancel</tt> is called,
- * this task should never run. If the task has already started,
- * then the <tt>mayInterruptIfRunning</tt> parameter determines
- * whether the thread executing this task should be interrupted in
- * an attempt to stop the task.</p>
- *
- * <p>Calling this method will result in {@link #onCancelled(Object)} being
- * invoked on the UI thread after {@link #doInBackground(Object[])}
- * returns. Calling this method guarantees that {@link #onPostExecute(Object)}
- * is never invoked. After invoking this method, you should check the
- * value returned by {@link #isCancelled()} periodically from
- * {@link #doInBackground(Object[])} to finish the task as early as
- * possible.</p>
- *
- * @param mayInterruptIfRunning <tt>true</tt> if the thread executing this
- * task should be interrupted; otherwise, in-progress tasks are allowed
- * to complete.
- *
- * @return <tt>false</tt> if the task could not be cancelled,
- * typically because it has already completed normally;
- * <tt>true</tt> otherwise
- *
- * @see #isCancelled()
- * @see #onCancelled(Object)
- */
- public final boolean cancel(boolean mayInterruptIfRunning) {
- mCancelled.set(true);
- return mFuture.cancel(mayInterruptIfRunning);
- }
-
- /**
- * Waits if necessary for the computation to complete, and then
- * retrieves its result.
- *
- * @return The computed result.
- *
- * @throws CancellationException If the computation was cancelled.
- * @throws ExecutionException If the computation threw an exception.
- * @throws InterruptedException If the current thread was interrupted
- * while waiting.
- */
- public final Result get() throws InterruptedException, ExecutionException {
- return mFuture.get();
- }
-
- /**
- * Waits if necessary for at most the given time for the computation
- * to complete, and then retrieves its result.
- *
- * @param timeout Time to wait before cancelling the operation.
- * @param unit The time unit for the timeout.
- *
- * @return The computed result.
- *
- * @throws CancellationException If the computation was cancelled.
- * @throws ExecutionException If the computation threw an exception.
- * @throws InterruptedException If the current thread was interrupted
- * while waiting.
- * @throws TimeoutException If the wait timed out.
- */
- public final Result get(long timeout, TimeUnit unit) throws InterruptedException,
- ExecutionException, TimeoutException {
- return mFuture.get(timeout, unit);
- }
-
- /**
- * Executes the task with the specified parameters. The task returns
- * itself (this) so that the caller can keep a reference to it.
- *
- * <p>Note: this function schedules the task on a queue for a single background
- * thread or pool of threads depending on the platform version. When first
- * introduced, AsyncTasks were executed serially on a single background thread.
- * Starting with {@link android.os.Build.VERSION_CODES#DONUT}, this was changed
- * to a pool of threads allowing multiple tasks to operate in parallel. Starting
- * {@link android.os.Build.VERSION_CODES#HONEYCOMB}, tasks are back to being
- * executed on a single thread to avoid common application errors caused
- * by parallel execution. If you truly want parallel execution, you can use
- * the {@link #executeOnExecutor} version of this method
- * with {@link #THREAD_POOL_EXECUTOR}; however, see commentary there for warnings
- * on its use.
- *
- * <p>This method must be invoked on the UI thread.
- *
- * @param params The parameters of the task.
- *
- * @return This instance of AsyncTask.
- *
- * @throws IllegalStateException If {@link #getStatus()} returns either
- * {@link AsyncTask.Status#RUNNING} or {@link AsyncTask.Status#FINISHED}.
- *
- * @see #executeOnExecutor(java.util.concurrent.Executor, Object[])
- * @see #execute(Runnable)
- */
- public final AsyncTask<Params, Progress, Result> execute(Params... params) {
- return executeOnExecutor(sDefaultExecutor, params);
- }
-
- /**
- * Executes the task with the specified parameters. The task returns
- * itself (this) so that the caller can keep a reference to it.
- *
- * <p>This method is typically used with {@link #THREAD_POOL_EXECUTOR} to
- * allow multiple tasks to run in parallel on a pool of threads managed by
- * AsyncTask, however you can also use your own {@link Executor} for custom
- * behavior.
- *
- * <p><em>Warning:</em> Allowing multiple tasks to run in parallel from
- * a thread pool is generally <em>not</em> what one wants, because the order
- * of their operation is not defined. For example, if these tasks are used
- * to modify any state in common (such as writing a file due to a button click),
- * there are no guarantees on the order of the modifications.
- * Without careful work it is possible in rare cases for the newer version
- * of the data to be over-written by an older one, leading to obscure data
- * loss and stability issues. Such changes are best
- * executed in serial; to guarantee such work is serialized regardless of
- * platform version you can use this function with {@link #SERIAL_EXECUTOR}.
- *
- * <p>This method must be invoked on the UI thread.
- *
- * @param exec The executor to use. {@link #THREAD_POOL_EXECUTOR} is available as a
- * convenient process-wide thread pool for tasks that are loosely coupled.
- * @param params The parameters of the task.
- *
- * @return This instance of AsyncTask.
- *
- * @throws IllegalStateException If {@link #getStatus()} returns either
- * {@link AsyncTask.Status#RUNNING} or {@link AsyncTask.Status#FINISHED}.
- *
- * @see #execute(Object[])
- */
- public final AsyncTask<Params, Progress, Result> executeOnExecutor(Executor exec,
- Params... params) {
- if (mStatus != Status.PENDING) {
- switch (mStatus) {
- case RUNNING:
- throw new IllegalStateException("Cannot execute task:"
- + " the task is already running.");
- case FINISHED:
- throw new IllegalStateException("Cannot execute task:"
- + " the task has already been executed "
- + "(a task can be executed only once)");
- }
- }
-
- mStatus = Status.RUNNING;
-
- onPreExecute();
-
- mWorker.mParams = params;
- exec.execute(mFuture);
-
- return this;
- }
-
- /**
- * Convenience version of {@link #execute(Object...)} for use with
- * a simple Runnable object. See {@link #execute(Object[])} for more
- * information on the order of execution.
- *
- * @see #execute(Object[])
- * @see #executeOnExecutor(java.util.concurrent.Executor, Object[])
- */
- public static void execute(Runnable runnable) {
- sDefaultExecutor.execute(runnable);
- }
-
- /**
- * This method can be invoked from {@link #doInBackground} to
- * publish updates on the UI thread while the background computation is
- * still running. Each call to this method will trigger the execution of
- * {@link #onProgressUpdate} on the UI thread.
- *
- * {@link #onProgressUpdate} will note be called if the task has been
- * canceled.
- *
- * @param values The progress values to update the UI with.
- *
- * @see #onProgressUpdate
- * @see #doInBackground
- */
- protected final void publishProgress(Progress... values) {
- if (!isCancelled()) {
- sHandler.obtainMessage(MESSAGE_POST_PROGRESS,
- new AsyncTaskResult<Progress>(this, values)).sendToTarget();
- }
- }
-
- private void finish(Result result) {
- if (isCancelled()) {
- onCancelled(result);
- } else {
- onPostExecute(result);
- }
- mStatus = Status.FINISHED;
- }
-
- private static class InternalHandler extends Handler {
- @SuppressWarnings({"unchecked", "RawUseOfParameterizedType"})
- @Override
- public void handleMessage(Message msg) {
- AsyncTaskResult result = (AsyncTaskResult) msg.obj;
- switch (msg.what) {
- case MESSAGE_POST_RESULT:
- // There is only one result
- result.mTask.finish(result.mData[0]);
- break;
- case MESSAGE_POST_PROGRESS:
- result.mTask.onProgressUpdate(result.mData);
- break;
- }
- }
- }
-
- private static abstract class WorkerRunnable<Params, Result> implements Callable<Result> {
- Params[] mParams;
- }
-
- @SuppressWarnings({"RawUseOfParameterizedType"})
- private static class AsyncTaskResult<Data> {
- final AsyncTask mTask;
- final Data[] mData;
-
- AsyncTaskResult(AsyncTask task, Data... data) {
- mTask = task;
- mData = data;
- }
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/CancellableAsyncTask.java b/platform/android/viewer/src/com/artifex/mupdfdemo/CancellableAsyncTask.java
deleted file mode 100644
index 53d16f57..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/CancellableAsyncTask.java
+++ /dev/null
@@ -1,83 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.util.concurrent.CancellationException;
-import java.util.concurrent.ExecutionException;
-
-// Ideally this would be a subclass of AsyncTask, however the cancel() method is final, and cannot
-// be overridden. I felt that having two different, but similar cancel methods was a bad idea.
-public class CancellableAsyncTask<Params, Result>
-{
- private final AsyncTask<Params, Void, Result> asyncTask;
- private final CancellableTaskDefinition<Params, Result> ourTask;
-
- public void onPreExecute()
- {
-
- }
-
- public void onPostExecute(Result result)
- {
-
- }
-
- public CancellableAsyncTask(final CancellableTaskDefinition<Params, Result> task)
- {
- if (task == null)
- throw new IllegalArgumentException();
-
- this.ourTask = task;
- asyncTask = new AsyncTask<Params, Void, Result>()
- {
- @Override
- protected Result doInBackground(Params... params)
- {
- return task.doInBackground(params);
- }
-
- @Override
- protected void onPreExecute()
- {
- CancellableAsyncTask.this.onPreExecute();
- }
-
- @Override
- protected void onPostExecute(Result result)
- {
- CancellableAsyncTask.this.onPostExecute(result);
- task.doCleanup();
- }
-
- @Override
- protected void onCancelled(Result result)
- {
- task.doCleanup();
- }
- };
- }
-
- public void cancel()
- {
- this.asyncTask.cancel(true);
- ourTask.doCancel();
-
- try
- {
- this.asyncTask.get();
- }
- catch (InterruptedException e)
- {
- }
- catch (ExecutionException e)
- {
- }
- catch (CancellationException e)
- {
- }
- }
-
- public void execute(Params ... params)
- {
- asyncTask.execute(params);
- }
-
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/CancellableTaskDefinition.java b/platform/android/viewer/src/com/artifex/mupdfdemo/CancellableTaskDefinition.java
deleted file mode 100644
index 62b04f30..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/CancellableTaskDefinition.java
+++ /dev/null
@@ -1,8 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public interface CancellableTaskDefinition <Params, Result>
-{
- public Result doInBackground(Params ... params);
- public void doCancel();
- public void doCleanup();
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFActivity.java b/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFActivity.java
deleted file mode 100644
index 90270f5e..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFActivity.java
+++ /dev/null
@@ -1,228 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.io.File;
-import java.io.FileFilter;
-import java.util.Arrays;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.Map;
-
-import android.app.AlertDialog;
-import android.app.ListActivity;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnClickListener;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.net.Uri;
-import android.os.Bundle;
-import android.os.Environment;
-import android.os.FileObserver;
-import android.os.Handler;
-import android.view.View;
-import android.widget.ListView;
-
-enum Purpose {
- PickPDF,
- PickKeyFile
-}
-
-public class ChoosePDFActivity extends ListActivity {
- static public final String PICK_KEY_FILE = "com.artifex.mupdfdemo.PICK_KEY_FILE";
- static private File mDirectory;
- static private Map<String, Integer> mPositions = new HashMap<String, Integer>();
- private File mParent;
- private File [] mDirs;
- private File [] mFiles;
- private Handler mHandler;
- private Runnable mUpdateFiles;
- private ChoosePDFAdapter adapter;
- private Purpose mPurpose;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- mPurpose = PICK_KEY_FILE.equals(getIntent().getAction()) ? Purpose.PickKeyFile : Purpose.PickPDF;
-
- String storageState = Environment.getExternalStorageState();
-
- if (!Environment.MEDIA_MOUNTED.equals(storageState)
- && !Environment.MEDIA_MOUNTED_READ_ONLY.equals(storageState))
- {
- AlertDialog.Builder builder = new AlertDialog.Builder(this);
- builder.setTitle(R.string.no_media_warning);
- builder.setMessage(R.string.no_media_hint);
- AlertDialog alert = builder.create();
- alert.setButton(AlertDialog.BUTTON_POSITIVE,getString(R.string.dismiss),
- new OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- finish();
- }
- });
- alert.show();
- return;
- }
-
- if (mDirectory == null)
- mDirectory = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS);
-
- // Create a list adapter...
- adapter = new ChoosePDFAdapter(getLayoutInflater());
- setListAdapter(adapter);
-
- // ...that is updated dynamically when files are scanned
- mHandler = new Handler();
- mUpdateFiles = new Runnable() {
- public void run() {
- Resources res = getResources();
- String appName = res.getString(R.string.app_name);
- String version = res.getString(R.string.version);
- String title = res.getString(R.string.picker_title_App_Ver_Dir);
- setTitle(String.format(title, appName, version, mDirectory));
-
- mParent = mDirectory.getParentFile();
-
- mDirs = mDirectory.listFiles(new FileFilter() {
-
- public boolean accept(File file) {
- return file.isDirectory();
- }
- });
- if (mDirs == null)
- mDirs = new File[0];
-
- mFiles = mDirectory.listFiles(new FileFilter() {
-
- public boolean accept(File file) {
- if (file.isDirectory())
- return false;
- String fname = file.getName().toLowerCase();
- switch (mPurpose) {
- case PickPDF:
- if (fname.endsWith(".pdf"))
- return true;
- if (fname.endsWith(".xps"))
- return true;
- if (fname.endsWith(".cbz"))
- return true;
- if (fname.endsWith(".epub"))
- return true;
- if (fname.endsWith(".fb2"))
- return true;
- if (fname.endsWith(".png"))
- return true;
- if (fname.endsWith(".jpe"))
- return true;
- if (fname.endsWith(".jpeg"))
- return true;
- if (fname.endsWith(".jpg"))
- return true;
- if (fname.endsWith(".jfif"))
- return true;
- if (fname.endsWith(".jfif-tbnl"))
- return true;
- if (fname.endsWith(".tif"))
- return true;
- if (fname.endsWith(".tiff"))
- return true;
- return false;
- case PickKeyFile:
- if (fname.endsWith(".pfx"))
- return true;
- return false;
- default:
- return false;
- }
- }
- });
- if (mFiles == null)
- mFiles = new File[0];
-
- Arrays.sort(mFiles, new Comparator<File>() {
- public int compare(File arg0, File arg1) {
- return arg0.getName().compareToIgnoreCase(arg1.getName());
- }
- });
-
- Arrays.sort(mDirs, new Comparator<File>() {
- public int compare(File arg0, File arg1) {
- return arg0.getName().compareToIgnoreCase(arg1.getName());
- }
- });
-
- adapter.clear();
- if (mParent != null)
- adapter.add(new ChoosePDFItem(ChoosePDFItem.Type.PARENT, getString(R.string.parent_directory)));
- for (File f : mDirs)
- adapter.add(new ChoosePDFItem(ChoosePDFItem.Type.DIR, f.getName()));
- for (File f : mFiles)
- adapter.add(new ChoosePDFItem(ChoosePDFItem.Type.DOC, f.getName()));
-
- lastPosition();
- }
- };
-
- // Start initial file scan...
- mHandler.post(mUpdateFiles);
-
- // ...and observe the directory and scan files upon changes.
- FileObserver observer = new FileObserver(mDirectory.getPath(), FileObserver.CREATE | FileObserver.DELETE) {
- public void onEvent(int event, String path) {
- mHandler.post(mUpdateFiles);
- }
- };
- observer.startWatching();
- }
-
- private void lastPosition() {
- String p = mDirectory.getAbsolutePath();
- if (mPositions.containsKey(p))
- getListView().setSelection(mPositions.get(p));
- }
-
- @Override
- protected void onListItemClick(ListView l, View v, int position, long id) {
- super.onListItemClick(l, v, position, id);
-
- mPositions.put(mDirectory.getAbsolutePath(), getListView().getFirstVisiblePosition());
-
- if (position < (mParent == null ? 0 : 1)) {
- mDirectory = mParent;
- mHandler.post(mUpdateFiles);
- return;
- }
-
- position -= (mParent == null ? 0 : 1);
-
- if (position < mDirs.length) {
- mDirectory = mDirs[position];
- mHandler.post(mUpdateFiles);
- return;
- }
-
- position -= mDirs.length;
-
- Uri uri = Uri.fromFile(mFiles[position]);
- Intent intent = new Intent(this,MuPDFActivity.class);
- intent.setAction(Intent.ACTION_VIEW);
- intent.setData(uri);
- switch (mPurpose) {
- case PickPDF:
- // Start an activity to display the PDF file
- startActivity(intent);
- break;
- case PickKeyFile:
- // Return the uri to the caller
- setResult(RESULT_OK, intent);
- finish();
- break;
- }
- }
-
- @Override
- protected void onPause() {
- super.onPause();
- if (mDirectory != null)
- mPositions.put(mDirectory.getAbsolutePath(), getListView().getFirstVisiblePosition());
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFAdapter.java b/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFAdapter.java
deleted file mode 100644
index 0b3c6418..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFAdapter.java
+++ /dev/null
@@ -1,66 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.util.LinkedList;
-
-import android.graphics.Color;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-import android.widget.ImageView;
-import android.widget.TextView;
-
-public class ChoosePDFAdapter extends BaseAdapter {
- private final LinkedList<ChoosePDFItem> mItems;
- private final LayoutInflater mInflater;
-
- public ChoosePDFAdapter(LayoutInflater inflater) {
- mInflater = inflater;
- mItems = new LinkedList<ChoosePDFItem>();
- }
-
- public void clear() {
- mItems.clear();
- }
-
- public void add(ChoosePDFItem item) {
- mItems.add(item);
- notifyDataSetChanged();
- }
-
- public int getCount() {
- return mItems.size();
- }
-
- public Object getItem(int i) {
- return null;
- }
-
- public long getItemId(int arg0) {
- return 0;
- }
-
- private int iconForType(ChoosePDFItem.Type type) {
- switch (type) {
- case PARENT: return R.drawable.ic_arrow_up;
- case DIR: return R.drawable.ic_dir;
- case DOC: return R.drawable.ic_doc;
- default: return 0;
- }
- }
-
- public View getView(int position, View convertView, ViewGroup parent) {
- View v;
- if (convertView == null) {
- v = mInflater.inflate(R.layout.picker_entry, null);
- } else {
- v = convertView;
- }
- ChoosePDFItem item = mItems.get(position);
- ((TextView)v.findViewById(R.id.name)).setText(item.name);
- ((ImageView)v.findViewById(R.id.icon)).setImageResource(iconForType(item.type));
- ((ImageView)v.findViewById(R.id.icon)).setColorFilter(Color.argb(255, 0, 0, 0));
- return v;
- }
-
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFItem.java b/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFItem.java
deleted file mode 100644
index de6e1d52..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/ChoosePDFItem.java
+++ /dev/null
@@ -1,15 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class ChoosePDFItem {
- enum Type {
- PARENT, DIR, DOC
- }
-
- final public Type type;
- final public String name;
-
- public ChoosePDFItem (Type t, String n) {
- type = t;
- name = n;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/Deque.java b/platform/android/viewer/src/com/artifex/mupdfdemo/Deque.java
deleted file mode 100644
index 97aefeab..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/Deque.java
+++ /dev/null
@@ -1,552 +0,0 @@
-/*
- * Written by Doug Lea and Josh Bloch with assistance from members of
- * JCP JSR-166 Expert Group and released to the public domain, as explained
- * at http://creativecommons.org/publicdomain/zero/1.0/
- */
-
-package com.artifex.mupdfdemo;
-
-import java.util.Collection;
-import java.util.Iterator;
-import java.util.List;
-import java.util.NoSuchElementException;
-import java.util.Queue;
-import java.util.Stack;
-
-// BEGIN android-note
-// removed link to collections framework docs
-// END android-note
-
-/**
- * A linear collection that supports element insertion and removal at
- * both ends. The name <i>deque</i> is short for "double ended queue"
- * and is usually pronounced "deck". Most <tt>Deque</tt>
- * implementations place no fixed limits on the number of elements
- * they may contain, but this interface supports capacity-restricted
- * deques as well as those with no fixed size limit.
- *
- * <p>This interface defines methods to access the elements at both
- * ends of the deque. Methods are provided to insert, remove, and
- * examine the element. Each of these methods exists in two forms:
- * one throws an exception if the operation fails, the other returns a
- * special value (either <tt>null</tt> or <tt>false</tt>, depending on
- * the operation). The latter form of the insert operation is
- * designed specifically for use with capacity-restricted
- * <tt>Deque</tt> implementations; in most implementations, insert
- * operations cannot fail.
- *
- * <p>The twelve methods described above are summarized in the
- * following table:
- *
- * <p>
- * <table BORDER CELLPADDING=3 CELLSPACING=1>
- * <tr>
- * <td></td>
- * <td ALIGN=CENTER COLSPAN = 2> <b>First Element (Head)</b></td>
- * <td ALIGN=CENTER COLSPAN = 2> <b>Last Element (Tail)</b></td>
- * </tr>
- * <tr>
- * <td></td>
- * <td ALIGN=CENTER><em>Throws exception</em></td>
- * <td ALIGN=CENTER><em>Special value</em></td>
- * <td ALIGN=CENTER><em>Throws exception</em></td>
- * <td ALIGN=CENTER><em>Special value</em></td>
- * </tr>
- * <tr>
- * <td><b>Insert</b></td>
- * <td>{@link #addFirst addFirst(e)}</td>
- * <td>{@link #offerFirst offerFirst(e)}</td>
- * <td>{@link #addLast addLast(e)}</td>
- * <td>{@link #offerLast offerLast(e)}</td>
- * </tr>
- * <tr>
- * <td><b>Remove</b></td>
- * <td>{@link #removeFirst removeFirst()}</td>
- * <td>{@link #pollFirst pollFirst()}</td>
- * <td>{@link #removeLast removeLast()}</td>
- * <td>{@link #pollLast pollLast()}</td>
- * </tr>
- * <tr>
- * <td><b>Examine</b></td>
- * <td>{@link #getFirst getFirst()}</td>
- * <td>{@link #peekFirst peekFirst()}</td>
- * <td>{@link #getLast getLast()}</td>
- * <td>{@link #peekLast peekLast()}</td>
- * </tr>
- * </table>
- *
- * <p>This interface extends the {@link Queue} interface. When a deque is
- * used as a queue, FIFO (First-In-First-Out) behavior results. Elements are
- * added at the end of the deque and removed from the beginning. The methods
- * inherited from the <tt>Queue</tt> interface are precisely equivalent to
- * <tt>Deque</tt> methods as indicated in the following table:
- *
- * <p>
- * <table BORDER CELLPADDING=3 CELLSPACING=1>
- * <tr>
- * <td ALIGN=CENTER> <b><tt>Queue</tt> Method</b></td>
- * <td ALIGN=CENTER> <b>Equivalent <tt>Deque</tt> Method</b></td>
- * </tr>
- * <tr>
- * <td>{@link java.util.Queue#add add(e)}</td>
- * <td>{@link #addLast addLast(e)}</td>
- * </tr>
- * <tr>
- * <td>{@link java.util.Queue#offer offer(e)}</td>
- * <td>{@link #offerLast offerLast(e)}</td>
- * </tr>
- * <tr>
- * <td>{@link java.util.Queue#remove remove()}</td>
- * <td>{@link #removeFirst removeFirst()}</td>
- * </tr>
- * <tr>
- * <td>{@link java.util.Queue#poll poll()}</td>
- * <td>{@link #pollFirst pollFirst()}</td>
- * </tr>
- * <tr>
- * <td>{@link java.util.Queue#element element()}</td>
- * <td>{@link #getFirst getFirst()}</td>
- * </tr>
- * <tr>
- * <td>{@link java.util.Queue#peek peek()}</td>
- * <td>{@link #peek peekFirst()}</td>
- * </tr>
- * </table>
- *
- * <p>Deques can also be used as LIFO (Last-In-First-Out) stacks. This
- * interface should be used in preference to the legacy {@link Stack} class.
- * When a deque is used as a stack, elements are pushed and popped from the
- * beginning of the deque. Stack methods are precisely equivalent to
- * <tt>Deque</tt> methods as indicated in the table below:
- *
- * <p>
- * <table BORDER CELLPADDING=3 CELLSPACING=1>
- * <tr>
- * <td ALIGN=CENTER> <b>Stack Method</b></td>
- * <td ALIGN=CENTER> <b>Equivalent <tt>Deque</tt> Method</b></td>
- * </tr>
- * <tr>
- * <td>{@link #push push(e)}</td>
- * <td>{@link #addFirst addFirst(e)}</td>
- * </tr>
- * <tr>
- * <td>{@link #pop pop()}</td>
- * <td>{@link #removeFirst removeFirst()}</td>
- * </tr>
- * <tr>
- * <td>{@link #peek peek()}</td>
- * <td>{@link #peekFirst peekFirst()}</td>
- * </tr>
- * </table>
- *
- * <p>Note that the {@link #peek peek} method works equally well when
- * a deque is used as a queue or a stack; in either case, elements are
- * drawn from the beginning of the deque.
- *
- * <p>This interface provides two methods to remove interior
- * elements, {@link #removeFirstOccurrence removeFirstOccurrence} and
- * {@link #removeLastOccurrence removeLastOccurrence}.
- *
- * <p>Unlike the {@link List} interface, this interface does not
- * provide support for indexed access to elements.
- *
- * <p>While <tt>Deque</tt> implementations are not strictly required
- * to prohibit the insertion of null elements, they are strongly
- * encouraged to do so. Users of any <tt>Deque</tt> implementations
- * that do allow null elements are strongly encouraged <i>not</i> to
- * take advantage of the ability to insert nulls. This is so because
- * <tt>null</tt> is used as a special return value by various methods
- * to indicated that the deque is empty.
- *
- * <p><tt>Deque</tt> implementations generally do not define
- * element-based versions of the <tt>equals</tt> and <tt>hashCode</tt>
- * methods, but instead inherit the identity-based versions from class
- * <tt>Object</tt>.
- *
- * @author Doug Lea
- * @author Josh Bloch
- * @since 1.6
- * @param <E> the type of elements held in this collection
- */
-
-public interface Deque<E> extends Queue<E> {
- /**
- * Inserts the specified element at the front of this deque if it is
- * possible to do so immediately without violating capacity restrictions.
- * When using a capacity-restricted deque, it is generally preferable to
- * use method {@link #offerFirst}.
- *
- * @param e the element to add
- * @throws IllegalStateException if the element cannot be added at this
- * time due to capacity restrictions
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- void addFirst(E e);
-
- /**
- * Inserts the specified element at the end of this deque if it is
- * possible to do so immediately without violating capacity restrictions.
- * When using a capacity-restricted deque, it is generally preferable to
- * use method {@link #offerLast}.
- *
- * <p>This method is equivalent to {@link #add}.
- *
- * @param e the element to add
- * @throws IllegalStateException if the element cannot be added at this
- * time due to capacity restrictions
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- void addLast(E e);
-
- /**
- * Inserts the specified element at the front of this deque unless it would
- * violate capacity restrictions. When using a capacity-restricted deque,
- * this method is generally preferable to the {@link #addFirst} method,
- * which can fail to insert an element only by throwing an exception.
- *
- * @param e the element to add
- * @return <tt>true</tt> if the element was added to this deque, else
- * <tt>false</tt>
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- boolean offerFirst(E e);
-
- /**
- * Inserts the specified element at the end of this deque unless it would
- * violate capacity restrictions. When using a capacity-restricted deque,
- * this method is generally preferable to the {@link #addLast} method,
- * which can fail to insert an element only by throwing an exception.
- *
- * @param e the element to add
- * @return <tt>true</tt> if the element was added to this deque, else
- * <tt>false</tt>
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- boolean offerLast(E e);
-
- /**
- * Retrieves and removes the first element of this deque. This method
- * differs from {@link #pollFirst pollFirst} only in that it throws an
- * exception if this deque is empty.
- *
- * @return the head of this deque
- * @throws NoSuchElementException if this deque is empty
- */
- E removeFirst();
-
- /**
- * Retrieves and removes the last element of this deque. This method
- * differs from {@link #pollLast pollLast} only in that it throws an
- * exception if this deque is empty.
- *
- * @return the tail of this deque
- * @throws NoSuchElementException if this deque is empty
- */
- E removeLast();
-
- /**
- * Retrieves and removes the first element of this deque,
- * or returns <tt>null</tt> if this deque is empty.
- *
- * @return the head of this deque, or <tt>null</tt> if this deque is empty
- */
- E pollFirst();
-
- /**
- * Retrieves and removes the last element of this deque,
- * or returns <tt>null</tt> if this deque is empty.
- *
- * @return the tail of this deque, or <tt>null</tt> if this deque is empty
- */
- E pollLast();
-
- /**
- * Retrieves, but does not remove, the first element of this deque.
- *
- * This method differs from {@link #peekFirst peekFirst} only in that it
- * throws an exception if this deque is empty.
- *
- * @return the head of this deque
- * @throws NoSuchElementException if this deque is empty
- */
- E getFirst();
-
- /**
- * Retrieves, but does not remove, the last element of this deque.
- * This method differs from {@link #peekLast peekLast} only in that it
- * throws an exception if this deque is empty.
- *
- * @return the tail of this deque
- * @throws NoSuchElementException if this deque is empty
- */
- E getLast();
-
- /**
- * Retrieves, but does not remove, the first element of this deque,
- * or returns <tt>null</tt> if this deque is empty.
- *
- * @return the head of this deque, or <tt>null</tt> if this deque is empty
- */
- E peekFirst();
-
- /**
- * Retrieves, but does not remove, the last element of this deque,
- * or returns <tt>null</tt> if this deque is empty.
- *
- * @return the tail of this deque, or <tt>null</tt> if this deque is empty
- */
- E peekLast();
-
- /**
- * Removes the first occurrence of the specified element from this deque.
- * If the deque does not contain the element, it is unchanged.
- * More formally, removes the first element <tt>e</tt> such that
- * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>
- * (if such an element exists).
- * Returns <tt>true</tt> if this deque contained the specified element
- * (or equivalently, if this deque changed as a result of the call).
- *
- * @param o element to be removed from this deque, if present
- * @return <tt>true</tt> if an element was removed as a result of this call
- * @throws ClassCastException if the class of the specified element
- * is incompatible with this deque (optional)
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements (optional)
- */
- boolean removeFirstOccurrence(Object o);
-
- /**
- * Removes the last occurrence of the specified element from this deque.
- * If the deque does not contain the element, it is unchanged.
- * More formally, removes the last element <tt>e</tt> such that
- * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>
- * (if such an element exists).
- * Returns <tt>true</tt> if this deque contained the specified element
- * (or equivalently, if this deque changed as a result of the call).
- *
- * @param o element to be removed from this deque, if present
- * @return <tt>true</tt> if an element was removed as a result of this call
- * @throws ClassCastException if the class of the specified element
- * is incompatible with this deque (optional)
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements (optional)
- */
- boolean removeLastOccurrence(Object o);
-
- // *** Queue methods ***
-
- /**
- * Inserts the specified element into the queue represented by this deque
- * (in other words, at the tail of this deque) if it is possible to do so
- * immediately without violating capacity restrictions, returning
- * <tt>true</tt> upon success and throwing an
- * <tt>IllegalStateException</tt> if no space is currently available.
- * When using a capacity-restricted deque, it is generally preferable to
- * use {@link #offer(Object) offer}.
- *
- * <p>This method is equivalent to {@link #addLast}.
- *
- * @param e the element to add
- * @return <tt>true</tt> (as specified by {@link Collection#add})
- * @throws IllegalStateException if the element cannot be added at this
- * time due to capacity restrictions
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- boolean add(E e);
-
- /**
- * Inserts the specified element into the queue represented by this deque
- * (in other words, at the tail of this deque) if it is possible to do so
- * immediately without violating capacity restrictions, returning
- * <tt>true</tt> upon success and <tt>false</tt> if no space is currently
- * available. When using a capacity-restricted deque, this method is
- * generally preferable to the {@link #add} method, which can fail to
- * insert an element only by throwing an exception.
- *
- * <p>This method is equivalent to {@link #offerLast}.
- *
- * @param e the element to add
- * @return <tt>true</tt> if the element was added to this deque, else
- * <tt>false</tt>
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- boolean offer(E e);
-
- /**
- * Retrieves and removes the head of the queue represented by this deque
- * (in other words, the first element of this deque).
- * This method differs from {@link #poll poll} only in that it throws an
- * exception if this deque is empty.
- *
- * <p>This method is equivalent to {@link #removeFirst()}.
- *
- * @return the head of the queue represented by this deque
- * @throws NoSuchElementException if this deque is empty
- */
- E remove();
-
- /**
- * Retrieves and removes the head of the queue represented by this deque
- * (in other words, the first element of this deque), or returns
- * <tt>null</tt> if this deque is empty.
- *
- * <p>This method is equivalent to {@link #pollFirst()}.
- *
- * @return the first element of this deque, or <tt>null</tt> if
- * this deque is empty
- */
- E poll();
-
- /**
- * Retrieves, but does not remove, the head of the queue represented by
- * this deque (in other words, the first element of this deque).
- * This method differs from {@link #peek peek} only in that it throws an
- * exception if this deque is empty.
- *
- * <p>This method is equivalent to {@link #getFirst()}.
- *
- * @return the head of the queue represented by this deque
- * @throws NoSuchElementException if this deque is empty
- */
- E element();
-
- /**
- * Retrieves, but does not remove, the head of the queue represented by
- * this deque (in other words, the first element of this deque), or
- * returns <tt>null</tt> if this deque is empty.
- *
- * <p>This method is equivalent to {@link #peekFirst()}.
- *
- * @return the head of the queue represented by this deque, or
- * <tt>null</tt> if this deque is empty
- */
- E peek();
-
- // *** Stack methods ***
-
- /**
- * Pushes an element onto the stack represented by this deque (in other
- * words, at the head of this deque) if it is possible to do so
- * immediately without violating capacity restrictions, returning
- * <tt>true</tt> upon success and throwing an
- * <tt>IllegalStateException</tt> if no space is currently available.
- *
- * <p>This method is equivalent to {@link #addFirst}.
- *
- * @param e the element to push
- * @throws IllegalStateException if the element cannot be added at this
- * time due to capacity restrictions
- * @throws ClassCastException if the class of the specified element
- * prevents it from being added to this deque
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements
- * @throws IllegalArgumentException if some property of the specified
- * element prevents it from being added to this deque
- */
- void push(E e);
-
- /**
- * Pops an element from the stack represented by this deque. In other
- * words, removes and returns the first element of this deque.
- *
- * <p>This method is equivalent to {@link #removeFirst()}.
- *
- * @return the element at the front of this deque (which is the top
- * of the stack represented by this deque)
- * @throws NoSuchElementException if this deque is empty
- */
- E pop();
-
- // *** Collection methods ***
-
- /**
- * Removes the first occurrence of the specified element from this deque.
- * If the deque does not contain the element, it is unchanged.
- * More formally, removes the first element <tt>e</tt> such that
- * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>
- * (if such an element exists).
- * Returns <tt>true</tt> if this deque contained the specified element
- * (or equivalently, if this deque changed as a result of the call).
- *
- * <p>This method is equivalent to {@link #removeFirstOccurrence}.
- *
- * @param o element to be removed from this deque, if present
- * @return <tt>true</tt> if an element was removed as a result of this call
- * @throws ClassCastException if the class of the specified element
- * is incompatible with this deque (optional)
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements (optional)
- */
- boolean remove(Object o);
-
- /**
- * Returns <tt>true</tt> if this deque contains the specified element.
- * More formally, returns <tt>true</tt> if and only if this deque contains
- * at least one element <tt>e</tt> such that
- * <tt>(o==null&nbsp;?&nbsp;e==null&nbsp;:&nbsp;o.equals(e))</tt>.
- *
- * @param o element whose presence in this deque is to be tested
- * @return <tt>true</tt> if this deque contains the specified element
- * @throws ClassCastException if the type of the specified element
- * is incompatible with this deque (optional)
- * @throws NullPointerException if the specified element is null and this
- * deque does not permit null elements (optional)
- */
- boolean contains(Object o);
-
- /**
- * Returns the number of elements in this deque.
- *
- * @return the number of elements in this deque
- */
- public int size();
-
- /**
- * Returns an iterator over the elements in this deque in proper sequence.
- * The elements will be returned in order from first (head) to last (tail).
- *
- * @return an iterator over the elements in this deque in proper sequence
- */
- Iterator<E> iterator();
-
- /**
- * Returns an iterator over the elements in this deque in reverse
- * sequential order. The elements will be returned in order from
- * last (tail) to first (head).
- *
- * @return an iterator over the elements in this deque in reverse
- * sequence
- */
- Iterator<E> descendingIterator();
-
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/FilePicker.java b/platform/android/viewer/src/com/artifex/mupdfdemo/FilePicker.java
deleted file mode 100644
index d1953531..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/FilePicker.java
+++ /dev/null
@@ -1,21 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.net.Uri;
-
-public abstract class FilePicker {
- public interface FilePickerSupport {
- void performPickFor(FilePicker picker);
- }
-
- private final FilePickerSupport support;
-
- FilePicker(FilePickerSupport _support) {
- support = _support;
- }
-
- void pick() {
- support.performPickFor(this);
- }
-
- abstract void onPick(Uri uri);
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfo.java b/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfo.java
deleted file mode 100644
index 5aeaccbe..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfo.java
+++ /dev/null
@@ -1,14 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.graphics.RectF;
-
-public class LinkInfo {
- final public RectF rect;
-
- public LinkInfo(float l, float t, float r, float b) {
- rect = new RectF(l, t, r, b);
- }
-
- public void acceptVisitor(LinkInfoVisitor visitor) {
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoExternal.java b/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoExternal.java
deleted file mode 100644
index 574b6264..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoExternal.java
+++ /dev/null
@@ -1,14 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class LinkInfoExternal extends LinkInfo {
- final public String url;
-
- public LinkInfoExternal(float l, float t, float r, float b, String u) {
- super(l, t, r, b);
- url = u;
- }
-
- public void acceptVisitor(LinkInfoVisitor visitor) {
- visitor.visitExternal(this);
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoInternal.java b/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoInternal.java
deleted file mode 100644
index 761bf87a..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoInternal.java
+++ /dev/null
@@ -1,14 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class LinkInfoInternal extends LinkInfo {
- final public int pageNumber;
-
- public LinkInfoInternal(float l, float t, float r, float b, int p) {
- super(l, t, r, b);
- pageNumber = p;
- }
-
- public void acceptVisitor(LinkInfoVisitor visitor) {
- visitor.visitInternal(this);
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoRemote.java b/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoRemote.java
deleted file mode 100644
index 731e6408..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoRemote.java
+++ /dev/null
@@ -1,18 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class LinkInfoRemote extends LinkInfo {
- final public String fileSpec;
- final public int pageNumber;
- final public boolean newWindow;
-
- public LinkInfoRemote(float l, float t, float r, float b, String f, int p, boolean n) {
- super(l, t, r, b);
- fileSpec = f;
- pageNumber = p;
- newWindow = n;
- }
-
- public void acceptVisitor(LinkInfoVisitor visitor) {
- visitor.visitRemote(this);
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoVisitor.java b/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoVisitor.java
deleted file mode 100644
index ecd093e4..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/LinkInfoVisitor.java
+++ /dev/null
@@ -1,7 +0,0 @@
-package com.artifex.mupdfdemo;
-
-abstract public class LinkInfoVisitor {
- public abstract void visitInternal(LinkInfoInternal li);
- public abstract void visitExternal(LinkInfoExternal li);
- public abstract void visitRemote(LinkInfoRemote li);
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFActivity.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFActivity.java
deleted file mode 100644
index 8deb8f5a..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFActivity.java
+++ /dev/null
@@ -1,1423 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.Intent;
-import android.content.SharedPreferences;
-import android.content.res.Resources;
-import android.database.Cursor;
-import android.graphics.Color;
-import android.graphics.Rect;
-import android.graphics.drawable.ShapeDrawable;
-import android.graphics.drawable.shapes.RectShape;
-import android.net.Uri;
-import android.os.Bundle;
-import android.os.Handler;
-import android.text.Editable;
-import android.text.TextWatcher;
-import android.text.method.PasswordTransformationMethod;
-import android.view.KeyEvent;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.MenuItem.OnMenuItemClickListener;
-import android.view.View;
-import android.view.animation.Animation;
-import android.view.animation.TranslateAnimation;
-import android.view.inputmethod.EditorInfo;
-import android.view.inputmethod.InputMethodManager;
-import android.widget.EditText;
-import android.widget.ImageButton;
-import android.widget.PopupMenu;
-import android.widget.RelativeLayout;
-import android.widget.SeekBar;
-import android.widget.TextView;
-import android.widget.ViewAnimator;
-
-import java.io.ByteArrayOutputStream;
-import java.io.InputStream;
-import java.lang.reflect.Field;
-import java.lang.reflect.Method;
-import java.util.concurrent.Executor;
-
-class ThreadPerTaskExecutor implements Executor {
- public void execute(Runnable r) {
- new Thread(r).start();
- }
-}
-
-public class MuPDFActivity extends Activity implements FilePicker.FilePickerSupport
-{
- /* The core rendering instance */
- enum TopBarMode {Main, Search, Annot, Delete, More, Accept};
- enum AcceptMode {Highlight, Underline, StrikeOut, Ink, CopyText};
-
- private final int OUTLINE_REQUEST=0;
- private final int PRINT_REQUEST=1;
- private final int FILEPICK_REQUEST=2;
- private final int PROOF_REQUEST=3;
- private MuPDFCore core;
- private String mFileName;
- private MuPDFReaderView mDocView;
- private View mButtonsView;
- private boolean mButtonsVisible;
- private EditText mPasswordView;
- private TextView mFilenameView;
- private SeekBar mPageSlider;
- private int mPageSliderRes;
- private TextView mPageNumberView;
- private TextView mInfoView;
- private ImageButton mSearchButton;
- private ImageButton mReflowButton;
- private ImageButton mOutlineButton;
- private ImageButton mMoreButton;
- private TextView mAnnotTypeText;
- private ImageButton mAnnotButton;
- private ViewAnimator mTopBarSwitcher;
- private ImageButton mLinkButton;
- private TopBarMode mTopBarMode = TopBarMode.Main;
- private AcceptMode mAcceptMode;
- private ImageButton mSearchBack;
- private ImageButton mSearchFwd;
- private EditText mSearchText;
- private SearchTask mSearchTask;
- private ImageButton mProofButton;
- private ImageButton mSepsButton;
- private AlertDialog.Builder mAlertBuilder;
- private boolean mLinkHighlight = false;
- private final Handler mHandler = new Handler();
- private boolean mAlertsActive= false;
- private boolean mReflow = false;
- private AsyncTask<Void,Void,MuPDFAlert> mAlertTask;
- private AlertDialog mAlertDialog;
- private FilePicker mFilePicker;
- private String mProofFile;
- private boolean mSepEnabled[][];
-
- static private AlertDialog.Builder gAlertBuilder;
- static public AlertDialog.Builder getAlertBuilder() {return gAlertBuilder;}
-
- public void createAlertWaiter() {
- mAlertsActive = true;
- // All mupdf library calls are performed on asynchronous tasks to avoid stalling
- // the UI. Some calls can lead to javascript-invoked requests to display an
- // alert dialog and collect a reply from the user. The task has to be blocked
- // until the user's reply is received. This method creates an asynchronous task,
- // the purpose of which is to wait of these requests and produce the dialog
- // in response, while leaving the core blocked. When the dialog receives the
- // user's response, it is sent to the core via replyToAlert, unblocking it.
- // Another alert-waiting task is then created to pick up the next alert.
- if (mAlertTask != null) {
- mAlertTask.cancel(true);
- mAlertTask = null;
- }
- if (mAlertDialog != null) {
- mAlertDialog.cancel();
- mAlertDialog = null;
- }
- mAlertTask = new AsyncTask<Void,Void,MuPDFAlert>() {
-
- @Override
- protected MuPDFAlert doInBackground(Void... arg0) {
- if (!mAlertsActive)
- return null;
-
- return core.waitForAlert();
- }
-
- @Override
- protected void onPostExecute(final MuPDFAlert result) {
- // core.waitForAlert may return null when shutting down
- if (result == null)
- return;
- final MuPDFAlert.ButtonPressed pressed[] = new MuPDFAlert.ButtonPressed[3];
- for(int i = 0; i < 3; i++)
- pressed[i] = MuPDFAlert.ButtonPressed.None;
- DialogInterface.OnClickListener listener = new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- mAlertDialog = null;
- if (mAlertsActive) {
- int index = 0;
- switch (which) {
- case AlertDialog.BUTTON1: index=0; break;
- case AlertDialog.BUTTON2: index=1; break;
- case AlertDialog.BUTTON3: index=2; break;
- }
- result.buttonPressed = pressed[index];
- // Send the user's response to the core, so that it can
- // continue processing.
- core.replyToAlert(result);
- // Create another alert-waiter to pick up the next alert.
- createAlertWaiter();
- }
- }
- };
- mAlertDialog = mAlertBuilder.create();
- mAlertDialog.setTitle(result.title);
- mAlertDialog.setMessage(result.message);
- switch (result.iconType)
- {
- case Error:
- break;
- case Warning:
- break;
- case Question:
- break;
- case Status:
- break;
- }
- switch (result.buttonGroupType)
- {
- case OkCancel:
- mAlertDialog.setButton(AlertDialog.BUTTON2, getString(R.string.cancel), listener);
- pressed[1] = MuPDFAlert.ButtonPressed.Cancel;
- case Ok:
- mAlertDialog.setButton(AlertDialog.BUTTON1, getString(R.string.okay), listener);
- pressed[0] = MuPDFAlert.ButtonPressed.Ok;
- break;
- case YesNoCancel:
- mAlertDialog.setButton(AlertDialog.BUTTON3, getString(R.string.cancel), listener);
- pressed[2] = MuPDFAlert.ButtonPressed.Cancel;
- case YesNo:
- mAlertDialog.setButton(AlertDialog.BUTTON1, getString(R.string.yes), listener);
- pressed[0] = MuPDFAlert.ButtonPressed.Yes;
- mAlertDialog.setButton(AlertDialog.BUTTON2, getString(R.string.no), listener);
- pressed[1] = MuPDFAlert.ButtonPressed.No;
- break;
- }
- mAlertDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
- public void onCancel(DialogInterface dialog) {
- mAlertDialog = null;
- if (mAlertsActive) {
- result.buttonPressed = MuPDFAlert.ButtonPressed.None;
- core.replyToAlert(result);
- createAlertWaiter();
- }
- }
- });
-
- mAlertDialog.show();
- }
- };
-
- mAlertTask.executeOnExecutor(new ThreadPerTaskExecutor());
- }
-
- public void destroyAlertWaiter() {
- mAlertsActive = false;
- if (mAlertDialog != null) {
- mAlertDialog.cancel();
- mAlertDialog = null;
- }
- if (mAlertTask != null) {
- mAlertTask.cancel(true);
- mAlertTask = null;
- }
- }
-
- private MuPDFCore openFile(String path)
- {
- int lastSlashPos = path.lastIndexOf('/');
- mFileName = new String(lastSlashPos == -1
- ? path
- : path.substring(lastSlashPos+1));
- System.out.println("Trying to open " + path);
- try
- {
- core = new MuPDFCore(this, path);
- // New file: drop the old outline data
- OutlineActivityData.set(null);
- }
- catch (Exception e)
- {
- System.out.println(e);
- return null;
- }
- catch (java.lang.OutOfMemoryError e)
- {
- // out of memory is not an Exception, so we catch it separately.
- System.out.println(e);
- return null;
- }
- return core;
- }
-
- private MuPDFCore openBuffer(byte buffer[], String magic)
- {
- System.out.println("Trying to open byte buffer");
- try
- {
- core = new MuPDFCore(this, buffer, magic);
- // New file: drop the old outline data
- OutlineActivityData.set(null);
- }
- catch (Exception e)
- {
- System.out.println(e);
- return null;
- }
- return core;
- }
-
- // determine whether the current activity is a proofing activity.
- public boolean isProofing()
- {
- String format = core.fileFormat();
- return (format.equals("GPROOF"));
- }
-
- /** Called when the activity is first created. */
- @Override
- public void onCreate(final Bundle savedInstanceState)
- {
- super.onCreate(savedInstanceState);
-
- mAlertBuilder = new AlertDialog.Builder(this);
- gAlertBuilder = mAlertBuilder; // keep a static copy of this that other classes can use
-
- if (core == null) {
- core = (MuPDFCore)getLastNonConfigurationInstance();
-
- if (savedInstanceState != null && savedInstanceState.containsKey("FileName")) {
- mFileName = savedInstanceState.getString("FileName");
- }
- }
- if (core == null) {
- Intent intent = getIntent();
- byte buffer[] = null;
-
- if (Intent.ACTION_VIEW.equals(intent.getAction())) {
- Uri uri = intent.getData();
- System.out.println("URI to open is: " + uri);
- if (uri.toString().startsWith("content://")) {
- String reason = null;
- try {
- InputStream is = getContentResolver().openInputStream(uri);
- int len;
- ByteArrayOutputStream bufferStream = new ByteArrayOutputStream();
- byte[] data = new byte[16384];
- while ((len = is.read(data, 0, data.length)) != -1) {
- bufferStream.write(data, 0, len);
- }
- bufferStream.flush();
- buffer = bufferStream.toByteArray();
- is.close();
- }
- catch (java.lang.OutOfMemoryError e) {
- System.out.println("Out of memory during buffer reading");
- reason = e.toString();
- }
- catch (Exception e) {
- System.out.println("Exception reading from stream: " + e);
-
- // Handle view requests from the Transformer Prime's file manager
- // Hopefully other file managers will use this same scheme, if not
- // using explicit paths.
- // I'm hoping that this case below is no longer needed...but it's
- // hard to test as the file manager seems to have changed in 4.x.
- try {
- Cursor cursor = getContentResolver().query(uri, new String[]{"_data"}, null, null, null);
- if (cursor.moveToFirst()) {
- String str = cursor.getString(0);
- if (str == null) {
- reason = "Couldn't parse data in intent";
- }
- else {
- uri = Uri.parse(str);
- }
- }
- }
- catch (Exception e2) {
- System.out.println("Exception in Transformer Prime file manager code: " + e2);
- reason = e2.toString();
- }
- }
- if (reason != null) {
- buffer = null;
- Resources res = getResources();
- AlertDialog alert = mAlertBuilder.create();
- setTitle(String.format(res.getString(R.string.cannot_open_document_Reason), reason));
- alert.setButton(AlertDialog.BUTTON_POSITIVE, getString(R.string.dismiss),
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- finish();
- }
- });
- alert.show();
- return;
- }
- }
- if (buffer != null) {
- core = openBuffer(buffer, intent.getType());
- } else {
- String path = Uri.decode(uri.getEncodedPath());
- if (path == null) {
- path = uri.toString();
- }
- core = openFile(path);
- }
- SearchTaskResult.set(null);
- }
- if (core != null && core.needsPassword()) {
- requestPassword(savedInstanceState);
- return;
- }
- if (core != null && core.countPages() == 0)
- {
- core = null;
- }
- }
- if (core == null)
- {
- AlertDialog alert = mAlertBuilder.create();
- alert.setTitle(R.string.cannot_open_document);
- alert.setButton(AlertDialog.BUTTON_POSITIVE, getString(R.string.dismiss),
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- finish();
- }
- });
- alert.setOnCancelListener(new OnCancelListener() {
-
- @Override
- public void onCancel(DialogInterface dialog) {
- finish();
- }
- });
- alert.show();
- return;
- }
-
- createUI(savedInstanceState);
-
- // hide the proof button if this file can't be proofed
- if (!core.canProof()) {
- mProofButton.setVisibility(View.INVISIBLE);
- }
-
- if (isProofing()) {
-
- // start the activity with a new array
- mSepEnabled = null;
-
- // show the separations button
- mSepsButton.setVisibility(View.VISIBLE);
-
- // hide some other buttons
- mLinkButton.setVisibility(View.INVISIBLE);
- mReflowButton.setVisibility(View.INVISIBLE);
- mOutlineButton.setVisibility(View.INVISIBLE);
- mSearchButton.setVisibility(View.INVISIBLE);
- mMoreButton.setVisibility(View.INVISIBLE);
- }
- else {
- // hide the separations button
- mSepsButton.setVisibility(View.INVISIBLE);
- }
-
- }
-
- public void requestPassword(final Bundle savedInstanceState) {
- mPasswordView = new EditText(this);
- mPasswordView.setInputType(EditorInfo.TYPE_TEXT_VARIATION_PASSWORD);
- mPasswordView.setTransformationMethod(new PasswordTransformationMethod());
-
- AlertDialog alert = mAlertBuilder.create();
- alert.setTitle(R.string.enter_password);
- alert.setView(mPasswordView);
- alert.setButton(AlertDialog.BUTTON_POSITIVE, getString(R.string.okay),
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- if (core.authenticatePassword(mPasswordView.getText().toString())) {
- createUI(savedInstanceState);
- } else {
- requestPassword(savedInstanceState);
- }
- }
- });
- alert.setButton(AlertDialog.BUTTON_NEGATIVE, getString(R.string.cancel),
- new DialogInterface.OnClickListener() {
-
- public void onClick(DialogInterface dialog, int which) {
- finish();
- }
- });
- alert.show();
- }
-
- public void createUI(Bundle savedInstanceState) {
- if (core == null)
- return;
-
- // Now create the UI.
- // First create the document view
- mDocView = new MuPDFReaderView(this) {
- @Override
- protected void onMoveToChild(int i) {
- if (core == null)
- return;
-
- mPageNumberView.setText(String.format("%d / %d", i + 1,
- core.countPages()));
- mPageSlider.setMax((core.countPages() - 1) * mPageSliderRes);
- mPageSlider.setProgress(i * mPageSliderRes);
- super.onMoveToChild(i);
- }
-
- @Override
- protected void onTapMainDocArea() {
- if (!mButtonsVisible) {
- showButtons();
- } else {
- if (mTopBarMode == TopBarMode.Main)
- hideButtons();
- }
- }
-
- @Override
- protected void onDocMotion() {
- hideButtons();
- }
-
- @Override
- protected void onHit(Hit item) {
- switch (mTopBarMode) {
- case Annot:
- if (item == Hit.Annotation) {
- showButtons();
- mTopBarMode = TopBarMode.Delete;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
- break;
- case Delete:
- mTopBarMode = TopBarMode.Annot;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- // fall through
- default:
- // Not in annotation editing mode, but the pageview will
- // still select and highlight hit annotations, so
- // deselect just in case.
- MuPDFView pageView = (MuPDFView) mDocView.getDisplayedView();
- if (pageView != null)
- pageView.deselectAnnotation();
- break;
- }
- }
- };
- mDocView.setAdapter(new MuPDFPageAdapter(this, this, core));
-
- mSearchTask = new SearchTask(this, core) {
- @Override
- protected void onTextFound(SearchTaskResult result) {
- SearchTaskResult.set(result);
- // Ask the ReaderView to move to the resulting page
- mDocView.setDisplayedViewIndex(result.pageNumber);
- // Make the ReaderView act on the change to SearchTaskResult
- // via overridden onChildSetup method.
- mDocView.resetupChildren();
- }
- };
-
- // Make the buttons overlay, and store all its
- // controls in variables
- makeButtonsView();
-
- // Set up the page slider
- int smax = Math.max(core.countPages()-1,1);
- mPageSliderRes = ((10 + smax - 1)/smax) * 2;
-
- // Set the file-name text
- mFilenameView.setText(mFileName);
-
- // Activate the seekbar
- mPageSlider.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
- public void onStopTrackingTouch(SeekBar seekBar) {
- mDocView.setDisplayedViewIndex((seekBar.getProgress()+mPageSliderRes/2)/mPageSliderRes);
- }
-
- public void onStartTrackingTouch(SeekBar seekBar) {}
-
- public void onProgressChanged(SeekBar seekBar, int progress,
- boolean fromUser) {
- updatePageNumView((progress+mPageSliderRes/2)/mPageSliderRes);
- }
- });
-
- // Activate the search-preparing button
- mSearchButton.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- searchModeOn();
- }
- });
-
- // Activate the reflow button
- mReflowButton.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- toggleReflow();
- }
- });
-
- if (core.fileFormat().startsWith("PDF") && core.isUnencryptedPDF() && !core.wasOpenedFromBuffer())
- {
- mAnnotButton.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- mTopBarMode = TopBarMode.Annot;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
- });
- }
- else
- {
- mAnnotButton.setVisibility(View.GONE);
- }
-
- // Search invoking buttons are disabled while there is no text specified
- mSearchBack.setEnabled(false);
- mSearchFwd.setEnabled(false);
- mSearchBack.setColorFilter(Color.argb(255, 128, 128, 128));
- mSearchFwd.setColorFilter(Color.argb(255, 128, 128, 128));
-
- // React to interaction with the text widget
- mSearchText.addTextChangedListener(new TextWatcher() {
-
- public void afterTextChanged(Editable s) {
- boolean haveText = s.toString().length() > 0;
- setButtonEnabled(mSearchBack, haveText);
- setButtonEnabled(mSearchFwd, haveText);
-
- // Remove any previous search results
- if (SearchTaskResult.get() != null && !mSearchText.getText().toString().equals(SearchTaskResult.get().txt)) {
- SearchTaskResult.set(null);
- mDocView.resetupChildren();
- }
- }
- public void beforeTextChanged(CharSequence s, int start, int count,
- int after) {}
- public void onTextChanged(CharSequence s, int start, int before,
- int count) {}
- });
-
- //React to Done button on keyboard
- mSearchText.setOnEditorActionListener(new TextView.OnEditorActionListener() {
- public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
- if (actionId == EditorInfo.IME_ACTION_DONE)
- search(1);
- return false;
- }
- });
-
- mSearchText.setOnKeyListener(new View.OnKeyListener() {
- public boolean onKey(View v, int keyCode, KeyEvent event) {
- if (event.getAction() == KeyEvent.ACTION_DOWN && keyCode == KeyEvent.KEYCODE_ENTER)
- search(1);
- return false;
- }
- });
-
- // Activate search invoking buttons
- mSearchBack.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- search(-1);
- }
- });
- mSearchFwd.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- search(1);
- }
- });
-
- mLinkButton.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- setLinkHighlight(!mLinkHighlight);
- }
- });
-
- if (core.hasOutline()) {
- mOutlineButton.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- OutlineItem outline[] = core.getOutline();
- if (outline != null) {
- OutlineActivityData.get().items = outline;
- Intent intent = new Intent(MuPDFActivity.this, OutlineActivity.class);
- startActivityForResult(intent, OUTLINE_REQUEST);
- }
- }
- });
- } else {
- mOutlineButton.setVisibility(View.GONE);
- }
-
- // Reenstate last state if it was recorded
- SharedPreferences prefs = getPreferences(Context.MODE_PRIVATE);
- mDocView.setDisplayedViewIndex(prefs.getInt("page"+mFileName, 0));
-
- if (savedInstanceState == null || !savedInstanceState.getBoolean("ButtonsHidden", false))
- showButtons();
-
- if(savedInstanceState != null && savedInstanceState.getBoolean("SearchMode", false))
- searchModeOn();
-
- if(savedInstanceState != null && savedInstanceState.getBoolean("ReflowMode", false))
- reflowModeSet(true);
-
- // Stick the document view and the buttons overlay into a parent view
- RelativeLayout layout = new RelativeLayout(this);
- layout.addView(mDocView);
- layout.addView(mButtonsView);
- setContentView(layout);
-
- if (isProofing()) {
- // go to the current page
- int currentPage = getIntent().getIntExtra("startingPage", 0);
- mDocView.setDisplayedViewIndex(currentPage);
- }
-
- }
-
- @Override
- protected void onActivityResult(int requestCode, int resultCode, Intent data) {
- switch (requestCode) {
- case OUTLINE_REQUEST:
- if (resultCode >= 0)
- mDocView.setDisplayedViewIndex(resultCode);
- break;
- case PRINT_REQUEST:
- if (resultCode == RESULT_CANCELED)
- showInfo(getString(R.string.print_failed));
- break;
- case FILEPICK_REQUEST:
- if (mFilePicker != null && resultCode == RESULT_OK)
- mFilePicker.onPick(data.getData());
- case PROOF_REQUEST:
- // we're returning from a proofing activity
-
- if (mProofFile != null)
- {
- core.endProof(mProofFile);
- mProofFile = null;
- }
-
- // return the top bar to default
- mTopBarMode = TopBarMode.Main;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- super.onActivityResult(requestCode, resultCode, data);
- }
-
- public Object onRetainNonConfigurationInstance()
- {
- MuPDFCore mycore = core;
- core = null;
- return mycore;
- }
-
- private void reflowModeSet(boolean reflow)
- {
- mReflow = reflow;
- mDocView.setAdapter(mReflow ? new MuPDFReflowAdapter(this, core) : new MuPDFPageAdapter(this, this, core));
- mReflowButton.setColorFilter(mReflow ? Color.argb(0xFF, 172, 114, 37) : Color.argb(0xFF, 255, 255, 255));
- setButtonEnabled(mAnnotButton, !reflow);
- setButtonEnabled(mSearchButton, !reflow);
- if (reflow) setLinkHighlight(false);
- setButtonEnabled(mLinkButton, !reflow);
- setButtonEnabled(mMoreButton, !reflow);
- mDocView.refresh(mReflow);
- }
-
- private void toggleReflow() {
- reflowModeSet(!mReflow);
- showInfo(mReflow ? getString(R.string.entering_reflow_mode) : getString(R.string.leaving_reflow_mode));
- }
-
- @Override
- protected void onSaveInstanceState(Bundle outState) {
- super.onSaveInstanceState(outState);
-
- if (mFileName != null && mDocView != null) {
- outState.putString("FileName", mFileName);
-
- // Store current page in the prefs against the file name,
- // so that we can pick it up each time the file is loaded
- // Other info is needed only for screen-orientation change,
- // so it can go in the bundle
- SharedPreferences prefs = getPreferences(Context.MODE_PRIVATE);
- SharedPreferences.Editor edit = prefs.edit();
- edit.putInt("page"+mFileName, mDocView.getDisplayedViewIndex());
- edit.commit();
- }
-
- if (!mButtonsVisible)
- outState.putBoolean("ButtonsHidden", true);
-
- if (mTopBarMode == TopBarMode.Search)
- outState.putBoolean("SearchMode", true);
-
- if (mReflow)
- outState.putBoolean("ReflowMode", true);
- }
-
- @Override
- protected void onPause() {
- super.onPause();
-
- if (mSearchTask != null)
- mSearchTask.stop();
-
- if (mFileName != null && mDocView != null) {
- SharedPreferences prefs = getPreferences(Context.MODE_PRIVATE);
- SharedPreferences.Editor edit = prefs.edit();
- edit.putInt("page"+mFileName, mDocView.getDisplayedViewIndex());
- edit.commit();
- }
- }
-
- public void onDestroy()
- {
- if (mDocView != null) {
- mDocView.applyToChildren(new ReaderView.ViewMapper() {
- void applyToView(View view) {
- ((MuPDFView)view).releaseBitmaps();
- }
- });
- }
- if (core != null)
- core.onDestroy();
- if (mAlertTask != null) {
- mAlertTask.cancel(true);
- mAlertTask = null;
- }
- core = null;
- super.onDestroy();
- }
-
- private void setButtonEnabled(ImageButton button, boolean enabled) {
- button.setEnabled(enabled);
- button.setColorFilter(enabled ? Color.argb(255, 255, 255, 255) : Color.argb(255, 128, 128, 128));
- }
-
- private void setLinkHighlight(boolean highlight) {
- mLinkHighlight = highlight;
- // LINK_COLOR tint
- mLinkButton.setColorFilter(highlight ? Color.argb(0xFF, 172, 114, 37) : Color.argb(0xFF, 255, 255, 255));
- // Inform pages of the change.
- mDocView.setLinksEnabled(highlight);
- }
-
- private void showButtons() {
- if (core == null)
- return;
- if (!mButtonsVisible) {
- mButtonsVisible = true;
- // Update page number text and slider
- int index = mDocView.getDisplayedViewIndex();
- updatePageNumView(index);
- mPageSlider.setMax((core.countPages()-1)*mPageSliderRes);
- mPageSlider.setProgress(index * mPageSliderRes);
- if (mTopBarMode == TopBarMode.Search) {
- mSearchText.requestFocus();
- showKeyboard();
- }
-
- Animation anim = new TranslateAnimation(0, 0, -mTopBarSwitcher.getHeight(), 0);
- anim.setDuration(200);
- anim.setAnimationListener(new Animation.AnimationListener() {
- public void onAnimationStart(Animation animation) {
- mTopBarSwitcher.setVisibility(View.VISIBLE);
- }
- public void onAnimationRepeat(Animation animation) {}
- public void onAnimationEnd(Animation animation) {}
- });
- mTopBarSwitcher.startAnimation(anim);
-
- anim = new TranslateAnimation(0, 0, mPageSlider.getHeight(), 0);
- anim.setDuration(200);
- anim.setAnimationListener(new Animation.AnimationListener() {
- public void onAnimationStart(Animation animation) {
- mPageSlider.setVisibility(View.VISIBLE);
- }
- public void onAnimationRepeat(Animation animation) {}
- public void onAnimationEnd(Animation animation) {
- mPageNumberView.setVisibility(View.VISIBLE);
- }
- });
- mPageSlider.startAnimation(anim);
- }
- }
-
- private void hideButtons() {
- if (mButtonsVisible) {
- mButtonsVisible = false;
- hideKeyboard();
-
- Animation anim = new TranslateAnimation(0, 0, 0, -mTopBarSwitcher.getHeight());
- anim.setDuration(200);
- anim.setAnimationListener(new Animation.AnimationListener() {
- public void onAnimationStart(Animation animation) {}
- public void onAnimationRepeat(Animation animation) {}
- public void onAnimationEnd(Animation animation) {
- mTopBarSwitcher.setVisibility(View.INVISIBLE);
- }
- });
- mTopBarSwitcher.startAnimation(anim);
-
- anim = new TranslateAnimation(0, 0, 0, mPageSlider.getHeight());
- anim.setDuration(200);
- anim.setAnimationListener(new Animation.AnimationListener() {
- public void onAnimationStart(Animation animation) {
- mPageNumberView.setVisibility(View.INVISIBLE);
- }
- public void onAnimationRepeat(Animation animation) {}
- public void onAnimationEnd(Animation animation) {
- mPageSlider.setVisibility(View.INVISIBLE);
- }
- });
- mPageSlider.startAnimation(anim);
- }
- }
-
- private void searchModeOn() {
- if (mTopBarMode != TopBarMode.Search) {
- mTopBarMode = TopBarMode.Search;
- //Focus on EditTextWidget
- mSearchText.requestFocus();
- showKeyboard();
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
- }
-
- private void searchModeOff() {
- if (mTopBarMode == TopBarMode.Search) {
- mTopBarMode = TopBarMode.Main;
- hideKeyboard();
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- SearchTaskResult.set(null);
- // Make the ReaderView act on the change to mSearchTaskResult
- // via overridden onChildSetup method.
- mDocView.resetupChildren();
- }
- }
-
- private void updatePageNumView(int index) {
- if (core == null)
- return;
- mPageNumberView.setText(String.format("%d / %d", index + 1, core.countPages()));
- }
-
- private void printDoc() {
- if (!core.fileFormat().startsWith("PDF")) {
- showInfo(getString(R.string.format_currently_not_supported));
- return;
- }
-
- Intent myIntent = getIntent();
- Uri docUri = myIntent != null ? myIntent.getData() : null;
-
- if (docUri == null) {
- showInfo(getString(R.string.print_failed));
- }
-
- if (docUri.getScheme() == null)
- docUri = Uri.parse("file://"+docUri.toString());
-
- Intent printIntent = new Intent(this, PrintDialogActivity.class);
- printIntent.setDataAndType(docUri, "aplication/pdf");
- printIntent.putExtra("title", mFileName);
- startActivityForResult(printIntent, PRINT_REQUEST);
- }
-
- private void showInfo(String message) {
- mInfoView.setText(message);
-
- int currentApiVersion = android.os.Build.VERSION.SDK_INT;
- if (currentApiVersion >= android.os.Build.VERSION_CODES.HONEYCOMB) {
- SafeAnimatorInflater safe = new SafeAnimatorInflater((Activity)this, R.animator.info, (View)mInfoView);
- } else {
- mInfoView.setVisibility(View.VISIBLE);
- mHandler.postDelayed(new Runnable() {
- public void run() {
- mInfoView.setVisibility(View.INVISIBLE);
- }
- }, 500);
- }
- }
-
- private void makeButtonsView() {
- mButtonsView = getLayoutInflater().inflate(R.layout.buttons,null);
- mFilenameView = (TextView)mButtonsView.findViewById(R.id.docNameText);
- mPageSlider = (SeekBar)mButtonsView.findViewById(R.id.pageSlider);
- mPageNumberView = (TextView)mButtonsView.findViewById(R.id.pageNumber);
- mInfoView = (TextView)mButtonsView.findViewById(R.id.info);
- mSearchButton = (ImageButton)mButtonsView.findViewById(R.id.searchButton);
- mReflowButton = (ImageButton)mButtonsView.findViewById(R.id.reflowButton);
- mOutlineButton = (ImageButton)mButtonsView.findViewById(R.id.outlineButton);
- mAnnotButton = (ImageButton)mButtonsView.findViewById(R.id.editAnnotButton);
- mAnnotTypeText = (TextView)mButtonsView.findViewById(R.id.annotType);
- mTopBarSwitcher = (ViewAnimator)mButtonsView.findViewById(R.id.switcher);
- mSearchBack = (ImageButton)mButtonsView.findViewById(R.id.searchBack);
- mSearchFwd = (ImageButton)mButtonsView.findViewById(R.id.searchForward);
- mSearchText = (EditText)mButtonsView.findViewById(R.id.searchText);
- mLinkButton = (ImageButton)mButtonsView.findViewById(R.id.linkButton);
- mMoreButton = (ImageButton)mButtonsView.findViewById(R.id.moreButton);
- mProofButton = (ImageButton)mButtonsView.findViewById(R.id.proofButton);
- mSepsButton = (ImageButton)mButtonsView.findViewById(R.id.sepsButton);
- mTopBarSwitcher.setVisibility(View.INVISIBLE);
- mPageNumberView.setVisibility(View.INVISIBLE);
- mInfoView.setVisibility(View.INVISIBLE);
-
- mPageSlider.setVisibility(View.INVISIBLE);
- if (!core.gprfSupported()) {
- mProofButton.setVisibility(View.INVISIBLE);
- }
- mSepsButton.setVisibility(View.INVISIBLE);
- }
-
- public void OnMoreButtonClick(View v) {
- mTopBarMode = TopBarMode.More;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- public void OnCancelMoreButtonClick(View v) {
- mTopBarMode = TopBarMode.Main;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- public void OnPrintButtonClick(View v) {
- printDoc();
- }
-
- // start a proof activity with the given resolution.
- public void proofWithResolution (int resolution)
- {
- mProofFile = core.startProof(resolution);
- Uri uri = Uri.parse("file://"+mProofFile);
- Intent intent = new Intent(this, MuPDFActivity.class);
- intent.setAction(Intent.ACTION_VIEW);
- intent.setData(uri);
- // add the current page so it can be found when the activity is running
- intent.putExtra("startingPage", mDocView.getDisplayedViewIndex());
- startActivityForResult(intent, PROOF_REQUEST);
- }
-
- public void OnProofButtonClick(final View v)
- {
- // set up the menu or resolutions.
- final PopupMenu popup = new PopupMenu(this, v);
- popup.getMenu().add(0, 1, 0, "Select a resolution:");
- popup.getMenu().add(0, 72, 0, "72");
- popup.getMenu().add(0, 96, 0, "96");
- popup.getMenu().add(0, 150, 0, "150");
- popup.getMenu().add(0, 300, 0, "300");
- popup.getMenu().add(0, 600, 0, "600");
- popup.getMenu().add(0, 1200, 0, "1200");
- popup.getMenu().add(0, 2400, 0, "2400");
-
- // prevent the first item from being dismissed.
- // is there not a better way to do this? It requires minimum API 14
- MenuItem item = popup.getMenu().getItem(0);
- item.setShowAsAction(MenuItem.SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW);
- item.setActionView(new View(v.getContext()));
- item.setOnActionExpandListener(new MenuItem.OnActionExpandListener() {
- @Override
- public boolean onMenuItemActionExpand(MenuItem item) {
- return false;
- }
-
- @Override
- public boolean onMenuItemActionCollapse(MenuItem item) {
- return false;
- }
- });
-
- popup.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- int id = item.getItemId();
- if (id != 1) {
- // it's a resolution. The id is also the resolution value
- proofWithResolution(id);
- return true;
- }
- return false;
- }
- });
-
- popup.show();
- }
-
- public void OnSepsButtonClick(final View v)
- {
- if (isProofing()) {
-
- // get the current page
- final int currentPage = mDocView.getDisplayedViewIndex();
-
- // buid a popup menu based on the given separations
- final PopupMenu menu = new PopupMenu(this, v);
-
- // This makes the popup menu display icons, which by default it does not do.
- // I worry that this relies on the internals of PopupMenu, which could change.
- try {
- Field[] fields = menu.getClass().getDeclaredFields();
- for (Field field : fields) {
- if ("mPopup".equals(field.getName())) {
- field.setAccessible(true);
- Object menuPopupHelper = field.get(menu);
- Class<?> classPopupHelper = Class.forName(menuPopupHelper
- .getClass().getName());
- Method setForceIcons = classPopupHelper.getMethod(
- "setForceShowIcon", boolean.class);
- setForceIcons.invoke(menuPopupHelper, true);
- break;
- }
- }
- } catch (Exception e) {
- e.printStackTrace();
- }
-
- // get the maximum number of seps on any page.
- // We use this to dimension an array further down
- int maxSeps = 0;
- int numPages = core.countPages();
- for (int page=0; page<numPages; page++) {
- int numSeps = core.getNumSepsOnPage(page);
- if (numSeps>maxSeps)
- maxSeps = numSeps;
- }
-
- // if this is the first time, create the "enabled" array
- if (mSepEnabled==null) {
- mSepEnabled = new boolean[numPages][maxSeps];
- for (int page=0; page<numPages; page++) {
- for (int i = 0; i < maxSeps; i++)
- mSepEnabled[page][i] = true;
- }
- }
-
- // count the seps on this page
- int numSeps = core.getNumSepsOnPage(currentPage);
-
- // for each sep,
- for (int i = 0; i < numSeps; i++) {
-
-// // Robin use this to skip separations
-// if (i==12)
-// break;
-
- // get the name
- Separation sep = core.getSep(currentPage,i);
- String name = sep.name;
-
- // make a checkable menu item with that name
- // and the separation index as the id
- MenuItem item = menu.getMenu().add(0, i, 0, name+" ");
- item.setCheckable(true);
-
- // set an icon that's the right color
- int iconSize = 48;
- int alpha = (sep.rgba >> 24) & 0xFF;
- int red = (sep.rgba >> 16) & 0xFF;
- int green = (sep.rgba >> 8 ) & 0xFF;
- int blue = (sep.rgba >> 0 ) & 0xFF;
- int color = (alpha << 24) | (red << 16) | (green << 8) | (blue << 0);
-
- ShapeDrawable swatch = new ShapeDrawable (new RectShape());
- swatch.setIntrinsicHeight(iconSize);
- swatch.setIntrinsicWidth(iconSize);
- swatch.setBounds(new Rect(0, 0, iconSize, iconSize));
- swatch.getPaint().setColor(color);
- item.setShowAsAction(MenuItem.SHOW_AS_ACTION_ALWAYS);
- item.setIcon(swatch);
-
- // check it (or not)
- item.setChecked(mSepEnabled[currentPage][i]);
-
- // establishing a menu item listener
- item.setOnMenuItemClickListener(new OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- // someone tapped a menu item. get the ID
- int sep = item.getItemId();
-
- // toggle the sep
- mSepEnabled[currentPage][sep] = !mSepEnabled[currentPage][sep];
- item.setChecked(mSepEnabled[currentPage][sep]);
- core.controlSepOnPage(currentPage, sep, !mSepEnabled[currentPage][sep]);
-
- // prevent the menu from being dismissed by these items
- item.setShowAsAction(MenuItem.SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW);
- item.setActionView(new View(v.getContext()));
- item.setOnActionExpandListener(new MenuItem.OnActionExpandListener() {
- @Override
- public boolean onMenuItemActionExpand(MenuItem item) {
- return false;
- }
-
- @Override
- public boolean onMenuItemActionCollapse(MenuItem item) {
- return false;
- }
- });
- return false;
- }
- });
-
- // tell core to enable or disable each sep as appropriate
- // but don't refresh the page yet.
- core.controlSepOnPage(currentPage, i, !mSepEnabled[currentPage][i]);
- }
-
- // add one for done
- MenuItem itemDone = menu.getMenu().add(0, 0, 0, "Done");
- itemDone.setOnMenuItemClickListener(new OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- // refresh the view
- mDocView.refresh(false);
- return true;
- }
- });
-
- // show the menu
- menu.show();
- }
-
- }
-
- public void OnCopyTextButtonClick(View v) {
- mTopBarMode = TopBarMode.Accept;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- mAcceptMode = AcceptMode.CopyText;
- mDocView.setMode(MuPDFReaderView.Mode.Selecting);
- mAnnotTypeText.setText(getString(R.string.copy_text));
- showInfo(getString(R.string.select_text));
- }
-
- public void OnEditAnnotButtonClick(View v) {
- mTopBarMode = TopBarMode.Annot;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- public void OnCancelAnnotButtonClick(View v) {
- mTopBarMode = TopBarMode.More;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- public void OnHighlightButtonClick(View v) {
- mTopBarMode = TopBarMode.Accept;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- mAcceptMode = AcceptMode.Highlight;
- mDocView.setMode(MuPDFReaderView.Mode.Selecting);
- mAnnotTypeText.setText(R.string.highlight);
- showInfo(getString(R.string.select_text));
- }
-
- public void OnUnderlineButtonClick(View v) {
- mTopBarMode = TopBarMode.Accept;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- mAcceptMode = AcceptMode.Underline;
- mDocView.setMode(MuPDFReaderView.Mode.Selecting);
- mAnnotTypeText.setText(R.string.underline);
- showInfo(getString(R.string.select_text));
- }
-
- public void OnStrikeOutButtonClick(View v) {
- mTopBarMode = TopBarMode.Accept;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- mAcceptMode = AcceptMode.StrikeOut;
- mDocView.setMode(MuPDFReaderView.Mode.Selecting);
- mAnnotTypeText.setText(R.string.strike_out);
- showInfo(getString(R.string.select_text));
- }
-
- public void OnInkButtonClick(View v) {
- mTopBarMode = TopBarMode.Accept;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- mAcceptMode = AcceptMode.Ink;
- mDocView.setMode(MuPDFReaderView.Mode.Drawing);
- mAnnotTypeText.setText(R.string.ink);
- showInfo(getString(R.string.draw_annotation));
- }
-
- public void OnCancelAcceptButtonClick(View v) {
- MuPDFView pageView = (MuPDFView) mDocView.getDisplayedView();
- if (pageView != null) {
- pageView.deselectText();
- pageView.cancelDraw();
- }
- mDocView.setMode(MuPDFReaderView.Mode.Viewing);
- switch (mAcceptMode) {
- case CopyText:
- mTopBarMode = TopBarMode.More;
- break;
- default:
- mTopBarMode = TopBarMode.Annot;
- break;
- }
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- public void OnAcceptButtonClick(View v) {
- MuPDFView pageView = (MuPDFView) mDocView.getDisplayedView();
- boolean success = false;
- switch (mAcceptMode) {
- case CopyText:
- if (pageView != null)
- success = pageView.copySelection();
- mTopBarMode = TopBarMode.More;
- showInfo(success?getString(R.string.copied_to_clipboard):getString(R.string.no_text_selected));
- break;
-
- case Highlight:
- if (pageView != null)
- success = pageView.markupSelection(Annotation.Type.HIGHLIGHT);
- mTopBarMode = TopBarMode.Annot;
- if (!success)
- showInfo(getString(R.string.no_text_selected));
- break;
-
- case Underline:
- if (pageView != null)
- success = pageView.markupSelection(Annotation.Type.UNDERLINE);
- mTopBarMode = TopBarMode.Annot;
- if (!success)
- showInfo(getString(R.string.no_text_selected));
- break;
-
- case StrikeOut:
- if (pageView != null)
- success = pageView.markupSelection(Annotation.Type.STRIKEOUT);
- mTopBarMode = TopBarMode.Annot;
- if (!success)
- showInfo(getString(R.string.no_text_selected));
- break;
-
- case Ink:
- if (pageView != null)
- success = pageView.saveDraw();
- mTopBarMode = TopBarMode.Annot;
- if (!success)
- showInfo(getString(R.string.nothing_to_save));
- break;
- }
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- mDocView.setMode(MuPDFReaderView.Mode.Viewing);
- }
-
- public void OnCancelSearchButtonClick(View v) {
- searchModeOff();
- }
-
- public void OnDeleteButtonClick(View v) {
- MuPDFView pageView = (MuPDFView) mDocView.getDisplayedView();
- if (pageView != null)
- pageView.deleteSelectedAnnotation();
- mTopBarMode = TopBarMode.Annot;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- public void OnCancelDeleteButtonClick(View v) {
- MuPDFView pageView = (MuPDFView) mDocView.getDisplayedView();
- if (pageView != null)
- pageView.deselectAnnotation();
- mTopBarMode = TopBarMode.Annot;
- mTopBarSwitcher.setDisplayedChild(mTopBarMode.ordinal());
- }
-
- private void showKeyboard() {
- InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
- if (imm != null)
- imm.showSoftInput(mSearchText, 0);
- }
-
- private void hideKeyboard() {
- InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
- if (imm != null)
- imm.hideSoftInputFromWindow(mSearchText.getWindowToken(), 0);
- }
-
- private void search(int direction) {
- hideKeyboard();
- int displayPage = mDocView.getDisplayedViewIndex();
- SearchTaskResult r = SearchTaskResult.get();
- int searchPage = r != null ? r.pageNumber : -1;
- mSearchTask.go(mSearchText.getText().toString(), direction, displayPage, searchPage);
- }
-
- @Override
- public boolean onSearchRequested() {
- if (mButtonsVisible && mTopBarMode == TopBarMode.Search) {
- hideButtons();
- } else {
- showButtons();
- searchModeOn();
- }
- return super.onSearchRequested();
- }
-
- @Override
- public boolean onPrepareOptionsMenu(Menu menu) {
- if (mButtonsVisible && mTopBarMode != TopBarMode.Search) {
- hideButtons();
- } else {
- showButtons();
- searchModeOff();
- }
- return super.onPrepareOptionsMenu(menu);
- }
-
- @Override
- protected void onStart() {
- if (core != null)
- {
- core.startAlerts();
- createAlertWaiter();
- }
-
- super.onStart();
- }
-
- @Override
- protected void onStop() {
- if (core != null)
- {
- destroyAlertWaiter();
- core.stopAlerts();
- }
-
- super.onStop();
- }
-
- @Override
- public void onBackPressed() {
- if (core != null && core.hasChanges()) {
- DialogInterface.OnClickListener listener = new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- if (which == AlertDialog.BUTTON_POSITIVE)
- core.save();
-
- finish();
- }
- };
- AlertDialog alert = mAlertBuilder.create();
- alert.setTitle("MuPDF");
- alert.setMessage(getString(R.string.document_has_changes_save_them_));
- alert.setButton(AlertDialog.BUTTON_POSITIVE, getString(R.string.yes), listener);
- alert.setButton(AlertDialog.BUTTON_NEGATIVE, getString(R.string.no), listener);
- alert.show();
- } else {
- super.onBackPressed();
- }
- }
-
- @Override
- public void performPickFor(FilePicker picker) {
- mFilePicker = picker;
- Intent intent = new Intent(this, ChoosePDFActivity.class);
- intent.setAction(ChoosePDFActivity.PICK_KEY_FILE);
- startActivityForResult(intent, FILEPICK_REQUEST);
- }
-
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlert.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlert.java
deleted file mode 100644
index 76ed3a65..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlert.java
+++ /dev/null
@@ -1,21 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class MuPDFAlert {
- public enum IconType {Error,Warning,Question,Status};
- public enum ButtonPressed {None,Ok,Cancel,No,Yes};
- public enum ButtonGroupType {Ok,OkCancel,YesNo,YesNoCancel};
-
- public final String message;
- public final IconType iconType;
- public final ButtonGroupType buttonGroupType;
- public final String title;
- public ButtonPressed buttonPressed;
-
- MuPDFAlert(String aMessage, IconType aIconType, ButtonGroupType aButtonGroupType, String aTitle, ButtonPressed aButtonPressed) {
- message = aMessage;
- iconType = aIconType;
- buttonGroupType = aButtonGroupType;
- title = aTitle;
- buttonPressed = aButtonPressed;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlertInternal.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlertInternal.java
deleted file mode 100644
index 5d65768f..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFAlertInternal.java
+++ /dev/null
@@ -1,30 +0,0 @@
-package com.artifex.mupdfdemo;
-
-// Version of MuPDFAlert without enums to simplify JNI
-public class MuPDFAlertInternal {
- public final String message;
- public final int iconType;
- public final int buttonGroupType;
- public final String title;
- public int buttonPressed;
-
- MuPDFAlertInternal(String aMessage, int aIconType, int aButtonGroupType, String aTitle, int aButtonPressed) {
- message = aMessage;
- iconType = aIconType;
- buttonGroupType = aButtonGroupType;
- title = aTitle;
- buttonPressed = aButtonPressed;
- }
-
- MuPDFAlertInternal(MuPDFAlert alert) {
- message = alert.message;
- iconType = alert.iconType.ordinal();
- buttonGroupType = alert.buttonGroupType.ordinal();
- title = alert.message;
- buttonPressed = alert.buttonPressed.ordinal();
- }
-
- MuPDFAlert toAlert() {
- return new MuPDFAlert(message, MuPDFAlert.IconType.values()[iconType], MuPDFAlert.ButtonGroupType.values()[buttonGroupType], title, MuPDFAlert.ButtonPressed.values()[buttonPressed]);
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCancellableTaskDefinition.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCancellableTaskDefinition.java
deleted file mode 100644
index b95d8e93..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCancellableTaskDefinition.java
+++ /dev/null
@@ -1,38 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public abstract class MuPDFCancellableTaskDefinition<Params, Result> implements CancellableTaskDefinition<Params, Result>
-{
- private MuPDFCore.Cookie cookie;
-
- public MuPDFCancellableTaskDefinition(MuPDFCore core)
- {
- this.cookie = core.new Cookie();
- }
-
- @Override
- public void doCancel()
- {
- if (cookie == null)
- return;
-
- cookie.abort();
- }
-
- @Override
- public void doCleanup()
- {
- if (cookie == null)
- return;
-
- cookie.destroy();
- cookie = null;
- }
-
- @Override
- public final Result doInBackground(Params ... params)
- {
- return doInBackground(cookie, params);
- }
-
- public abstract Result doInBackground(MuPDFCore.Cookie cookie, Params ... params);
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCore.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCore.java
deleted file mode 100644
index 6c105e0d..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFCore.java
+++ /dev/null
@@ -1,402 +0,0 @@
-package com.artifex.mupdfdemo;
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.PointF;
-import android.graphics.RectF;
-
-import java.util.ArrayList;
-
-public class MuPDFCore
-{
- /* load our native library */
- private static boolean gs_so_available = false;
- static {
- System.out.println("Loading dll");
- System.loadLibrary("mupdf_java32");
- System.out.println("Loaded dll");
- if (gprfSupportedInternal())
- {
- try {
- System.loadLibrary("gs");
- gs_so_available = true;
- }
- catch (UnsatisfiedLinkError e) {
- gs_so_available = false;
- }
- }
- }
-
- /* Readable members */
- private int numPages = -1;
- private float pageWidth;
- private float pageHeight;
- private long globals;
- private byte fileBuffer[];
- private String file_format;
- private boolean isUnencryptedPDF;
- private final boolean wasOpenedFromBuffer;
-
- /* The native functions */
- private static native boolean gprfSupportedInternal();
- private native long openFile(String filename);
- private native long openBuffer(String magic);
- private native String fileFormatInternal();
- private native boolean isUnencryptedPDFInternal();
- private native int countPagesInternal();
- private native void gotoPageInternal(int localActionPageNum);
- private native float getPageWidth();
- private native float getPageHeight();
- private native void drawPage(Bitmap bitmap,
- int pageW, int pageH,
- int patchX, int patchY,
- int patchW, int patchH,
- long cookiePtr);
- private native void updatePageInternal(Bitmap bitmap,
- int page,
- int pageW, int pageH,
- int patchX, int patchY,
- int patchW, int patchH,
- long cookiePtr);
- private native RectF[] searchPage(String text);
- private native TextChar[][][][] text();
- private native byte[] textAsHtml();
- private native void addMarkupAnnotationInternal(PointF[] quadPoints, int type);
- private native void addInkAnnotationInternal(PointF[][] arcs);
- private native void deleteAnnotationInternal(int annot_index);
- private native int passClickEventInternal(int page, float x, float y);
- private native void setFocusedWidgetChoiceSelectedInternal(String [] selected);
- private native String [] getFocusedWidgetChoiceSelected();
- private native String [] getFocusedWidgetChoiceOptions();
- private native int getFocusedWidgetSignatureState();
- private native String checkFocusedSignatureInternal();
- private native boolean signFocusedSignatureInternal(String keyFile, String password);
- private native int setFocusedWidgetTextInternal(String text);
- private native String getFocusedWidgetTextInternal();
- private native int getFocusedWidgetTypeInternal();
- private native LinkInfo [] getPageLinksInternal(int page);
- private native RectF[] getWidgetAreasInternal(int page);
- private native Annotation[] getAnnotationsInternal(int page);
- private native OutlineItem [] getOutlineInternal();
- private native boolean hasOutlineInternal();
- private native boolean needsPasswordInternal();
- private native boolean authenticatePasswordInternal(String password);
- private native MuPDFAlertInternal waitForAlertInternal();
- private native void replyToAlertInternal(MuPDFAlertInternal alert);
- private native void startAlertsInternal();
- private native void stopAlertsInternal();
- private native void destroying();
- private native boolean hasChangesInternal();
- private native void saveInternal();
- private native long createCookie();
- private native void destroyCookie(long cookie);
- private native void abortCookie(long cookie);
-
- private native String startProofInternal(int resolution);
- private native void endProofInternal(String filename);
- private native int getNumSepsOnPageInternal(int page);
- private native int controlSepOnPageInternal(int page, int sep, boolean disable);
- private native Separation getSepInternal(int page, int sep);
-
- public native boolean javascriptSupported();
-
- public class Cookie
- {
- private final long cookiePtr;
-
- public Cookie()
- {
- cookiePtr = createCookie();
- if (cookiePtr == 0)
- throw new OutOfMemoryError();
- }
-
- public void abort()
- {
- abortCookie(cookiePtr);
- }
-
- public void destroy()
- {
- // We could do this in finalize, but there's no guarantee that
- // a finalize will occur before the muPDF context occurs.
- destroyCookie(cookiePtr);
- }
- }
-
- public MuPDFCore(Context context, String filename) throws Exception
- {
- globals = openFile(filename);
- if (globals == 0)
- {
- throw new Exception(String.format(context.getString(R.string.cannot_open_file_Path), filename));
- }
- file_format = fileFormatInternal();
- isUnencryptedPDF = isUnencryptedPDFInternal();
- wasOpenedFromBuffer = false;
- }
-
- public MuPDFCore(Context context, byte buffer[], String magic) throws Exception {
- fileBuffer = buffer;
- globals = openBuffer(magic != null ? magic : "");
- if (globals == 0)
- {
- throw new Exception(context.getString(R.string.cannot_open_buffer));
- }
- file_format = fileFormatInternal();
- isUnencryptedPDF = isUnencryptedPDFInternal();
- wasOpenedFromBuffer = true;
- }
-
- public int countPages()
- {
- if (numPages < 0)
- numPages = countPagesSynchronized();
- return numPages;
- }
-
- public String fileFormat()
- {
- return file_format;
- }
-
- public boolean isUnencryptedPDF()
- {
- return isUnencryptedPDF;
- }
-
- public boolean wasOpenedFromBuffer()
- {
- return wasOpenedFromBuffer;
- }
-
- private synchronized int countPagesSynchronized() {
- return countPagesInternal();
- }
-
- /* Shim function */
- private void gotoPage(int page)
- {
- if (page > numPages-1)
- page = numPages-1;
- else if (page < 0)
- page = 0;
- gotoPageInternal(page);
- this.pageWidth = getPageWidth();
- this.pageHeight = getPageHeight();
- }
-
- public synchronized PointF getPageSize(int page) {
- gotoPage(page);
- return new PointF(pageWidth, pageHeight);
- }
-
- public MuPDFAlert waitForAlert() {
- MuPDFAlertInternal alert = waitForAlertInternal();
- return alert != null ? alert.toAlert() : null;
- }
-
- public void replyToAlert(MuPDFAlert alert) {
- replyToAlertInternal(new MuPDFAlertInternal(alert));
- }
-
- public void stopAlerts() {
- stopAlertsInternal();
- }
-
- public void startAlerts() {
- startAlertsInternal();
- }
-
- public synchronized void onDestroy() {
- destroying();
- globals = 0;
- }
-
- public synchronized void drawPage(Bitmap bm, int page,
- int pageW, int pageH,
- int patchX, int patchY,
- int patchW, int patchH,
- MuPDFCore.Cookie cookie) {
- gotoPage(page);
- drawPage(bm, pageW, pageH, patchX, patchY, patchW, patchH, cookie.cookiePtr);
- }
-
- public synchronized void updatePage(Bitmap bm, int page,
- int pageW, int pageH,
- int patchX, int patchY,
- int patchW, int patchH,
- MuPDFCore.Cookie cookie) {
- updatePageInternal(bm, page, pageW, pageH, patchX, patchY, patchW, patchH, cookie.cookiePtr);
- }
-
- public synchronized PassClickResult passClickEvent(int page, float x, float y) {
- boolean changed = passClickEventInternal(page, x, y) != 0;
-
- switch (WidgetType.values()[getFocusedWidgetTypeInternal()])
- {
- case TEXT:
- return new PassClickResultText(changed, getFocusedWidgetTextInternal());
- case LISTBOX:
- case COMBOBOX:
- return new PassClickResultChoice(changed, getFocusedWidgetChoiceOptions(), getFocusedWidgetChoiceSelected());
- case SIGNATURE:
- return new PassClickResultSignature(changed, getFocusedWidgetSignatureState());
- default:
- return new PassClickResult(changed);
- }
-
- }
-
- public synchronized boolean setFocusedWidgetText(int page, String text) {
- boolean success;
- gotoPage(page);
- success = setFocusedWidgetTextInternal(text) != 0 ? true : false;
-
- return success;
- }
-
- public synchronized void setFocusedWidgetChoiceSelected(String [] selected) {
- setFocusedWidgetChoiceSelectedInternal(selected);
- }
-
- public synchronized String checkFocusedSignature() {
- return checkFocusedSignatureInternal();
- }
-
- public synchronized boolean signFocusedSignature(String keyFile, String password) {
- return signFocusedSignatureInternal(keyFile, password);
- }
-
- public synchronized LinkInfo [] getPageLinks(int page) {
- return getPageLinksInternal(page);
- }
-
- public synchronized RectF [] getWidgetAreas(int page) {
- return getWidgetAreasInternal(page);
- }
-
- public synchronized Annotation [] getAnnotations(int page) {
- return getAnnotationsInternal(page);
- }
-
- public synchronized RectF [] searchPage(int page, String text) {
- gotoPage(page);
- return searchPage(text);
- }
-
- public synchronized byte[] html(int page) {
- gotoPage(page);
- return textAsHtml();
- }
-
- public synchronized TextWord [][] textLines(int page) {
- gotoPage(page);
- TextChar[][][][] chars = text();
-
- // The text of the page held in a hierarchy (blocks, lines, spans).
- // Currently we don't need to distinguish the blocks level or
- // the spans, and we need to collect the text into words.
- ArrayList<TextWord[]> lns = new ArrayList<TextWord[]>();
-
- for (TextChar[][][] bl: chars) {
- if (bl == null)
- continue;
- for (TextChar[][] ln: bl) {
- ArrayList<TextWord> wds = new ArrayList<TextWord>();
- TextWord wd = new TextWord();
-
- for (TextChar[] sp: ln) {
- for (TextChar tc: sp) {
- if (tc.c != ' ') {
- wd.Add(tc);
- } else if (wd.w.length() > 0) {
- wds.add(wd);
- wd = new TextWord();
- }
- }
- }
-
- if (wd.w.length() > 0)
- wds.add(wd);
-
- if (wds.size() > 0)
- lns.add(wds.toArray(new TextWord[wds.size()]));
- }
- }
-
- return lns.toArray(new TextWord[lns.size()][]);
- }
-
- public synchronized void addMarkupAnnotation(int page, PointF[] quadPoints, Annotation.Type type) {
- gotoPage(page);
- addMarkupAnnotationInternal(quadPoints, type.ordinal());
- }
-
- public synchronized void addInkAnnotation(int page, PointF[][] arcs) {
- gotoPage(page);
- addInkAnnotationInternal(arcs);
- }
-
- public synchronized void deleteAnnotation(int page, int annot_index) {
- gotoPage(page);
- deleteAnnotationInternal(annot_index);
- }
-
- public synchronized boolean hasOutline() {
- return hasOutlineInternal();
- }
-
- public synchronized OutlineItem [] getOutline() {
- return getOutlineInternal();
- }
-
- public synchronized boolean needsPassword() {
- return needsPasswordInternal();
- }
-
- public synchronized boolean authenticatePassword(String password) {
- return authenticatePasswordInternal(password);
- }
-
- public synchronized boolean hasChanges() {
- return hasChangesInternal();
- }
-
- public synchronized void save() {
- saveInternal();
- }
-
- public synchronized String startProof(int resolution) {
- return startProofInternal(resolution);
- }
-
- public synchronized void endProof(String filename) {
- endProofInternal(filename);
- }
-
- public static boolean gprfSupported() {
- if (gs_so_available == false)
- return false;
- return gprfSupportedInternal();
- }
-
- public boolean canProof()
- {
- String format = fileFormat();
- if (format.contains("PDF"))
- return true;
- return false;
- }
-
- public synchronized int getNumSepsOnPage(int page) {
- return getNumSepsOnPageInternal(page);
- }
-
- public synchronized int controlSepOnPage(int page, int sep, boolean disable) {
- return controlSepOnPageInternal(page, sep, disable);
- }
-
- public synchronized Separation getSep(int page, int sep) {
- return getSepInternal(page, sep);
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageAdapter.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageAdapter.java
deleted file mode 100644
index abdac845..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageAdapter.java
+++ /dev/null
@@ -1,87 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.util.SparseArray;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-
-public class MuPDFPageAdapter extends BaseAdapter {
- private final Context mContext;
- private final FilePicker.FilePickerSupport mFilePickerSupport;
- private final MuPDFCore mCore;
- private final SparseArray<PointF> mPageSizes = new SparseArray<PointF>();
- private Bitmap mSharedHqBm;
-
- public MuPDFPageAdapter(Context c, FilePicker.FilePickerSupport filePickerSupport, MuPDFCore core) {
- mContext = c;
- mFilePickerSupport = filePickerSupport;
- mCore = core;
- }
-
- public int getCount() {
- return mCore.countPages();
- }
-
- public Object getItem(int position) {
- return null;
- }
-
- public long getItemId(int position) {
- return 0;
- }
-
- public void releaseBitmaps()
- {
- // recycle and release the shared bitmap.
- if (mSharedHqBm!=null)
- mSharedHqBm.recycle();
- mSharedHqBm = null;
- }
-
- public View getView(final int position, View convertView, ViewGroup parent) {
- final MuPDFPageView pageView;
- if (convertView == null) {
- if (mSharedHqBm == null || mSharedHqBm.getWidth() != parent.getWidth() || mSharedHqBm.getHeight() != parent.getHeight())
- mSharedHqBm = Bitmap.createBitmap(parent.getWidth(), parent.getHeight(), Bitmap.Config.ARGB_8888);
-
- pageView = new MuPDFPageView(mContext, mFilePickerSupport, mCore, new Point(parent.getWidth(), parent.getHeight()), mSharedHqBm);
- } else {
- pageView = (MuPDFPageView) convertView;
- }
-
- PointF pageSize = mPageSizes.get(position);
- if (pageSize != null) {
- // We already know the page size. Set it up
- // immediately
- pageView.setPage(position, pageSize);
- } else {
- // Page size as yet unknown. Blank it for now, and
- // start a background task to find the size
- pageView.blank(position);
- AsyncTask<Void,Void,PointF> sizingTask = new AsyncTask<Void,Void,PointF>() {
- @Override
- protected PointF doInBackground(Void... arg0) {
- return mCore.getPageSize(position);
- }
-
- @Override
- protected void onPostExecute(PointF result) {
- super.onPostExecute(result);
- // We now know the page size
- mPageSizes.put(position, result);
- // Check that this view hasn't been reused for
- // another page since we started
- if (pageView.getPage() == position)
- pageView.setPage(position, result);
- }
- };
-
- sizingTask.execute((Void)null);
- }
- return pageView;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageView.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageView.java
deleted file mode 100644
index 3f48cc37..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFPageView.java
+++ /dev/null
@@ -1,691 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.util.ArrayList;
-
-import com.artifex.mupdfdemo.MuPDFCore.Cookie;
-
-import android.annotation.TargetApi;
-import android.app.AlertDialog;
-import android.content.ClipData;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.graphics.Bitmap;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.RectF;
-import android.net.Uri;
-import android.os.Build;
-import android.text.method.PasswordTransformationMethod;
-import android.view.LayoutInflater;
-import android.view.WindowManager;
-import android.view.inputmethod.EditorInfo;
-import android.widget.EditText;
-
-/* This enum should be kept in line with the cooresponding C enum in mupdf.c */
-enum SignatureState {
- NoSupport,
- Unsigned,
- Signed
-}
-
-abstract class PassClickResultVisitor {
- public abstract void visitText(PassClickResultText result);
- public abstract void visitChoice(PassClickResultChoice result);
- public abstract void visitSignature(PassClickResultSignature result);
-}
-
-class PassClickResult {
- public final boolean changed;
-
- public PassClickResult(boolean _changed) {
- changed = _changed;
- }
-
- public void acceptVisitor(PassClickResultVisitor visitor) {
- }
-}
-
-class PassClickResultText extends PassClickResult {
- public final String text;
-
- public PassClickResultText(boolean _changed, String _text) {
- super(_changed);
- text = _text;
- }
-
- public void acceptVisitor(PassClickResultVisitor visitor) {
- visitor.visitText(this);
- }
-}
-
-class PassClickResultChoice extends PassClickResult {
- public final String [] options;
- public final String [] selected;
-
- public PassClickResultChoice(boolean _changed, String [] _options, String [] _selected) {
- super(_changed);
- options = _options;
- selected = _selected;
- }
-
- public void acceptVisitor(PassClickResultVisitor visitor) {
- visitor.visitChoice(this);
- }
-}
-
-class PassClickResultSignature extends PassClickResult {
- public final SignatureState state;
-
- public PassClickResultSignature(boolean _changed, int _state) {
- super(_changed);
- state = SignatureState.values()[_state];
- }
-
- public void acceptVisitor(PassClickResultVisitor visitor) {
- visitor.visitSignature(this);
- }
-}
-
-public class MuPDFPageView extends PageView implements MuPDFView {
- final private FilePicker.FilePickerSupport mFilePickerSupport;
- private final MuPDFCore mCore;
- private AsyncTask<Void,Void,PassClickResult> mPassClick;
- private RectF mWidgetAreas[];
- private Annotation mAnnotations[];
- private int mSelectedAnnotationIndex = -1;
- private AsyncTask<Void,Void,RectF[]> mLoadWidgetAreas;
- private AsyncTask<Void,Void,Annotation[]> mLoadAnnotations;
- private AlertDialog.Builder mTextEntryBuilder;
- private AlertDialog.Builder mChoiceEntryBuilder;
- private AlertDialog.Builder mSigningDialogBuilder;
- private AlertDialog.Builder mSignatureReportBuilder;
- private AlertDialog.Builder mPasswordEntryBuilder;
- private EditText mPasswordText;
- private AlertDialog mTextEntry;
- private AlertDialog mPasswordEntry;
- private EditText mEditText;
- private AsyncTask<String,Void,Boolean> mSetWidgetText;
- private AsyncTask<String,Void,Void> mSetWidgetChoice;
- private AsyncTask<PointF[],Void,Void> mAddStrikeOut;
- private AsyncTask<PointF[][],Void,Void> mAddInk;
- private AsyncTask<Integer,Void,Void> mDeleteAnnotation;
- private AsyncTask<Void,Void,String> mCheckSignature;
- private AsyncTask<Void,Void,Boolean> mSign;
- private Runnable changeReporter;
-
- public MuPDFPageView(Context c, FilePicker.FilePickerSupport filePickerSupport, MuPDFCore core, Point parentSize, Bitmap sharedHqBm) {
- super(c, parentSize, sharedHqBm);
- mFilePickerSupport = filePickerSupport;
- mCore = core;
- mTextEntryBuilder = new AlertDialog.Builder(c);
- mTextEntryBuilder.setTitle(getContext().getString(R.string.fill_out_text_field));
- LayoutInflater inflater = (LayoutInflater)c.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- mEditText = (EditText)inflater.inflate(R.layout.textentry, null);
- mTextEntryBuilder.setView(mEditText);
- mTextEntryBuilder.setNegativeButton(R.string.cancel, new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- dialog.dismiss();
- }
- });
- mTextEntryBuilder.setPositiveButton(R.string.okay, new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- mSetWidgetText = new AsyncTask<String,Void,Boolean> () {
- @Override
- protected Boolean doInBackground(String... arg0) {
- return mCore.setFocusedWidgetText(mPageNumber, arg0[0]);
- }
- @Override
- protected void onPostExecute(Boolean result) {
- changeReporter.run();
- if (!result)
- invokeTextDialog(mEditText.getText().toString());
- }
- };
-
- mSetWidgetText.execute(mEditText.getText().toString());
- }
- });
- mTextEntry = mTextEntryBuilder.create();
-
- mChoiceEntryBuilder = new AlertDialog.Builder(c);
- mChoiceEntryBuilder.setTitle(getContext().getString(R.string.choose_value));
-
- mSigningDialogBuilder = new AlertDialog.Builder(c);
- mSigningDialogBuilder.setTitle("Select certificate and sign?");
- mSigningDialogBuilder.setNegativeButton(R.string.cancel, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- dialog.dismiss();
- }
- });
- mSigningDialogBuilder.setPositiveButton(R.string.okay, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- FilePicker picker = new FilePicker(mFilePickerSupport) {
- @Override
- void onPick(Uri uri) {
- signWithKeyFile(uri);
- }
- };
-
- picker.pick();
- }
- });
-
- mSignatureReportBuilder = new AlertDialog.Builder(c);
- mSignatureReportBuilder.setTitle("Signature checked");
- mSignatureReportBuilder.setPositiveButton(R.string.okay, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- dialog.dismiss();
- }
- });
-
- mPasswordText = new EditText(c);
- mPasswordText.setInputType(EditorInfo.TYPE_TEXT_VARIATION_PASSWORD);
- mPasswordText.setTransformationMethod(new PasswordTransformationMethod());
-
- mPasswordEntryBuilder = new AlertDialog.Builder(c);
- mPasswordEntryBuilder.setTitle(R.string.enter_password);
- mPasswordEntryBuilder.setView(mPasswordText);
- mPasswordEntryBuilder.setNegativeButton(R.string.cancel, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- dialog.dismiss();
- }
- });
-
- mPasswordEntry = mPasswordEntryBuilder.create();
- }
-
- private void signWithKeyFile(final Uri uri) {
- mPasswordEntry.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
- mPasswordEntry.setButton(AlertDialog.BUTTON_POSITIVE, "Sign", new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- dialog.dismiss();
- signWithKeyFileAndPassword(uri, mPasswordText.getText().toString());
- }
- });
-
- mPasswordEntry.show();
- }
-
- private void signWithKeyFileAndPassword(final Uri uri, final String password) {
- mSign = new AsyncTask<Void,Void,Boolean>() {
- @Override
- protected Boolean doInBackground(Void... params) {
- return mCore.signFocusedSignature(Uri.decode(uri.getEncodedPath()), password);
- }
- @Override
- protected void onPostExecute(Boolean result) {
- if (result)
- {
- changeReporter.run();
- }
- else
- {
- mPasswordText.setText("");
- signWithKeyFile(uri);
- }
- }
-
- };
-
- mSign.execute();
- }
-
- public LinkInfo hitLink(float x, float y) {
- // Since link highlighting was implemented, the super class
- // PageView has had sufficient information to be able to
- // perform this method directly. Making that change would
- // make MuPDFCore.hitLinkPage superfluous.
- float scale = mSourceScale*(float)getWidth()/(float)mSize.x;
- float docRelX = (x - getLeft())/scale;
- float docRelY = (y - getTop())/scale;
-
- for (LinkInfo l: mLinks)
- if (l.rect.contains(docRelX, docRelY))
- return l;
-
- return null;
- }
-
- private void invokeTextDialog(String text) {
- mEditText.setText(text);
- mTextEntry.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
- mTextEntry.show();
- }
-
- private void invokeChoiceDialog(final String [] options) {
- mChoiceEntryBuilder.setItems(options, new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- mSetWidgetChoice = new AsyncTask<String,Void,Void>() {
- @Override
- protected Void doInBackground(String... params) {
- String [] sel = {params[0]};
- mCore.setFocusedWidgetChoiceSelected(sel);
- return null;
- }
-
- @Override
- protected void onPostExecute(Void result) {
- changeReporter.run();
- }
- };
-
- mSetWidgetChoice.execute(options[which]);
- }
- });
- AlertDialog dialog = mChoiceEntryBuilder.create();
- dialog.show();
- }
-
- private void invokeSignatureCheckingDialog() {
- mCheckSignature = new AsyncTask<Void,Void,String> () {
- @Override
- protected String doInBackground(Void... params) {
- return mCore.checkFocusedSignature();
- }
- @Override
- protected void onPostExecute(String result) {
- AlertDialog report = mSignatureReportBuilder.create();
- report.setMessage(result);
- report.show();
- }
- };
-
- mCheckSignature.execute();
- }
-
- private void invokeSigningDialog() {
- AlertDialog dialog = mSigningDialogBuilder.create();
- dialog.show();
- }
-
- private void warnNoSignatureSupport() {
- AlertDialog dialog = mSignatureReportBuilder.create();
- dialog.setTitle("App built with no signature support");
- dialog.show();
- }
-
- public void setChangeReporter(Runnable reporter) {
- changeReporter = reporter;
- }
-
- public Hit passClickEvent(float x, float y) {
- float scale = mSourceScale*(float)getWidth()/(float)mSize.x;
- final float docRelX = (x - getLeft())/scale;
- final float docRelY = (y - getTop())/scale;
- boolean hit = false;
- int i;
-
- if (mAnnotations != null) {
- for (i = 0; i < mAnnotations.length; i++)
- if (mAnnotations[i].contains(docRelX, docRelY)) {
- hit = true;
- break;
- }
-
- if (hit) {
- switch (mAnnotations[i].type) {
- case HIGHLIGHT:
- case UNDERLINE:
- case SQUIGGLY:
- case STRIKEOUT:
- case INK:
- mSelectedAnnotationIndex = i;
- setItemSelectBox(mAnnotations[i]);
- return Hit.Annotation;
- }
- }
- }
-
- mSelectedAnnotationIndex = -1;
- setItemSelectBox(null);
-
- if (!mCore.javascriptSupported())
- return Hit.Nothing;
-
- if (mWidgetAreas != null) {
- for (i = 0; i < mWidgetAreas.length && !hit; i++)
- if (mWidgetAreas[i].contains(docRelX, docRelY))
- hit = true;
- }
-
- if (hit) {
- mPassClick = new AsyncTask<Void,Void,PassClickResult>() {
- @Override
- protected PassClickResult doInBackground(Void... arg0) {
- return mCore.passClickEvent(mPageNumber, docRelX, docRelY);
- }
-
- @Override
- protected void onPostExecute(PassClickResult result) {
- if (result.changed) {
- changeReporter.run();
- }
-
- result.acceptVisitor(new PassClickResultVisitor() {
- @Override
- public void visitText(PassClickResultText result) {
- invokeTextDialog(result.text);
- }
-
- @Override
- public void visitChoice(PassClickResultChoice result) {
- invokeChoiceDialog(result.options);
- }
-
- @Override
- public void visitSignature(PassClickResultSignature result) {
- switch (result.state) {
- case NoSupport:
- warnNoSignatureSupport();
- break;
- case Unsigned:
- invokeSigningDialog();
- break;
- case Signed:
- invokeSignatureCheckingDialog();
- break;
- }
- }
- });
- }
- };
-
- mPassClick.execute();
- return Hit.Widget;
- }
-
- return Hit.Nothing;
- }
-
- @TargetApi(11)
- public boolean copySelection() {
- final StringBuilder text = new StringBuilder();
-
- processSelectedText(new TextProcessor() {
- StringBuilder line;
-
- public void onStartLine() {
- line = new StringBuilder();
- }
-
- public void onWord(TextWord word) {
- if (line.length() > 0)
- line.append(' ');
- line.append(word.w);
- }
-
- public void onEndLine() {
- if (text.length() > 0)
- text.append('\n');
- text.append(line);
- }
- });
-
- if (text.length() == 0)
- return false;
-
- int currentApiVersion = android.os.Build.VERSION.SDK_INT;
- if (currentApiVersion >= android.os.Build.VERSION_CODES.HONEYCOMB) {
- android.content.ClipboardManager cm = (android.content.ClipboardManager)mContext.getSystemService(Context.CLIPBOARD_SERVICE);
-
- cm.setPrimaryClip(ClipData.newPlainText("MuPDF", text));
- } else {
- android.text.ClipboardManager cm = (android.text.ClipboardManager)mContext.getSystemService(Context.CLIPBOARD_SERVICE);
- cm.setText(text);
- }
-
- deselectText();
-
- return true;
- }
-
- public boolean markupSelection(final Annotation.Type type) {
- final ArrayList<PointF> quadPoints = new ArrayList<PointF>();
- processSelectedText(new TextProcessor() {
- RectF rect;
-
- public void onStartLine() {
- rect = new RectF();
- }
-
- public void onWord(TextWord word) {
- rect.union(word);
- }
-
- public void onEndLine() {
- if (!rect.isEmpty()) {
- quadPoints.add(new PointF(rect.left, rect.bottom));
- quadPoints.add(new PointF(rect.right, rect.bottom));
- quadPoints.add(new PointF(rect.right, rect.top));
- quadPoints.add(new PointF(rect.left, rect.top));
- }
- }
- });
-
- if (quadPoints.size() == 0)
- return false;
-
- mAddStrikeOut = new AsyncTask<PointF[],Void,Void>() {
- @Override
- protected Void doInBackground(PointF[]... params) {
- addMarkup(params[0], type);
- return null;
- }
-
- @Override
- protected void onPostExecute(Void result) {
- loadAnnotations();
- update();
- }
- };
-
- mAddStrikeOut.execute(quadPoints.toArray(new PointF[quadPoints.size()]));
-
- deselectText();
-
- return true;
- }
-
- public void deleteSelectedAnnotation() {
- if (mSelectedAnnotationIndex != -1) {
- if (mDeleteAnnotation != null)
- mDeleteAnnotation.cancel(true);
-
- mDeleteAnnotation = new AsyncTask<Integer,Void,Void>() {
- @Override
- protected Void doInBackground(Integer... params) {
- mCore.deleteAnnotation(mPageNumber, params[0]);
- return null;
- }
-
- @Override
- protected void onPostExecute(Void result) {
- loadAnnotations();
- update();
- }
- };
-
- mDeleteAnnotation.execute(mSelectedAnnotationIndex);
-
- mSelectedAnnotationIndex = -1;
- setItemSelectBox(null);
- }
- }
-
- public void deselectAnnotation() {
- mSelectedAnnotationIndex = -1;
- setItemSelectBox(null);
- }
-
- public boolean saveDraw() {
- PointF[][] path = getDraw();
-
- if (path == null)
- return false;
-
- if (mAddInk != null) {
- mAddInk.cancel(true);
- mAddInk = null;
- }
- mAddInk = new AsyncTask<PointF[][],Void,Void>() {
- @Override
- protected Void doInBackground(PointF[][]... params) {
- mCore.addInkAnnotation(mPageNumber, params[0]);
- return null;
- }
-
- @Override
- protected void onPostExecute(Void result) {
- loadAnnotations();
- update();
- }
-
- };
-
- mAddInk.execute(getDraw());
- cancelDraw();
-
- return true;
- }
-
- @Override
- protected CancellableTaskDefinition<Void, Void> getDrawPageTask(final Bitmap bm, final int sizeX, final int sizeY,
- final int patchX, final int patchY, final int patchWidth, final int patchHeight) {
- return new MuPDFCancellableTaskDefinition<Void, Void>(mCore) {
- @Override
- public Void doInBackground(MuPDFCore.Cookie cookie, Void ... params) {
- // Workaround bug in Android Honeycomb 3.x, where the bitmap generation count
- // is not incremented when drawing.
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB &&
- Build.VERSION.SDK_INT < Build.VERSION_CODES.ICE_CREAM_SANDWICH)
- bm.eraseColor(0);
- mCore.drawPage(bm, mPageNumber, sizeX, sizeY, patchX, patchY, patchWidth, patchHeight, cookie);
- return null;
- }
- };
-
- }
-
- protected CancellableTaskDefinition<Void, Void> getUpdatePageTask(final Bitmap bm, final int sizeX, final int sizeY,
- final int patchX, final int patchY, final int patchWidth, final int patchHeight)
- {
- return new MuPDFCancellableTaskDefinition<Void, Void>(mCore) {
-
- @Override
- public Void doInBackground(MuPDFCore.Cookie cookie, Void ... params) {
- // Workaround bug in Android Honeycomb 3.x, where the bitmap generation count
- // is not incremented when drawing.
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB &&
- Build.VERSION.SDK_INT < Build.VERSION_CODES.ICE_CREAM_SANDWICH)
- bm.eraseColor(0);
- mCore.updatePage(bm, mPageNumber, sizeX, sizeY, patchX, patchY, patchWidth, patchHeight, cookie);
- return null;
- }
- };
- }
-
- @Override
- protected LinkInfo[] getLinkInfo() {
- return mCore.getPageLinks(mPageNumber);
- }
-
- @Override
- protected TextWord[][] getText() {
- return mCore.textLines(mPageNumber);
- }
-
- @Override
- protected void addMarkup(PointF[] quadPoints, Annotation.Type type) {
- mCore.addMarkupAnnotation(mPageNumber, quadPoints, type);
- }
-
- private void loadAnnotations() {
- mAnnotations = null;
- if (mLoadAnnotations != null)
- mLoadAnnotations.cancel(true);
- mLoadAnnotations = new AsyncTask<Void,Void,Annotation[]> () {
- @Override
- protected Annotation[] doInBackground(Void... params) {
- return mCore.getAnnotations(mPageNumber);
- }
-
- @Override
- protected void onPostExecute(Annotation[] result) {
- mAnnotations = result;
- }
- };
-
- mLoadAnnotations.execute();
- }
-
- @Override
- public void setPage(final int page, PointF size) {
- loadAnnotations();
-
- mLoadWidgetAreas = new AsyncTask<Void,Void,RectF[]> () {
- @Override
- protected RectF[] doInBackground(Void... arg0) {
- return mCore.getWidgetAreas(page);
- }
-
- @Override
- protected void onPostExecute(RectF[] result) {
- mWidgetAreas = result;
- }
- };
-
- mLoadWidgetAreas.execute();
-
- super.setPage(page, size);
- }
-
- public void setScale(float scale) {
- // This type of view scales automatically to fit the size
- // determined by the parent view groups during layout
- }
-
- @Override
- public void releaseResources() {
- if (mPassClick != null) {
- mPassClick.cancel(true);
- mPassClick = null;
- }
-
- if (mLoadWidgetAreas != null) {
- mLoadWidgetAreas.cancel(true);
- mLoadWidgetAreas = null;
- }
-
- if (mLoadAnnotations != null) {
- mLoadAnnotations.cancel(true);
- mLoadAnnotations = null;
- }
-
- if (mSetWidgetText != null) {
- mSetWidgetText.cancel(true);
- mSetWidgetText = null;
- }
-
- if (mSetWidgetChoice != null) {
- mSetWidgetChoice.cancel(true);
- mSetWidgetChoice = null;
- }
-
- if (mAddStrikeOut != null) {
- mAddStrikeOut.cancel(true);
- mAddStrikeOut = null;
- }
-
- if (mDeleteAnnotation != null) {
- mDeleteAnnotation.cancel(true);
- mDeleteAnnotation = null;
- }
-
- super.releaseResources();
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReaderView.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReaderView.java
deleted file mode 100644
index b712cba9..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReaderView.java
+++ /dev/null
@@ -1,277 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.app.Activity;
-import android.content.Context;
-import android.content.Intent;
-import android.net.Uri;
-import android.util.AttributeSet;
-import android.util.DisplayMetrics;
-import android.view.MotionEvent;
-import android.view.ScaleGestureDetector;
-import android.view.View;
-import android.view.WindowManager;
-
-public class MuPDFReaderView extends ReaderView {
- public enum Mode {Viewing, Selecting, Drawing}
- private final Context mContext;
- private boolean mLinksEnabled = false;
- private Mode mMode = Mode.Viewing;
- private boolean tapDisabled = false;
- private int tapPageMargin;
-
- protected void onTapMainDocArea() {}
- protected void onDocMotion() {}
- protected void onHit(Hit item) {};
-
- public void setLinksEnabled(boolean b) {
- mLinksEnabled = b;
- resetupChildren();
- }
-
- public void setMode(Mode m) {
- mMode = m;
- }
-
- private void setup()
- {
- // Get the screen size etc to customise tap margins.
- // We calculate the size of 1 inch of the screen for tapping.
- // On some devices the dpi values returned are wrong, so we
- // sanity check it: we first restrict it so that we are never
- // less than 100 pixels (the smallest Android device screen
- // dimension I've seen is 480 pixels or so). Then we check
- // to ensure we are never more than 1/5 of the screen width.
- DisplayMetrics dm = new DisplayMetrics();
- WindowManager wm = (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
- wm.getDefaultDisplay().getMetrics(dm);
- tapPageMargin = (int)dm.xdpi;
- if (tapPageMargin < 100)
- tapPageMargin = 100;
- if (tapPageMargin > dm.widthPixels/5)
- tapPageMargin = dm.widthPixels/5;
- }
-
- public MuPDFReaderView(Context context) {
- super(context);
- mContext = context;
- setup();
- }
-
- public MuPDFReaderView(Context context, AttributeSet attrs)
- {
- super(context, attrs);
- mContext = context;
- setup();
- }
-
- public boolean onSingleTapUp(MotionEvent e) {
- LinkInfo link = null;
-
- if (mMode == Mode.Viewing && !tapDisabled) {
- MuPDFView pageView = (MuPDFView) getDisplayedView();
- Hit item = pageView != null ? pageView.passClickEvent(e.getX(), e.getY()) : null;
- if (item != null)
- onHit(item);
- if (item == Hit.Nothing) {
- if (mLinksEnabled && pageView != null
- && (link = pageView.hitLink(e.getX(), e.getY())) != null) {
- link.acceptVisitor(new LinkInfoVisitor() {
- @Override
- public void visitInternal(LinkInfoInternal li) {
- // Clicked on an internal (GoTo) link
- setDisplayedViewIndex(li.pageNumber);
- }
-
- @Override
- public void visitExternal(LinkInfoExternal li) {
- Intent intent = new Intent(Intent.ACTION_VIEW, Uri
- .parse(li.url));
- mContext.startActivity(intent);
- }
-
- @Override
- public void visitRemote(LinkInfoRemote li) {
- // Clicked on a remote (GoToR) link
- }
- });
- } else if (e.getX() < tapPageMargin) {
- super.smartMoveBackwards();
- } else if (e.getX() > super.getWidth() - tapPageMargin) {
- super.smartMoveForwards();
- } else if (e.getY() < tapPageMargin) {
- super.smartMoveBackwards();
- } else if (e.getY() > super.getHeight() - tapPageMargin) {
- super.smartMoveForwards();
- } else {
- onTapMainDocArea();
- }
- }
- }
- return super.onSingleTapUp(e);
- }
-
- @Override
- public boolean onDown(MotionEvent e) {
-
- return super.onDown(e);
- }
-
- public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX,
- float distanceY) {
- MuPDFView pageView = (MuPDFView)getDisplayedView();
- switch (mMode) {
- case Viewing:
- if (!tapDisabled)
- onDocMotion();
-
- return super.onScroll(e1, e2, distanceX, distanceY);
- case Selecting:
- if (pageView != null)
- pageView.selectText(e1.getX(), e1.getY(), e2.getX(), e2.getY());
- return true;
- default:
- return true;
- }
- }
-
- @Override
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
- float velocityY) {
- switch (mMode) {
- case Viewing:
- return super.onFling(e1, e2, velocityX, velocityY);
- default:
- return true;
- }
- }
-
- public boolean onScaleBegin(ScaleGestureDetector d) {
- // Disabled showing the buttons until next touch.
- // Not sure why this is needed, but without it
- // pinch zoom can make the buttons appear
- tapDisabled = true;
- return super.onScaleBegin(d);
- }
-
- public boolean onTouchEvent(MotionEvent event) {
-
- if ( mMode == Mode.Drawing )
- {
- float x = event.getX();
- float y = event.getY();
- switch (event.getAction())
- {
- case MotionEvent.ACTION_DOWN:
- touch_start(x, y);
- break;
- case MotionEvent.ACTION_MOVE:
- touch_move(x, y);
- break;
- case MotionEvent.ACTION_UP:
- touch_up();
- break;
- }
- }
-
- if ((event.getAction() & event.getActionMasked()) == MotionEvent.ACTION_DOWN)
- {
- tapDisabled = false;
- }
-
- return super.onTouchEvent(event);
- }
-
- private float mX, mY;
-
- private static final float TOUCH_TOLERANCE = 2;
-
- private void touch_start(float x, float y) {
-
- MuPDFView pageView = (MuPDFView)getDisplayedView();
- if (pageView != null)
- {
- pageView.startDraw(x, y);
- }
- mX = x;
- mY = y;
- }
-
- private void touch_move(float x, float y) {
-
- float dx = Math.abs(x - mX);
- float dy = Math.abs(y - mY);
- if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE)
- {
- MuPDFView pageView = (MuPDFView)getDisplayedView();
- if (pageView != null)
- {
- pageView.continueDraw(x, y);
- }
- mX = x;
- mY = y;
- }
- }
-
- private void touch_up() {
-
- // NOOP
- }
-
- protected void onChildSetup(int i, View v) {
- if (SearchTaskResult.get() != null
- && SearchTaskResult.get().pageNumber == i)
- ((MuPDFView) v).setSearchBoxes(SearchTaskResult.get().searchBoxes);
- else
- ((MuPDFView) v).setSearchBoxes(null);
-
- ((MuPDFView) v).setLinkHighlighting(mLinksEnabled);
-
- ((MuPDFView) v).setChangeReporter(new Runnable() {
- public void run() {
- applyToChildren(new ReaderView.ViewMapper() {
- @Override
- void applyToView(View view) {
- ((MuPDFView) view).update();
- }
- });
- }
- });
- }
-
- protected void onMoveToChild(int i) {
- if (SearchTaskResult.get() != null
- && SearchTaskResult.get().pageNumber != i) {
- SearchTaskResult.set(null);
- resetupChildren();
- }
- }
-
- @Override
- protected void onMoveOffChild(int i) {
- View v = getView(i);
- if (v != null)
- ((MuPDFView)v).deselectAnnotation();
- }
-
- protected void onSettle(View v) {
- // When the layout has settled ask the page to render
- // in HQ
- ((MuPDFView) v).updateHq(false);
- }
-
- protected void onUnsettle(View v) {
- // When something changes making the previous settled view
- // no longer appropriate, tell the page to remove HQ
- ((MuPDFView) v).removeHq();
- }
-
- @Override
- protected void onNotInUse(View v) {
- ((MuPDFView) v).releaseResources();
- }
-
- @Override
- protected void onScaleChild(View v, Float scale) {
- ((MuPDFView) v).setScale(scale);
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowAdapter.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowAdapter.java
deleted file mode 100644
index 48625a7e..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowAdapter.java
+++ /dev/null
@@ -1,43 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.content.Context;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-
-public class MuPDFReflowAdapter extends BaseAdapter {
- private final Context mContext;
- private final MuPDFCore mCore;
-
- public MuPDFReflowAdapter(Context c, MuPDFCore core) {
- mContext = c;
- mCore = core;
- }
-
- public int getCount() {
- return mCore.countPages();
- }
-
- public Object getItem(int arg0) {
- return null;
- }
-
- public long getItemId(int arg0) {
- return 0;
- }
-
- public View getView(int position, View convertView, ViewGroup parent) {
- final MuPDFReflowView reflowView;
- if (convertView == null) {
- reflowView = new MuPDFReflowView(mContext, mCore, new Point(parent.getWidth(), parent.getHeight()));
- } else {
- reflowView = (MuPDFReflowView) convertView;
- }
-
- reflowView.setPage(position, new PointF());
-
- return reflowView;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowView.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowView.java
deleted file mode 100644
index 7d41a9b9..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFReflowView.java
+++ /dev/null
@@ -1,182 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.content.Context;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.RectF;
-import android.os.Handler;
-import android.util.Base64;
-import android.view.MotionEvent;
-import android.view.View;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
-
-public class MuPDFReflowView extends WebView implements MuPDFView {
- private final MuPDFCore mCore;
- private final Handler mHandler;
- private final Point mParentSize;
- private int mPage;
- private float mScale;
- private int mContentHeight;
- AsyncTask<Void,Void,byte[]> mLoadHTML;
-
- public MuPDFReflowView(Context c, MuPDFCore core, Point parentSize) {
- super(c);
- mHandler = new Handler();
- mCore = core;
- mParentSize = parentSize;
- mScale = 1.0f;
- mContentHeight = parentSize.y;
- getSettings().setJavaScriptEnabled(true);
- addJavascriptInterface(new Object(){
- public void reportContentHeight(String value) {
- mContentHeight = (int)Float.parseFloat(value);
- mHandler.post(new Runnable() {
- public void run() {
- requestLayout();
- }
- });
- }
- }, "HTMLOUT");
- setWebViewClient(new WebViewClient() {
- @Override
- public void onPageFinished(WebView view, String url) {
- setScale(mScale);
- }
- });
- }
-
- private void requestHeight() {
- // Get the webview to report the content height via the interface setup
- // above. Workaround for getContentHeight not working
- loadUrl("javascript:elem=document.getElementById('content');window.HTMLOUT.reportContentHeight("+mParentSize.x+"*elem.offsetHeight/elem.offsetWidth)");
- }
-
- public void setPage(int page, PointF size) {
- mPage = page;
- if (mLoadHTML != null) {
- mLoadHTML.cancel(true);
- }
- mLoadHTML = new AsyncTask<Void,Void,byte[]>() {
- @Override
- protected byte[] doInBackground(Void... params) {
- return mCore.html(mPage);
- }
- @Override
- protected void onPostExecute(byte[] result) {
- String b64 = Base64.encodeToString(result, Base64.DEFAULT);
- loadData(b64, "text/html; charset=utf-8", "base64");
- }
- };
- mLoadHTML.execute();
- }
-
- public int getPage() {
- return mPage;
- }
-
- public void setScale(float scale) {
- mScale = scale;
- loadUrl("javascript:document.getElementById('content').style.zoom=\""+(int)(mScale*100)+"%\"");
- requestHeight();
- }
-
- public void blank(int page) {
- }
-
- public Hit passClickEvent(float x, float y) {
- return Hit.Nothing;
- }
-
- public LinkInfo hitLink(float x, float y) {
- return null;
- }
-
- public void selectText(float x0, float y0, float x1, float y1) {
- }
-
- public void deselectText() {
- }
-
- public boolean copySelection() {
- return false;
- }
-
- public boolean markupSelection(Annotation.Type type) {
- return false;
- }
-
- public void startDraw(float x, float y) {
- }
-
- public void continueDraw(float x, float y) {
- }
-
- public void cancelDraw() {
- }
-
- public boolean saveDraw() {
- return false;
- }
-
- public void setSearchBoxes(RectF[] searchBoxes) {
- }
-
- public void setLinkHighlighting(boolean f) {
- }
-
- public void deleteSelectedAnnotation() {
- }
-
- public void deselectAnnotation() {
- }
-
- public void setChangeReporter(Runnable reporter) {
- }
-
- public void update() {
- }
-
- public void updateHq(boolean update) {
- }
-
- public void removeHq() {
- }
-
- public void releaseResources() {
- if (mLoadHTML != null) {
- mLoadHTML.cancel(true);
- mLoadHTML = null;
- }
- }
-
- public void releaseBitmaps() {
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- int x, y;
- switch(View.MeasureSpec.getMode(widthMeasureSpec)) {
- case View.MeasureSpec.UNSPECIFIED:
- x = mParentSize.x;
- break;
- default:
- x = View.MeasureSpec.getSize(widthMeasureSpec);
- }
- switch(View.MeasureSpec.getMode(heightMeasureSpec)) {
- case View.MeasureSpec.UNSPECIFIED:
- y = mContentHeight;
- break;
- default:
- y = View.MeasureSpec.getSize(heightMeasureSpec);
- }
-
- setMeasuredDimension(x, y);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent ev) {
- // TODO Auto-generated method stub
- return false;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFView.java b/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFView.java
deleted file mode 100644
index ec3d3d9a..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/MuPDFView.java
+++ /dev/null
@@ -1,33 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.graphics.PointF;
-import android.graphics.RectF;
-
-enum Hit {Nothing, Widget, Annotation};
-
-public interface MuPDFView {
- public void setPage(int page, PointF size);
- public void setScale(float scale);
- public int getPage();
- public void blank(int page);
- public Hit passClickEvent(float x, float y);
- public LinkInfo hitLink(float x, float y);
- public void selectText(float x0, float y0, float x1, float y1);
- public void deselectText();
- public boolean copySelection();
- public boolean markupSelection(Annotation.Type type);
- public void deleteSelectedAnnotation();
- public void setSearchBoxes(RectF searchBoxes[]);
- public void setLinkHighlighting(boolean f);
- public void deselectAnnotation();
- public void startDraw(float x, float y);
- public void continueDraw(float x, float y);
- public void cancelDraw();
- public boolean saveDraw();
- public void setChangeReporter(Runnable reporter);
- public void update();
- public void updateHq(boolean update);
- public void removeHq();
- public void releaseResources();
- public void releaseBitmaps();
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivity.java b/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivity.java
deleted file mode 100644
index 52b0d410..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivity.java
+++ /dev/null
@@ -1,31 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.app.ListActivity;
-import android.os.Bundle;
-import android.view.View;
-import android.widget.ListView;
-
-public class OutlineActivity extends ListActivity {
- OutlineItem mItems[];
-
- /** Called when the activity is first created. */
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- mItems = OutlineActivityData.get().items;
- setListAdapter(new OutlineAdapter(getLayoutInflater(),mItems));
- // Restore the position within the list from last viewing
- getListView().setSelection(OutlineActivityData.get().position);
- getListView().setDividerHeight(0);
- setResult(-1);
- }
-
- @Override
- protected void onListItemClick(ListView l, View v, int position, long id) {
- super.onListItemClick(l, v, position, id);
- OutlineActivityData.get().position = getListView().getFirstVisiblePosition();
- setResult(mItems[position].page);
- finish();
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivityData.java b/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivityData.java
deleted file mode 100644
index be1386e6..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineActivityData.java
+++ /dev/null
@@ -1,17 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class OutlineActivityData {
- public OutlineItem items[];
- public int position;
- static private OutlineActivityData singleton;
-
- static public void set(OutlineActivityData d) {
- singleton = d;
- }
-
- static public OutlineActivityData get() {
- if (singleton == null)
- singleton = new OutlineActivityData();
- return singleton;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineAdapter.java b/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineAdapter.java
deleted file mode 100644
index c1b22021..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineAdapter.java
+++ /dev/null
@@ -1,46 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-import android.widget.TextView;
-
-public class OutlineAdapter extends BaseAdapter {
- private final OutlineItem mItems[];
- private final LayoutInflater mInflater;
- public OutlineAdapter(LayoutInflater inflater, OutlineItem items[]) {
- mInflater = inflater;
- mItems = items;
- }
-
- public int getCount() {
- return mItems.length;
- }
-
- public Object getItem(int arg0) {
- return null;
- }
-
- public long getItemId(int arg0) {
- return 0;
- }
-
- public View getView(int position, View convertView, ViewGroup parent) {
- View v;
- if (convertView == null) {
- v = mInflater.inflate(R.layout.outline_entry, null);
- } else {
- v = convertView;
- }
- int level = mItems[position].level;
- if (level > 8) level = 8;
- String space = "";
- for (int i=0; i<level;i++)
- space += " ";
- ((TextView)v.findViewById(R.id.title)).setText(space+mItems[position].title);
- ((TextView)v.findViewById(R.id.page)).setText(String.valueOf(mItems[position].page+1));
- return v;
- }
-
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineItem.java b/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineItem.java
deleted file mode 100644
index 0ed041c2..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/OutlineItem.java
+++ /dev/null
@@ -1,14 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class OutlineItem {
- public final int level;
- public final String title;
- public final int page;
-
- OutlineItem(int _level, String _title, int _page) {
- level = _level;
- title = _title;
- page = _page;
- }
-
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/PageView.java b/platform/android/viewer/src/com/artifex/mupdfdemo/PageView.java
deleted file mode 100644
index 5f5cc638..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/PageView.java
+++ /dev/null
@@ -1,697 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.os.Handler;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ImageView;
-import android.widget.ProgressBar;
-
-// Make our ImageViews opaque to optimize redraw
-class OpaqueImageView extends ImageView {
-
- public OpaqueImageView(Context context) {
- super(context);
- }
-
- @Override
- public boolean isOpaque() {
- return true;
- }
-}
-
-interface TextProcessor {
- void onStartLine();
- void onWord(TextWord word);
- void onEndLine();
-}
-
-class TextSelector {
- final private TextWord[][] mText;
- final private RectF mSelectBox;
-
- public TextSelector(TextWord[][] text, RectF selectBox) {
- mText = text;
- mSelectBox = selectBox;
- }
-
- public void select(TextProcessor tp) {
- if (mText == null || mSelectBox == null)
- return;
-
- ArrayList<TextWord[]> lines = new ArrayList<TextWord[]>();
- for (TextWord[] line : mText)
- if (line[0].bottom > mSelectBox.top && line[0].top < mSelectBox.bottom)
- lines.add(line);
-
- Iterator<TextWord[]> it = lines.iterator();
- while (it.hasNext()) {
- TextWord[] line = it.next();
- boolean firstLine = line[0].top < mSelectBox.top;
- boolean lastLine = line[0].bottom > mSelectBox.bottom;
- float start = Float.NEGATIVE_INFINITY;
- float end = Float.POSITIVE_INFINITY;
-
- if (firstLine && lastLine) {
- start = Math.min(mSelectBox.left, mSelectBox.right);
- end = Math.max(mSelectBox.left, mSelectBox.right);
- } else if (firstLine) {
- start = mSelectBox.left;
- } else if (lastLine) {
- end = mSelectBox.right;
- }
-
- tp.onStartLine();
-
- for (TextWord word : line)
- if (word.right > start && word.left < end)
- tp.onWord(word);
-
- tp.onEndLine();
- }
- }
-}
-
-public abstract class PageView extends ViewGroup {
- private static final int HIGHLIGHT_COLOR = 0x802572AC;
- private static final int LINK_COLOR = 0x80AC7225;
- private static final int BOX_COLOR = 0xFF4444FF;
- private static final int INK_COLOR = 0xFFFF0000;
- private static final float INK_THICKNESS = 10.0f;
- private static final int BACKGROUND_COLOR = 0xFFFFFFFF;
- private static final int PROGRESS_DIALOG_DELAY = 200;
- protected final Context mContext;
- protected int mPageNumber;
- private Point mParentSize;
- protected Point mSize; // Size of page at minimum zoom
- protected float mSourceScale;
-
- private ImageView mEntire; // Image rendered at minimum zoom
- private Bitmap mEntireBm;
- private Matrix mEntireMat;
- private AsyncTask<Void,Void,TextWord[][]> mGetText;
- private AsyncTask<Void,Void,LinkInfo[]> mGetLinkInfo;
- private CancellableAsyncTask<Void, Void> mDrawEntire;
-
- private Point mPatchViewSize; // View size on the basis of which the patch was created
- private Rect mPatchArea;
- private ImageView mPatch;
- private Bitmap mPatchBm;
- private CancellableAsyncTask<Void,Void> mDrawPatch;
- private RectF mSearchBoxes[];
- protected LinkInfo mLinks[];
- private RectF mSelectBox;
- private TextWord mText[][];
- private RectF mItemSelectBox;
- protected ArrayList<ArrayList<PointF>> mDrawing;
- private View mSearchView;
- private boolean mIsBlank;
- private boolean mHighlightLinks;
-
- private ProgressBar mBusyIndicator;
- private final Handler mHandler = new Handler();
-
- public PageView(Context c, Point parentSize, Bitmap sharedHqBm) {
- super(c);
- mContext = c;
- mParentSize = parentSize;
- setBackgroundColor(BACKGROUND_COLOR);
- mEntireBm = Bitmap.createBitmap(parentSize.x, parentSize.y, Config.ARGB_8888);
- mPatchBm = sharedHqBm;
- mEntireMat = new Matrix();
- }
-
- protected abstract CancellableTaskDefinition<Void, Void> getDrawPageTask(Bitmap bm, int sizeX, int sizeY, int patchX, int patchY, int patchWidth, int patchHeight);
- protected abstract CancellableTaskDefinition<Void, Void> getUpdatePageTask(Bitmap bm, int sizeX, int sizeY, int patchX, int patchY, int patchWidth, int patchHeight);
- protected abstract LinkInfo[] getLinkInfo();
- protected abstract TextWord[][] getText();
- protected abstract void addMarkup(PointF[] quadPoints, Annotation.Type type);
-
- private void reinit() {
- // Cancel pending render task
- if (mDrawEntire != null) {
- mDrawEntire.cancel();
- mDrawEntire = null;
- }
-
- if (mDrawPatch != null) {
- mDrawPatch.cancel();
- mDrawPatch = null;
- }
-
- if (mGetLinkInfo != null) {
- mGetLinkInfo.cancel(true);
- mGetLinkInfo = null;
- }
-
- if (mGetText != null) {
- mGetText.cancel(true);
- mGetText = null;
- }
-
- mIsBlank = true;
- mPageNumber = 0;
-
- if (mSize == null)
- mSize = mParentSize;
-
- if (mEntire != null) {
- mEntire.setImageBitmap(null);
- mEntire.invalidate();
- }
-
- if (mPatch != null) {
- mPatch.setImageBitmap(null);
- mPatch.invalidate();
- }
-
- mPatchViewSize = null;
- mPatchArea = null;
-
- mSearchBoxes = null;
- mLinks = null;
- mSelectBox = null;
- mText = null;
- mItemSelectBox = null;
- }
-
- public void releaseResources() {
- reinit();
-
- if (mBusyIndicator != null) {
- removeView(mBusyIndicator);
- mBusyIndicator = null;
- }
- }
-
- public void releaseBitmaps() {
- reinit();
-
- // recycle bitmaps before releasing them.
-
- if (mEntireBm!=null)
- mEntireBm.recycle();
- mEntireBm = null;
-
- if (mPatchBm!=null)
- mPatchBm.recycle();
- mPatchBm = null;
- }
-
- public void blank(int page) {
- reinit();
- mPageNumber = page;
-
- if (mBusyIndicator == null) {
- mBusyIndicator = new ProgressBar(mContext);
- mBusyIndicator.setIndeterminate(true);
- mBusyIndicator.setBackgroundResource(R.drawable.busy);
- addView(mBusyIndicator);
- }
-
- setBackgroundColor(BACKGROUND_COLOR);
- }
-
- public void setPage(int page, PointF size) {
- // Cancel pending render task
- if (mDrawEntire != null) {
- mDrawEntire.cancel();
- mDrawEntire = null;
- }
-
- mIsBlank = false;
- // Highlights may be missing because mIsBlank was true on last draw
- if (mSearchView != null)
- mSearchView.invalidate();
-
- mPageNumber = page;
- if (mEntire == null) {
- mEntire = new OpaqueImageView(mContext);
- mEntire.setScaleType(ImageView.ScaleType.MATRIX);
- addView(mEntire);
- }
-
- // Calculate scaled size that fits within the screen limits
- // This is the size at minimum zoom
- mSourceScale = Math.min(mParentSize.x/size.x, mParentSize.y/size.y);
- Point newSize = new Point((int)(size.x*mSourceScale), (int)(size.y*mSourceScale));
- mSize = newSize;
-
- mEntire.setImageBitmap(null);
- mEntire.invalidate();
-
- // Get the link info in the background
- mGetLinkInfo = new AsyncTask<Void,Void,LinkInfo[]>() {
- protected LinkInfo[] doInBackground(Void... v) {
- return getLinkInfo();
- }
-
- protected void onPostExecute(LinkInfo[] v) {
- mLinks = v;
- if (mSearchView != null)
- mSearchView.invalidate();
- }
- };
-
- mGetLinkInfo.execute();
-
- // Render the page in the background
- mDrawEntire = new CancellableAsyncTask<Void, Void>(getDrawPageTask(mEntireBm, mSize.x, mSize.y, 0, 0, mSize.x, mSize.y)) {
-
- @Override
- public void onPreExecute() {
- setBackgroundColor(BACKGROUND_COLOR);
- mEntire.setImageBitmap(null);
- mEntire.invalidate();
-
- if (mBusyIndicator == null) {
- mBusyIndicator = new ProgressBar(mContext);
- mBusyIndicator.setIndeterminate(true);
- mBusyIndicator.setBackgroundResource(R.drawable.busy);
- addView(mBusyIndicator);
- mBusyIndicator.setVisibility(INVISIBLE);
- mHandler.postDelayed(new Runnable() {
- public void run() {
- if (mBusyIndicator != null)
- mBusyIndicator.setVisibility(VISIBLE);
- }
- }, PROGRESS_DIALOG_DELAY);
- }
- }
-
- @Override
- public void onPostExecute(Void result) {
- removeView(mBusyIndicator);
- mBusyIndicator = null;
- mEntire.setImageBitmap(mEntireBm);
- mEntire.invalidate();
- setBackgroundColor(Color.TRANSPARENT);
-
- }
- };
-
- mDrawEntire.execute();
-
- if (mSearchView == null) {
- mSearchView = new View(mContext) {
- @Override
- protected void onDraw(final Canvas canvas) {
- super.onDraw(canvas);
- // Work out current total scale factor
- // from source to view
- final float scale = mSourceScale*(float)getWidth()/(float)mSize.x;
- final Paint paint = new Paint();
-
- if (!mIsBlank && mSearchBoxes != null) {
- paint.setColor(HIGHLIGHT_COLOR);
- for (RectF rect : mSearchBoxes)
- canvas.drawRect(rect.left*scale, rect.top*scale,
- rect.right*scale, rect.bottom*scale,
- paint);
- }
-
- if (!mIsBlank && mLinks != null && mHighlightLinks) {
- paint.setColor(LINK_COLOR);
- for (LinkInfo link : mLinks)
- canvas.drawRect(link.rect.left*scale, link.rect.top*scale,
- link.rect.right*scale, link.rect.bottom*scale,
- paint);
- }
-
- if (mSelectBox != null && mText != null) {
- paint.setColor(HIGHLIGHT_COLOR);
- processSelectedText(new TextProcessor() {
- RectF rect;
-
- public void onStartLine() {
- rect = new RectF();
- }
-
- public void onWord(TextWord word) {
- rect.union(word);
- }
-
- public void onEndLine() {
- if (!rect.isEmpty())
- canvas.drawRect(rect.left*scale, rect.top*scale, rect.right*scale, rect.bottom*scale, paint);
- }
- });
- }
-
- if (mItemSelectBox != null) {
- paint.setStyle(Paint.Style.STROKE);
- paint.setColor(BOX_COLOR);
- canvas.drawRect(mItemSelectBox.left*scale, mItemSelectBox.top*scale, mItemSelectBox.right*scale, mItemSelectBox.bottom*scale, paint);
- }
-
- if (mDrawing != null) {
- Path path = new Path();
- PointF p;
-
- paint.setAntiAlias(true);
- paint.setDither(true);
- paint.setStrokeJoin(Paint.Join.ROUND);
- paint.setStrokeCap(Paint.Cap.ROUND);
-
- paint.setStyle(Paint.Style.FILL);
- paint.setStrokeWidth(INK_THICKNESS * scale);
- paint.setColor(INK_COLOR);
-
- Iterator<ArrayList<PointF>> it = mDrawing.iterator();
- while (it.hasNext()) {
- ArrayList<PointF> arc = it.next();
- if (arc.size() >= 2) {
- Iterator<PointF> iit = arc.iterator();
- p = iit.next();
- float mX = p.x * scale;
- float mY = p.y * scale;
- path.moveTo(mX, mY);
- while (iit.hasNext()) {
- p = iit.next();
- float x = p.x * scale;
- float y = p.y * scale;
- path.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
- mX = x;
- mY = y;
- }
- path.lineTo(mX, mY);
- } else {
- p = arc.get(0);
- canvas.drawCircle(p.x * scale, p.y * scale, INK_THICKNESS * scale / 2, paint);
- }
- }
-
- paint.setStyle(Paint.Style.STROKE);
- canvas.drawPath(path, paint);
- }
- }
- };
-
- addView(mSearchView);
- }
- requestLayout();
- }
-
- public void setSearchBoxes(RectF searchBoxes[]) {
- mSearchBoxes = searchBoxes;
- if (mSearchView != null)
- mSearchView.invalidate();
- }
-
- public void setLinkHighlighting(boolean f) {
- mHighlightLinks = f;
- if (mSearchView != null)
- mSearchView.invalidate();
- }
-
- public void deselectText() {
- mSelectBox = null;
- mSearchView.invalidate();
- }
-
- public void selectText(float x0, float y0, float x1, float y1) {
- float scale = mSourceScale*(float)getWidth()/(float)mSize.x;
- float docRelX0 = (x0 - getLeft())/scale;
- float docRelY0 = (y0 - getTop())/scale;
- float docRelX1 = (x1 - getLeft())/scale;
- float docRelY1 = (y1 - getTop())/scale;
- // Order on Y but maintain the point grouping
- if (docRelY0 <= docRelY1)
- mSelectBox = new RectF(docRelX0, docRelY0, docRelX1, docRelY1);
- else
- mSelectBox = new RectF(docRelX1, docRelY1, docRelX0, docRelY0);
-
- mSearchView.invalidate();
-
- if (mGetText == null) {
- mGetText = new AsyncTask<Void,Void,TextWord[][]>() {
- @Override
- protected TextWord[][] doInBackground(Void... params) {
- return getText();
- }
- @Override
- protected void onPostExecute(TextWord[][] result) {
- mText = result;
- mSearchView.invalidate();
- }
- };
-
- mGetText.execute();
- }
- }
-
- public void startDraw(float x, float y) {
- float scale = mSourceScale*(float)getWidth()/(float)mSize.x;
- float docRelX = (x - getLeft())/scale;
- float docRelY = (y - getTop())/scale;
- if (mDrawing == null)
- mDrawing = new ArrayList<ArrayList<PointF>>();
-
- ArrayList<PointF> arc = new ArrayList<PointF>();
- arc.add(new PointF(docRelX, docRelY));
- mDrawing.add(arc);
- mSearchView.invalidate();
- }
-
- public void continueDraw(float x, float y) {
- float scale = mSourceScale*(float)getWidth()/(float)mSize.x;
- float docRelX = (x - getLeft())/scale;
- float docRelY = (y - getTop())/scale;
-
- if (mDrawing != null && mDrawing.size() > 0) {
- ArrayList<PointF> arc = mDrawing.get(mDrawing.size() - 1);
- arc.add(new PointF(docRelX, docRelY));
- mSearchView.invalidate();
- }
- }
-
- public void cancelDraw() {
- mDrawing = null;
- mSearchView.invalidate();
- }
-
- protected PointF[][] getDraw() {
- if (mDrawing == null)
- return null;
-
- PointF[][] path = new PointF[mDrawing.size()][];
-
- for (int i = 0; i < mDrawing.size(); i++) {
- ArrayList<PointF> arc = mDrawing.get(i);
- path[i] = arc.toArray(new PointF[arc.size()]);
- }
-
- return path;
- }
-
- protected void processSelectedText(TextProcessor tp) {
- (new TextSelector(mText, mSelectBox)).select(tp);
- }
-
- public void setItemSelectBox(RectF rect) {
- mItemSelectBox = rect;
- if (mSearchView != null)
- mSearchView.invalidate();
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- int x, y;
- switch(View.MeasureSpec.getMode(widthMeasureSpec)) {
- case View.MeasureSpec.UNSPECIFIED:
- x = mSize.x;
- break;
- default:
- x = View.MeasureSpec.getSize(widthMeasureSpec);
- }
- switch(View.MeasureSpec.getMode(heightMeasureSpec)) {
- case View.MeasureSpec.UNSPECIFIED:
- y = mSize.y;
- break;
- default:
- y = View.MeasureSpec.getSize(heightMeasureSpec);
- }
-
- setMeasuredDimension(x, y);
-
- if (mBusyIndicator != null) {
- int limit = Math.min(mParentSize.x, mParentSize.y)/2;
- mBusyIndicator.measure(View.MeasureSpec.AT_MOST | limit, View.MeasureSpec.AT_MOST | limit);
- }
- }
-
- @Override
- protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
- int w = right-left;
- int h = bottom-top;
-
- if (mEntire != null) {
- if (mEntire.getWidth() != w || mEntire.getHeight() != h) {
- mEntireMat.setScale(w/(float)mSize.x, h/(float)mSize.y);
- mEntire.setImageMatrix(mEntireMat);
- mEntire.invalidate();
- }
- mEntire.layout(0, 0, w, h);
- }
-
- if (mSearchView != null) {
- mSearchView.layout(0, 0, w, h);
- }
-
- if (mPatchViewSize != null) {
- if (mPatchViewSize.x != w || mPatchViewSize.y != h) {
- // Zoomed since patch was created
- mPatchViewSize = null;
- mPatchArea = null;
- if (mPatch != null) {
- mPatch.setImageBitmap(null);
- mPatch.invalidate();
- }
- } else {
- mPatch.layout(mPatchArea.left, mPatchArea.top, mPatchArea.right, mPatchArea.bottom);
- }
- }
-
- if (mBusyIndicator != null) {
- int bw = mBusyIndicator.getMeasuredWidth();
- int bh = mBusyIndicator.getMeasuredHeight();
-
- mBusyIndicator.layout((w-bw)/2, (h-bh)/2, (w+bw)/2, (h+bh)/2);
- }
- }
-
- public void updateHq(boolean update) {
- Rect viewArea = new Rect(getLeft(),getTop(),getRight(),getBottom());
- if (viewArea.width() == mSize.x || viewArea.height() == mSize.y) {
- // If the viewArea's size matches the unzoomed size, there is no need for an hq patch
- if (mPatch != null) {
- mPatch.setImageBitmap(null);
- mPatch.invalidate();
- }
- } else {
- final Point patchViewSize = new Point(viewArea.width(), viewArea.height());
- final Rect patchArea = new Rect(0, 0, mParentSize.x, mParentSize.y);
-
- // Intersect and test that there is an intersection
- if (!patchArea.intersect(viewArea))
- return;
-
- // Offset patch area to be relative to the view top left
- patchArea.offset(-viewArea.left, -viewArea.top);
-
- boolean area_unchanged = patchArea.equals(mPatchArea) && patchViewSize.equals(mPatchViewSize);
-
- // If being asked for the same area as last time and not because of an update then nothing to do
- if (area_unchanged && !update)
- return;
-
- boolean completeRedraw = !(area_unchanged && update);
-
- // Stop the drawing of previous patch if still going
- if (mDrawPatch != null) {
- mDrawPatch.cancel();
- mDrawPatch = null;
- }
-
- // Create and add the image view if not already done
- if (mPatch == null) {
- mPatch = new OpaqueImageView(mContext);
- mPatch.setScaleType(ImageView.ScaleType.MATRIX);
- addView(mPatch);
- mSearchView.bringToFront();
- }
-
- CancellableTaskDefinition<Void, Void> task;
-
- if (completeRedraw)
- task = getDrawPageTask(mPatchBm, patchViewSize.x, patchViewSize.y,
- patchArea.left, patchArea.top,
- patchArea.width(), patchArea.height());
- else
- task = getUpdatePageTask(mPatchBm, patchViewSize.x, patchViewSize.y,
- patchArea.left, patchArea.top,
- patchArea.width(), patchArea.height());
-
- mDrawPatch = new CancellableAsyncTask<Void,Void>(task) {
-
- public void onPostExecute(Void result) {
- mPatchViewSize = patchViewSize;
- mPatchArea = patchArea;
- mPatch.setImageBitmap(mPatchBm);
- mPatch.invalidate();
- //requestLayout();
- // Calling requestLayout here doesn't lead to a later call to layout. No idea
- // why, but apparently others have run into the problem.
- mPatch.layout(mPatchArea.left, mPatchArea.top, mPatchArea.right, mPatchArea.bottom);
- }
- };
-
- mDrawPatch.execute();
- }
- }
-
- public void update() {
- // Cancel pending render task
- if (mDrawEntire != null) {
- mDrawEntire.cancel();
- mDrawEntire = null;
- }
-
- if (mDrawPatch != null) {
- mDrawPatch.cancel();
- mDrawPatch = null;
- }
-
- // Render the page in the background
- mDrawEntire = new CancellableAsyncTask<Void, Void>(getUpdatePageTask(mEntireBm, mSize.x, mSize.y, 0, 0, mSize.x, mSize.y)) {
-
- public void onPostExecute(Void result) {
- mEntire.setImageBitmap(mEntireBm);
- mEntire.invalidate();
- }
- };
-
- mDrawEntire.execute();
-
- updateHq(true);
- }
-
- public void removeHq() {
- // Stop the drawing of the patch if still going
- if (mDrawPatch != null) {
- mDrawPatch.cancel();
- mDrawPatch = null;
- }
-
- // And get rid of it
- mPatchViewSize = null;
- mPatchArea = null;
- if (mPatch != null) {
- mPatch.setImageBitmap(null);
- mPatch.invalidate();
- }
- }
-
- public int getPage() {
- return mPageNumber;
- }
-
- @Override
- public boolean isOpaque() {
- return true;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/PrintDialogActivity.java b/platform/android/viewer/src/com/artifex/mupdfdemo/PrintDialogActivity.java
deleted file mode 100644
index d96322d5..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/PrintDialogActivity.java
+++ /dev/null
@@ -1,145 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.io.ByteArrayOutputStream;
-import java.io.InputStream;
-
-import android.app.Activity;
-import android.content.ActivityNotFoundException;
-import android.content.ContentResolver;
-import android.content.Intent;
-import android.os.Bundle;
-import android.util.Base64;
-import android.webkit.WebSettings;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
-
-public class PrintDialogActivity extends Activity {
- private static final String PRINT_DIALOG_URL = "https://www.google.com/cloudprint/dialog.html";
- private static final String JS_INTERFACE = "AndroidPrintDialog";
- private static final String CONTENT_TRANSFER_ENCODING = "base64";
-
- private static final String ZXING_URL = "http://zxing.appspot.com";
- private static final int ZXING_SCAN_REQUEST = 65743;
-
- /**
- * Post message that is sent by Print Dialog web page when the printing dialog
- * needs to be closed.
- */
- private static final String CLOSE_POST_MESSAGE_NAME = "cp-dialog-on-close";
-
- /**
- * Web view element to show the printing dialog in.
- */
- private WebView dialogWebView;
-
- /**
- * Intent that started the action.
- */
- Intent cloudPrintIntent;
-
- private int resultCode;
-
- @Override
- public void onCreate(Bundle icicle) {
- super.onCreate(icicle);
-
- resultCode = RESULT_OK;
- setContentView(R.layout.print_dialog);
- dialogWebView = (WebView) findViewById(R.id.webview);
- cloudPrintIntent = this.getIntent();
-
- WebSettings settings = dialogWebView.getSettings();
- settings.setJavaScriptEnabled(true);
-
- dialogWebView.setWebViewClient(new PrintDialogWebClient());
- dialogWebView.addJavascriptInterface(
- new PrintDialogJavaScriptInterface(), JS_INTERFACE);
-
- dialogWebView.loadUrl(PRINT_DIALOG_URL);
- }
-
- @Override
- public void onActivityResult(int requestCode, int resultCode, Intent intent) {
- if (requestCode == ZXING_SCAN_REQUEST && resultCode == RESULT_OK) {
- dialogWebView.loadUrl(intent.getStringExtra("SCAN_RESULT"));
- }
- }
-
- final class PrintDialogJavaScriptInterface {
- public String getType() {
- return cloudPrintIntent.getType();
- }
-
- public String getTitle() {
- return cloudPrintIntent.getExtras().getString("title");
- }
-
- public String getContent() {
- try {
- ContentResolver contentResolver = getContentResolver();
- InputStream is = contentResolver.openInputStream(cloudPrintIntent.getData());
- ByteArrayOutputStream baos = new ByteArrayOutputStream();
-
- byte[] buffer = new byte[4096];
- int n = is.read(buffer);
- while (n >= 0) {
- baos.write(buffer, 0, n);
- n = is.read(buffer);
- }
- is.close();
- baos.flush();
-
- return Base64.encodeToString(baos.toByteArray(), Base64.DEFAULT);
- } catch (Throwable e) {
- resultCode = RESULT_CANCELED;
- setResult(resultCode);
- finish();
- e.printStackTrace();
- }
- return "";
- }
-
- public String getEncoding() {
- return CONTENT_TRANSFER_ENCODING;
- }
-
- public void onPostMessage(String message) {
- if (message.startsWith(CLOSE_POST_MESSAGE_NAME)) {
- setResult(resultCode);
- finish();
- }
- }
- }
-
- private final class PrintDialogWebClient extends WebViewClient {
- @Override
- public boolean shouldOverrideUrlLoading(WebView view, String url) {
- if (url.startsWith(ZXING_URL)) {
- Intent intentScan = new Intent("com.google.zxing.client.android.SCAN");
- intentScan.putExtra("SCAN_MODE", "QR_CODE_MODE");
- try {
- startActivityForResult(intentScan, ZXING_SCAN_REQUEST);
- } catch (ActivityNotFoundException error) {
- view.loadUrl(url);
- }
- } else {
- view.loadUrl(url);
- }
- return false;
- }
-
- @Override
- public void onPageFinished(WebView view, String url) {
- if (PRINT_DIALOG_URL.equals(url)) {
- // Submit print document.
- view.loadUrl("javascript:printDialog.setPrintDocument(printDialog.createPrintDocument("
- + "window." + JS_INTERFACE + ".getType(),window." + JS_INTERFACE + ".getTitle(),"
- + "window." + JS_INTERFACE + ".getContent(),window." + JS_INTERFACE + ".getEncoding()))");
-
- // Add post messages listener.
- view.loadUrl("javascript:window.addEventListener('message',"
- + "function(evt){window." + JS_INTERFACE + ".onPostMessage(evt.data)}, false)");
- }
- }
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/ReaderView.java b/platform/android/viewer/src/com/artifex/mupdfdemo/ReaderView.java
deleted file mode 100644
index afcd077f..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/ReaderView.java
+++ /dev/null
@@ -1,936 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import java.util.LinkedList;
-import java.util.NoSuchElementException;
-
-import android.app.Activity;
-import android.app.ActivityManager;
-import android.app.AlertDialog;
-import android.content.DialogInterface;
-
-import android.content.Context;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.util.AttributeSet;
-import android.util.SparseArray;
-import android.view.GestureDetector;
-import android.view.MotionEvent;
-import android.view.ScaleGestureDetector;
-import android.view.View;
-import android.widget.Adapter;
-import android.widget.AdapterView;
-import android.widget.Scroller;
-
-public class ReaderView
- extends AdapterView<Adapter>
- implements GestureDetector.OnGestureListener, ScaleGestureDetector.OnScaleGestureListener, Runnable {
- private static final int MOVING_DIAGONALLY = 0;
- private static final int MOVING_LEFT = 1;
- private static final int MOVING_RIGHT = 2;
- private static final int MOVING_UP = 3;
- private static final int MOVING_DOWN = 4;
-
- private static final int FLING_MARGIN = 100;
- private static final int GAP = 20;
-
- private static final float MIN_SCALE = 1.0f;
- private static final float MAX_SCALE = 64.0f;
- private static final float REFLOW_SCALE_FACTOR = 0.5f;
-
- private static final boolean HORIZONTAL_SCROLLING = true;
-
- private Adapter mAdapter;
- private int mCurrent; // Adapter's index for the current view
- private boolean mResetLayout;
- private final SparseArray<View>
- mChildViews = new SparseArray<View>(3);
- // Shadows the children of the adapter view
- // but with more sensible indexing
- private final LinkedList<View>
- mViewCache = new LinkedList<View>();
- private boolean mUserInteracting; // Whether the user is interacting
- private boolean mScaling; // Whether the user is currently pinch zooming
- private float mScale = 1.0f;
- private int mXScroll; // Scroll amounts recorded from events.
- private int mYScroll; // and then accounted for in onLayout
- private boolean mReflow = false;
- private boolean mReflowChanged = false;
- private final GestureDetector
- mGestureDetector;
- private final ScaleGestureDetector
- mScaleGestureDetector;
- private final Scroller mScroller;
- private final Stepper mStepper;
- private int mScrollerLastX;
- private int mScrollerLastY;
- private float mLastScaleFocusX;
- private float mLastScaleFocusY;
-
- static abstract class ViewMapper {
- abstract void applyToView(View view);
- }
-
- public ReaderView(Context context) {
- super(context);
- mGestureDetector = new GestureDetector(this);
- mScaleGestureDetector = new ScaleGestureDetector(context, this);
- mScroller = new Scroller(context);
- mStepper = new Stepper(this, this);
- }
-
- public ReaderView(Context context, AttributeSet attrs) {
- super(context, attrs);
-
- // "Edit mode" means when the View is being displayed in the Android GUI editor. (this class
- // is instantiated in the IDE, so we need to be a bit careful what we do).
- if (isInEditMode())
- {
- mGestureDetector = null;
- mScaleGestureDetector = null;
- mScroller = null;
- mStepper = null;
- }
- else
- {
- mGestureDetector = new GestureDetector(this);
- mScaleGestureDetector = new ScaleGestureDetector(context, this);
- mScroller = new Scroller(context);
- mStepper = new Stepper(this, this);
- }
- }
-
- public ReaderView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- mGestureDetector = new GestureDetector(this);
- mScaleGestureDetector = new ScaleGestureDetector(context, this);
- mScroller = new Scroller(context);
- mStepper = new Stepper(this, this);
- }
-
- public int getDisplayedViewIndex() {
- return mCurrent;
- }
-
- public void setDisplayedViewIndex(int i) {
- if (0 <= i && i < mAdapter.getCount()) {
- onMoveOffChild(mCurrent);
- mCurrent = i;
- onMoveToChild(i);
- mResetLayout = true;
- requestLayout();
- }
- }
-
- public void moveToNext() {
- View v = mChildViews.get(mCurrent+1);
- if (v != null)
- slideViewOntoScreen(v);
- }
-
- public void moveToPrevious() {
- View v = mChildViews.get(mCurrent-1);
- if (v != null)
- slideViewOntoScreen(v);
- }
-
- // When advancing down the page, we want to advance by about
- // 90% of a screenful. But we'd be happy to advance by between
- // 80% and 95% if it means we hit the bottom in a whole number
- // of steps.
- private int smartAdvanceAmount(int screenHeight, int max) {
- int advance = (int)(screenHeight * 0.9 + 0.5);
- int leftOver = max % advance;
- int steps = max / advance;
- if (leftOver == 0) {
- // We'll make it exactly. No adjustment
- } else if ((float)leftOver / steps <= screenHeight * 0.05) {
- // We can adjust up by less than 5% to make it exact.
- advance += (int)((float)leftOver/steps + 0.5);
- } else {
- int overshoot = advance - leftOver;
- if ((float)overshoot / steps <= screenHeight * 0.1) {
- // We can adjust down by less than 10% to make it exact.
- advance -= (int)((float)overshoot/steps + 0.5);
- }
- }
- if (advance > max)
- advance = max;
- return advance;
- }
-
- public void smartMoveForwards() {
- View v = mChildViews.get(mCurrent);
- if (v == null)
- return;
-
- // The following code works in terms of where the screen is on the views;
- // so for example, if the currentView is at (-100,-100), the visible
- // region would be at (100,100). If the previous page was (2000, 3000) in
- // size, the visible region of the previous page might be (2100 + GAP, 100)
- // (i.e. off the previous page). This is different to the way the rest of
- // the code in this file is written, but it's easier for me to think about.
- // At some point we may refactor this to fit better with the rest of the
- // code.
-
- // screenWidth/Height are the actual width/height of the screen. e.g. 480/800
- int screenWidth = getWidth();
- int screenHeight = getHeight();
- // We might be mid scroll; we want to calculate where we scroll to based on
- // where this scroll would end, not where we are now (to allow for people
- // bashing 'forwards' very fast.
- int remainingX = mScroller.getFinalX() - mScroller.getCurrX();
- int remainingY = mScroller.getFinalY() - mScroller.getCurrY();
- // right/bottom is in terms of pixels within the scaled document; e.g. 1000
- int top = -(v.getTop() + mYScroll + remainingY);
- int right = screenWidth -(v.getLeft() + mXScroll + remainingX);
- int bottom = screenHeight+top;
- // docWidth/Height are the width/height of the scaled document e.g. 2000x3000
- int docWidth = v.getMeasuredWidth();
- int docHeight = v.getMeasuredHeight();
-
- int xOffset, yOffset;
- if (bottom >= docHeight) {
- // We are flush with the bottom. Advance to next column.
- if (right + screenWidth > docWidth) {
- // No room for another column - go to next page
- View nv = mChildViews.get(mCurrent+1);
- if (nv == null) // No page to advance to
- return;
- int nextTop = -(nv.getTop() + mYScroll + remainingY);
- int nextLeft = -(nv.getLeft() + mXScroll + remainingX);
- int nextDocWidth = nv.getMeasuredWidth();
- int nextDocHeight = nv.getMeasuredHeight();
-
- // Allow for the next page maybe being shorter than the screen is high
- yOffset = (nextDocHeight < screenHeight ? ((nextDocHeight - screenHeight)>>1) : 0);
-
- if (nextDocWidth < screenWidth) {
- // Next page is too narrow to fill the screen. Scroll to the top, centred.
- xOffset = (nextDocWidth - screenWidth)>>1;
- } else {
- // Reset X back to the left hand column
- xOffset = right % screenWidth;
- // Adjust in case the previous page is less wide
- if (xOffset + screenWidth > nextDocWidth)
- xOffset = nextDocWidth - screenWidth;
- }
- xOffset -= nextLeft;
- yOffset -= nextTop;
- } else {
- // Move to top of next column
- xOffset = screenWidth;
- yOffset = screenHeight - bottom;
- }
- } else {
- // Advance by 90% of the screen height downwards (in case lines are partially cut off)
- xOffset = 0;
- yOffset = smartAdvanceAmount(screenHeight, docHeight - bottom);
- }
- mScrollerLastX = mScrollerLastY = 0;
- mScroller.startScroll(0, 0, remainingX - xOffset, remainingY - yOffset, 400);
- mStepper.prod();
- }
-
- public void smartMoveBackwards() {
- View v = mChildViews.get(mCurrent);
- if (v == null)
- return;
-
- // The following code works in terms of where the screen is on the views;
- // so for example, if the currentView is at (-100,-100), the visible
- // region would be at (100,100). If the previous page was (2000, 3000) in
- // size, the visible region of the previous page might be (2100 + GAP, 100)
- // (i.e. off the previous page). This is different to the way the rest of
- // the code in this file is written, but it's easier for me to think about.
- // At some point we may refactor this to fit better with the rest of the
- // code.
-
- // screenWidth/Height are the actual width/height of the screen. e.g. 480/800
- int screenWidth = getWidth();
- int screenHeight = getHeight();
- // We might be mid scroll; we want to calculate where we scroll to based on
- // where this scroll would end, not where we are now (to allow for people
- // bashing 'forwards' very fast.
- int remainingX = mScroller.getFinalX() - mScroller.getCurrX();
- int remainingY = mScroller.getFinalY() - mScroller.getCurrY();
- // left/top is in terms of pixels within the scaled document; e.g. 1000
- int left = -(v.getLeft() + mXScroll + remainingX);
- int top = -(v.getTop() + mYScroll + remainingY);
- // docWidth/Height are the width/height of the scaled document e.g. 2000x3000
- int docHeight = v.getMeasuredHeight();
-
- int xOffset, yOffset;
- if (top <= 0) {
- // We are flush with the top. Step back to previous column.
- if (left < screenWidth) {
- /* No room for previous column - go to previous page */
- View pv = mChildViews.get(mCurrent-1);
- if (pv == null) /* No page to advance to */
- return;
- int prevDocWidth = pv.getMeasuredWidth();
- int prevDocHeight = pv.getMeasuredHeight();
-
- // Allow for the next page maybe being shorter than the screen is high
- yOffset = (prevDocHeight < screenHeight ? ((prevDocHeight - screenHeight)>>1) : 0);
-
- int prevLeft = -(pv.getLeft() + mXScroll);
- int prevTop = -(pv.getTop() + mYScroll);
- if (prevDocWidth < screenWidth) {
- // Previous page is too narrow to fill the screen. Scroll to the bottom, centred.
- xOffset = (prevDocWidth - screenWidth)>>1;
- } else {
- // Reset X back to the right hand column
- xOffset = (left > 0 ? left % screenWidth : 0);
- if (xOffset + screenWidth > prevDocWidth)
- xOffset = prevDocWidth - screenWidth;
- while (xOffset + screenWidth*2 < prevDocWidth)
- xOffset += screenWidth;
- }
- xOffset -= prevLeft;
- yOffset -= prevTop-prevDocHeight+screenHeight;
- } else {
- // Move to bottom of previous column
- xOffset = -screenWidth;
- yOffset = docHeight - screenHeight + top;
- }
- } else {
- // Retreat by 90% of the screen height downwards (in case lines are partially cut off)
- xOffset = 0;
- yOffset = -smartAdvanceAmount(screenHeight, top);
- }
- mScrollerLastX = mScrollerLastY = 0;
- mScroller.startScroll(0, 0, remainingX - xOffset, remainingY - yOffset, 400);
- mStepper.prod();
- }
-
- public void resetupChildren() {
- for (int i = 0; i < mChildViews.size(); i++)
- onChildSetup(mChildViews.keyAt(i), mChildViews.valueAt(i));
- }
-
- public void applyToChildren(ViewMapper mapper) {
- for (int i = 0; i < mChildViews.size(); i++)
- mapper.applyToView(mChildViews.valueAt(i));
- }
-
- public void refresh(boolean reflow) {
- mReflow = reflow;
- mReflowChanged = true;
- mResetLayout = true;
-
- mScale = 1.0f;
- mXScroll = mYScroll = 0;
-
- requestLayout();
- }
-
- protected void onChildSetup(int i, View v) {}
-
- protected void onMoveToChild(int i) {}
-
- protected void onMoveOffChild(int i) {}
-
- protected void onSettle(View v) {};
-
- protected void onUnsettle(View v) {};
-
- protected void onNotInUse(View v) {};
-
- protected void onScaleChild(View v, Float scale) {};
-
- public View getView(int i) {
- return mChildViews.get(i);
- }
-
- public View getDisplayedView() {
- return mChildViews.get(mCurrent);
- }
-
- public void run() {
- if (!mScroller.isFinished()) {
- mScroller.computeScrollOffset();
- int x = mScroller.getCurrX();
- int y = mScroller.getCurrY();
- mXScroll += x - mScrollerLastX;
- mYScroll += y - mScrollerLastY;
- mScrollerLastX = x;
- mScrollerLastY = y;
- requestLayout();
- mStepper.prod();
- }
- else if (!mUserInteracting) {
- // End of an inertial scroll and the user is not interacting.
- // The layout is stable
- View v = mChildViews.get(mCurrent);
- if (v != null)
- postSettle(v);
- }
- }
-
- public boolean onDown(MotionEvent arg0) {
- mScroller.forceFinished(true);
- return true;
- }
-
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
- float velocityY) {
- if (mScaling)
- return true;
-
- View v = mChildViews.get(mCurrent);
- if (v != null) {
- Rect bounds = getScrollBounds(v);
- switch(directionOfTravel(velocityX, velocityY)) {
- case MOVING_LEFT:
- if (HORIZONTAL_SCROLLING && bounds.left >= 0) {
- // Fling off to the left bring next view onto screen
- View vl = mChildViews.get(mCurrent+1);
-
- if (vl != null) {
- slideViewOntoScreen(vl);
- return true;
- }
- }
- break;
- case MOVING_UP:
- if (!HORIZONTAL_SCROLLING && bounds.top >= 0) {
- // Fling off to the top bring next view onto screen
- View vl = mChildViews.get(mCurrent+1);
-
- if (vl != null) {
- slideViewOntoScreen(vl);
- return true;
- }
- }
- break;
- case MOVING_RIGHT:
- if (HORIZONTAL_SCROLLING && bounds.right <= 0) {
- // Fling off to the right bring previous view onto screen
- View vr = mChildViews.get(mCurrent-1);
-
- if (vr != null) {
- slideViewOntoScreen(vr);
- return true;
- }
- }
- break;
- case MOVING_DOWN:
- if (!HORIZONTAL_SCROLLING && bounds.bottom <= 0) {
- // Fling off to the bottom bring previous view onto screen
- View vr = mChildViews.get(mCurrent-1);
-
- if (vr != null) {
- slideViewOntoScreen(vr);
- return true;
- }
- }
- break;
- }
- mScrollerLastX = mScrollerLastY = 0;
- // If the page has been dragged out of bounds then we want to spring back
- // nicely. fling jumps back into bounds instantly, so we don't want to use
- // fling in that case. On the other hand, we don't want to forgo a fling
- // just because of a slightly off-angle drag taking us out of bounds other
- // than in the direction of the drag, so we test for out of bounds only
- // in the direction of travel.
- //
- // Also don't fling if out of bounds in any direction by more than fling
- // margin
- Rect expandedBounds = new Rect(bounds);
- expandedBounds.inset(-FLING_MARGIN, -FLING_MARGIN);
-
- if(withinBoundsInDirectionOfTravel(bounds, velocityX, velocityY)
- && expandedBounds.contains(0, 0)) {
- mScroller.fling(0, 0, (int)velocityX, (int)velocityY, bounds.left, bounds.right, bounds.top, bounds.bottom);
- mStepper.prod();
- }
- }
-
- return true;
- }
-
- public void onLongPress(MotionEvent e) {
- }
-
- public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX,
- float distanceY) {
- if (!mScaling) {
- mXScroll -= distanceX;
- mYScroll -= distanceY;
- requestLayout();
- }
- return true;
- }
-
- public void onShowPress(MotionEvent e) {
- }
-
- public boolean onSingleTapUp(MotionEvent e) {
- return false;
- }
-
- public boolean onScale(ScaleGestureDetector detector) {
- float previousScale = mScale;
- float scale_factor = mReflow ? REFLOW_SCALE_FACTOR : 1.0f;
- float min_scale = MIN_SCALE * scale_factor;
- float max_scale = MAX_SCALE * scale_factor;
- mScale = Math.min(Math.max(mScale * detector.getScaleFactor(), min_scale), max_scale);
-
- if (mReflow) {
- View v = mChildViews.get(mCurrent);
- if (v != null)
- onScaleChild(v, mScale);
- } else {
- float factor = mScale/previousScale;
-
- View v = mChildViews.get(mCurrent);
- if (v != null) {
- float currentFocusX = detector.getFocusX();
- float currentFocusY = detector.getFocusY();
- // Work out the focus point relative to the view top left
- int viewFocusX = (int)currentFocusX - (v.getLeft() + mXScroll);
- int viewFocusY = (int)currentFocusY - (v.getTop() + mYScroll);
- // Scroll to maintain the focus point
- mXScroll += viewFocusX - viewFocusX * factor;
- mYScroll += viewFocusY - viewFocusY * factor;
-
- if (mLastScaleFocusX>=0)
- mXScroll+=currentFocusX-mLastScaleFocusX;
- if (mLastScaleFocusY>=0)
- mYScroll+=currentFocusY-mLastScaleFocusY;
-
- mLastScaleFocusX=currentFocusX;
- mLastScaleFocusY=currentFocusY;
- requestLayout();
- }
- }
- return true;
- }
-
- public boolean onScaleBegin(ScaleGestureDetector detector) {
- mScaling = true;
- // Ignore any scroll amounts yet to be accounted for: the
- // screen is not showing the effect of them, so they can
- // only confuse the user
- mXScroll = mYScroll = 0;
- mLastScaleFocusX = mLastScaleFocusY = -1;
- return true;
- }
-
- public void onScaleEnd(ScaleGestureDetector detector) {
- if (mReflow) {
- applyToChildren(new ViewMapper() {
- @Override
- void applyToView(View view) {
- onScaleChild(view, mScale);
- }
- });
- }
- mScaling = false;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- mScaleGestureDetector.onTouchEvent(event);
- mGestureDetector.onTouchEvent(event);
-
- if ((event.getAction() & MotionEvent.ACTION_MASK) == MotionEvent.ACTION_DOWN) {
- mUserInteracting = true;
- }
- if ((event.getAction() & MotionEvent.ACTION_MASK) == MotionEvent.ACTION_UP) {
- mUserInteracting = false;
-
- View v = mChildViews.get(mCurrent);
- if (v != null) {
- if (mScroller.isFinished()) {
- // If, at the end of user interaction, there is no
- // current inertial scroll in operation then animate
- // the view onto screen if necessary
- slideViewOntoScreen(v);
- }
-
- if (mScroller.isFinished()) {
- // If still there is no inertial scroll in operation
- // then the layout is stable
- postSettle(v);
- }
- }
- }
-
- requestLayout();
- return true;
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-
- int n = getChildCount();
- for (int i = 0; i < n; i++)
- measureView(getChildAt(i));
- }
-
- @Override
- protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
- super.onLayout(changed, left, top, right, bottom);
-
- try {
- onLayout2(changed, left, top, right, bottom);
- }
- catch (java.lang.OutOfMemoryError e) {
- System.out.println("Out of memory during layout");
-
- // we might get an out of memory error.
- // so let's display an alert.
- // TODO: a better message, in resources.
-
- if (!memAlert) {
- memAlert = true;
- AlertDialog alertDialog = MuPDFActivity.getAlertBuilder().create();
- alertDialog.setMessage("Out of memory during layout");
- alertDialog.setButton(AlertDialog.BUTTON_NEUTRAL, "OK",
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- dialog.dismiss();
- memAlert = false;
- }
- });
- alertDialog.show();
- }
- }
- }
-
- private boolean memAlert = false;
-
- private void onLayout2(boolean changed, int left, int top, int right,
- int bottom) {
-
- // "Edit mode" means when the View is being displayed in the Android GUI editor. (this class
- // is instantiated in the IDE, so we need to be a bit careful what we do).
- if (isInEditMode())
- return;
-
- View cv = mChildViews.get(mCurrent);
- Point cvOffset;
-
- if (!mResetLayout) {
- // Move to next or previous if current is sufficiently off center
- if (cv != null) {
- boolean move;
- cvOffset = subScreenSizeOffset(cv);
- // cv.getRight() may be out of date with the current scale
- // so add left to the measured width for the correct position
- if (HORIZONTAL_SCROLLING)
- move = cv.getLeft() + cv.getMeasuredWidth() + cvOffset.x + GAP/2 + mXScroll < getWidth()/2;
- else
- move = cv.getTop() + cv.getMeasuredHeight() + cvOffset.y + GAP/2 + mYScroll < getHeight()/2;
- if (move && mCurrent + 1 < mAdapter.getCount()) {
- postUnsettle(cv);
- // post to invoke test for end of animation
- // where we must set hq area for the new current view
- mStepper.prod();
-
- onMoveOffChild(mCurrent);
- mCurrent++;
- onMoveToChild(mCurrent);
- }
-
- if (HORIZONTAL_SCROLLING)
- move = cv.getLeft() - cvOffset.x - GAP/2 + mXScroll >= getWidth()/2;
- else
- move = cv.getTop() - cvOffset.y - GAP/2 + mYScroll >= getHeight()/2;
- if (move && mCurrent > 0) {
- postUnsettle(cv);
- // post to invoke test for end of animation
- // where we must set hq area for the new current view
- mStepper.prod();
-
- onMoveOffChild(mCurrent);
- mCurrent--;
- onMoveToChild(mCurrent);
- }
- }
-
- // Remove not needed children and hold them for reuse
- int numChildren = mChildViews.size();
- int childIndices[] = new int[numChildren];
- for (int i = 0; i < numChildren; i++)
- childIndices[i] = mChildViews.keyAt(i);
-
- for (int i = 0; i < numChildren; i++) {
- int ai = childIndices[i];
- if (ai < mCurrent - 1 || ai > mCurrent + 1) {
- View v = mChildViews.get(ai);
- onNotInUse(v);
- mViewCache.add(v);
- removeViewInLayout(v);
- mChildViews.remove(ai);
- }
- }
- } else {
- mResetLayout = false;
- mXScroll = mYScroll = 0;
-
- // Remove all children and hold them for reuse
- int numChildren = mChildViews.size();
- for (int i = 0; i < numChildren; i++) {
- View v = mChildViews.valueAt(i);
- onNotInUse(v);
- mViewCache.add(v);
- removeViewInLayout(v);
- }
- mChildViews.clear();
-
- // Don't reuse cached views if the adapter has changed
- if (mReflowChanged) {
- mReflowChanged = false;
- mViewCache.clear();
- }
-
- // post to ensure generation of hq area
- mStepper.prod();
- }
-
- // Ensure current view is present
- int cvLeft, cvRight, cvTop, cvBottom;
- boolean notPresent = (mChildViews.get(mCurrent) == null);
- cv = getOrCreateChild(mCurrent);
- // When the view is sub-screen-size in either dimension we
- // offset it to center within the screen area, and to keep
- // the views spaced out
- cvOffset = subScreenSizeOffset(cv);
- if (notPresent) {
- // Main item not already present. Just place it top left
- cvLeft = cvOffset.x;
- cvTop = cvOffset.y;
- } else {
- // Main item already present. Adjust by scroll offsets
- cvLeft = cv.getLeft() + mXScroll;
- cvTop = cv.getTop() + mYScroll;
- }
- // Scroll values have been accounted for
- mXScroll = mYScroll = 0;
- cvRight = cvLeft + cv.getMeasuredWidth();
- cvBottom = cvTop + cv.getMeasuredHeight();
-
- if (!mUserInteracting && mScroller.isFinished()) {
- Point corr = getCorrection(getScrollBounds(cvLeft, cvTop, cvRight, cvBottom));
- cvRight += corr.x;
- cvLeft += corr.x;
- cvTop += corr.y;
- cvBottom += corr.y;
- } else if (HORIZONTAL_SCROLLING && cv.getMeasuredHeight() <= getHeight()) {
- // When the current view is as small as the screen in height, clamp
- // it vertically
- Point corr = getCorrection(getScrollBounds(cvLeft, cvTop, cvRight, cvBottom));
- cvTop += corr.y;
- cvBottom += corr.y;
- } else if (!HORIZONTAL_SCROLLING && cv.getMeasuredWidth() <= getWidth()) {
- // When the current view is as small as the screen in width, clamp
- // it horizontally
- Point corr = getCorrection(getScrollBounds(cvLeft, cvTop, cvRight, cvBottom));
- cvRight += corr.x;
- cvLeft += corr.x;
- }
-
- cv.layout(cvLeft, cvTop, cvRight, cvBottom);
-
- if (mCurrent > 0) {
- View lv = getOrCreateChild(mCurrent - 1);
- Point leftOffset = subScreenSizeOffset(lv);
- if (HORIZONTAL_SCROLLING)
- {
- int gap = leftOffset.x + GAP + cvOffset.x;
- lv.layout(cvLeft - lv.getMeasuredWidth() - gap,
- (cvBottom + cvTop - lv.getMeasuredHeight())/2,
- cvLeft - gap,
- (cvBottom + cvTop + lv.getMeasuredHeight())/2);
- } else {
- int gap = leftOffset.y + GAP + cvOffset.y;
- lv.layout((cvLeft + cvRight - lv.getMeasuredWidth())/2,
- cvTop - lv.getMeasuredHeight() - gap,
- (cvLeft + cvRight + lv.getMeasuredWidth())/2,
- cvTop - gap);
- }
- }
-
- if (mCurrent + 1 < mAdapter.getCount()) {
- View rv = getOrCreateChild(mCurrent + 1);
- Point rightOffset = subScreenSizeOffset(rv);
- if (HORIZONTAL_SCROLLING)
- {
- int gap = cvOffset.x + GAP + rightOffset.x;
- rv.layout(cvRight + gap,
- (cvBottom + cvTop - rv.getMeasuredHeight())/2,
- cvRight + rv.getMeasuredWidth() + gap,
- (cvBottom + cvTop + rv.getMeasuredHeight())/2);
- } else {
- int gap = cvOffset.y + GAP + rightOffset.y;
- rv.layout((cvLeft + cvRight - rv.getMeasuredWidth())/2,
- cvBottom + gap,
- (cvLeft + cvRight + rv.getMeasuredWidth())/2,
- cvBottom + gap + rv.getMeasuredHeight());
- }
- }
-
- invalidate();
- }
-
- @Override
- public Adapter getAdapter() {
- return mAdapter;
- }
-
- @Override
- public View getSelectedView() {
- return null;
- }
-
- @Override
- public void setAdapter(Adapter adapter) {
-
- // release previous adapter's bitmaps
- if (null!=mAdapter && adapter!=mAdapter) {
- if (adapter instanceof MuPDFPageAdapter){
- ((MuPDFPageAdapter) adapter).releaseBitmaps();
- }
- }
-
- mAdapter = adapter;
-
- requestLayout();
- }
-
- @Override
- public void setSelection(int arg0) {
- throw new UnsupportedOperationException(getContext().getString(R.string.not_supported));
- }
-
- private View getCached() {
- if (mViewCache.size() == 0)
- return null;
- else
- return mViewCache.removeFirst();
- }
-
- private View getOrCreateChild(int i) {
- View v = mChildViews.get(i);
- if (v == null) {
- v = mAdapter.getView(i, getCached(), this);
- addAndMeasureChild(i, v);
- onChildSetup(i, v);
- onScaleChild(v, mScale);
- }
-
- return v;
- }
-
- private void addAndMeasureChild(int i, View v) {
- LayoutParams params = v.getLayoutParams();
- if (params == null) {
- params = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
- }
- addViewInLayout(v, 0, params, true);
- mChildViews.append(i, v); // Record the view against it's adapter index
- measureView(v);
- }
-
- private void measureView(View v) {
- // See what size the view wants to be
- v.measure(View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED);
-
- if (!mReflow) {
- // Work out a scale that will fit it to this view
- float scale = Math.min((float)getWidth()/(float)v.getMeasuredWidth(),
- (float)getHeight()/(float)v.getMeasuredHeight());
- // Use the fitting values scaled by our current scale factor
- v.measure(View.MeasureSpec.EXACTLY | (int)(v.getMeasuredWidth()*scale*mScale),
- View.MeasureSpec.EXACTLY | (int)(v.getMeasuredHeight()*scale*mScale));
- } else {
- v.measure(View.MeasureSpec.EXACTLY | (int)(v.getMeasuredWidth()),
- View.MeasureSpec.EXACTLY | (int)(v.getMeasuredHeight()));
- }
- }
-
- private Rect getScrollBounds(int left, int top, int right, int bottom) {
- int xmin = getWidth() - right;
- int xmax = -left;
- int ymin = getHeight() - bottom;
- int ymax = -top;
-
- // In either dimension, if view smaller than screen then
- // constrain it to be central
- if (xmin > xmax) xmin = xmax = (xmin + xmax)/2;
- if (ymin > ymax) ymin = ymax = (ymin + ymax)/2;
-
- return new Rect(xmin, ymin, xmax, ymax);
- }
-
- private Rect getScrollBounds(View v) {
- // There can be scroll amounts not yet accounted for in
- // onLayout, so add mXScroll and mYScroll to the current
- // positions when calculating the bounds.
- return getScrollBounds(v.getLeft() + mXScroll,
- v.getTop() + mYScroll,
- v.getLeft() + v.getMeasuredWidth() + mXScroll,
- v.getTop() + v.getMeasuredHeight() + mYScroll);
- }
-
- private Point getCorrection(Rect bounds) {
- return new Point(Math.min(Math.max(0,bounds.left),bounds.right),
- Math.min(Math.max(0,bounds.top),bounds.bottom));
- }
-
- private void postSettle(final View v) {
- // onSettle and onUnsettle are posted so that the calls
- // wont be executed until after the system has performed
- // layout.
- post (new Runnable() {
- public void run () {
- onSettle(v);
- }
- });
- }
-
- private void postUnsettle(final View v) {
- post (new Runnable() {
- public void run () {
- onUnsettle(v);
- }
- });
- }
-
- private void slideViewOntoScreen(View v) {
- Point corr = getCorrection(getScrollBounds(v));
- if (corr.x != 0 || corr.y != 0) {
- mScrollerLastX = mScrollerLastY = 0;
- mScroller.startScroll(0, 0, corr.x, corr.y, 400);
- mStepper.prod();
- }
- }
-
- private Point subScreenSizeOffset(View v) {
- return new Point(Math.max((getWidth() - v.getMeasuredWidth())/2, 0),
- Math.max((getHeight() - v.getMeasuredHeight())/2, 0));
- }
-
- private static int directionOfTravel(float vx, float vy) {
- if (Math.abs(vx) > 2 * Math.abs(vy))
- return (vx > 0) ? MOVING_RIGHT : MOVING_LEFT;
- else if (Math.abs(vy) > 2 * Math.abs(vx))
- return (vy > 0) ? MOVING_DOWN : MOVING_UP;
- else
- return MOVING_DIAGONALLY;
- }
-
- private static boolean withinBoundsInDirectionOfTravel(Rect bounds, float vx, float vy) {
- switch (directionOfTravel(vx, vy)) {
- case MOVING_DIAGONALLY: return bounds.contains(0, 0);
- case MOVING_LEFT: return bounds.left <= 0;
- case MOVING_RIGHT: return bounds.right >= 0;
- case MOVING_UP: return bounds.top <= 0;
- case MOVING_DOWN: return bounds.bottom >= 0;
- default: throw new NoSuchElementException();
- }
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/SafeAnimatorInflater.java b/platform/android/viewer/src/com/artifex/mupdfdemo/SafeAnimatorInflater.java
deleted file mode 100644
index 7f715bb4..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/SafeAnimatorInflater.java
+++ /dev/null
@@ -1,35 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.animation.Animator;
-import android.animation.AnimatorInflater;
-import android.animation.AnimatorSet;
-import android.app.Activity;
-import android.view.View;
-
-public class SafeAnimatorInflater
-{
- private View mView;
-
- public SafeAnimatorInflater(Activity activity, int animation, View view)
- {
- AnimatorSet set = (AnimatorSet) AnimatorInflater.loadAnimator(activity, R.animator.info);
- mView = view;
- set.setTarget(view);
- set.addListener(new Animator.AnimatorListener() {
- public void onAnimationStart(Animator animation) {
- mView.setVisibility(View.VISIBLE);
- }
-
- public void onAnimationRepeat(Animator animation) {
- }
-
- public void onAnimationEnd(Animator animation) {
- mView.setVisibility(View.INVISIBLE);
- }
-
- public void onAnimationCancel(Animator animation) {
- }
- });
- set.start();
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/SearchTask.java b/platform/android/viewer/src/com/artifex/mupdfdemo/SearchTask.java
deleted file mode 100644
index 7e15f98d..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/SearchTask.java
+++ /dev/null
@@ -1,128 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.app.AlertDialog;
-import android.app.ProgressDialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.graphics.RectF;
-import android.os.Handler;
-
-class ProgressDialogX extends ProgressDialog {
- public ProgressDialogX(Context context) {
- super(context);
- }
-
- private boolean mCancelled = false;
-
- public boolean isCancelled() {
- return mCancelled;
- }
-
- @Override
- public void cancel() {
- mCancelled = true;
- super.cancel();
- }
-}
-
-public abstract class SearchTask {
- private static final int SEARCH_PROGRESS_DELAY = 200;
- private final Context mContext;
- private final MuPDFCore mCore;
- private final Handler mHandler;
- private final AlertDialog.Builder mAlertBuilder;
- private AsyncTask<Void,Integer,SearchTaskResult> mSearchTask;
-
- public SearchTask(Context context, MuPDFCore core) {
- mContext = context;
- mCore = core;
- mHandler = new Handler();
- mAlertBuilder = new AlertDialog.Builder(context);
- }
-
- protected abstract void onTextFound(SearchTaskResult result);
-
- public void stop() {
- if (mSearchTask != null) {
- mSearchTask.cancel(true);
- mSearchTask = null;
- }
- }
-
- public void go(final String text, int direction, int displayPage, int searchPage) {
- if (mCore == null)
- return;
- stop();
-
- final int increment = direction;
- final int startIndex = searchPage == -1 ? displayPage : searchPage + increment;
-
- final ProgressDialogX progressDialog = new ProgressDialogX(mContext);
- progressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
- progressDialog.setTitle(mContext.getString(R.string.searching_));
- progressDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
- public void onCancel(DialogInterface dialog) {
- stop();
- }
- });
- progressDialog.setMax(mCore.countPages());
-
- mSearchTask = new AsyncTask<Void,Integer,SearchTaskResult>() {
- @Override
- protected SearchTaskResult doInBackground(Void... params) {
- int index = startIndex;
-
- while (0 <= index && index < mCore.countPages() && !isCancelled()) {
- publishProgress(index);
- RectF searchHits[] = mCore.searchPage(index, text);
-
- if (searchHits != null && searchHits.length > 0)
- return new SearchTaskResult(text, index, searchHits);
-
- index += increment;
- }
- return null;
- }
-
- @Override
- protected void onPostExecute(SearchTaskResult result) {
- progressDialog.cancel();
- if (result != null) {
- onTextFound(result);
- } else {
- mAlertBuilder.setTitle(SearchTaskResult.get() == null ? R.string.text_not_found : R.string.no_further_occurrences_found);
- AlertDialog alert = mAlertBuilder.create();
- alert.setButton(AlertDialog.BUTTON_POSITIVE, mContext.getString(R.string.dismiss),
- (DialogInterface.OnClickListener)null);
- alert.show();
- }
- }
-
- @Override
- protected void onCancelled() {
- progressDialog.cancel();
- }
-
- @Override
- protected void onProgressUpdate(Integer... values) {
- progressDialog.setProgress(values[0].intValue());
- }
-
- @Override
- protected void onPreExecute() {
- super.onPreExecute();
- mHandler.postDelayed(new Runnable() {
- public void run() {
- if (!progressDialog.isCancelled())
- {
- progressDialog.show();
- progressDialog.setProgress(startIndex);
- }
- }
- }, SEARCH_PROGRESS_DELAY);
- }
- };
-
- mSearchTask.execute();
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/SearchTaskResult.java b/platform/android/viewer/src/com/artifex/mupdfdemo/SearchTaskResult.java
deleted file mode 100644
index 6c337fe2..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/SearchTaskResult.java
+++ /dev/null
@@ -1,24 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.graphics.RectF;
-
-public class SearchTaskResult {
- public final String txt;
- public final int pageNumber;
- public final RectF searchBoxes[];
- static private SearchTaskResult singleton;
-
- SearchTaskResult(String _txt, int _pageNumber, RectF _searchBoxes[]) {
- txt = _txt;
- pageNumber = _pageNumber;
- searchBoxes = _searchBoxes;
- }
-
- static public SearchTaskResult get() {
- return singleton;
- }
-
- static public void set(SearchTaskResult r) {
- singleton = r;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/Separation.java b/platform/android/viewer/src/com/artifex/mupdfdemo/Separation.java
deleted file mode 100644
index eadda4ba..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/Separation.java
+++ /dev/null
@@ -1,15 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public class Separation
-{
- String name;
- int rgba;
- int cmyk;
-
- public Separation(String name, int rgba, int cmyk)
- {
- this.name = name;
- this.rgba = rgba;
- this.cmyk = cmyk;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/Stepper.java b/platform/android/viewer/src/com/artifex/mupdfdemo/Stepper.java
deleted file mode 100644
index d22240ef..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/Stepper.java
+++ /dev/null
@@ -1,42 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.annotation.SuppressLint;
-import android.os.Build;
-import android.view.View;
-
-public class Stepper {
- protected final View mPoster;
- protected final Runnable mTask;
- protected boolean mPending;
-
- public Stepper(View v, Runnable r) {
- mPoster = v;
- mTask = r;
- mPending = false;
- }
-
- @SuppressLint("NewApi")
- public void prod() {
- if (!mPending) {
- mPending = true;
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
- mPoster.postOnAnimation(new Runnable() {
- @Override
- public void run() {
- mPending = false;
- mTask.run();
- }
- });
- } else {
- mPoster.post(new Runnable() {
- @Override
- public void run() {
- mPending = false;
- mTask.run();
- }
- });
-
- }
- }
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/TextChar.java b/platform/android/viewer/src/com/artifex/mupdfdemo/TextChar.java
deleted file mode 100644
index aebf519f..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/TextChar.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.graphics.RectF;
-
-public class TextChar extends RectF {
- public char c;
-
- public TextChar(float x0, float y0, float x1, float y1, char _c) {
- super(x0, y0, x1, y1);
- c = _c;
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/TextWord.java b/platform/android/viewer/src/com/artifex/mupdfdemo/TextWord.java
deleted file mode 100644
index d9672573..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/TextWord.java
+++ /dev/null
@@ -1,17 +0,0 @@
-package com.artifex.mupdfdemo;
-
-import android.graphics.RectF;
-
-public class TextWord extends RectF {
- public String w;
-
- public TextWord() {
- super();
- w = new String();
- }
-
- public void Add(TextChar tc) {
- super.union(tc);
- w = w.concat(new String(new char[]{tc.c}));
- }
-}
diff --git a/platform/android/viewer/src/com/artifex/mupdfdemo/WidgetType.java b/platform/android/viewer/src/com/artifex/mupdfdemo/WidgetType.java
deleted file mode 100644
index 882a38f2..00000000
--- a/platform/android/viewer/src/com/artifex/mupdfdemo/WidgetType.java
+++ /dev/null
@@ -1,9 +0,0 @@
-package com.artifex.mupdfdemo;
-
-public enum WidgetType {
- NONE,
- TEXT,
- LISTBOX,
- COMBOBOX,
- SIGNATURE
-}