Added search by size

pull/180/head
M66B 5 years ago
parent 2fd9d02810
commit e69f29abda

@ -71,6 +71,7 @@ import javax.mail.search.OrTerm;
import javax.mail.search.ReceivedDateTerm; import javax.mail.search.ReceivedDateTerm;
import javax.mail.search.RecipientStringTerm; import javax.mail.search.RecipientStringTerm;
import javax.mail.search.SearchTerm; import javax.mail.search.SearchTerm;
import javax.mail.search.SizeTerm;
import javax.mail.search.SubjectTerm; import javax.mail.search.SubjectTerm;
import io.requery.android.database.sqlite.SQLiteDatabase; import io.requery.android.database.sqlite.SQLiteDatabase;
@ -239,6 +240,7 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
criteria.with_hidden, criteria.with_hidden,
criteria.with_encrypted, criteria.with_encrypted,
criteria.with_attachments, criteria.with_attachments,
criteria.with_size,
criteria.after, criteria.after,
criteria.before, criteria.before,
SEARCH_LIMIT, state.offset); SEARCH_LIMIT, state.offset);
@ -617,6 +619,7 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
boolean with_hidden; boolean with_hidden;
boolean with_encrypted; boolean with_encrypted;
boolean with_attachments; boolean with_attachments;
Integer with_size = null;
Long after = null; Long after = null;
Long before = null; Long before = null;
@ -642,7 +645,8 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
with_flagged || with_flagged ||
with_hidden || with_hidden ||
with_encrypted || with_encrypted ||
with_attachments); with_attachments ||
with_size != null);
} }
SearchTerm getTerms(boolean utf8, Flags flags, String[] keywords) { SearchTerm getTerms(boolean utf8, Flags flags, String[] keywords) {
@ -685,6 +689,9 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
if (with_flagged && flags.contains(Flags.Flag.FLAGGED)) if (with_flagged && flags.contains(Flags.Flag.FLAGGED))
and.add(new FlagTerm(new Flags(Flags.Flag.FLAGGED), true)); and.add(new FlagTerm(new Flags(Flags.Flag.FLAGGED), true));
if (with_size != null)
and.add(new SizeTerm(ComparisonTerm.GT, with_size));
if (after != null) if (after != null)
and.add(new ReceivedDateTerm(ComparisonTerm.GE, new Date(after))); and.add(new ReceivedDateTerm(ComparisonTerm.GE, new Date(after)));
if (before != null) if (before != null)
@ -716,6 +723,9 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
flags.add(context.getString(R.string.title_search_flag_encrypted)); flags.add(context.getString(R.string.title_search_flag_encrypted));
if (with_attachments) if (with_attachments)
flags.add(context.getString(R.string.title_search_flag_attachments)); flags.add(context.getString(R.string.title_search_flag_attachments));
if (with_size != null)
flags.add(context.getString(R.string.title_search_flag_size,
Helper.humanReadableByteCount(with_size, true)));
return (query == null ? "" : query) return (query == null ? "" : query)
+ (flags.size() > 0 ? " +" : "") + (flags.size() > 0 ? " +" : "")
+ TextUtils.join(",", flags); + TextUtils.join(",", flags);
@ -736,6 +746,7 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
this.with_hidden == other.with_hidden && this.with_hidden == other.with_hidden &&
this.with_encrypted == other.with_encrypted && this.with_encrypted == other.with_encrypted &&
this.with_attachments == other.with_attachments && this.with_attachments == other.with_attachments &&
Objects.equals(this.with_size, other.with_size) &&
Objects.equals(this.after, other.after) && Objects.equals(this.after, other.after) &&
Objects.equals(this.before, other.before)); Objects.equals(this.before, other.before));
} else } else
@ -756,6 +767,7 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback<TupleMe
" hidden=" + with_hidden + " hidden=" + with_hidden +
" encrypted=" + with_encrypted + " encrypted=" + with_encrypted +
" attachments=" + with_attachments + " attachments=" + with_attachments +
" size=" + with_size +
" after=" + (after == null ? "" : new Date(after)) + " after=" + (after == null ? "" : new Date(after)) +
" before=" + (before == null ? "" : new Date(before)); " before=" + (before == null ? "" : new Date(before));
} }

