Library now showing favorite mangas

This commit is contained in:
inorichi 2015-10-27 00:00:09 +01:00
parent baa24fbf17
commit 35b8be6c75
16 changed files with 78 additions and 42 deletions

View file

@ -53,7 +53,7 @@ dependencies {
final DAGGER_VERSION = '2.0.1' final DAGGER_VERSION = '2.0.1'
final HAMCREST_VERSION = '1.3' final HAMCREST_VERSION = '1.3'
final MOCKITO_VERSION = '1.10.19' final MOCKITO_VERSION = '1.10.19'
final STORIO_VERSION = '1.4.0' final STORIO_VERSION = '1.5.0'
final NUCLEUS_VERSION = '2.0.1' final NUCLEUS_VERSION = '2.0.1'
final ICEPICK_VERSION = '3.1.0' final ICEPICK_VERSION = '3.1.0'
@ -65,8 +65,8 @@ dependencies {
compile "com.android.support:design:$SUPPORT_LIBRARY_VERSION" compile "com.android.support:design:$SUPPORT_LIBRARY_VERSION"
compile "com.android.support:recyclerview-v7:$SUPPORT_LIBRARY_VERSION" compile "com.android.support:recyclerview-v7:$SUPPORT_LIBRARY_VERSION"
compile "com.android.support:support-annotations:$SUPPORT_LIBRARY_VERSION" compile "com.android.support:support-annotations:$SUPPORT_LIBRARY_VERSION"
compile 'com.squareup.okhttp:okhttp-urlconnection:2.4.0' compile 'com.squareup.okhttp:okhttp-urlconnection:2.5.0'
compile 'com.squareup.okhttp:okhttp:2.4.0' compile 'com.squareup.okhttp:okhttp:2.5.0'
compile 'com.squareup.okio:okio:1.6.0' compile 'com.squareup.okio:okio:1.6.0'
compile 'com.google.code.gson:gson:2.4' compile 'com.google.code.gson:gson:2.4'
compile 'com.jakewharton:disklrucache:2.0.2' compile 'com.jakewharton:disklrucache:2.0.2'
@ -80,7 +80,7 @@ dependencies {
compile 'de.greenrobot:eventbus:2.4.0' compile 'de.greenrobot:eventbus:2.4.0'
compile 'com.github.bumptech.glide:glide:3.6.1' compile 'com.github.bumptech.glide:glide:3.6.1'
compile 'com.jakewharton:butterknife:7.0.1' compile 'com.jakewharton:butterknife:7.0.1'
compile 'com.jakewharton.timber:timber:3.1.0' compile 'com.jakewharton.timber:timber:4.1.0'
compile 'uk.co.ribot:easyadapter:1.5.0@aar' compile 'uk.co.ribot:easyadapter:1.5.0@aar'
compile 'ch.acra:acra:4.6.2' compile 'ch.acra:acra:4.6.2'
compile 'com.github.castorflex.verticalviewpager:library:19.0.1' compile 'com.github.castorflex.verticalviewpager:library:19.0.1'

View file

@ -21,16 +21,17 @@ public class MangaManagerImpl extends BaseManager implements MangaManager {
super(db); super(db);
} }
private final String mangasWithUnreadQuery = String.format( private final String favoriteMangasWithUnreadQuery = String.format(
"SELECT %1$s.*, COUNT(C.%4$s) AS %5$s FROM %1$s LEFT JOIN " + "SELECT %1$s.*, COUNT(C.%4$s) AS %5$s FROM %1$s LEFT JOIN " +
"(SELECT %4$s FROM %2$s WHERE %6$s = 0) AS C ON %3$s = C.%4$s " + "(SELECT %4$s FROM %2$s WHERE %6$s = 0) AS C ON %3$s = C.%4$s " +
"GROUP BY %3$s", "WHERE %7$s = 1 GROUP BY %3$s",
MangasTable.TABLE, MangasTable.TABLE,
ChaptersTable.TABLE, ChaptersTable.TABLE,
MangasTable.TABLE + "." + MangasTable.COLUMN_ID, MangasTable.TABLE + "." + MangasTable.COLUMN_ID,
ChaptersTable.COLUMN_MANGA_ID, ChaptersTable.COLUMN_MANGA_ID,
MangasTable.COLUMN_UNREAD, MangasTable.COLUMN_UNREAD,
ChaptersTable.COLUMN_READ ChaptersTable.COLUMN_READ,
MangasTable.COLUMN_FAVORITE
); );
public Observable<List<Manga>> getMangas() { public Observable<List<Manga>> getMangas() {
@ -47,7 +48,7 @@ public class MangaManagerImpl extends BaseManager implements MangaManager {
return db.get() return db.get()
.listOfObjects(Manga.class) .listOfObjects(Manga.class)
.withQuery(RawQuery.builder() .withQuery(RawQuery.builder()
.query(mangasWithUnreadQuery) .query(favoriteMangasWithUnreadQuery)
.observesTables(MangasTable.TABLE, ChaptersTable.TABLE) .observesTables(MangasTable.TABLE, ChaptersTable.TABLE)
.build()) .build())
.prepare() .prepare()

View file

@ -38,8 +38,8 @@ public class Manga {
@StorIOSQLiteColumn(name = MangasTable.COLUMN_THUMBNAIL_URL) @StorIOSQLiteColumn(name = MangasTable.COLUMN_THUMBNAIL_URL)
public String thumbnail_url; public String thumbnail_url;
@StorIOSQLiteColumn(name = MangasTable.COLUMN_RANK) @StorIOSQLiteColumn(name = MangasTable.COLUMN_FAVORITE)
public int rank; public boolean favorite;
@StorIOSQLiteColumn(name = MangasTable.COLUMN_LAST_UPDATE) @StorIOSQLiteColumn(name = MangasTable.COLUMN_LAST_UPDATE)
public long last_update; public long last_update;
@ -57,30 +57,6 @@ public class Manga {
public Manga() {} public Manga() {}
public Manga(String title) {
this.title = title;
}
public Manga(String title, String author, String artist, String url,
String description, String genre, String status, int rank,
String thumbnail_url) {
this.title = title;
this.author = author;
this.artist = artist;
this.url = url;
this.description = description;
this.genre = genre;
this.status = status;
this.rank = rank;
this.thumbnail_url = thumbnail_url;
}
public static Manga newManga(String title, String author, String artist, String url,
String description, String genre, String status, int rank,
String thumbnail_url) {
return new Manga(title, author, artist, url, description, genre, status, rank, thumbnail_url);
}
public static void copyFromNetwork(Manga local, Manga network) { public static void copyFromNetwork(Manga local, Manga network) {
if (network.title != null) if (network.title != null)
local.title = network.title; local.title = network.title;
@ -107,6 +83,7 @@ public class Manga {
local.thumbnail_url = network.thumbnail_url; local.thumbnail_url = network.thumbnail_url;
local.initialized = true; local.initialized = true;
} }
@Override @Override

View file

@ -2,9 +2,6 @@ package eu.kanade.mangafeed.data.tables;
import android.support.annotation.NonNull; import android.support.annotation.NonNull;
/**
* Created by len on 23/09/2015.
*/
public class MangasTable { public class MangasTable {
@NonNull @NonNull
@ -41,7 +38,7 @@ public class MangasTable {
public static final String COLUMN_THUMBNAIL_URL = "thumbnail_url"; public static final String COLUMN_THUMBNAIL_URL = "thumbnail_url";
@NonNull @NonNull
public static final String COLUMN_RANK = "rank"; public static final String COLUMN_FAVORITE = "favorite";
@NonNull @NonNull
public static final String COLUMN_LAST_UPDATE = "last_update"; public static final String COLUMN_LAST_UPDATE = "last_update";
@ -78,7 +75,7 @@ public class MangasTable {
+ COLUMN_TITLE + " TEXT NOT NULL, " + COLUMN_TITLE + " TEXT NOT NULL, "
+ COLUMN_STATUS + " TEXT, " + COLUMN_STATUS + " TEXT, "
+ COLUMN_THUMBNAIL_URL + " TEXT, " + COLUMN_THUMBNAIL_URL + " TEXT, "
+ COLUMN_RANK + " INTEGER, " + COLUMN_FAVORITE + " INTEGER NOT NULL, "
+ COLUMN_LAST_UPDATE + " LONG, " + COLUMN_LAST_UPDATE + " LONG, "
+ COLUMN_INITIALIZED + " BOOLEAN NOT NULL, " + COLUMN_INITIALIZED + " BOOLEAN NOT NULL, "
+ COLUMN_VIEWER + " INTEGER NOT NULL, " + COLUMN_VIEWER + " INTEGER NOT NULL, "

View file

@ -52,8 +52,12 @@ public class LibraryPresenter extends BasePresenter<LibraryFragment> {
.observeOn(Schedulers.io()) .observeOn(Schedulers.io())
.map(checkedItems::keyAt) .map(checkedItems::keyAt)
.map(adapter::getItem) .map(adapter::getItem)
.map(manga -> {
manga.favorite = false;
return manga;
})
.toList() .toList()
.flatMap(db::deleteMangas) .flatMap(db::insertMangas)
.subscribe()); .subscribe());
} }

View file

@ -17,6 +17,8 @@ public class MangaDetailPresenter extends BasePresenter<MangaDetailActivity> {
@Inject DatabaseHelper db; @Inject DatabaseHelper db;
private long mangaId; private long mangaId;
private Manga manga;
private static final int DB_MANGA = 1; private static final int DB_MANGA = 1;
@Override @Override
@ -24,9 +26,11 @@ public class MangaDetailPresenter extends BasePresenter<MangaDetailActivity> {
super.onCreate(savedState); super.onCreate(savedState);
restartableLatestCache(DB_MANGA, restartableLatestCache(DB_MANGA,
this::getDbMangaObservable, () -> getDbMangaObservable()
.doOnNext(manga -> this.manga = manga),
(view, manga) -> { (view, manga) -> {
view.setManga(manga); view.setManga(manga);
view.setFavoriteBtnVisible(!manga.favorite);
EventBus.getDefault().postSticky(manga); EventBus.getDefault().postSticky(manga);
}); });
} }
@ -41,7 +45,6 @@ public class MangaDetailPresenter extends BasePresenter<MangaDetailActivity> {
private Observable<Manga> getDbMangaObservable() { private Observable<Manga> getDbMangaObservable() {
return db.getManga(mangaId) return db.getManga(mangaId)
.subscribeOn(Schedulers.io()) .subscribeOn(Schedulers.io())
.take(1)
.flatMap(Observable::from) .flatMap(Observable::from)
.observeOn(AndroidSchedulers.mainThread()); .observeOn(AndroidSchedulers.mainThread());
} }
@ -51,4 +54,14 @@ public class MangaDetailPresenter extends BasePresenter<MangaDetailActivity> {
start(DB_MANGA); start(DB_MANGA);
} }
public void setFavoriteVisibility() {
if (getView() != null) {
getView().setFavoriteBtnVisible(!manga.favorite);
}
}
public boolean addToFavorites() {
manga.favorite = true;
return db.insertMangaBlock(manga).numberOfRowsUpdated() == 1;
}
} }

View file

@ -10,7 +10,9 @@ 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.Menu;
import android.view.MenuItem; import android.view.MenuItem;
import android.widget.Toast;
import butterknife.Bind; import butterknife.Bind;
import butterknife.ButterKnife; import butterknife.ButterKnife;
@ -32,6 +34,7 @@ public class MangaDetailActivity extends BaseRxActivity<MangaDetailPresenter> {
private MangaDetailAdapter adapter; private MangaDetailAdapter adapter;
private long manga_id; private long manga_id;
private boolean is_online; private boolean is_online;
private MenuItem favoriteBtn;
public final static String MANGA_ID = "manga_id"; public final static String MANGA_ID = "manga_id";
public final static String MANGA_ONLINE = "manga_online"; public final static String MANGA_ONLINE = "manga_online";
@ -62,12 +65,23 @@ public class MangaDetailActivity extends BaseRxActivity<MangaDetailPresenter> {
getPresenter().queryManga(manga_id); getPresenter().queryManga(manga_id);
} }
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.manga, menu);
favoriteBtn = menu.findItem(R.id.action_favorite);
getPresenter().setFavoriteVisibility();
return true;
}
@Override @Override
public boolean onOptionsItemSelected(MenuItem item) { public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) { switch (item.getItemId()) {
case android.R.id.home: case android.R.id.home:
finish(); finish();
return true; return true;
case R.id.action_favorite:
onFavoriteClick();
return true;
} }
return super.onOptionsItemSelected(item); return super.onOptionsItemSelected(item);
} }
@ -98,10 +112,22 @@ public class MangaDetailActivity extends BaseRxActivity<MangaDetailPresenter> {
setToolbarTitle(manga.title); setToolbarTitle(manga.title);
} }
public void setFavoriteBtnVisible(boolean visible) {
if (favoriteBtn != null)
favoriteBtn.setVisible(visible);
}
public boolean isOnlineManga() { public boolean isOnlineManga() {
return is_online; return is_online;
} }
private void onFavoriteClick() {
if (getPresenter().addToFavorites()) {
Toast.makeText(this, getString(R.string.toast_added_favorites), Toast.LENGTH_SHORT)
.show();
}
}
class MangaDetailAdapter extends FragmentPagerAdapter { class MangaDetailAdapter extends FragmentPagerAdapter {
final int PAGE_COUNT = 2; final int PAGE_COUNT = 2;

View file

@ -101,6 +101,9 @@ public class LoginDialogPreference extends DialogPreference {
if (requestSubscription != null) if (requestSubscription != null)
requestSubscription.unsubscribe(); requestSubscription.unsubscribe();
if (username.getText().length() == 0 || password.getText().length() == 0)
return;
loginBtn.setProgress(1); loginBtn.setProgress(1);
requestSubscription = source.login(username.getText().toString(), requestSubscription = source.login(username.getText().toString(),

Binary file not shown.

After

Width:  |  Height:  |  Size: 387 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 262 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 479 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 707 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 901 B

View file

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<item
android:id="@+id/action_favorite"
android:title="@string/action_favorite"
android:icon="@drawable/ic_action_favorite"
app:showAsAction="always"
android:visible="false"/>
</menu>

View file

@ -71,5 +71,7 @@
<string name="success">Success</string> <string name="success">Success</string>
<string name="invalid_login">Login error</string> <string name="invalid_login">Login error</string>
<string name="loading">Loading…</string> <string name="loading">Loading…</string>
<string name="toast_added_favorites">Added to favorites</string>
<string name="action_favorite">Favorite</string>
</resources> </resources>

View file

@ -1,4 +1,5 @@
// Top-level build file where you can add configuration options common to all sub-projects/modules. // Top-level build file where you can add configuration options common to all sub-projects/modules.
apply plugin: 'com.github.ben-manes.versions'
buildscript { buildscript {
repositories { repositories {
@ -13,6 +14,7 @@ buildscript {
classpath 'com.zeroturnaround.jrebel.android:jr-android-gradle:0.9.+' classpath 'com.zeroturnaround.jrebel.android:jr-android-gradle:0.9.+'
classpath 'com.neenbedankt.gradle.plugins:android-apt:1.7' classpath 'com.neenbedankt.gradle.plugins:android-apt:1.7'
classpath 'me.tatarka:gradle-retrolambda:3.2.3' classpath 'me.tatarka:gradle-retrolambda:3.2.3'
classpath 'com.github.ben-manes:gradle-versions-plugin:0.11.3'
// NOTE: Do not place your application dependencies here; they belong // NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files // in the individual module build.gradle files
} }