diff options
author | Allan Wang <me@allanwang.ca> | 2017-06-22 15:20:11 -0700 |
---|---|---|
committer | Allan Wang <me@allanwang.ca> | 2017-06-22 15:20:11 -0700 |
commit | 56678f8a76a4034ae8a63c92e49ba39cc54ee057 (patch) | |
tree | 7ebad2c45dc573d6e28824462478b6f9d2bf30ed /app/src | |
parent | 297e6704a6332c43408b8a3579ccfaccaa6591a1 (diff) | |
download | frost-56678f8a76a4034ae8a63c92e49ba39cc54ee057.tar.gz frost-56678f8a76a4034ae8a63c92e49ba39cc54ee057.tar.bz2 frost-56678f8a76a4034ae8a63c92e49ba39cc54ee057.zip |
Add notification filtering
Diffstat (limited to 'app/src')
11 files changed, 272 insertions, 22 deletions
diff --git a/app/src/main/kotlin/com/pitchedapps/frost/SettingsActivity.kt b/app/src/main/kotlin/com/pitchedapps/frost/SettingsActivity.kt index bcf30614..ca823513 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/SettingsActivity.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/SettingsActivity.kt @@ -11,19 +11,37 @@ import ca.allanwang.kau.utils.* import ca.allanwang.kau.views.RippleCanvas import com.mikepenz.google_material_typeface_library.GoogleMaterial import com.pitchedapps.frost.utils.* +import com.pitchedapps.frost.views.Keywords /** * Created by Allan Wang on 2017-06-06. */ class SettingsActivity : KPrefActivity() { + override fun kPrefCoreAttributes(): CoreAttributeContract.() -> Unit = { textColor = { Prefs.textColor } - accentColor = { Prefs.textColor } + accentColor = { + if (Prefs.headerColor.isColorVisibleOn(Prefs.bgColor, 100)) Prefs.headerColor + else Prefs.textColor + } } override fun onCreateKPrefs(savedInstanceState: android.os.Bundle?): KPrefAdapterBuilder.() -> Unit = { - header(R.string.settings) + subItems(R.string.appearance, subPrefsAppearance()) { + descRes = R.string.appearance_desc + iicon = GoogleMaterial.Icon.gmd_palette + } + subItems(R.string.notifications, subPrefsNotifications()) { + descRes = R.string.notifications_desc + iicon = GoogleMaterial.Icon.gmd_notifications + } + } + + fun subPrefsAppearance(): KPrefAdapterBuilder.() -> Unit = { + + header(R.string.base_customization) + text(R.string.theme, { Prefs.theme }, { Prefs.theme = it }) { onClick = { _, _, item -> @@ -88,15 +106,32 @@ class SettingsActivity : KPrefActivity() { onDisabledClick = { itemView, _, _ -> itemView.snackbar(R.string.requires_custom_theme); true } allowCustom = true } + + checkbox(R.string.rounded_icons, { Prefs.showRoundedIcons }, { Prefs.showRoundedIcons = it }) + + checkbox(R.string.fancy_animations, { Prefs.animate }, { Prefs.animate = it; animate = it }) { + descRes = R.string.fancy_animations_desc + } + + header(R.string.feed_customization) + + checkbox(R.string.suggested_friends, { Prefs.showSuggestedFriends }, { Prefs.showSuggestedFriends = it }) { + descRes = R.string.suggested_friends_desc + } } - text(R.string.notifications, { Prefs.notificationFreq }, { Prefs.notificationFreq = it; reloadByTitle(R.string.notifications) }) { + + } + + fun subPrefsNotifications(): KPrefAdapterBuilder.() -> Unit = { + + text(R.string.notification_frequency, { Prefs.notificationFreq }, { Prefs.notificationFreq = it; reloadByTitle(R.string.notifications) }) { val options = longArrayOf(-1, 15, 30, 60, 120, 180, 300, 1440, 2880) val texts = options.map { this@SettingsActivity.minuteToText(it) } onClick = { _, _, item -> this@SettingsActivity.materialDialogThemed { - title(R.string.notifications) + title(R.string.notification_frequency) items(texts) itemsCallbackSingleChoice(options.indexOf(item.pref), { _, _, which, text -> @@ -110,6 +145,23 @@ class SettingsActivity : KPrefActivity() { textGetter = { this@SettingsActivity.minuteToText(it) } } + text<String?>(R.string.notification_keywords, { null }, { }) { + descRes = R.string.notification_keywords_desc + onClick = { + _, _, _ -> + val keywordView = Keywords(this@SettingsActivity) + this@SettingsActivity.materialDialogThemed { + title(R.string.notification_keywords) + customView(keywordView, false) + canceledOnTouchOutside(false) + positiveText(R.string.kau_done) + negativeText(R.string.kau_cancel) + onPositive { _, _ -> keywordView.save() } + } + true + } + } + } fun shouldRestartMain() { @@ -118,6 +170,7 @@ class SettingsActivity : KPrefActivity() { override fun onCreate(savedInstanceState: Bundle?) { setFrostTheme(true) + animate = Prefs.animate super.onCreate(savedInstanceState) themeExterior(false) } @@ -132,7 +185,8 @@ class SettingsActivity : KPrefActivity() { } override fun onBackPressed() { - finishSlideOut() + if (!super.backPress()) + finishSlideOut() } override fun onCreateOptionsMenu(menu: Menu): Boolean { diff --git a/app/src/main/kotlin/com/pitchedapps/frost/services/NotificationService.kt b/app/src/main/kotlin/com/pitchedapps/frost/services/NotificationService.kt index 03dd21a4..23bf7f96 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/services/NotificationService.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/services/NotificationService.kt @@ -18,6 +18,7 @@ import com.pitchedapps.frost.facebook.FACEBOOK_COM import com.pitchedapps.frost.facebook.FB_URL_BASE import com.pitchedapps.frost.facebook.FbTab import com.pitchedapps.frost.utils.L +import com.pitchedapps.frost.utils.Prefs import com.pitchedapps.frost.utils.frostAnswersCustom import com.pitchedapps.frost.utils.frostNotification import org.jetbrains.anko.doAsync @@ -83,6 +84,7 @@ class NotificationService : JobService() { val abbr = element.getElementsByTag("abbr") val timeString = abbr?.text() var text = a.text().replace("\u00a0", " ") //remove + if (Prefs.notificationKeywords.any { text.contains(it, ignoreCase = true) }) return null //notification filtered out if (timeString != null) text = text.removeSuffix(timeString) text = text.trim() val abbrData = abbr?.attr("data-store") diff --git a/app/src/main/kotlin/com/pitchedapps/frost/utils/Prefs.kt b/app/src/main/kotlin/com/pitchedapps/frost/utils/Prefs.kt index 83564be9..428d0c30 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/utils/Prefs.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/utils/Prefs.kt @@ -2,6 +2,7 @@ package com.pitchedapps.frost.utils import android.graphics.Color import ca.allanwang.kau.kpref.KPref +import ca.allanwang.kau.kpref.StringSet import ca.allanwang.kau.kpref.kpref import ca.allanwang.kau.utils.lazyResettable import com.pitchedapps.frost.injectors.InjectorContract @@ -60,4 +61,12 @@ object Prefs : KPref() { val isCustomTheme: Boolean get() = t == Theme.CUSTOM + + var showRoundedIcons: Boolean by kpref("rounded_icons", true) + + var showSuggestedFriends: Boolean by kpref("suggested_friends_feed", true) + + var animate: Boolean by kpref("fancy_animations", true) + + var notificationKeywords: StringSet by kpref("notification_keywords", mutableSetOf<String>()) } diff --git a/app/src/main/kotlin/com/pitchedapps/frost/views/AccountItem.kt b/app/src/main/kotlin/com/pitchedapps/frost/views/AccountItem.kt index 3de038bf..c9ee5a76 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/views/AccountItem.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/views/AccountItem.kt @@ -33,7 +33,7 @@ class AccountItem(val cookie: CookieModel?) : AbstractItem<AccountItem, AccountI override fun getLayoutRes(): Int = R.layout.view_account - override fun bindView(viewHolder: ViewHolder, payloads: List<Any>) { + override fun bindView(viewHolder: ViewHolder, payloads: List<Any>?) { super.bindView(viewHolder, payloads) with(viewHolder) { text.visibility = View.INVISIBLE diff --git a/app/src/main/kotlin/com/pitchedapps/frost/views/Keywords.kt b/app/src/main/kotlin/com/pitchedapps/frost/views/Keywords.kt new file mode 100644 index 00000000..25079834 --- /dev/null +++ b/app/src/main/kotlin/com/pitchedapps/frost/views/Keywords.kt @@ -0,0 +1,101 @@ +package com.pitchedapps.frost.views + +import android.content.Context +import android.graphics.drawable.Drawable +import android.support.constraint.ConstraintLayout +import android.support.v7.widget.AppCompatEditText +import android.support.v7.widget.AppCompatTextView +import android.support.v7.widget.LinearLayoutManager +import android.support.v7.widget.RecyclerView +import android.util.AttributeSet +import android.view.View +import android.widget.ImageView +import ca.allanwang.kau.kpref.StringSet +import ca.allanwang.kau.utils.bindView +import ca.allanwang.kau.utils.string +import ca.allanwang.kau.utils.tint +import ca.allanwang.kau.utils.toDrawable +import com.mikepenz.fastadapter.FastAdapter +import com.mikepenz.fastadapter.commons.adapters.FastItemAdapter +import com.mikepenz.fastadapter.items.AbstractItem +import com.mikepenz.fastadapter.listeners.ClickEventHook +import com.mikepenz.google_material_typeface_library.GoogleMaterial +import com.mikepenz.iconics.typeface.IIcon +import com.pitchedapps.frost.R +import com.pitchedapps.frost.utils.Prefs + + +/** + * Created by Allan Wang on 2017-06-19. + */ +class Keywords @JvmOverloads constructor( + context: Context, attrs: AttributeSet? = null, defStyleAttr: Int = 0 +) : ConstraintLayout(context, attrs, defStyleAttr) { + + val editText: AppCompatEditText by bindView(R.id.edit_text) + val addIcon: ImageView by bindView(R.id.add_icon) + val recycler: RecyclerView by bindView(R.id.recycler) + val adapter = FastItemAdapter<KeywordItem>() + + init { + inflate(context, R.layout.view_keywords, this) + editText.tint(Prefs.textColor) + addIcon.setImageDrawable(GoogleMaterial.Icon.gmd_add.keywordDrawable(context)) + addIcon.setOnClickListener { + if (editText.text.isEmpty()) editText.error = context.string(R.string.empty_keyword) + else { + adapter.add(0, KeywordItem(editText.text.toString())) + editText.text.clear() + } + } + adapter.add(Prefs.notificationKeywords.map { KeywordItem(it) }) + recycler.layoutManager = LinearLayoutManager(context) + recycler.adapter = adapter + adapter.withEventHook(object : ClickEventHook<KeywordItem>() { + override fun onBind(viewHolder: RecyclerView.ViewHolder): View? + = (viewHolder as? KeywordItem.ViewHolder)?.delete + + override fun onClick(v: View, position: Int, fastAdapter: FastAdapter<KeywordItem>, item: KeywordItem) { + adapter.remove(position) + } + }) + } + + fun save() { + val keywords = adapter.adapterItems.map { it.keyword } + Prefs.notificationKeywords = StringSet(keywords) + } + + +} + +private fun IIcon.keywordDrawable(context: Context): Drawable = toDrawable(context, 20, Prefs.textColor) + +class KeywordItem(val keyword: String) : AbstractItem<KeywordItem, KeywordItem.ViewHolder>() { + + override fun getViewHolder(v: View): ViewHolder = ViewHolder(v) + + override fun getType(): Int = R.id.item_keyword + + override fun getLayoutRes(): Int = R.layout.item_keyword + + override fun bindView(holder: ViewHolder, payloads: MutableList<Any>?) { + super.bindView(holder, payloads) + holder.text.text = keyword + } + + override fun unbindView(holder: ViewHolder) { + super.unbindView(holder) + holder.text.text = null + } + + class ViewHolder(v: View) : RecyclerView.ViewHolder(v) { + val text: AppCompatTextView by bindView(R.id.keyword_text) + val delete: ImageView by bindView(R.id.keyword_delete) + + init { + text.setTextColor(Prefs.textColor) + delete.setImageDrawable(GoogleMaterial.Icon.gmd_delete.keywordDrawable(itemView.context)) + } + } +}
\ No newline at end of file diff --git a/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewClient.kt b/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewClient.kt index a791363e..8b1eca1e 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewClient.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewClient.kt @@ -12,10 +12,7 @@ import com.pitchedapps.frost.MainActivity import com.pitchedapps.frost.SelectorActivity import com.pitchedapps.frost.facebook.FACEBOOK_COM import com.pitchedapps.frost.facebook.FbCookie -import com.pitchedapps.frost.injectors.CssHider -import com.pitchedapps.frost.injectors.JsActions -import com.pitchedapps.frost.injectors.JsAssets -import com.pitchedapps.frost.injectors.jsInject +import com.pitchedapps.frost.injectors.* import com.pitchedapps.frost.utils.L import com.pitchedapps.frost.utils.Prefs import com.pitchedapps.frost.utils.cookies @@ -53,7 +50,9 @@ open class FrostWebViewClient(val webCore: FrostWebViewCore) : WebViewClient() { refreshObservable.onNext(false) return } - view.jsInject(JsActions.LOGIN_CHECK, JsAssets.HEADER_BADGES.maybe(webCore.baseEnum != null)) + view.jsInject(JsActions.LOGIN_CHECK, + CssAssets.ROUND_ICONS.maybe(Prefs.showRoundedIcons), + JsAssets.HEADER_BADGES.maybe(webCore.baseEnum != null)) onPageFinishedActions(url) } diff --git a/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewCore.kt b/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewCore.kt index 6e9e956f..b953e092 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewCore.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/web/FrostWebViewCore.kt @@ -18,6 +18,7 @@ import ca.allanwang.kau.utils.fadeOut import ca.allanwang.kau.utils.isVisible import com.pitchedapps.frost.facebook.FbTab import com.pitchedapps.frost.facebook.USER_AGENT_BASIC +import com.pitchedapps.frost.utils.Prefs import io.reactivex.Scheduler import io.reactivex.android.schedulers.AndroidSchedulers import io.reactivex.disposables.Disposable @@ -93,7 +94,7 @@ class FrostWebViewCore @JvmOverloads constructor( if (isVisible()) fadeOut(duration = 200L) } else if (loading) { dispose?.dispose() - if (animate) circularReveal(offset = 150L) + if (animate && Prefs.animate) circularReveal(offset = 150L) else fadeIn(duration = 100L) } } diff --git a/app/src/main/res/layout/item_keyword.xml b/app/src/main/res/layout/item_keyword.xml new file mode 100644 index 00000000..2c24997f --- /dev/null +++ b/app/src/main/res/layout/item_keyword.xml @@ -0,0 +1,25 @@ +<?xml version="1.0" encoding="utf-8"?> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:gravity="center_vertical" + android:orientation="horizontal" + android:paddingBottom="8dp" + android:paddingTop="8dp"> + + <android.support.v7.widget.AppCompatTextView + android:id="@+id/keyword_text" + android:layout_width="0dp" + android:layout_height="wrap_content" + android:layout_weight="1" + android:paddingEnd="@dimen/kau_dialog_margin" /> + + <ImageView + android:id="@+id/keyword_delete" + android:layout_width="48dp" + android:layout_height="48dp" + android:background="?android:attr/selectableItemBackground" + android:scaleType="center" /> + + +</LinearLayout>
\ No newline at end of file diff --git a/app/src/main/res/layout/view_keywords.xml b/app/src/main/res/layout/view_keywords.xml new file mode 100644 index 00000000..88498826 --- /dev/null +++ b/app/src/main/res/layout/view_keywords.xml @@ -0,0 +1,44 @@ +<?xml version="1.0" encoding="utf-8"?> +<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:app="http://schemas.android.com/apk/res-auto" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:paddingBottom="@dimen/kau_dialog_margin_bottom" + android:paddingEnd="@dimen/kau_dialog_margin" + android:paddingStart="@dimen/kau_dialog_margin"> + + <android.support.v7.widget.AppCompatEditText + android:id="@+id/edit_text" + android:layout_width="0dp" + android:layout_height="48dp" + android:hint="@string/hint_keyword" + android:paddingEnd="@dimen/kau_dialog_margin" + app:layout_constraintVertical_bias="0.5" + app:layout_constraintEnd_toStartOf="@+id/add_icon" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toTopOf="parent" /> + + <ImageView + android:id="@id/add_icon" + android:layout_width="48dp" + android:layout_height="48dp" + android:layout_marginBottom="8dp" + android:layout_marginTop="8dp" + android:background="?android:attr/selectableItemBackgroundBorderless" + android:scaleType="center" + app:layout_constraintBottom_toBottomOf="@id/edit_text" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toEndOf="@id/edit_text" + app:layout_constraintTop_toTopOf="parent" /> + + <android.support.v7.widget.RecyclerView + android:id="@+id/recycler" + android:layout_width="0dp" + android:layout_height="0dp" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintHeight_default="wrap" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toBottomOf="@id/edit_text" /> + +</android.support.constraint.ConstraintLayout>
\ No newline at end of file diff --git a/app/src/main/res/values/ids.xml b/app/src/main/res/values/ids.xml index 76a167af..9ce1b4e3 100644 --- a/app/src/main/res/values/ids.xml +++ b/app/src/main/res/values/ids.xml @@ -1,14 +1,5 @@ <?xml version="1.0" encoding="utf-8"?> <resources> <item name="item_account" type="id" /> - <item name="pref_item_header" type="id" /> - <item name="pref_item_text" type="id" /> - <item name="pref_item_checkbox" type="id" /> - - <item name="pref_view_title" type="id" /> - <item name="pref_view_desc" type="id" /> - <item name="pref_view_icon" type="id" /> - <item name="pref_view_icon_frame" type="id" /> - <item name="pref_view_inner_frame" type="id" /> - <item name="pref_view_checkbox" type="id" /> + <item name="item_keyword" type="id" /> </resources>
\ No newline at end of file diff --git a/app/src/main/res/values/strings_preferences b/app/src/main/res/values/strings_preferences index 1352360c..2aad590f 100644 --- a/app/src/main/res/values/strings_preferences +++ b/app/src/main/res/values/strings_preferences @@ -1,7 +1,31 @@ <resources> + <!--categories--> + <string name="appearance">Appearance</string> + <string name="appearance_desc">Theme, Items to display, etc</string> + + <string name="notifications_desc">Frequency, filters, etc</string> + + <!--themes--> <string name="theme">Theme</string> <string name="text_color">Text Color</string> <string name="background_color">Background Color</string> <string name="header_color">Header Color</string> <string name="icon_color">Icon Color</string> + + <string name="rounded_icons">Rounded Icons</string> + <string name="base_customization">Base Customization</string> + <string name="feed_customization">Feed Customization</string> + <string name="suggested_friends">Suggested Friends</string> + <string name="suggested_friends_desc">Show suggested friends in the feed</string> + + <string name="notification_frequency">Notification Frequency</string> + <string name="notification_keywords">Keywords</string> + <string name="notification_keywords_desc">Does not notify when notification contains any of these keys.</string> + <string name="add_keyword">Add Keyword</string> + <string name="hint_keyword">Type keyword and press +</string> + <string name="empty_keyword">Empty Keyword</string> + + <string name="fancy_animations">Fancy Animations</string> + <string name="fancy_animations_desc">Reveal webviews using ripples and animate transitions</string> + </resources>
\ No newline at end of file |