Add an initial menu for the reader, and some minor changes.

This commit is contained in:
inorichi 2015-11-18 21:54:33 +01:00
parent b389db9773
commit 3c1b00435c
20 changed files with 214 additions and 104 deletions

View file

@ -15,7 +15,6 @@
android:theme="@style/AppTheme" > android:theme="@style/AppTheme" >
<activity <activity
android:name=".ui.main.MainActivity" android:name=".ui.main.MainActivity"
android:launchMode="singleTop"
android:theme="@style/AppTheme.NoActionBar" > android:theme="@style/AppTheme.NoActionBar" >
<intent-filter> <intent-filter>
<action android:name="android.intent.action.MAIN" /> <action android:name="android.intent.action.MAIN" />

View file

@ -60,8 +60,10 @@ public class Chapter {
return url.hashCode(); return url.hashCode();
} }
public static Chapter newChapter() { public static Chapter create() {
return new Chapter(); Chapter chapter = new Chapter();
chapter.chapter_number = -1;
return chapter;
} }
} }

View file

@ -36,8 +36,8 @@ public class PreferencesHelper {
prefs.edit().clear().apply(); prefs.edit().clear().apply();
} }
public boolean useFullscreenSet() { public boolean isHideStatusBarSet() {
return prefs.getBoolean(getKey(R.string.pref_fullscreen_key), false); return prefs.getBoolean(getKey(R.string.pref_hide_status_bar_key), true);
} }
public int getDefaultViewer() { public int getDefaultViewer() {

View file

@ -92,9 +92,4 @@ public abstract class BaseSource {
return builder; return builder;
} }
// Number of images to download at the same time. 3 by default
protected int overrideNumberOfConcurrentPageDownloads() {
return 3;
}
} }

View file

