Skip to content

Commit 6fd0e8b

Browse files
committed
refactor(headline): Improve metadata display
- Use utils for relative time - Compacted metadata info - Use chips for category/source
1 parent c8e707a commit 6fd0e8b

File tree

1 file changed

+57
-65
lines changed

1 file changed

+57
-65
lines changed

lib/shared/widgets/headline_tile_text_only.dart

Lines changed: 57 additions & 65 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
import 'package:flutter/material.dart';
22
import 'package:ht_main/l10n/l10n.dart';
33
import 'package:ht_main/shared/constants/app_spacing.dart';
4+
import 'package:ht_main/shared/utils/utils.dart'; // Import the new utility
45
import 'package:ht_shared/ht_shared.dart' show Headline;
5-
import 'package:timeago/timeago.dart' as timeago;
6+
// timeago import removed from here, handled by utility
67

78
/// {@template headline_tile_text_only}
89
/// A widget to display a headline item with text only.
@@ -96,109 +97,100 @@ class _HeadlineMetadataRow extends StatelessWidget {
9697

9798
@override
9899
Widget build(BuildContext context) {
99-
final String formattedDate;
100-
if (headline.publishedAt != null) {
101-
formattedDate = timeago.format(
102-
headline.publishedAt!,
103-
locale: Localizations.localeOf(context).languageCode,
104-
);
105-
} else {
106-
formattedDate = '';
107-
}
100+
final formattedDate = formatRelativeTime(context, headline.publishedAt);
108101

109102
final metadataStyle = textTheme.bodySmall?.copyWith(
110103
color: colorScheme.onSurfaceVariant,
111104
);
112-
const iconSize = 12.0;
105+
final chipLabelStyle = textTheme.labelSmall?.copyWith(
106+
color: colorScheme.onSurfaceVariant,
107+
);
108+
final chipBackgroundColor =
109+
colorScheme.surfaceContainerHighest.withOpacity(0.5);
110+
const iconSize = 12.0; // Kept for date icon
113111

114112
return Wrap(
115-
spacing: AppSpacing.md, // Spacing between items in the row
116-
runSpacing: AppSpacing.xs, // Spacing if items wrap
113+
spacing: AppSpacing.sm, // Reduced spacing for more compactness
114+
runSpacing: AppSpacing.xs,
117115
crossAxisAlignment: WrapCrossAlignment.center,
118116
children: [
119-
if (headline.category?.name != null)
117+
if (formattedDate.isNotEmpty)
120118
GestureDetector(
121119
onTap: () {
122120
ScaffoldMessenger.of(context)
123121
..hideCurrentSnackBar()
124122
..showSnackBar(
125-
SnackBar(
126-
content: Text(
127-
'Tapped Category: ${headline.category!.name}',
128-
),
129-
),
123+
SnackBar(content: Text('Tapped Date: $formattedDate')),
130124
);
131125
},
132-
child: Chip(
133-
avatar: Icon(
134-
Icons.label_outline,
135-
size: iconSize,
136-
color: colorScheme.onSurfaceVariant, // Changed color
137-
),
138-
label: Text(headline.category!.name),
139-
labelStyle: textTheme.labelSmall?.copyWith(
140-
color: colorScheme.onSurfaceVariant, // Changed color
141-
),
142-
// backgroundColor removed
143-
padding: const EdgeInsets.symmetric(horizontal: AppSpacing.sm),
144-
visualDensity: VisualDensity.compact,
145-
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
126+
child: Row(
127+
mainAxisSize: MainAxisSize.min,
128+
children: [
129+
Icon(
130+
Icons.calendar_today_outlined,
131+
size: iconSize,
132+
color: colorScheme.onSurfaceVariant,
133+
),
134+
const SizedBox(width: AppSpacing.xs),
135+
Text(formattedDate, style: metadataStyle),
136+
],
146137
),
147138
),
148-
if (headline.source?.name != null)
139+
if (headline.category?.name != null) ...[
140+
if (formattedDate.isNotEmpty)
141+
Padding(
142+
padding:
143+
const EdgeInsets.symmetric(horizontal: AppSpacing.xs / 2),
144+
child: Text('•', style: metadataStyle),
145+
),
149146
GestureDetector(
150147
onTap: () {
151148
ScaffoldMessenger.of(context)
152149
..hideCurrentSnackBar()
153150
..showSnackBar(
154151
SnackBar(
155-
content: Text('Tapped Source: ${headline.source!.name}'),
152+
content:
153+
Text('Tapped Category: ${headline.category!.name}'),
156154
),
157155
);
158156
},
159-
child: Row(
160-
mainAxisSize: MainAxisSize.min,
161-
children: [
162-
Icon(
163-
Icons.source_outlined,
164-
size: iconSize,
165-
color: colorScheme.onSurfaceVariant,
166-
),
167-
const SizedBox(width: AppSpacing.xs),
168-
Flexible(
169-
child: Text(
170-
headline.source!.name,
171-
style: metadataStyle,
172-
overflow: TextOverflow.ellipsis,
173-
),
174-
),
175-
],
157+
child: Chip(
158+
label: Text(headline.category!.name),
159+
labelStyle: chipLabelStyle,
160+
backgroundColor: chipBackgroundColor,
161+
padding: const EdgeInsets.symmetric(horizontal: AppSpacing.sm),
162+
visualDensity: VisualDensity.compact,
163+
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
176164
),
177165
),
178-
if (formattedDate.isNotEmpty)
166+
],
167+
if (headline.source?.name != null) ...[
168+
if (formattedDate.isNotEmpty || headline.category?.name != null)
169+
Padding(
170+
padding:
171+
const EdgeInsets.symmetric(horizontal: AppSpacing.xs / 2),
172+
child: Text('•', style: metadataStyle),
173+
),
179174
GestureDetector(
180175
onTap: () {
181176
ScaffoldMessenger.of(context)
182177
..hideCurrentSnackBar()
183178
..showSnackBar(
184179
SnackBar(
185-
content: Text('Tapped Date: $formattedDate'),
180+
content: Text('Tapped Source: ${headline.source!.name}'),
186181
),
187182
);
188183
},
189-
child: Row(
190-
mainAxisSize: MainAxisSize.min,
191-
children: [
192-
Icon(
193-
Icons.calendar_today_outlined,
194-
size: iconSize,
195-
color: colorScheme.onSurfaceVariant,
196-
),
197-
const SizedBox(width: AppSpacing.xs),
198-
Text(formattedDate, style: metadataStyle),
199-
],
184+
child: Chip(
185+
label: Text(headline.source!.name),
186+
labelStyle: chipLabelStyle,
187+
backgroundColor: chipBackgroundColor,
188+
padding: const EdgeInsets.symmetric(horizontal: AppSpacing.sm),
189+
visualDensity: VisualDensity.compact,
190+
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
200191
),
201192
),
193+
],
202194
],
203195
);
204196
}

0 commit comments

Comments
 (0)