Skip to content

Commit f546b80

Browse files
authored
Merge pull request #3 from tmaxxdd/feature/handle-code-card-state
Handle code card state
2 parents 234cdc5 + 93335d9 commit f546b80

File tree

10 files changed

+179
-894
lines changed

10 files changed

+179
-894
lines changed

app/src/main/java/pl/tkadziolka/snipmeandroid/Bridge.java

Lines changed: 0 additions & 843 deletions
This file was deleted.

app/src/main/java/pl/tkadziolka/snipmeandroid/bridge/Bridge.java

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -87,6 +87,17 @@ private SnippetFilterType(final int index) {
8787
}
8888
}
8989

90+
public enum UserReaction {
91+
NONE(0),
92+
LIKE(1),
93+
DISLIKE(2);
94+
95+
private int index;
96+
private UserReaction(final int index) {
97+
this.index = index;
98+
}
99+
}
100+
90101
public enum ModelState {
91102
LOADING(0),
92103
LOADED(1),
@@ -141,6 +152,12 @@ public void setOwner(@Nullable Owner setterArg) {
141152
this.owner = setterArg;
142153
}
143154

155+
private @Nullable Boolean isOwner;
156+
public @Nullable Boolean getIsOwner() { return isOwner; }
157+
public void setIsOwner(@Nullable Boolean setterArg) {
158+
this.isOwner = setterArg;
159+
}
160+
144161
private @Nullable String timeAgo;
145162
public @Nullable String getTimeAgo() { return timeAgo; }
146163
public void setTimeAgo(@Nullable String setterArg) {
@@ -153,6 +170,12 @@ public void setVoteResult(@Nullable Long setterArg) {
153170
this.voteResult = setterArg;
154171
}
155172

173+
private @Nullable UserReaction userReaction;
174+
public @Nullable UserReaction getUserReaction() { return userReaction; }
175+
public void setUserReaction(@Nullable UserReaction setterArg) {
176+
this.userReaction = setterArg;
177+
}
178+
156179
public static final class Builder {
157180
private @Nullable String uuid;
158181
public @NonNull Builder setUuid(@Nullable String setterArg) {
@@ -179,6 +202,11 @@ public static final class Builder {
179202
this.owner = setterArg;
180203
return this;
181204
}
205+
private @Nullable Boolean isOwner;
206+
public @NonNull Builder setIsOwner(@Nullable Boolean setterArg) {
207+
this.isOwner = setterArg;
208+
return this;
209+
}
182210
private @Nullable String timeAgo;
183211
public @NonNull Builder setTimeAgo(@Nullable String setterArg) {
184212
this.timeAgo = setterArg;
@@ -189,15 +217,22 @@ public static final class Builder {
189217
this.voteResult = setterArg;
190218
return this;
191219
}
220+
private @Nullable UserReaction userReaction;
221+
public @NonNull Builder setUserReaction(@Nullable UserReaction setterArg) {
222+
this.userReaction = setterArg;
223+
return this;
224+
}
192225
public @NonNull Snippet build() {
193226
Snippet pigeonReturn = new Snippet();
194227
pigeonReturn.setUuid(uuid);
195228
pigeonReturn.setTitle(title);
196229
pigeonReturn.setCode(code);
197230
pigeonReturn.setLanguage(language);
198231
pigeonReturn.setOwner(owner);
232+
pigeonReturn.setIsOwner(isOwner);
199233
pigeonReturn.setTimeAgo(timeAgo);
200234
pigeonReturn.setVoteResult(voteResult);
235+
pigeonReturn.setUserReaction(userReaction);
201236
return pigeonReturn;
202237
}
203238
}
@@ -208,8 +243,10 @@ public static final class Builder {
208243
toMapResult.put("code", (code == null) ? null : code.toMap());
209244
toMapResult.put("language", (language == null) ? null : language.toMap());
210245
toMapResult.put("owner", (owner == null) ? null : owner.toMap());
246+
toMapResult.put("isOwner", isOwner);
211247
toMapResult.put("timeAgo", timeAgo);
212248
toMapResult.put("voteResult", voteResult);
249+
toMapResult.put("userReaction", userReaction == null ? null : userReaction.index);
213250
return toMapResult;
214251
}
215252
static @NonNull Snippet fromMap(@NonNull Map<String, Object> map) {
@@ -224,10 +261,14 @@ public static final class Builder {
224261
pigeonResult.setLanguage((language == null) ? null : SnippetLanguage.fromMap((Map)language));
225262
Object owner = map.get("owner");
226263
pigeonResult.setOwner((owner == null) ? null : Owner.fromMap((Map)owner));
264+
Object isOwner = map.get("isOwner");
265+
pigeonResult.setIsOwner((Boolean)isOwner);
227266
Object timeAgo = map.get("timeAgo");
228267
pigeonResult.setTimeAgo((String)timeAgo);
229268
Object voteResult = map.get("voteResult");
230269
pigeonResult.setVoteResult((voteResult == null) ? null : ((voteResult instanceof Integer) ? (Integer)voteResult : (Long)voteResult));
270+
Object userReaction = map.get("userReaction");
271+
pigeonResult.setUserReaction(userReaction == null ? null : UserReaction.values()[(int)userReaction]);
231272
return pigeonResult;
232273
}
233274
}

app/src/main/java/pl/tkadziolka/snipmeandroid/bridge/main/MainModelPlugin.kt

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,11 @@ import android.text.Spanned
44
import android.text.format.DateUtils
55
import android.text.style.ForegroundColorSpan
66
import androidx.core.text.getSpans
7-
import io.flutter.embedding.engine.plugins.FlutterPlugin
87
import io.flutter.plugin.common.BinaryMessenger
98
import org.koin.core.component.inject
10-
import pl.tkadziolka.snipmeandroid.Bridge
9+
import pl.tkadziolka.snipmeandroid.bridge.Bridge
1110
import pl.tkadziolka.snipmeandroid.bridge.ModelPlugin
11+
import pl.tkadziolka.snipmeandroid.domain.reaction.UserReaction
1212
import pl.tkadziolka.snipmeandroid.domain.snippets.Owner
1313
import pl.tkadziolka.snipmeandroid.domain.snippets.Snippet
1414
import pl.tkadziolka.snipmeandroid.domain.snippets.SnippetCode
@@ -86,7 +86,9 @@ class MainModelPlugin : ModelPlugin<Bridge.MainModelBridge>(), Bridge.MainModelB
8686
code = it.code.toModelSnippetCode()
8787
language = it.language.toModelSnippetLanguage()
8888
owner = it.owner.toModelOwner()
89+
isOwner = it.isOwner
8990
voteResult = (it.numberOfLikes - it.numberOfDislikes).toLong()
91+
userReaction = it.userReaction.toModelUserReaction()
9092
timeAgo = DateUtils.getRelativeTimeSpanString(
9193
it.modifiedAt.time,
9294
Date().time,
@@ -125,4 +127,11 @@ class MainModelPlugin : ModelPlugin<Bridge.MainModelBridge>(), Bridge.MainModelB
125127
it.color = foregroundColor.toLong()
126128
it
127129
}
130+
131+
private fun UserReaction.toModelUserReaction(): Bridge.UserReaction =
132+
when(this) {
133+
UserReaction.LIKE -> Bridge.UserReaction.LIKE
134+
UserReaction.DISLIKE -> Bridge.UserReaction.DISLIKE
135+
else -> Bridge.UserReaction.NONE
136+
}
128137
}

flutter_module/bridge/main_model.dart

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,10 @@ class Snippet {
88
SnippetCode? code;
99
SnippetLanguage? language;
1010
Owner? owner;
11+
bool? isOwner;
1112
String? timeAgo;
1213
int? voteResult;
14+
UserReaction? userReaction;
1315
}
1416

1517
class SnippetCode {
@@ -87,6 +89,12 @@ class SnippetFilter {
8789
SnippetFilterType? type;
8890
}
8991

92+
enum UserReaction {
93+
none,
94+
like,
95+
dislike
96+
}
97+
9098
// State
9199

92100
enum ModelState { loading, loaded, error }
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
///This file is automatically generated. DO NOT EDIT, all your changes would be lost.
2+
class Assets {
3+
Assets._();
4+
5+
static const String reactionDislike = 'assets/images/icons/reaction_dislike.png';
6+
static const String reactionLike = 'assets/images/icons/reaction_like.png';
7+
static const String reactionUndefined = 'assets/images/icons/reaction_undefined.png';
8+
9+
}

flutter_module/lib/model/main_model.dart

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,12 @@ enum SnippetFilterType {
6161
shared,
6262
}
6363

64+
enum UserReaction {
65+
none,
66+
like,
67+
dislike,
68+
}
69+
6470
enum ModelState {
6571
loading,
6672
loaded,
@@ -80,17 +86,21 @@ class Snippet {
8086
this.code,
8187
this.language,
8288
this.owner,
89+
this.isOwner,
8390
this.timeAgo,
8491
this.voteResult,
92+
this.userReaction,
8593
});
8694

8795
String? uuid;
8896
String? title;
8997
SnippetCode? code;
9098
SnippetLanguage? language;
9199
Owner? owner;
100+
bool? isOwner;
92101
String? timeAgo;
93102
int? voteResult;
103+
UserReaction? userReaction;
94104

95105
Object encode() {
96106
final Map<Object?, Object?> pigeonMap = <Object?, Object?>{};
@@ -99,8 +109,10 @@ class Snippet {
99109
pigeonMap['code'] = code?.encode();
100110
pigeonMap['language'] = language?.encode();
101111
pigeonMap['owner'] = owner?.encode();
112+
pigeonMap['isOwner'] = isOwner;
102113
pigeonMap['timeAgo'] = timeAgo;
103114
pigeonMap['voteResult'] = voteResult;
115+
pigeonMap['userReaction'] = userReaction?.index;
104116
return pigeonMap;
105117
}
106118

@@ -118,8 +130,12 @@ class Snippet {
118130
owner: pigeonMap['owner'] != null
119131
? Owner.decode(pigeonMap['owner']!)
120132
: null,
133+
isOwner: pigeonMap['isOwner'] as bool?,
121134
timeAgo: pigeonMap['timeAgo'] as String?,
122135
voteResult: pigeonMap['voteResult'] as int?,
136+
userReaction: pigeonMap['userReaction'] != null
137+
? UserReaction.values[pigeonMap['userReaction']! as int]
138+
: null,
123139
);
124140
}
125141
}

flutter_module/lib/presentation/styles/text_styles.dart

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,16 @@ class TextStyles extends Text {
3434
style: const TextStyle(color: Colors.grey),
3535
);
3636

37+
const TextStyles.secondaryBold(this.text, {Key? key})
38+
: super(
39+
text,
40+
key: key,
41+
style: const TextStyle(
42+
color: Colors.grey,
43+
fontWeight: FontWeight.bold,
44+
),
45+
);
46+
3747
const TextStyles.label(this.text, {Key? key})
3848
: super(
3949
text,
Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
import 'package:flutter/material.dart';
2+
import 'package:flutter_module/generated/assets.dart';
3+
import 'package:flutter_module/model/main_model.dart';
4+
import 'package:flutter_module/presentation/styles/dimens.dart';
5+
import 'package:flutter_module/presentation/styles/surface_styles.dart';
6+
import 'package:flutter_module/presentation/styles/text_styles.dart';
7+
8+
class SnippetDetailsBar extends StatelessWidget {
9+
const SnippetDetailsBar({
10+
Key? key,
11+
required this.snippet,
12+
}) : super(key: key);
13+
14+
final Snippet snippet;
15+
16+
@override
17+
Widget build(BuildContext context) {
18+
return Row(
19+
children: [
20+
Expanded(
21+
child: Column(
22+
mainAxisSize: MainAxisSize.min,
23+
crossAxisAlignment: CrossAxisAlignment.stretch,
24+
children: [
25+
TextStyles.regular(snippet.language?.raw ?? "Unknown language"),
26+
const SizedBox(height: Dimens.m),
27+
snippet.isOwner == true
28+
? TextStyles.secondaryBold(snippet.owner?.login ?? "")
29+
: TextStyles.secondary(snippet.owner?.login ?? ""),
30+
const SizedBox(height: Dimens.s),
31+
TextStyles.helper(snippet.timeAgo ?? "")
32+
],
33+
),
34+
),
35+
_UserReactionIndicator(reaction: snippet.userReaction),
36+
const SizedBox(width: Dimens.l),
37+
SurfaceStyles.rateBox(
38+
TextStyles.title(
39+
_getVoteCountText(snippet.voteResult),
40+
),
41+
)
42+
],
43+
);
44+
}
45+
46+
String _getVoteCountText(int? voteResult) {
47+
const defaultValue = '+0';
48+
if (voteResult == null) return defaultValue;
49+
if (voteResult == 0) return defaultValue;
50+
if (voteResult > 0) return '+$voteResult';
51+
return '-$voteResult';
52+
}
53+
}
54+
55+
class _UserReactionIndicator extends StatelessWidget {
56+
const _UserReactionIndicator({
57+
Key? key,
58+
this.reaction,
59+
}) : super(key: key);
60+
61+
final UserReaction? reaction;
62+
63+
@override
64+
Widget build(BuildContext context) {
65+
if (reaction == UserReaction.like) {
66+
return Image.asset(Assets.reactionLike);
67+
}
68+
69+
if (reaction == UserReaction.dislike) {
70+
return Image.asset(Assets.reactionDislike);
71+
}
72+
73+
return Image.asset(Assets.reactionUndefined);
74+
}
75+
}

flutter_module/lib/presentation/widgets/snippet_list_item.dart

Lines changed: 2 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import 'package:flutter_module/presentation/styles/dimens.dart';
66
import 'package:flutter_module/presentation/styles/surface_styles.dart';
77
import 'package:flutter_module/presentation/styles/text_styles.dart';
88
import 'package:flutter_module/presentation/widgets/code_text_view.dart';
9+
import 'package:flutter_module/presentation/widgets/snippet_details_bar.dart';
910

1011
class SnippetListTile extends HookWidget {
1112
const SnippetListTile({
@@ -61,46 +62,4 @@ class SnippetListTile extends HookWidget {
6162
),
6263
);
6364
}
64-
}
65-
66-
class SnippetDetailsBar extends StatelessWidget {
67-
const SnippetDetailsBar({
68-
Key? key,
69-
required this.snippet,
70-
}) : super(key: key);
71-
72-
final Snippet snippet;
73-
74-
@override
75-
Widget build(BuildContext context) {
76-
return Row(
77-
children: [
78-
Expanded(
79-
child: Column(
80-
mainAxisSize: MainAxisSize.min,
81-
crossAxisAlignment: CrossAxisAlignment.stretch,
82-
children: [
83-
TextStyles.regular(snippet.language?.raw ?? ""),
84-
const SizedBox(height: Dimens.m),
85-
TextStyles.secondary(snippet.owner?.login ?? ""),
86-
const SizedBox(height: Dimens.s),
87-
TextStyles.helper(snippet.timeAgo ?? "")
88-
],
89-
),
90-
),
91-
SurfaceStyles.rateBox(
92-
TextStyles.title(
93-
_getVoteCountText(snippet.voteResult),
94-
),
95-
)
96-
],
97-
);
98-
}
99-
100-
String _getVoteCountText(int? voteResult) {
101-
if (voteResult == null) return '-';
102-
if (voteResult == 0) return '-';
103-
if (voteResult > 0) return '+$voteResult';
104-
return '-$voteResult';
105-
}
106-
}
65+
}

0 commit comments

Comments
 (0)