diff --git a/CHANGELOG.md b/CHANGELOG.md index 4d51df957e..3641d156fb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,10 @@ ### [Adratiklit](https://en.wikipedia.org/wiki/Adratiklit) +### Next version + +* Added account categories + ### 1.1751 * Fixed updating system folder properties diff --git a/app/src/main/assets/CHANGELOG.md b/app/src/main/assets/CHANGELOG.md index 4d51df957e..3641d156fb 100644 --- a/app/src/main/assets/CHANGELOG.md +++ b/app/src/main/assets/CHANGELOG.md @@ -4,6 +4,10 @@ ### [Adratiklit](https://en.wikipedia.org/wiki/Adratiklit) +### Next version + +* Added account categories + ### 1.1751 * Fixed updating system folder properties diff --git a/app/src/main/java/eu/faircode/email/AdapterFolder.java b/app/src/main/java/eu/faircode/email/AdapterFolder.java index ef39524902..914cd1eba0 100644 --- a/app/src/main/java/eu/faircode/email/AdapterFolder.java +++ b/app/src/main/java/eu/faircode/email/AdapterFolder.java @@ -1449,6 +1449,13 @@ public class AdapterFolder extends RecyclerView.Adapter= 0 && pos < selected.size()) + return selected.get(pos); + else + return null; + } + @Override public int getItemCount() { return selected.size(); diff --git a/app/src/main/java/eu/faircode/email/DaoFolder.java b/app/src/main/java/eu/faircode/email/DaoFolder.java index 0bfac4cc4a..a0101e04a2 100644 --- a/app/src/main/java/eu/faircode/email/DaoFolder.java +++ b/app/src/main/java/eu/faircode/email/DaoFolder.java @@ -38,7 +38,7 @@ public interface DaoFolder { @Query("SELECT folder.*" + ", account.id AS accountId, account.pop AS accountProtocol, account.`order` AS accountOrder" + - ", account.name AS accountName, account.color AS accountColor, account.state AS accountState" + + ", account.name AS accountName, account.category AS accountCategory, account.color AS accountColor, account.state AS accountState" + ", COUNT(DISTINCT CASE WHEN rule.enabled THEN rule.id ELSE NULL END) rules" + ", COUNT(DISTINCT message.id) AS messages" + ", COUNT(DISTINCT CASE WHEN message.content = 1 THEN message.id ELSE NULL END) AS content" + @@ -77,7 +77,7 @@ public interface DaoFolder { @Transaction @Query("SELECT folder.*" + ", account.id AS accountId, account.pop AS accountProtocol, account.`order` AS accountOrder" + - ", account.name AS accountName, account.color AS accountColor, account.state AS accountState" + + ", account.name AS accountName, account.category AS accountCategory, account.color AS accountColor, account.state AS accountState" + ", COUNT(DISTINCT CASE WHEN rule.enabled THEN rule.id ELSE NULL END) rules" + ", COUNT(DISTINCT CASE WHEN message.ui_hide THEN NULL ELSE message.id END) AS messages" + ", COUNT(DISTINCT CASE WHEN message.content = 1 AND NOT message.ui_hide THEN message.id ELSE NULL END) AS content" + @@ -100,7 +100,7 @@ public interface DaoFolder { @Query("SELECT folder.*" + ", account.id AS accountId, account.pop AS accountProtocol, account.`order` AS accountOrder" + - ", account.name AS accountName, account.color AS accountColor, account.state AS accountState" + + ", account.name AS accountName, account.category AS accountCategory, account.color AS accountColor, account.state AS accountState" + ", COUNT(DISTINCT CASE WHEN rule.enabled THEN rule.id ELSE NULL END) rules" + ", COUNT(DISTINCT message.id) AS messages" + ", COUNT(DISTINCT CASE WHEN message.content = 1 THEN message.id ELSE NULL END) AS content" + @@ -124,7 +124,7 @@ public interface DaoFolder { @Query("SELECT folder.*" + ", account.id AS accountId, account.pop AS accountProtocol, account.`order` AS accountOrder" + - ", account.name AS accountName, account.color AS accountColor, account.state AS accountState" + + ", account.name AS accountName, account.category AS accountCategory, account.color AS accountColor, account.state AS accountState" + ", COUNT(DISTINCT CASE WHEN rule.enabled THEN rule.id ELSE NULL END) rules" + ", COUNT(DISTINCT message.id) AS messages" + ", COUNT(DISTINCT CASE WHEN message.content = 1 THEN message.id ELSE NULL END) AS content" + diff --git a/app/src/main/java/eu/faircode/email/FragmentAccounts.java b/app/src/main/java/eu/faircode/email/FragmentAccounts.java index a1ed50a339..001d960003 100644 --- a/app/src/main/java/eu/faircode/email/FragmentAccounts.java +++ b/app/src/main/java/eu/faircode/email/FragmentAccounts.java @@ -144,7 +144,7 @@ public class FragmentAccounts extends FragmentBase { rvAccount.addItemDecoration(itemDecorator); } - DividerItemDecoration dateDecorator = new DividerItemDecoration(getContext(), llm.getOrientation()) { + DividerItemDecoration categoryDecorator = new DividerItemDecoration(getContext(), llm.getOrientation()) { @Override public void onDraw(@NonNull Canvas canvas, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) { int count = parent.getChildCount(); @@ -191,15 +191,15 @@ public class FragmentAccounts extends FragmentBase { return null; } - View header = inflater.inflate(R.layout.item_message_date, parent, false); - TextView tvDate = header.findViewById(R.id.tvDate); + View header = inflater.inflate(R.layout.item_category, parent, false); + TextView tvCategory = header.findViewById(R.id.tvCategory); if (cards) { - View vSeparatorDate = header.findViewById(R.id.vSeparatorDate); - vSeparatorDate.setVisibility(View.GONE); + View vSeparatorCategory = header.findViewById(R.id.vSeparatorCategory); + vSeparatorCategory.setVisibility(View.GONE); } - tvDate.setText(account.category); + tvCategory.setText(account.category); header.measure(View.MeasureSpec.makeMeasureSpec(parent.getWidth(), View.MeasureSpec.EXACTLY), View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED)); @@ -208,7 +208,7 @@ public class FragmentAccounts extends FragmentBase { return header; } }; - rvAccount.addItemDecoration(dateDecorator); + rvAccount.addItemDecoration(categoryDecorator); adapter = new AdapterAccount(this, settings); rvAccount.setAdapter(adapter); diff --git a/app/src/main/java/eu/faircode/email/FragmentFolders.java b/app/src/main/java/eu/faircode/email/FragmentFolders.java index 5956fde3c7..8dbd166159 100644 --- a/app/src/main/java/eu/faircode/email/FragmentFolders.java +++ b/app/src/main/java/eu/faircode/email/FragmentFolders.java @@ -21,6 +21,8 @@ package eu.faircode.email; import static android.app.Activity.RESULT_OK; +import static androidx.recyclerview.widget.RecyclerView.NO_POSITION; + import android.app.Dialog; import android.app.NotificationManager; import android.content.ContentResolver; @@ -28,6 +30,7 @@ import android.content.Context; import android.content.DialogInterface; import android.content.Intent; import android.content.SharedPreferences; +import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Rect; import android.net.Uri; @@ -44,6 +47,7 @@ import android.widget.CompoundButton; import android.widget.EditText; import android.widget.ImageButton; import android.widget.RadioGroup; +import android.widget.TextView; import android.widget.Toast; import androidx.annotation.NonNull; @@ -79,6 +83,7 @@ import java.util.Collections; import java.util.Date; import java.util.List; import java.util.Locale; +import java.util.Objects; import java.util.Properties; import javax.mail.Message; @@ -197,19 +202,79 @@ public class FragmentFolders extends FragmentBase { rvFolder.setLayoutManager(llm); if (!cards) { - DividerItemDecoration itemDecorator = new DividerItemDecoration(getContext(), llm.getOrientation()) { - @Override - public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) { - if (view.findViewById(R.id.clItem).getVisibility() == View.GONE) - outRect.setEmpty(); - else - super.getItemOffsets(outRect, view, parent, state); - } - }; + DividerItemDecoration itemDecorator = new DividerItemDecoration(getContext(), llm.getOrientation()); itemDecorator.setDrawable(getContext().getDrawable(R.drawable.divider)); rvFolder.addItemDecoration(itemDecorator); } + if (unified) { + DividerItemDecoration categoryDecorator = new DividerItemDecoration(getContext(), llm.getOrientation()) { + @Override + public void onDraw(@NonNull Canvas canvas, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) { + int count = parent.getChildCount(); + for (int i = 0; i < count; i++) { + View view = parent.getChildAt(i); + int pos = parent.getChildAdapterPosition(view); + + View header = getView(view, parent, pos); + if (header != null) { + canvas.save(); + canvas.translate(0, parent.getChildAt(i).getTop() - header.getMeasuredHeight()); + header.draw(canvas); + canvas.restore(); + } + } + } + + @Override + public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) { + int pos = parent.getChildAdapterPosition(view); + View header = getView(view, parent, pos); + if (header == null) + outRect.setEmpty(); + else + outRect.top = header.getMeasuredHeight(); + } + + private View getView(View view, RecyclerView parent, int pos) { + if (pos == NO_POSITION) + return null; + + TupleFolderEx prev = adapter.getItemAtPosition(pos - 1); + TupleFolderEx account = adapter.getItemAtPosition(pos); + if (pos > 0 && prev == null) + return null; + if (account == null) + return null; + + if (pos > 0) { + if (Objects.equals(prev.accountCategory, account.accountCategory)) + return null; + } else { + if (account.accountCategory == null) + return null; + } + + View header = inflater.inflate(R.layout.item_category, parent, false); + TextView tvCategory = header.findViewById(R.id.tvCategory); + + if (cards) { + View vSeparatorCategory = header.findViewById(R.id.vSeparatorCategory); + vSeparatorCategory.setVisibility(View.GONE); + } + + tvCategory.setText(account.accountCategory); + + header.measure(View.MeasureSpec.makeMeasureSpec(parent.getWidth(), View.MeasureSpec.EXACTLY), + View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED)); + header.layout(0, 0, header.getMeasuredWidth(), header.getMeasuredHeight()); + + return header; + } + }; + rvFolder.addItemDecoration(categoryDecorator); + } + adapter = new AdapterFolder(this, account, unified, primary, compact, show_hidden, show_flagged, null); rvFolder.setAdapter(adapter); diff --git a/app/src/main/java/eu/faircode/email/TupleFolderEx.java b/app/src/main/java/eu/faircode/email/TupleFolderEx.java index daf99f957d..075138fa4d 100644 --- a/app/src/main/java/eu/faircode/email/TupleFolderEx.java +++ b/app/src/main/java/eu/faircode/email/TupleFolderEx.java @@ -41,6 +41,7 @@ public class TupleFolderEx extends EntityFolder implements Serializable { public Integer accountProtocol; public Integer accountOrder; public String accountName; + public String accountCategory; public Integer accountColor; public String accountState; public int rules; @@ -70,6 +71,7 @@ public class TupleFolderEx extends EntityFolder implements Serializable { Objects.equals(this.accountProtocol, other.accountProtocol) && Objects.equals(this.accountOrder, other.accountOrder) && Objects.equals(this.accountName, other.accountName) && + Objects.equals(this.accountCategory, other.accountCategory) && Objects.equals(this.accountColor, other.accountColor) && Objects.equals(this.accountState, other.accountState) && this.rules == other.rules && @@ -117,6 +119,12 @@ public class TupleFolderEx extends EntityFolder implements Serializable { TupleFolderEx f1 = (TupleFolderEx) o1; TupleFolderEx f2 = (TupleFolderEx) o2; + int c = collator.compare( + f1.accountCategory == null ? "" : f1.accountCategory, + f2.accountCategory == null ? "" : f2.accountCategory); + if (c != 0) + return c; + // Outbox if (f1.accountName == null && f2.accountName == null) return 0; diff --git a/app/src/main/res/layout/item_category.xml b/app/src/main/res/layout/item_category.xml new file mode 100644 index 0000000000..5b9ddbcee9 --- /dev/null +++ b/app/src/main/res/layout/item_category.xml @@ -0,0 +1,27 @@ + + + + + + + \ No newline at end of file diff --git a/metadata/en-US/changelogs/1751.txt b/metadata/en-US/changelogs/1751.txt index 4d51df957e..3641d156fb 100644 --- a/metadata/en-US/changelogs/1751.txt +++ b/metadata/en-US/changelogs/1751.txt @@ -4,6 +4,10 @@ ### [Adratiklit](https://en.wikipedia.org/wiki/Adratiklit) +### Next version + +* Added account categories + ### 1.1751 * Fixed updating system folder properties