1package eu.siacs.conversations.ui;
2
3import android.view.View;
4
5import com.google.android.material.chip.Chip;
6import com.google.android.material.chip.ChipGroup;
7import com.google.android.material.color.MaterialColors;
8import com.google.common.collect.Collections2;
9import com.google.common.collect.ImmutableSet;
10
11import eu.siacs.conversations.R;
12import eu.siacs.conversations.entities.Reaction;
13
14import java.util.Collection;
15import java.util.List;
16import java.util.Locale;
17import java.util.Map;
18import java.util.function.Consumer;
19
20public class BindingAdapters {
21
22 public static void setReactionsOnReceived(
23 final ChipGroup chipGroup,
24 final Reaction.Aggregated reactions,
25 final Consumer<Collection<String>> onModifiedReactions,
26 final Runnable addReaction) {
27 setReactions(chipGroup, reactions, true, onModifiedReactions, addReaction);
28 }
29
30 public static void setReactionsOnSent(
31 final ChipGroup chipGroup,
32 final Reaction.Aggregated reactions,
33 final Consumer<Collection<String>> onModifiedReactions) {
34 setReactions(chipGroup, reactions, false, onModifiedReactions, null);
35 }
36
37 private static void setReactions(
38 final ChipGroup chipGroup,
39 final Reaction.Aggregated aggregated,
40 final boolean onReceived,
41 final Consumer<Collection<String>> onModifiedReactions,
42 final Runnable addReaction) {
43 final var context = chipGroup.getContext();
44 final List<Map.Entry<String, Integer>> reactions = aggregated.reactions;
45 if (reactions == null || reactions.isEmpty()) {
46 chipGroup.setVisibility(View.GONE);
47 } else {
48 chipGroup.removeAllViews();
49 chipGroup.setVisibility(View.VISIBLE);
50 for (final Map.Entry<String, Integer> reaction : reactions) {
51 final var emoji = reaction.getKey();
52 final var count = reaction.getValue();
53 final Chip chip = new Chip(chipGroup.getContext());
54 chip.setEnsureMinTouchTargetSize(false);
55 chip.setChipStartPadding(0.0f);
56 chip.setChipEndPadding(0.0f);
57 if (count == 1) {
58 chip.setText(emoji);
59 } else {
60 chip.setText(String.format(Locale.ENGLISH, "%s %d", emoji, count));
61 }
62 final boolean oneOfOurs = aggregated.ourReactions.contains(emoji);
63 // received = surface; sent = surface high matches bubbles
64 if (oneOfOurs) {
65 chip.setChipBackgroundColor(
66 MaterialColors.getColorStateListOrNull(
67 context,
68 com.google.android.material.R.attr
69 .colorSurfaceContainerHighest));
70 } else {
71 chip.setChipBackgroundColor(
72 MaterialColors.getColorStateListOrNull(
73 context,
74 com.google.android.material.R.attr.colorSurfaceContainerLow));
75 }
76 chip.setOnClickListener(
77 v -> {
78 if (oneOfOurs) {
79 onModifiedReactions.accept(
80 ImmutableSet.copyOf(
81 Collections2.filter(
82 aggregated.ourReactions,
83 r -> !r.equals(emoji))));
84 } else {
85 onModifiedReactions.accept(
86 new ImmutableSet.Builder<String>()
87 .addAll(aggregated.ourReactions)
88 .add(emoji)
89 .build());
90 }
91 });
92 chipGroup.addView(chip);
93 }
94 if (onReceived) {
95 final Chip chip = new Chip(chipGroup.getContext());
96 chip.setChipIconResource(R.drawable.ic_add_reaction_24dp);
97 chip.setChipStrokeColor(
98 MaterialColors.getColorStateListOrNull(
99 chipGroup.getContext(),
100 com.google.android.material.R.attr.colorTertiary));
101 chip.setChipBackgroundColor(
102 MaterialColors.getColorStateListOrNull(
103 chipGroup.getContext(),
104 com.google.android.material.R.attr.colorTertiaryContainer));
105 chip.setChipIconTint(
106 MaterialColors.getColorStateListOrNull(
107 chipGroup.getContext(),
108 com.google.android.material.R.attr.colorOnTertiaryContainer));
109 chip.setEnsureMinTouchTargetSize(false);
110 chip.setTextEndPadding(0.0f);
111 chip.setTextStartPadding(0.0f);
112 chip.setOnClickListener(v -> addReaction.run());
113 chipGroup.addView(chip);
114 }
115 }
116 }
117}