@ -320,6 +320,7 @@ public interface DaoMessage {
" AND (NOT :hidden OR NOT ui_snoozed IS NULL)" + " AND (NOT :hidden OR NOT ui_snoozed IS NULL)" +
" AND (NOT :encrypted OR ui_encrypt > 0)" + " AND (NOT :encrypted OR ui_encrypt > 0)" +
" AND (NOT :attachments OR attachments > 0)" + " AND (NOT :attachments OR attachments > 0)" +
" AND (NOT :size OR total > :size)" +
" AND (:after IS NULL OR received > :after)" + " AND (:after IS NULL OR received > :after)" +
" AND (:before IS NULL OR received < :before)" + " AND (:before IS NULL OR received < :before)" +
" ORDER BY received DESC" + " ORDER BY received DESC" +
@ -328,6 +329,7 @@ public interface DaoMessage {
Long account, Long folder, String find, Long account, Long folder, String find,
boolean senders, boolean recipients, boolean subject, boolean keywords, boolean message, boolean senders, boolean recipients, boolean subject, boolean keywords, boolean message,
boolean unseen, boolean flagged, boolean hidden, boolean encrypted, boolean attachments, boolean unseen, boolean flagged, boolean hidden, boolean encrypted, boolean attachments,
Integer size,
Long after, Long before, Long after, Long before,
int limit, int offset); int limit, int offset);

@ -22,6 +22,7 @@ import android.widget.CompoundButton;
import android.widget.DatePicker; import android.widget.DatePicker;
import android.widget.FilterQueryProvider; import android.widget.FilterQueryProvider;
import android.widget.ImageButton; import android.widget.ImageButton;
import android.widget.Spinner;
import android.widget.TextView; import android.widget.TextView;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
@ -73,6 +74,7 @@ public class FragmentDialogSearch extends FragmentDialogBase {
final CheckBox cbHidden = dview.findViewById(R.id.cbHidden); final CheckBox cbHidden = dview.findViewById(R.id.cbHidden);
final CheckBox cbEncrypted = dview.findViewById(R.id.cbEncrypted); final CheckBox cbEncrypted = dview.findViewById(R.id.cbEncrypted);
final CheckBox cbAttachments = dview.findViewById(R.id.cbAttachments); final CheckBox cbAttachments = dview.findViewById(R.id.cbAttachments);
final Spinner spMessageSize = dview.findViewById(R.id.spMessageSize);
final Button btnBefore = dview.findViewById(R.id.btnBefore); final Button btnBefore = dview.findViewById(R.id.btnBefore);
final Button btnAfter = dview.findViewById(R.id.btnAfter); final Button btnAfter = dview.findViewById(R.id.btnAfter);
final TextView tvBefore = dview.findViewById(R.id.tvBefore); final TextView tvBefore = dview.findViewById(R.id.tvBefore);
@ -97,7 +99,6 @@ public class FragmentDialogSearch extends FragmentDialogBase {
new int[]{android.R.id.text1}, new int[]{android.R.id.text1},
0); 0);
adapter.setFilterQueryProvider(new FilterQueryProvider() { adapter.setFilterQueryProvider(new FilterQueryProvider() {
public Cursor runQuery(CharSequence typed) { public Cursor runQuery(CharSequence typed) {
Log.i("Search suggest=" + typed); Log.i("Search suggest=" + typed);
@ -156,6 +157,7 @@ public class FragmentDialogSearch extends FragmentDialogBase {
cbHidden.setEnabled(!isChecked); cbHidden.setEnabled(!isChecked);
cbEncrypted.setEnabled(!isChecked); cbEncrypted.setEnabled(!isChecked);
cbAttachments.setEnabled(!isChecked); cbAttachments.setEnabled(!isChecked);
spMessageSize.setEnabled(!isChecked);
} }
}); });
@ -255,6 +257,12 @@ public class FragmentDialogSearch extends FragmentDialogBase {
criteria.with_hidden = cbHidden.isChecked(); criteria.with_hidden = cbHidden.isChecked();
criteria.with_encrypted = cbEncrypted.isChecked(); criteria.with_encrypted = cbEncrypted.isChecked();
criteria.with_attachments = cbAttachments.isChecked(); criteria.with_attachments = cbAttachments.isChecked();
int pos = spMessageSize.getSelectedItemPosition();
if (pos > 0) {
int[] sizes = getResources().getIntArray(R.array.sizeValues);
criteria.with_size = sizes[pos];
}
} }
Object after = tvAfter.getTag(); Object after = tvAfter.getTag();

