chore(release): bump app version to 5.1.0

This commit is contained in:
zarzet committed 2026-10-03 16:12:01 +07:00
1 parent e35a3cbb84
commit 6550104df9
5 files changed
+25 -193

No files matched your search

+2 -2
View File
@@ -1,8 +1,8 @@
import 'package:flutter/foundation.dart';
class AppInfo {
static const String version = '5.0.8';
static const String buildNumber = '157';
static const String version = '5.1.0';
static const String buildNumber = '158';
static const String gitCommit = String.fromEnvironment('GIT_COMMIT');
static String get shortGitCommit =>
+6 -182
View File
@@ -79,11 +79,6 @@ class _DonatePageState extends State<DonatePage> {
const SizedBox(height: 16),
],
_DonateLinksCard(colorScheme: colorScheme, config: _config),
const SizedBox(height: 24),
_RecentDonorsCard(
colorScheme: colorScheme,
supporters: _config.supporters,
),
const SizedBox(height: 16),
_DonateNoticeCard(
colorScheme: colorScheme,
@@ -212,15 +207,6 @@ class _MonthlyDonationGoalCard extends StatelessWidget {
style: theme.textTheme.bodyMedium,
),
],
if (goal.showSupporterCount) ...[
const SizedBox(height: 12),
Text(
'${NumberFormat.decimalPattern(locale).format(goal.supporterCount)} supporters',
style: theme.textTheme.bodyMedium?.copyWith(
color: colorScheme.onSurfaceVariant,
),
),
],
if (goal.showSourceBreakdown && goal.sources.isNotEmpty) ...[
const SizedBox(height: 16),
for (final entry in goal.sources.entries)
@@ -236,8 +222,6 @@ class _MonthlyDonationGoalCard extends StatelessWidget {
},
if (goal.showAmounts && entry.value.amount != null)
currencyFormat.format(entry.value.amount),
if (goal.showSupporterCount)
'${NumberFormat.decimalPattern(locale).format(entry.value.supporterCount)} supporters',
].join(' · '),
style: theme.textTheme.bodySmall?.copyWith(
color: colorScheme.onSurfaceVariant,
@@ -281,33 +265,12 @@ class _DonateLinksCard extends StatelessWidget {
children: [
Padding(
padding: const EdgeInsets.fromLTRB(20, 18, 20, 14),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Expanded(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
config.title,
style: Theme.of(context).textTheme.titleMedium
?.copyWith(
fontWeight: FontWeight.w700,
color: colorScheme.onSurface,
),
),
const SizedBox(height: 4),
Text(
config.message,
style: Theme.of(context).textTheme.bodySmall?.copyWith(
color: colorScheme.onSurfaceVariant,
height: 1.35,
),
),
],
),
),
],
child: Text(
config.title,
style: Theme.of(context).textTheme.titleMedium?.copyWith(
fontWeight: FontWeight.w700,
color: colorScheme.onSurface,
),
),
),
Divider(
@@ -346,102 +309,6 @@ class _DonateLinksCard extends StatelessWidget {
}
}
class _RecentDonorsCard extends StatelessWidget {
final ColorScheme colorScheme;
final List<String> supporters;
const _RecentDonorsCard({
required this.colorScheme,
required this.supporters,
});
@override
Widget build(BuildContext context) {
final isDark = Theme.of(context).brightness == Brightness.dark;
final cardColor = isDark
? Color.alphaBlend(
Colors.white.withValues(alpha: 0.08),
colorScheme.surface,
)
: Color.alphaBlend(
Colors.black.withValues(alpha: 0.04),
colorScheme.surface,
);
return Card(
elevation: 0,
color: cardColor,
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(20)),
child: Padding(
padding: const EdgeInsets.all(20),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
children: [
Icon(Icons.star_rounded, size: 20, color: colorScheme.primary),
const SizedBox(width: 8),
Text(
'Recent Supporters',
style: Theme.of(context).textTheme.titleMedium?.copyWith(
fontWeight: FontWeight.w600,
color: colorScheme.onSurface,
),
),
],
),
const SizedBox(height: 4),
Text(
'Thank you for your generosity!',
style: Theme.of(context).textTheme.bodySmall?.copyWith(
color: colorScheme.onSurfaceVariant,
),
),
const SizedBox(height: 16),
if (supporters.isEmpty)
Center(
child: Padding(
padding: const EdgeInsets.symmetric(vertical: 8),
child: Column(
children: [
Icon(
Icons.emoji_events_outlined,
size: 32,
color: colorScheme.onSurfaceVariant.withValues(
alpha: 0.4,
),
),
const SizedBox(height: 8),
Text(
'No supporters yet - be the first!',
style: Theme.of(context).textTheme.bodyMedium?.copyWith(
color: colorScheme.onSurfaceVariant.withValues(
alpha: 0.6,
),
),
),
],
),
),
)
else
Wrap(
spacing: 8,
runSpacing: 8,
children: supporters
.map(
(name) =>
_SupporterChip(name: name, colorScheme: colorScheme),
)
.toList(),
),
],
),
),
);
}
}
class _DonateNoticeCard extends StatelessWidget {
final ColorScheme colorScheme;
final List<String> notices;
@@ -579,49 +446,6 @@ class _DonateMethodItem extends StatelessWidget {
}
}
class _SupporterChip extends StatelessWidget {
final String name;
final ColorScheme colorScheme;
const _SupporterChip({required this.name, required this.colorScheme});
@override
Widget build(BuildContext context) {
return Material(
color: colorScheme.secondaryContainer,
borderRadius: BorderRadius.circular(20),
child: Padding(
padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 8),
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
CircleAvatar(
radius: 10,
backgroundColor: colorScheme.primary.withValues(alpha: 0.2),
child: Text(
name.isNotEmpty ? name[0].toUpperCase() : '?',
style: TextStyle(
fontSize: 10,
fontWeight: FontWeight.bold,
color: colorScheme.primary,
),
),
),
const SizedBox(width: 8),
Text(
name,
style: Theme.of(context).textTheme.labelLarge?.copyWith(
color: colorScheme.onSecondaryContainer,
fontWeight: FontWeight.w500,
),
),
],
),
),
);
}
}
class _NoticeLine extends StatelessWidget {
final IconData icon;
final String text;
+13 -5
View File
@@ -162,8 +162,8 @@ class DonateConfig {
return DonateConfig(
enabled: json['enabled'] as bool? ?? true,
title: _readString(json['title']).isEmpty
? 'Support Development'
: _readString(json['title']),
? 'Support SpotiFLAC-Mobile'
: _mobileDonationText(_readString(json['title'])),
message: _readString(json['message']).isEmpty
? 'Optional support helps cover tools, testing devices, and hosting.'
: _readString(json['message']),
@@ -185,7 +185,7 @@ class DonateConfig {
factory DonateConfig.fallback() {
return const DonateConfig(
enabled: true,
title: 'Support Development',
title: 'Support SpotiFLAC-Mobile',
message: 'Optional support helps cover dev tools and testing devices.',
methods: [
DonateMethod(
@@ -272,8 +272,11 @@ class MonthlyDonationGoal {
enabled: _readBool(json['enabled']),
active: _readBool(json['active']),
period: _readString(json['period']),
title: _readNullableString(json['title']) ?? 'Monthly development goal',
description: _readString(json['description']),
title: _mobileDonationText(
_readNullableString(json['title']) ??
'Monthly SpotiFLAC-Mobile development goal',
),
description: _mobileDonationText(_readString(json['description'])),
progressPercent: (_readFiniteNumber(json['progress_percent']) ?? 0).clamp(
0,
double.maxFinite,
@@ -500,6 +503,11 @@ String _readString(Object? value) {
return value is String ? value.trim() : '';
}
String _mobileDonationText(String text) => text.replaceAll(
RegExp(r'\bSpotiFLAC(?:[ -]+Mobile)?\b', caseSensitive: false),
'SpotiFLAC-Mobile',
);
double? _readFiniteNumber(Object? value) {
final number = value is num
? value.toDouble()
+1 -1
View File
@@ -1,7 +1,7 @@
name: spotiflac_android
description: Extension-driven music metadata and downloads for mobile devices
publish_to: "none"
version: 5.0.8+157
version: 5.1.0+158
environment:
sdk: ^3.10.0
+3 -3
View File
@@ -63,7 +63,7 @@ void main() {
});
for (final brightness in Brightness.values) {
testWidgets('monthly goal respects hidden amounts in $brightness', (
testWidgets('monthly goal shows progress without counts in $brightness', (
tester,
) async {
tester.view.physicalSize = const Size(430, 932);
@@ -97,7 +97,7 @@ void main() {
expect(find.text('Monthly development goal'), findsOneWidget);
expect(find.text('Oktober 2026'), findsOneWidget);
expect(find.text('9%'), findsOneWidget);
expect(find.text('14 supporters'), findsOneWidget);
expect(find.text('14 supporters'), findsNothing);
expect(
tester
.widget<LinearProgressIndicator>(
@@ -150,7 +150,7 @@ void main() {
'display': {
'amounts': true,
'percentage': false,
'supporter_count': false,
'supporter_count': true,
'source_breakdown': true,
},
},