@ -97,8 +97,7 @@ public abstract class Source extends BaseSource {
public Observable<Page> getRemainingImageUrlsFromPageList(final List<Page> pages) { public Observable<Page> getRemainingImageUrlsFromPageList(final List<Page> pages) {
return Observable.from(pages) return Observable.from(pages)
.filter(page -> page.getImageUrl() == null) .filter(page -> page.getImageUrl() == null)
.window(overrideNumberOfConcurrentPageDownloads()) .concatMap(this::getImageUrlFromPage);
.concatMap(batchedPages -> batchedPages.concatMap(this::getImageUrlFromPage));
} }
public Observable<Page> getImageUrlFromPage(final Page page) { public Observable<Page> getImageUrlFromPage(final Page page) {

View file

@ -305,7 +305,7 @@ public class Batoto extends Source {
} }
private Chapter constructChapterFromHtmlBlock(Element chapterElement) { private Chapter constructChapterFromHtmlBlock(Element chapterElement) {
Chapter newChapter = Chapter.newChapter(); Chapter newChapter = Chapter.create();
Element urlElement = chapterElement.select("a[href^=http://bato.to/reader").first(); Element urlElement = chapterElement.select("a[href^=http://bato.to/reader").first();
Element nameElement = urlElement; Element nameElement = urlElement;

View file

@ -288,7 +288,7 @@ public class Mangahere extends Source {
} }
private Chapter constructChapterFromHtmlBlock(Element chapterElement) { private Chapter constructChapterFromHtmlBlock(Element chapterElement) {
Chapter newChapter = Chapter.newChapter(); Chapter newChapter = Chapter.create();
Element urlElement = chapterElement.select("a").first(); Element urlElement = chapterElement.select("a").first();
Element nameElement = chapterElement.select("a").first(); Element nameElement = chapterElement.select("a").first();

View file

@ -3,6 +3,7 @@ package eu.kanade.mangafeed.ui.base.activity;
import android.content.Context; import android.content.Context;
import android.support.v7.app.AppCompatActivity; import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.Toolbar; import android.support.v7.widget.Toolbar;
import android.view.MenuItem;
public class BaseActivity extends AppCompatActivity { public class BaseActivity extends AppCompatActivity {
@ -22,7 +23,28 @@ public class BaseActivity extends AppCompatActivity {
getSupportActionBar().setTitle(getString(titleResource)); getSupportActionBar().setTitle(getString(titleResource));
} }
public void setToolbarSubtitle(String title) {
if (getSupportActionBar() != null)
getSupportActionBar().setSubtitle(title);
}
public void setToolbarSubtitle(int titleResource) {
if (getSupportActionBar() != null)
getSupportActionBar().setSubtitle(getString(titleResource));
}
public Context getActivity() { public Context getActivity() {
return this; return this;
} }
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
onBackPressed();
return true;
}
return super.onOptionsItemSelected(item);
}
} }

View file

@ -10,7 +10,6 @@ import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter; import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.view.ViewPager; import android.support.v4.view.ViewPager;
import android.support.v7.widget.Toolbar; import android.support.v7.widget.Toolbar;
import android.view.MenuItem;
import butterknife.Bind; import butterknife.Bind;
import butterknife.ButterKnife; import butterknife.ButterKnife;
@ -61,16 +60,6 @@ public class MangaActivity extends BaseRxActivity<MangaPresenter> {
getPresenter().queryManga(manga_id); getPresenter().queryManga(manga_id);
} }
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
finish();
return true;
}
return super.onOptionsItemSelected(item);
}
private void disableToolbarElevation() { private void disableToolbarElevation() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
toolbar.setElevation(0); toolbar.setElevation(0);

View file

@ -4,6 +4,7 @@ import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.os.Build; import android.os.Build;
import android.os.Bundle; import android.os.Bundle;
import android.support.v7.widget.Toolbar;
import android.view.MotionEvent; import android.view.MotionEvent;
import android.view.View; import android.view.View;
import android.view.WindowManager; import android.view.WindowManager;
@ -18,6 +19,8 @@ import butterknife.Bind;
import butterknife.ButterKnife; import butterknife.ButterKnife;
import eu.kanade.mangafeed.App; import eu.kanade.mangafeed.App;
import eu.kanade.mangafeed.R; import eu.kanade.mangafeed.R;
import eu.kanade.mangafeed.data.database.models.Chapter;
import eu.kanade.mangafeed.data.database.models.Manga;
import eu.kanade.mangafeed.data.preference.PreferencesHelper; import eu.kanade.mangafeed.data.preference.PreferencesHelper;
import eu.kanade.mangafeed.data.source.model.Page; import eu.kanade.mangafeed.data.source.model.Page;
import eu.kanade.mangafeed.ui.base.activity.BaseRxActivity; import eu.kanade.mangafeed.ui.base.activity.BaseRxActivity;
@ -34,11 +37,14 @@ public class ReaderActivity extends BaseRxActivity<ReaderPresenter> {
@Bind(R.id.page_number) TextView pageNumber; @Bind(R.id.page_number) TextView pageNumber;
@Bind(R.id.reader) FrameLayout container; @Bind(R.id.reader) FrameLayout container;
@Bind(R.id.toolbar) Toolbar toolbar;
@Inject PreferencesHelper prefs; @Inject PreferencesHelper prefs;
private BaseReader viewer; private BaseReader viewer;
private boolean isFullscreen; private ReaderMenu readerMenu;
private int uiFlags;
private static final int LEFT_TO_RIGHT = 1; private static final int LEFT_TO_RIGHT = 1;
private static final int RIGHT_TO_LEFT = 2; private static final int RIGHT_TO_LEFT = 2;
@ -57,27 +63,19 @@ public class ReaderActivity extends BaseRxActivity<ReaderPresenter> {
setContentView(R.layout.activity_reader); setContentView(R.layout.activity_reader);
ButterKnife.bind(this); ButterKnife.bind(this);
if (prefs.useFullscreenSet()) setupToolbar(toolbar);
enableFullScreen();
readerMenu = new ReaderMenu(this, prefs);
createUiHideFlags();
enableHardwareAcceleration(); enableHardwareAcceleration();
viewer = getViewer(); viewer = getViewer();
} }
public void onPageListReady(List<Page> pages) { @Override
viewer.onPageListReady(pages); protected void onResume() {
viewer.updatePageNumber(); super.onResume();
} hideSystemUI();
public void onPageListError() {
finish();
ToastUtil.showShort(this, R.string.page_list_error);
}
public void onPageChanged(int currentPageIndex, int totalPages) {
String page = (currentPageIndex + 1) + "/" + totalPages;
pageNumber.setText(page);
} }
@Override @Override
@ -87,42 +85,37 @@ public class ReaderActivity extends BaseRxActivity<ReaderPresenter> {
super.onPause(); super.onPause();
} }
private void createUiHideFlags() {
uiFlags |= View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
if (prefs.isHideStatusBarSet())
uiFlags |= View.SYSTEM_UI_FLAG_FULLSCREEN;
if (Build.VERSION.SDK_INT > Build.VERSION_CODES.KITKAT)
uiFlags |= View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
}
public void onChapterReady(List<Page> pages, Manga manga, Chapter chapter) {
viewer.onPageListReady(pages);
viewer.updatePageNumber();
readerMenu.onChapterReady(pages.size(), manga, chapter);
}
public void onChapterError() {
finish();
ToastUtil.showShort(this, R.string.page_list_error);
}
public void onPageChanged(int currentPageIndex, int totalPages) {
String page = (currentPageIndex + 1) + "/" + totalPages;
pageNumber.setText(page);
readerMenu.onPageChanged(currentPageIndex);
}
public void setSelectedPage(int pageIndex) { public void setSelectedPage(int pageIndex) {
viewer.setSelectedPage(pageIndex); viewer.setSelectedPage(pageIndex);
} }
public void enableFullScreen() { public void hideSystemUI() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { getWindow().getDecorView().setSystemUiVisibility(uiFlags);
getWindow().getDecorView().setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LOW_PROFILE
| View.SYSTEM_UI_FLAG_LAYOUT_STABLE
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_FULLSCREEN
| View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
);
} else {
getWindow().getDecorView().setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LOW_PROFILE
);
}
isFullscreen = true;
}
public void disableFullscreen() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
getWindow().getDecorView().setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LAYOUT_STABLE
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
);
} else {
getWindow().getDecorView().setSystemUiVisibility(
View.VISIBLE
);
}
isFullscreen = false;
} }
public void enableHardwareAcceleration() { public void enableHardwareAcceleration() {
@ -136,14 +129,7 @@ public class ReaderActivity extends BaseRxActivity<ReaderPresenter> {
} }
public void onCenterSingleTap() { public void onCenterSingleTap() {
toggleFullscreen(); readerMenu.toggle();
}
private void toggleFullscreen() {
if (isFullscreen)
disableFullscreen();
else
enableFullScreen();
} }
private BaseReader getViewer() { private BaseReader getViewer() {

View file

@ -0,0 +1,80 @@
package eu.kanade.mangafeed.ui.reader;
import android.view.View;
import android.widget.RelativeLayout;
import android.widget.SeekBar;
import android.widget.TextView;
import java.text.DecimalFormat;
import butterknife.Bind;
import butterknife.ButterKnife;
import eu.kanade.mangafeed.R;
import eu.kanade.mangafeed.data.database.models.Chapter;
import eu.kanade.mangafeed.data.database.models.Manga;
import eu.kanade.mangafeed.data.preference.PreferencesHelper;
public class ReaderMenu {
@Bind(R.id.reader_menu) RelativeLayout menu;
@Bind(R.id.current_page) TextView currentPage;
@Bind(R.id.page_seeker) SeekBar seekBar;
@Bind(R.id.total_pages) TextView totalPages;
private ReaderActivity activity;
private PreferencesHelper preferences;
private boolean showing;
private DecimalFormat decimalFormat;
public ReaderMenu(ReaderActivity activity, PreferencesHelper preferences) {
this.activity = activity;
this.preferences = preferences;
ButterKnife.bind(this, activity);
seekBar.setOnSeekBarChangeListener(new PageSeekBarChangeListener());
decimalFormat = new DecimalFormat("#.##");
}
public void toggle() {
toggle(!showing);
}
private void toggle(boolean show) {
menu.setVisibility(show ? View.VISIBLE : View.GONE);
showing = show;
}
public void onChapterReady(int numPages, Manga manga, Chapter chapter) {
totalPages.setText("" + numPages);
seekBar.setMax(numPages - 1);
activity.setToolbarTitle(manga.title);
activity.setToolbarSubtitle(chapter.chapter_number != -1 ?
activity.getString(R.string.chapter_subtitle,
decimalFormat.format(chapter.chapter_number)) :
chapter.name);
}
public void onPageChanged(int pageIndex) {
currentPage.setText("" + (pageIndex + 1));
seekBar.setProgress(pageIndex);
}
class PageSeekBarChangeListener implements SeekBar.OnSeekBarChangeListener {
@Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
if (fromUser) {
activity.setSelectedPage(progress);
}
}
@Override
public void onStartTrackingTouch(SeekBar seekBar) {}
@Override
public void onStopTrackingTouch(SeekBar seekBar) {}
}
}

View file

@ -66,12 +66,12 @@ public class ReaderPresenter extends BasePresenter<ReaderActivity> {
start(RETRY_IMAGES); start(RETRY_IMAGES);
}), }),
(view, pages) -> { (view, pages) -> {
view.onPageListReady(pages); view.onChapterReady(pages, manga, chapter);
if (currentPage != 0) if (currentPage != 0)
view.setSelectedPage(currentPage); view.setSelectedPage(currentPage);
}, },
(view, error) -> { (view, error) -> {
view.onPageListError(); view.onChapterError();
}); });
restartableReplay(GET_PAGE_IMAGES, restartableReplay(GET_PAGE_IMAGES,
@ -158,7 +158,7 @@ public class ReaderPresenter extends BasePresenter<ReaderActivity> {
pages = Observable.from(pageList) pages = Observable.from(pageList)
.filter(page -> page.getImageUrl() != null) .filter(page -> page.getImageUrl() != null)
.mergeWith(source.getRemainingImageUrlsFromPageList(pageList)) .mergeWith(source.getRemainingImageUrlsFromPageList(pageList))
.flatMap(source::getCachedImage); .flatMap(source::getCachedImage, 3);
} else { } else {
File chapterDir = downloadManager.getAbsoluteChapterDirectory(source, manga, chapter); File chapterDir = downloadManager.getAbsoluteChapterDirectory(source, manga, chapter);
@ -178,7 +178,8 @@ public class ReaderPresenter extends BasePresenter<ReaderActivity> {
return Observable.just(page); return Observable.just(page);
}) })
.flatMap(source::getCachedImage) .flatMap(source::getCachedImage)
.subscribeOn(Schedulers.io()); .subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread());
} }
public void setCurrentPage(int currentPage) { public void setCurrentPage(int currentPage) {

View file

@ -2,7 +2,6 @@ package eu.kanade.mangafeed.ui.setting;
import android.os.Bundle; import android.os.Bundle;
import android.support.v7.widget.Toolbar; import android.support.v7.widget.Toolbar;
import android.view.MenuItem;
import butterknife.Bind; import butterknife.Bind;
import butterknife.ButterKnife; import butterknife.ButterKnife;
@ -32,14 +31,4 @@ public class SettingsActivity extends BaseActivity {
if( !getFragmentManager().popBackStackImmediate() ) super.onBackPressed(); if( !getFragmentManager().popBackStackImmediate() ) super.onBackPressed();
} }
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
onBackPressed();
return true;
}
return super.onOptionsItemSelected(item);
}
} }