@ -281,6 +281,43 @@
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/cbEncrypted" /> app:layout_constraintTop_toBottomOf="@id/cbEncrypted" />
<eu.faircode.email.FixedTextView
android:id="@+id/tvMessageSize"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="24dp"
android:layout_marginTop="12dp"
android:text="@string/title_search_with_size"
android:textAppearance="@style/TextAppearance.AppCompat.Small"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/cbAttachments" />
<Spinner
android:id="@+id/spMessageSize"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="24dp"
android:layout_marginTop="12dp"
android:entries="@array/sizeNames"
android:focusable="true"
android:focusableInTouchMode="true"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/tvMessageSize" />
<eu.faircode.email.FixedTextView
android:id="@+id/tvSizeHint"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="24dp"
android:layout_marginTop="6dp"
android:text="@string/title_search_size_hint"
android:textAppearance="@style/TextAppearance.AppCompat.Small"
android:textStyle="italic"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/spMessageSize" />
<Button <Button
android:id="@+id/btnAfter" android:id="@+id/btnAfter"
style="?android:attr/buttonStyleSmall" style="?android:attr/buttonStyleSmall"
@ -291,7 +328,7 @@
android:text="@string/title_search_with_after" android:text="@string/title_search_with_after"
app:layout_constraintEnd_toStartOf="@id/btnBefore" app:layout_constraintEnd_toStartOf="@id/btnBefore"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/cbAttachments" /> app:layout_constraintTop_toBottomOf="@id/tvSizeHint" />
<Button <Button
android:id="@+id/btnBefore" android:id="@+id/btnBefore"
@ -303,7 +340,7 @@
android:text="@string/title_search_with_before" android:text="@string/title_search_with_before"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/btnAfter" app:layout_constraintStart_toEndOf="@id/btnAfter"
app:layout_constraintTop_toBottomOf="@id/cbAttachments" /> app:layout_constraintTop_toBottomOf="@id/tvSizeHint" />
<eu.faircode.email.FixedTextView <eu.faircode.email.FixedTextView
android:id="@+id/tvAfter" android:id="@+id/tvAfter"
@ -334,6 +371,7 @@
app:constraint_referenced_ids=" app:constraint_referenced_ids="
cbSearchIndex,tvSearchIndexHint,cbSenders,cbRecipients,cbSubject,cbKeywords,cbMessage,tvSearchTextHint, cbSearchIndex,tvSearchIndexHint,cbSenders,cbRecipients,cbSubject,cbKeywords,cbMessage,tvSearchTextHint,
tvAnd,cbUnseen,cbFlagged,cbHidden,cbEncrypted,cbAttachments, tvAnd,cbUnseen,cbFlagged,cbHidden,cbEncrypted,cbAttachments,
tvMessageSize,spMessageSize,
btnAfter,btnBefore,tvBefore,tvAfter" /> btnAfter,btnBefore,tvBefore,tvAfter" />
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>
</eu.faircode.email.ScrollViewEx> </eu.faircode.email.ScrollViewEx>

