added scope for filters
This commit is contained in:
parent
3948954973
commit
b7f7944e00
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* Twidere - Twitter client for Android
|
||||
*
|
||||
* Copyright (C) 2012-2017 Mariotaku Lee <mariotaku.lee@gmail.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package org.mariotaku.twidere.annotation;
|
||||
|
||||
import android.support.annotation.IntDef;
|
||||
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
|
||||
@IntDef(value = {FilterScope.HOME, FilterScope.INTERACTIONS, FilterScope.MESSAGES,
|
||||
FilterScope.SEARCH_RESULT, FilterScope.LIST_GROUP_TIMELINE, FilterScope.FAVORITES,
|
||||
FilterScope.ALL}, flag = true)
|
||||
@Retention(RetentionPolicy.SOURCE)
|
||||
public @interface FilterScope {
|
||||
int HOME = 0x1;
|
||||
int INTERACTIONS = 0x2;
|
||||
int MESSAGES = 0x4;
|
||||
int SEARCH_RESULT = 0x8;
|
||||
int LIST_GROUP_TIMELINE = 0x16;
|
||||
int FAVORITES = 0x32;
|
||||
|
||||
// Contains all flags
|
||||
int ALL = 0xFFFFFFFF;
|
||||
}
|
|
@ -25,6 +25,7 @@ import com.bluelinelabs.logansquare.annotation.JsonObject;
|
|||
|
||||
import org.mariotaku.library.objectcursor.annotation.CursorField;
|
||||
import org.mariotaku.library.objectcursor.annotation.CursorObject;
|
||||
import org.mariotaku.twidere.annotation.FilterScope;
|
||||
import org.mariotaku.twidere.model.util.UserKeyConverter;
|
||||
import org.mariotaku.twidere.model.util.UserKeyCursorFieldConverter;
|
||||
import org.mariotaku.twidere.provider.TwidereDataStore;
|
||||
|
@ -109,6 +110,10 @@ public class FiltersData {
|
|||
@CursorField(value = Filters.Users.SOURCE, type = "INTEGER DEFAULT -1")
|
||||
@JsonField(name = "source")
|
||||
long source = -1;
|
||||
@CursorField(value = Filters.Users.SCOPE, type = "INTEGER DEFAULT 0")
|
||||
@JsonField(name = "scope")
|
||||
@FilterScope
|
||||
int scope = 0;
|
||||
|
||||
public UserKey getUserKey() {
|
||||
return userKey;
|
||||
|
@ -142,6 +147,15 @@ public class FiltersData {
|
|||
this.source = source;
|
||||
}
|
||||
|
||||
@FilterScope
|
||||
public int getScope() {
|
||||
return scope;
|
||||
}
|
||||
|
||||
public void setScope(@FilterScope int scope) {
|
||||
this.scope = scope;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "UserItem{" +
|
||||
|
@ -150,6 +164,7 @@ public class FiltersData {
|
|||
", name='" + name + '\'' +
|
||||
", screenName='" + screenName + '\'' +
|
||||
", source=" + source +
|
||||
", scope=" + scope +
|
||||
'}';
|
||||
}
|
||||
|
||||
|
@ -192,6 +207,11 @@ public class FiltersData {
|
|||
@Nullable
|
||||
UserKey userKey = null;
|
||||
|
||||
@CursorField(value = Filters.SCOPE, type = "INTEGER DEFAULT 0")
|
||||
@JsonField(name = "scope")
|
||||
@FilterScope
|
||||
int scope = 0;
|
||||
|
||||
public long getId() {
|
||||
return _id;
|
||||
}
|
||||
|
@ -221,6 +241,15 @@ public class FiltersData {
|
|||
this.userKey = userKey;
|
||||
}
|
||||
|
||||
@FilterScope
|
||||
public int getScope() {
|
||||
return scope;
|
||||
}
|
||||
|
||||
public void setScope(@FilterScope int scope) {
|
||||
this.scope = scope;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "BaseItem{" +
|
||||
|
@ -228,6 +257,7 @@ public class FiltersData {
|
|||
", value='" + value + '\'' +
|
||||
", source=" + source +
|
||||
", userKey=" + userKey +
|
||||
", scope=" + scope +
|
||||
'}';
|
||||
}
|
||||
|
||||
|
|
|
@ -498,11 +498,7 @@ public interface TwidereDataStore {
|
|||
|
||||
String USER_KEY = "user_key";
|
||||
|
||||
String ENABLE_IN_HOME_TIMELINE = "enable_in_home_timeline";
|
||||
|
||||
String ENABLE_IN_MENTIONS = "enable_in_mentions";
|
||||
|
||||
String ENABLE_FOR_RETWEETS = "enable_for_retweets";
|
||||
String SCOPE = "scope";
|
||||
|
||||
String[] COLUMNS = FiltersData$BaseItemTableInfo.COLUMNS;
|
||||
|
||||
|
@ -543,6 +539,7 @@ public interface TwidereDataStore {
|
|||
String NAME = "name";
|
||||
String SCREEN_NAME = "screen_name";
|
||||
String SOURCE = "source";
|
||||
String SCOPE = "scope";
|
||||
|
||||
String[] COLUMNS = FiltersData$UserItemTableInfo.COLUMNS;
|
||||
|
||||
|
@ -733,12 +730,6 @@ public interface TwidereDataStore {
|
|||
|
||||
String ACCOUNT_COLOR = "account_color";
|
||||
|
||||
String USER_NICKNAME = "user_nickname";
|
||||
|
||||
String QUOTED_USER_NICKNAME = "quoted_user_nickname";
|
||||
String RETWEET_USER_NICKNAME = "retweet_user_nickname";
|
||||
String IN_REPLY_TO_USER_NICKNAME = "in_reply_to_user_nickname";
|
||||
|
||||
String FILTER_FLAGS = "filter_flags";
|
||||
|
||||
String DEFAULT_SORT_ORDER = TIMESTAMP + " DESC, " + SORT_ID + " DESC, " + ID
|
||||
|
|
|
@ -30,7 +30,7 @@ import org.mariotaku.twidere.model.UserKey;
|
|||
public interface Constants extends TwidereConstants {
|
||||
|
||||
String DATABASES_NAME = "twidere.sqlite";
|
||||
int DATABASES_VERSION = 184;
|
||||
int DATABASES_VERSION = 185;
|
||||
|
||||
int EXTRA_FEATURES_NOTICE_VERSION = 2;
|
||||
|
||||
|
|
|
@ -76,6 +76,7 @@ import org.mariotaku.twidere.R
|
|||
import org.mariotaku.twidere.activity.iface.IControlBarActivity.ControlBarShowHideHelper
|
||||
import org.mariotaku.twidere.adapter.SupportTabsAdapter
|
||||
import org.mariotaku.twidere.annotation.CustomTabType
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.annotation.NavbarStyle
|
||||
import org.mariotaku.twidere.annotation.ReadPositionTag
|
||||
import org.mariotaku.twidere.constant.*
|
||||
|
@ -946,7 +947,7 @@ class HomeActivity : BaseActivity(), OnClickListener, OnPageChangeListener, Supp
|
|||
}.fold(0L, Math::max)
|
||||
val count = DataStoreUtils.getStatusesCount(context, preferences,
|
||||
Statuses.CONTENT_URI, spec.args, Statuses.TIMESTAMP, position,
|
||||
true, accountKeys)
|
||||
true, accountKeys, FilterScope.HOME)
|
||||
result.put(i, count)
|
||||
publishProgress(TabBadge(i, count))
|
||||
}
|
||||
|
|
|
@ -52,7 +52,7 @@ fun Account.toParcelable(accountKey: UserKey, position: Long = 0,
|
|||
obj.is_protected = isLocked
|
||||
obj.name = name
|
||||
obj.screen_name = username
|
||||
if (note?.isHtml ?: false) {
|
||||
if (note?.isHtml == true) {
|
||||
val descriptionHtml = HtmlSpanBuilder.fromHtml(note, note, MastodonSpanProcessor)
|
||||
obj.description_unescaped = descriptionHtml?.toString()
|
||||
obj.description_plain = obj.description_unescaped
|
||||
|
|
|
@ -37,6 +37,7 @@ import org.mariotaku.sqliteqb.library.Expression
|
|||
import org.mariotaku.twidere.R
|
||||
import org.mariotaku.twidere.adapter.iface.ILoadMoreSupportAdapter
|
||||
import org.mariotaku.twidere.adapter.iface.ILoadMoreSupportAdapter.IndicatorPosition
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.constant.IntentConstants.EXTRA_FROM_USER
|
||||
import org.mariotaku.twidere.extension.queryOne
|
||||
import org.mariotaku.twidere.loader.ExtendedObjectCursorLoader
|
||||
|
@ -68,6 +69,9 @@ abstract class CursorActivitiesFragment : AbsActivitiesFragment() {
|
|||
|
||||
protected abstract val isFilterEnabled: Boolean
|
||||
|
||||
@FilterScope
|
||||
protected abstract val filterScopes: Int
|
||||
|
||||
private var contentObserver: ContentObserver? = null
|
||||
|
||||
private val accountListener: OnAccountsUpdateListener = OnAccountsUpdateListener {
|
||||
|
@ -213,7 +217,7 @@ abstract class CursorActivitiesFragment : AbsActivitiesFragment() {
|
|||
|
||||
protected fun getFiltersWhere(table: String): Expression? {
|
||||
if (!isFilterEnabled) return null
|
||||
return DataStoreUtils.buildActivityFilterWhereClause(table, null)
|
||||
return DataStoreUtils.buildActivityFilterWhereClause(table, null, filterScopes)
|
||||
}
|
||||
|
||||
protected open fun processWhere(where: Expression, whereArgs: Array<String>): ParameterizedExpression {
|
||||
|
|
|
@ -38,6 +38,7 @@ import org.mariotaku.twidere.R
|
|||
import org.mariotaku.twidere.adapter.ListParcelableStatusesAdapter
|
||||
import org.mariotaku.twidere.adapter.iface.ILoadMoreSupportAdapter
|
||||
import org.mariotaku.twidere.adapter.iface.ILoadMoreSupportAdapter.IndicatorPosition
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.constant.IntentConstants.EXTRA_FROM_USER
|
||||
import org.mariotaku.twidere.loader.ExtendedObjectCursorLoader
|
||||
import org.mariotaku.twidere.model.ParameterizedExpression
|
||||
|
@ -75,6 +76,8 @@ abstract class CursorStatusesFragment : AbsStatusesFragment() {
|
|||
abstract val isFilterEnabled: Boolean
|
||||
abstract val notificationType: Int
|
||||
abstract val contentUri: Uri
|
||||
@FilterScope
|
||||
abstract val filterScopes: Int
|
||||
|
||||
private var contentObserver: ContentObserver? = null
|
||||
private val accountListener: OnAccountsUpdateListener = OnAccountsUpdateListener {
|
||||
|
@ -208,7 +211,7 @@ abstract class CursorStatusesFragment : AbsStatusesFragment() {
|
|||
|
||||
protected fun getFiltersWhere(table: String): Expression? {
|
||||
if (!isFilterEnabled) return null
|
||||
return buildStatusFilterWhereClause(preferences, table, null)
|
||||
return buildStatusFilterWhereClause(preferences, table, null, filterScopes)
|
||||
}
|
||||
|
||||
protected open fun processWhere(where: Expression, whereArgs: Array<String>): ParameterizedExpression {
|
||||
|
@ -316,6 +319,6 @@ abstract class CursorStatusesFragment : AbsStatusesFragment() {
|
|||
|
||||
companion object {
|
||||
private val statusColumnsLite = Statuses.COLUMNS - arrayOf(Statuses.MENTIONS_JSON,
|
||||
Statuses.CARD)
|
||||
Statuses.CARD, Statuses.FILTER_FLAGS)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,6 +21,7 @@ package org.mariotaku.twidere.fragment
|
|||
|
||||
import org.mariotaku.sqliteqb.library.Expression
|
||||
import org.mariotaku.twidere.TwidereConstants.NOTIFICATION_ID_HOME_TIMELINE
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.annotation.ReadPositionTag
|
||||
import org.mariotaku.twidere.constant.IntentConstants.EXTRA_EXTRAS
|
||||
import org.mariotaku.twidere.model.ParameterizedExpression
|
||||
|
@ -50,6 +51,9 @@ class HomeTimelineFragment : CursorStatusesFragment() {
|
|||
override val timelineSyncTag: String?
|
||||
get() = getTimelineSyncTag(accountKeys)
|
||||
|
||||
override val filterScopes: Int
|
||||
get() = FilterScope.HOME
|
||||
|
||||
override fun updateRefreshState() {
|
||||
val twitter = twitterWrapper
|
||||
refreshing = twitter.isStatusTimelineRefreshing(contentUri)
|
||||
|
|
|
@ -25,6 +25,7 @@ import org.mariotaku.microblog.library.twitter.model.Activity
|
|||
import org.mariotaku.sqliteqb.library.Expression
|
||||
import org.mariotaku.twidere.TwidereConstants.NOTIFICATION_ID_INTERACTIONS_TIMELINE
|
||||
import org.mariotaku.twidere.adapter.ParcelableActivitiesAdapter
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.annotation.ReadPositionTag
|
||||
import org.mariotaku.twidere.constant.IntentConstants.EXTRA_EXTRAS
|
||||
import org.mariotaku.twidere.model.ParameterizedExpression
|
||||
|
@ -50,6 +51,9 @@ class InteractionsTimelineFragment : CursorActivitiesFragment() {
|
|||
override val timelineSyncTag: String?
|
||||
get() = getTimelineSyncTag(accountKeys)
|
||||
|
||||
override val filterScopes: Int
|
||||
get() = FilterScope.INTERACTIONS
|
||||
|
||||
override fun onCreateAdapter(context: Context, requestManager: RequestManager): ParcelableActivitiesAdapter {
|
||||
val adapter = ParcelableActivitiesAdapter(context, requestManager)
|
||||
val extras: InteractionsTabExtras? = arguments.getParcelable(EXTRA_EXTRAS)
|
||||
|
|
|
@ -17,6 +17,7 @@ import org.mariotaku.ktextension.useCursor
|
|||
import org.mariotaku.library.objectcursor.ObjectCursor
|
||||
import org.mariotaku.sqliteqb.library.*
|
||||
import org.mariotaku.sqliteqb.library.Columns.Column
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.constant.filterPossibilitySensitiveStatusesKey
|
||||
import org.mariotaku.twidere.constant.filterUnavailableQuoteStatusesKey
|
||||
import org.mariotaku.twidere.extension.model.component1
|
||||
|
@ -32,21 +33,55 @@ import org.mariotaku.twidere.provider.TwidereDataStore.Messages.Conversations
|
|||
import org.mariotaku.twidere.util.DataStoreUtils.ACTIVITIES_URIS
|
||||
import java.io.IOException
|
||||
|
||||
/**
|
||||
* Created by mariotaku on 2016/12/24.
|
||||
*/
|
||||
|
||||
fun buildStatusFilterWhereClause(preferences: SharedPreferences, table: String,
|
||||
extraSelection: Expression?): Expression {
|
||||
extraSelection: Expression?, @FilterScope filterScopes: Int = FilterScope.ALL): Expression {
|
||||
val filteredUsersQuery = SQLQueryBuilder
|
||||
.select(Column(Table(Filters.Users.TABLE_NAME), Filters.Users.USER_KEY))
|
||||
.from(Tables(Filters.Users.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Users.TABLE_NAME), Filters.Users.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Users.TABLE_NAME}.${Filters.Users.SCOPE} & $filterScopes", 0)
|
||||
))
|
||||
.build()
|
||||
val filteredUsersWhere = Expression.or(
|
||||
Expression.`in`(Column(Table(table), Statuses.USER_KEY), filteredUsersQuery),
|
||||
Expression.`in`(Column(Table(table), Statuses.RETWEETED_BY_USER_KEY), filteredUsersQuery),
|
||||
Expression.`in`(Column(Table(table), Statuses.QUOTED_USER_KEY), filteredUsersQuery)
|
||||
)
|
||||
val filteredSourcesWhere = Expression.and(
|
||||
Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Sources.TABLE_NAME), Filters.Sources.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Sources.TABLE_NAME}.${Filters.Sources.SCOPE} & $filterScopes", 0)
|
||||
),
|
||||
Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Statuses.SOURCE),
|
||||
"'%>'||${Filters.Sources.TABLE_NAME}.${Filters.Sources.VALUE}||'</a>%'"),
|
||||
Expression.likeRaw(Column(Table(table), Statuses.QUOTED_SOURCE),
|
||||
"'%>'||${Filters.Sources.TABLE_NAME}.${Filters.Sources.VALUE}||'</a>%'")
|
||||
)
|
||||
)
|
||||
val filteredKeywordsWhere = Expression.and(
|
||||
Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Keywords.TABLE_NAME), Filters.Keywords.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.SCOPE} & $filterScopes", 0)
|
||||
),
|
||||
Expression.or(Expression.likeRaw(Column(Table(table), Statuses.TEXT_PLAIN),
|
||||
"'%'||${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.VALUE}||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Statuses.QUOTED_TEXT_PLAIN),
|
||||
"'%'||${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.VALUE}||'%'"))
|
||||
)
|
||||
val filteredLinksWhere = Expression.and(
|
||||
Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Links.TABLE_NAME), Filters.Links.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Links.TABLE_NAME}.${Filters.Links.SCOPE} & $filterScopes", 0)
|
||||
),
|
||||
Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Statuses.SPANS),
|
||||
"'%'||${Filters.Links.TABLE_NAME}.${Filters.Links.VALUE}||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Statuses.QUOTED_SPANS),
|
||||
"'%'||${Filters.Links.TABLE_NAME}.${Filters.Links.VALUE}||'%'")
|
||||
)
|
||||
)
|
||||
val filteredIdsQueryBuilder = SQLQueryBuilder
|
||||
.select(Column(Table(table), Statuses._ID))
|
||||
.from(Tables(table))
|
||||
|
@ -54,30 +89,15 @@ fun buildStatusFilterWhereClause(preferences: SharedPreferences, table: String,
|
|||
.union()
|
||||
.select(Columns(Column(Table(table), Statuses._ID)))
|
||||
.from(Tables(table, Filters.Sources.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Statuses.SOURCE),
|
||||
"'%>'||" + Filters.Sources.TABLE_NAME + "." + Filters.Sources.VALUE + "||'</a>%'"),
|
||||
Expression.likeRaw(Column(Table(table), Statuses.QUOTED_SOURCE),
|
||||
"'%>'||" + Filters.Sources.TABLE_NAME + "." + Filters.Sources.VALUE + "||'</a>%'")
|
||||
))
|
||||
.where(filteredSourcesWhere)
|
||||
.union()
|
||||
.select(Columns(Column(Table(table), Statuses._ID)))
|
||||
.from(Tables(table, Filters.Keywords.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Statuses.TEXT_PLAIN),
|
||||
"'%'||" + Filters.Keywords.TABLE_NAME + "." + Filters.Keywords.VALUE + "||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Statuses.QUOTED_TEXT_PLAIN),
|
||||
"'%'||" + Filters.Keywords.TABLE_NAME + "." + Filters.Keywords.VALUE + "||'%'")
|
||||
))
|
||||
.where(filteredKeywordsWhere)
|
||||
.union()
|
||||
.select(Columns(Column(Table(table), Statuses._ID)))
|
||||
.from(Tables(table, Filters.Links.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Statuses.SPANS),
|
||||
"'%'||" + Filters.Links.TABLE_NAME + "." + Filters.Links.VALUE + "||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Statuses.QUOTED_SPANS),
|
||||
"'%'||" + Filters.Links.TABLE_NAME + "." + Filters.Links.VALUE + "||'%'")
|
||||
))
|
||||
.where(filteredLinksWhere)
|
||||
var filterFlags: Long = 0
|
||||
if (preferences[filterUnavailableQuoteStatusesKey]) {
|
||||
filterFlags = filterFlags or FilterFlags.QUOTE_NOT_AVAILABLE
|
||||
|
|
|
@ -43,6 +43,7 @@ import org.mariotaku.sqliteqb.library.query.SQLSelectQuery
|
|||
import org.mariotaku.twidere.R
|
||||
import org.mariotaku.twidere.TwidereConstants.*
|
||||
import org.mariotaku.twidere.annotation.AccountType
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.constant.IntentConstants
|
||||
import org.mariotaku.twidere.constant.databaseItemLimitKey
|
||||
import org.mariotaku.twidere.extension.model.*
|
||||
|
@ -325,7 +326,7 @@ object DataStoreUtils {
|
|||
|
||||
fun getStatusesCount(context: Context, preferences: SharedPreferences, uri: Uri,
|
||||
extraArgs: Bundle?, compareColumn: String, compare: Long, greaterThan: Boolean,
|
||||
accountKeys: Array<UserKey>?): Int {
|
||||
accountKeys: Array<UserKey>?, @FilterScope filterScopes: Int = FilterScope.ALL): Int {
|
||||
val keys = accountKeys ?: getActivatedAccountKeys(context)
|
||||
|
||||
val expressions = ArrayList<Expression>()
|
||||
|
@ -342,7 +343,8 @@ object DataStoreUtils {
|
|||
expressions.add(Expression.lesserThan(compareColumn, compare))
|
||||
}
|
||||
|
||||
expressions.add(buildStatusFilterWhereClause(preferences, getTableNameByUri(uri)!!, null))
|
||||
expressions.add(buildStatusFilterWhereClause(preferences, getTableNameByUri(uri)!!,
|
||||
null, filterScopes))
|
||||
|
||||
if (extraArgs != null) {
|
||||
val extras = extraArgs.getParcelable<Parcelable>(EXTRA_EXTRAS)
|
||||
|
@ -356,7 +358,8 @@ object DataStoreUtils {
|
|||
}
|
||||
|
||||
fun getActivitiesCount(context: Context, uri: Uri, compareColumn: String,
|
||||
compare: Long, greaterThan: Boolean, accountKeys: Array<UserKey>?): Int {
|
||||
compare: Long, greaterThan: Boolean, accountKeys: Array<UserKey>?,
|
||||
@FilterScope filterScopes: Int = FilterScope.ALL): Int {
|
||||
val keys = accountKeys ?: getActivatedAccountKeys(context)
|
||||
val selection = Expression.and(
|
||||
Expression.inArgs(Column(Activities.ACCOUNT_KEY), keys.size),
|
||||
|
@ -365,7 +368,8 @@ object DataStoreUtils {
|
|||
} else {
|
||||
Expression.lesserThan(compareColumn, compare)
|
||||
},
|
||||
buildActivityFilterWhereClause(getTableNameByUri(uri)!!, null)
|
||||
buildActivityFilterWhereClause(getTableNameByUri(uri)!!, null,
|
||||
filterScopes)
|
||||
)
|
||||
val whereArgs = arrayListOf<String>()
|
||||
keys.mapTo(whereArgs) { it.toString() }
|
||||
|
@ -375,12 +379,13 @@ object DataStoreUtils {
|
|||
fun getActivitiesCount(context: Context, uri: Uri,
|
||||
extraWhere: Expression?, extraWhereArgs: Array<String>?,
|
||||
sinceColumn: String, since: Long, followingOnly: Boolean,
|
||||
accountKeys: Array<UserKey>?): Int {
|
||||
accountKeys: Array<UserKey>?, @FilterScope filterScopes: Int = FilterScope.ALL): Int {
|
||||
val keys = (accountKeys ?: getActivatedAccountKeys(context)).mapToArray { it.toString() }
|
||||
val expressions = ArrayList<Expression>()
|
||||
expressions.add(Expression.inArgs(Column(Activities.ACCOUNT_KEY), keys.size))
|
||||
expressions.add(Expression.greaterThan(sinceColumn, since))
|
||||
expressions.add(buildActivityFilterWhereClause(getTableNameByUri(uri)!!, null))
|
||||
expressions.add(buildActivityFilterWhereClause(getTableNameByUri(uri)!!, null,
|
||||
filterScopes))
|
||||
if (extraWhere != null) {
|
||||
expressions.add(extraWhere)
|
||||
}
|
||||
|
@ -457,16 +462,57 @@ object DataStoreUtils {
|
|||
return getTableNameById(getTableId(uri))
|
||||
}
|
||||
|
||||
fun buildActivityFilterWhereClause(table: String, extraSelection: Expression?): Expression {
|
||||
fun buildActivityFilterWhereClause(table: String, extraSelection: Expression?,
|
||||
@FilterScope filterScopes: Int = FilterScope.ALL): Expression {
|
||||
val filteredUsersQuery = SQLQueryBuilder
|
||||
.select(Column(Table(Filters.Users.TABLE_NAME), Filters.Users.USER_KEY))
|
||||
.from(Tables(Filters.Users.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Users.TABLE_NAME), Filters.Users.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Users.TABLE_NAME}.${Filters.Users.SCOPE} & $filterScopes", 0)
|
||||
))
|
||||
.build()
|
||||
val filteredUsersWhere = Expression.or(
|
||||
Expression.`in`(Column(Table(table), Activities.USER_KEY), filteredUsersQuery),
|
||||
Expression.`in`(Column(Table(table), Activities.RETWEETED_BY_USER_KEY), filteredUsersQuery),
|
||||
Expression.`in`(Column(Table(table), Activities.QUOTED_USER_KEY), filteredUsersQuery)
|
||||
)
|
||||
val filteredSourcesWhere = Expression.and(
|
||||
Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Sources.TABLE_NAME), Filters.Sources.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Sources.TABLE_NAME}.${Filters.Sources.SCOPE} & $filterScopes", 0)
|
||||
),
|
||||
Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Activities.SOURCE),
|
||||
"'%>'||${Filters.Sources.TABLE_NAME}.${Filters.Sources.VALUE}||'</a>%'"),
|
||||
Expression.likeRaw(Column(Table(table), Activities.QUOTED_SOURCE),
|
||||
"'%>'||${Filters.Sources.TABLE_NAME}.${Filters.Sources.VALUE}||'</a>%'")
|
||||
)
|
||||
)
|
||||
val filteredKeywordsWhere = Expression.and(
|
||||
Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Keywords.TABLE_NAME), Filters.Keywords.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.SCOPE} & $filterScopes", 0)
|
||||
),
|
||||
Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Activities.TEXT_PLAIN),
|
||||
"'%'||${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.VALUE}||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Activities.QUOTED_TEXT_PLAIN),
|
||||
"'%'||${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.VALUE}||'%'")
|
||||
)
|
||||
)
|
||||
val filteredLinksWhere = Expression.and(
|
||||
Expression.or(
|
||||
Expression.equals(Column(Table(Filters.Links.TABLE_NAME), Filters.Links.SCOPE), 0),
|
||||
Expression.notEquals("${Filters.Links.TABLE_NAME}.${Filters.Links.SCOPE} & $filterScopes", 0)
|
||||
),
|
||||
Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Activities.SPANS),
|
||||
"'%'||${Filters.Links.TABLE_NAME}.${Filters.Links.VALUE}||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Activities.QUOTED_SPANS),
|
||||
"'%'||${Filters.Links.TABLE_NAME}.${Filters.Links.VALUE}||'%'")
|
||||
)
|
||||
)
|
||||
val filteredIdsQueryBuilder = SQLQueryBuilder
|
||||
.select(Column(Table(table), Activities._ID))
|
||||
.from(Tables(table))
|
||||
|
@ -474,30 +520,15 @@ object DataStoreUtils {
|
|||
.union()
|
||||
.select(Columns(Column(Table(table), Activities._ID)))
|
||||
.from(Tables(table, Filters.Sources.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Activities.SOURCE),
|
||||
"'%>'||${Filters.Sources.TABLE_NAME}.${Filters.Sources.VALUE}||'</a>%'"),
|
||||
Expression.likeRaw(Column(Table(table), Activities.QUOTED_SOURCE),
|
||||
"'%>'||${Filters.Sources.TABLE_NAME}.${Filters.Sources.VALUE}||'</a>%'")
|
||||
))
|
||||
.where(filteredSourcesWhere)
|
||||
.union()
|
||||
.select(Columns(Column(Table(table), Activities._ID)))
|
||||
.from(Tables(table, Filters.Keywords.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Activities.TEXT_PLAIN),
|
||||
"'%'||${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.VALUE}||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Activities.QUOTED_TEXT_PLAIN),
|
||||
"'%'||${Filters.Keywords.TABLE_NAME}.${Filters.Keywords.VALUE}||'%'")
|
||||
))
|
||||
.where(filteredKeywordsWhere)
|
||||
.union()
|
||||
.select(Columns(Column(Table(table), Activities._ID)))
|
||||
.from(Tables(table, Filters.Links.TABLE_NAME))
|
||||
.where(Expression.or(
|
||||
Expression.likeRaw(Column(Table(table), Activities.SPANS),
|
||||
"'%'||${Filters.Links.TABLE_NAME}.${Filters.Links.VALUE}||'%'"),
|
||||
Expression.likeRaw(Column(Table(table), Activities.QUOTED_SPANS),
|
||||
"'%'||${Filters.Links.TABLE_NAME}.${Filters.Links.VALUE}||'%'")
|
||||
))
|
||||
.where(filteredLinksWhere)
|
||||
val filterExpression = Expression.or(
|
||||
Expression.notIn(Column(Table(table), Activities._ID), filteredIdsQueryBuilder.build()),
|
||||
Expression.equals(Column(Table(table), Activities.IS_GAP), 1)
|
||||
|
@ -802,7 +833,7 @@ object DataStoreUtils {
|
|||
}
|
||||
|
||||
fun getInteractionsCount(context: Context, extraArgs: Bundle?, accountKeys: Array<UserKey>,
|
||||
since: Long, sinceColumn: String): Int {
|
||||
since: Long, sinceColumn: String, @FilterScope filterScopes: Int = FilterScope.ALL): Int {
|
||||
var extraWhere: Expression? = null
|
||||
var extraWhereArgs: Array<String>? = null
|
||||
var followingOnly = false
|
||||
|
@ -819,7 +850,7 @@ object DataStoreUtils {
|
|||
}
|
||||
}
|
||||
return getActivitiesCount(context, Activities.AboutMe.CONTENT_URI, extraWhere, extraWhereArgs,
|
||||
sinceColumn, since, followingOnly, accountKeys)
|
||||
sinceColumn, since, followingOnly, accountKeys, filterScopes)
|
||||
}
|
||||
|
||||
fun addToFilter(context: Context, users: Collection<ParcelableUser>, filterAnywhere: Boolean) {
|
||||
|
|
|
@ -42,6 +42,7 @@ import org.mariotaku.twidere.TwidereConstants.*
|
|||
import org.mariotaku.twidere.activity.HomeActivity
|
||||
import org.mariotaku.twidere.activity.LinkHandlerActivity
|
||||
import org.mariotaku.twidere.annotation.CustomTabType
|
||||
import org.mariotaku.twidere.annotation.FilterScope
|
||||
import org.mariotaku.twidere.annotation.NotificationType
|
||||
import org.mariotaku.twidere.constant.IntentConstants
|
||||
import org.mariotaku.twidere.constant.iWantMyStarsBackKey
|
||||
|
@ -88,7 +89,7 @@ class ContentNotificationManager(
|
|||
)
|
||||
val selectionArgs = arrayOf(accountKey.toString())
|
||||
val filteredSelection = buildStatusFilterWhereClause(preferences, Statuses.TABLE_NAME,
|
||||
selection)
|
||||
selection, FilterScope.HOME)
|
||||
val userProjection = arrayOf(Statuses.USER_KEY, Statuses.USER_NAME, Statuses.USER_SCREEN_NAME)
|
||||
val statusProjection = arrayOf(Statuses.POSITION_KEY)
|
||||
|
||||
|
@ -169,12 +170,15 @@ class ContentNotificationManager(
|
|||
val cr = context.contentResolver
|
||||
val accountKey = pref.accountKey
|
||||
val account = AccountUtils.getAccountDetails(am, accountKey, false) ?: return
|
||||
val where = Expression.and(
|
||||
val selection = Expression.and(
|
||||
Expression.equalsArgs(Activities.ACCOUNT_KEY),
|
||||
Expression.greaterThan(Activities.POSITION_KEY, position),
|
||||
Expression.notEquals(Activities.IS_GAP, 1)
|
||||
).sql
|
||||
val whereArgs = arrayOf(accountKey.toString())
|
||||
)
|
||||
val selectionArgs = arrayOf(accountKey.toString())
|
||||
|
||||
val filteredSelection = DataStoreUtils.buildActivityFilterWhereClause(Activities.AboutMe.TABLE_NAME,
|
||||
selection, FilterScope.INTERACTIONS)
|
||||
val builder = NotificationChannelSpec.contentInteractions.accountNotificationBuilder(context,
|
||||
accountKey)
|
||||
val pebbleNotificationStringBuilder = StringBuilder()
|
||||
|
@ -197,7 +201,8 @@ class ContentNotificationManager(
|
|||
val filteredUserKeys = DataStoreUtils.getFilteredUserKeys(context)
|
||||
|
||||
|
||||
val (remaining, consumed) = cr.queryReference(Activities.AboutMe.CONTENT_URI, Activities.COLUMNS, where, whereArgs,
|
||||
val (remaining, consumed) = cr.queryReference(Activities.AboutMe.CONTENT_URI, Activities.COLUMNS,
|
||||
filteredSelection.sql, selectionArgs,
|
||||
OrderBy(Activities.TIMESTAMP, false).sql).use { (cur) ->
|
||||
if (cur == null || cur.isEmpty) return@use Pair(-1, -1)
|
||||
val ci = ObjectCursor.indicesFrom(cur, ParcelableActivity::class.java)
|
||||
|
|
Loading…
Reference in New Issue