View file

@ -14,7 +14,7 @@ public class ChapterRecognition {
private static Pattern p2 = Pattern.compile("(\\d+[\\.,]?\\d*)"); private static Pattern p2 = Pattern.compile("(\\d+[\\.,]?\\d*)");
public static void parseChapterNumber(Chapter chapter, Manga manga) { public static void parseChapterNumber(Chapter chapter, Manga manga) {
if (chapter.chapter_number != 0) if (chapter.chapter_number != -1)
return; return;
// Remove spaces and convert to lower case // Remove spaces and convert to lower case

View file

@ -6,17 +6,19 @@
<FrameLayout <FrameLayout
android:id="@+id/reader" android:id="@+id/reader"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content"> android:layout_height="match_parent">
</FrameLayout> </FrameLayout>
<TextView <TextView
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:padding="8dp" android:padding="4dp"
android:layout_gravity="bottom|left" android:layout_gravity="bottom|left"
android:background="@color/bg_light_grey" android:background="@color/page_number_background"
android:textColor="@color/black_87pc" android:textColor="@color/black_87pc"
android:textSize="12sp" android:textSize="12sp"
android:id="@+id/page_number"/> android:id="@+id/page_number"/>
<include layout="@layout/reader_menu"/>
</FrameLayout> </FrameLayout>

View file

@ -0,0 +1,43 @@
<?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"
android:id="@+id/reader_menu"
android:visibility="gone">
<include layout="@layout/toolbar"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@color/reader_menu_background"
android:layout_alignParentBottom="true">
<TextView
android:id="@+id/current_page"
android:layout_width="32dp"
android:layout_height="wrap_content"
android:layout_marginLeft="8dp"
android:layout_gravity="center_vertical"
android:textColor="@color/light_grey"
android:gravity="center_horizontal" />
<SeekBar
android:id="@+id/page_seeker"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_gravity="center_vertical" />
<TextView
android:id="@+id/total_pages"
android:layout_width="32dp"
android:layout_height="wrap_content"
android:layout_marginRight="8dp"
android:layout_gravity="center_vertical"
android:textColor="@color/light_grey"
android:gravity="center_horizontal" />
</LinearLayout>
</RelativeLayout>

View file

@ -17,4 +17,6 @@
<color name="library_text_background">#E8E8E8</color> <color name="library_text_background">#E8E8E8</color>
<color name="chapter_read_text">#909090</color> <color name="chapter_read_text">#909090</color>
<color name="list_choice_pressed_bg_light">#607D8B</color> <color name="list_choice_pressed_bg_light">#607D8B</color>
<color name="page_number_background">#AAE9E9E9</color>
<color name="reader_menu_background">#333333</color>
</resources> </resources>

View file

@ -3,7 +3,7 @@
<string name="pref_category_reader_key">pref_category_reader_key</string> <string name="pref_category_reader_key">pref_category_reader_key</string>
<string name="pref_category_accounts_key">pref_category_accounts_key</string> <string name="pref_category_accounts_key">pref_category_accounts_key</string>
<string name="pref_category_downloads_key">pref_category_downloads_key</string> <string name="pref_category_downloads_key">pref_category_downloads_key</string>
<string name="pref_fullscreen_key">pref_fullscreen_key</string> <string name="pref_hide_status_bar_key">pref_hide_status_bar_key</string>
<string name="pref_default_viewer_key">pref_default_viewer_key</string> <string name="pref_default_viewer_key">pref_default_viewer_key</string>
<string name="pref_download_directory_key">pref_download_directory_key</string> <string name="pref_download_directory_key">pref_download_directory_key</string>
<string name="pref_download_threads_key">pref_download_threads_key</string> <string name="pref_download_threads_key">pref_download_threads_key</string>

View file

@ -27,7 +27,7 @@
<string name="pref_category_downloads">Downloads</string> <string name="pref_category_downloads">Downloads</string>
<!-- Reader section --> <!-- Reader section -->
<string name="pref_fullscreen_mode">Read in fullscreen</string> <string name="pref_hide_status_bar">Hide status bar</string>
<string name="pref_viewer_type">Default viewer</string> <string name="pref_viewer_type">Default viewer</string>
<string name="left_to_right_viewer">Left to right</string> <string name="left_to_right_viewer">Left to right</string>
<string name="right_to_left_viewer">Right to left</string> <string name="right_to_left_viewer">Right to left</string>
@ -75,6 +75,7 @@
<string name="download_progress">Downloaded %1$d%%</string> <string name="download_progress">Downloaded %1$d%%</string>
<string name="chapter_progress">Page: %1$d</string> <string name="chapter_progress">Page: %1$d</string>
<string name="page_list_error">Error fetching page list. Is network available?</string> <string name="page_list_error">Error fetching page list. Is network available?</string>
<string name="chapter_subtitle">Chapter %1$s</string>
<!-- Library update service notifications --> <!-- Library update service notifications -->
<string name="notification_progress">Update progress: %1$d/%2$d</string> <string name="notification_progress">Update progress: %1$d/%2$d</string>

View file

@ -1,8 +1,8 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"> <PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
<CheckBoxPreference android:title="@string/pref_fullscreen_mode" <CheckBoxPreference android:title="@string/pref_hide_status_bar"
android:key="@string/pref_fullscreen_key" android:key="@string/pref_hide_status_bar_key"
android:defaultValue="true" /> android:defaultValue="true" />
<ListPreference android:title="@string/pref_viewer_type" <ListPreference android:title="@string/pref_viewer_type"