@ -945,7 +945,8 @@
To search the server too, tap on the \'search again\' button. To search the server too, tap on the \'search again\' button.
</string> </string>
<string name="title_search_index_hint">Searching via the search index is fast, but will only find whole words</string> <string name="title_search_index_hint">Searching via the search index is fast, but will only find whole words</string>
<string name="title_search_text_hint">Some email servers have trouble finding text in many messages</string> <string name="title_search_text_hint">Searching for text in messages, when there are a large number of messages, might not work on some servers</string>
<string name="title_search_size_hint">Searching for messages by size, when there are a large number of messages, might not work on some servers</string>
<string name="title_search_more">More options</string> <string name="title_search_more">More options</string>
<string name="title_search_use_index">Use search index</string> <string name="title_search_use_index">Use search index</string>
<string name="title_search_in_senders">In senders (from)</string> <string name="title_search_in_senders">In senders (from)</string>
@ -959,6 +960,7 @@
<string name="title_search_with_hidden">Hidden (on device only)</string> <string name="title_search_with_hidden">Hidden (on device only)</string>
<string name="title_search_with_encrypted">Encrypted (on device only)</string> <string name="title_search_with_encrypted">Encrypted (on device only)</string>
<string name="title_search_with_attachments">With attachments (on device only)</string> <string name="title_search_with_attachments">With attachments (on device only)</string>
<string name="title_search_with_size">Message size larger than</string>
<string name="title_search_with_before">Before</string> <string name="title_search_with_before">Before</string>
<string name="title_search_with_after">After</string> <string name="title_search_with_after">After</string>
<string name="title_search_flag_unseen">unread</string> <string name="title_search_flag_unseen">unread</string>
@ -966,6 +968,7 @@
<string name="title_search_flag_hidden">hidden</string> <string name="title_search_flag_hidden">hidden</string>
<string name="title_search_flag_encrypted">encrypted</string> <string name="title_search_flag_encrypted">encrypted</string>
<string name="title_search_flag_attachments">attachments</string> <string name="title_search_flag_attachments">attachments</string>
<string name="title_search_flag_size">size &gt; %1$s</string>
<string name="title_search_device">Search on device</string> <string name="title_search_device">Search on device</string>
<string name="title_search_server">Search on server</string> <string name="title_search_server">Search on server</string>
@ -1533,6 +1536,30 @@
<item>3</item> <item>3</item>
</integer-array> </integer-array>
<string-array name="sizeNames">
<item>0 B</item>
<item>256 KB</item>
<item>512 KB</item>
<item>1 MB</item>
<item>2 MB</item>
<item>5 MB</item>
<item>10 MB</item>
<item>20 MB</item>
<item>50 MB</item>
</string-array>
<integer-array name="sizeValues" translatable="false">
<item>0</item>
<item>250000</item>
<item>500000</item>
<item>1000000</item>
<item>2000000</item>
<item>5000000</item>
<item>10000000</item>
<item>20000000</item>
<item>50000000</item>
</integer-array>
<string name="fingerprint" translatable="false">17BA15C1AF55D925F98B99CEA4375D4CDF4C174B</string> <string name="fingerprint" translatable="false">17BA15C1AF55D925F98B99CEA4375D4CDF4C174B</string>
<string name="public_key" translatable="false">MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAtFbxEbzL8u5accPGgBw/XdyiSS5BBE6ZQ9ELpKyJ/OQN+kdYniCAOw3lsQ/GuJScy4Y2HobqbBgLL8GLHG+Yu2EHC9dLjA3v2Mc25vvnfn86BsrpQvz1poN2n+roTBdq09FWbtebJ8m0hDBVmtfRi7RhTKIL4No3kodLhksdnucKjcFheubebWKgpmvbmw7NwuELhaZmyhw8WTtnQ4rZPMhjY1JJZgzwNExXgD7zzg4pJPkuQlfkuRkkvBpHpi3C7VDnYjrBlLHngI4wv3wxQBVwJqlvAT9PmX8dOVnTsWWdJdLQBZVWphuqVY54kjBIovN+o8w03WjsV9QiOQq+XwIDAQAB</string> <string name="public_key" translatable="false">MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAtFbxEbzL8u5accPGgBw/XdyiSS5BBE6ZQ9ELpKyJ/OQN+kdYniCAOw3lsQ/GuJScy4Y2HobqbBgLL8GLHG+Yu2EHC9dLjA3v2Mc25vvnfn86BsrpQvz1poN2n+roTBdq09FWbtebJ8m0hDBVmtfRi7RhTKIL4No3kodLhksdnucKjcFheubebWKgpmvbmw7NwuELhaZmyhw8WTtnQ4rZPMhjY1JJZgzwNExXgD7zzg4pJPkuQlfkuRkkvBpHpi3C7VDnYjrBlLHngI4wv3wxQBVwJqlvAT9PmX8dOVnTsWWdJdLQBZVWphuqVY54kjBIovN+o8w03WjsV9QiOQq+XwIDAQAB</string>
</resources> </resources>

Loading…
Cancel
Save