Release Lunaris 2.0.1 polish update
This commit is contained in:
@@ -1,3 +1,5 @@
|
||||
import 'dart:async';
|
||||
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
|
||||
import '../../../app/app.dart';
|
||||
@@ -9,8 +11,12 @@ final feedControllerProvider =
|
||||
AsyncNotifierProvider<FeedController, FeedState>(FeedController.new);
|
||||
|
||||
class FeedController extends AsyncNotifier<FeedState> {
|
||||
Timer? _providerDebounce;
|
||||
int _loadRequestId = 0;
|
||||
|
||||
@override
|
||||
Future<FeedState> build() async {
|
||||
ref.onDispose(() => _providerDebounce?.cancel());
|
||||
final providers = await _loadProviders();
|
||||
final settings = await _settings();
|
||||
final providerIds = providers.map((provider) => provider.id).toSet();
|
||||
@@ -32,23 +38,29 @@ class FeedController extends AsyncNotifier<FeedState> {
|
||||
|
||||
Future<void> loadInitial() async {
|
||||
final current = state.value ?? const FeedState();
|
||||
final requestId = ++_loadRequestId;
|
||||
state = const AsyncLoading();
|
||||
final posts = await _load(refresh: true, current: current);
|
||||
if (requestId != _loadRequestId) return;
|
||||
state = AsyncData(current.copyWith(posts: posts, clearError: true));
|
||||
}
|
||||
|
||||
Future<void> refresh() async {
|
||||
final current = state.value ?? const FeedState();
|
||||
final requestId = ++_loadRequestId;
|
||||
state = AsyncData(current.copyWith(isLoadingMore: true, clearError: true));
|
||||
final posts = await _load(refresh: true, current: current);
|
||||
if (requestId != _loadRequestId) return;
|
||||
state = AsyncData(current.copyWith(posts: posts, isLoadingMore: false));
|
||||
}
|
||||
|
||||
Future<void> loadNextPage() async {
|
||||
final current = state.value;
|
||||
if (current == null || current.isLoadingMore || !current.hasMore) return;
|
||||
final requestId = ++_loadRequestId;
|
||||
state = AsyncData(current.copyWith(isLoadingMore: true, clearError: true));
|
||||
final posts = await _load(refresh: false, current: current);
|
||||
if (requestId != _loadRequestId) return;
|
||||
final existingKeys = current.posts.map((post) => post.cacheKey).toSet();
|
||||
final newPosts = posts
|
||||
.where((post) => existingKeys.add(post.cacheKey))
|
||||
@@ -98,16 +110,21 @@ class FeedController extends AsyncNotifier<FeedState> {
|
||||
|
||||
Future<void> setProviders(List<String> providerIds) async {
|
||||
final current = state.value ?? const FeedState();
|
||||
state = AsyncData(
|
||||
current.copyWith(selectedProviderIds: providerIds, posts: []));
|
||||
final enabledIds = current.providers.map((provider) => provider.id).toSet();
|
||||
final selected = providerIds.where(enabledIds.contains).toList();
|
||||
state =
|
||||
AsyncData(current.copyWith(selectedProviderIds: selected, posts: []));
|
||||
final settings = await _settings();
|
||||
await ref.read(settingsServiceProvider).updateSettings(
|
||||
settings.copyWith(
|
||||
selectedFeedProviderIds: providerIds,
|
||||
lastFeedProviderIds: providerIds,
|
||||
selectedFeedProviderIds: selected,
|
||||
lastFeedProviderIds: selected,
|
||||
),
|
||||
);
|
||||
await refresh();
|
||||
_providerDebounce?.cancel();
|
||||
_providerDebounce = Timer(const Duration(milliseconds: 320), () {
|
||||
refresh();
|
||||
});
|
||||
}
|
||||
|
||||
Future<void> setTopPeriod(TopPeriodFilter period) async {
|
||||
|
||||
@@ -235,6 +235,8 @@ class _FeedScreenState extends ConsumerState<FeedScreen> {
|
||||
blurExplicit: settings.blurExplicitContent,
|
||||
showBadges: settings.showPostBadges,
|
||||
nsfwEnabled: settings.nsfwEnabled,
|
||||
mediaQualityMode: MediaQualityMode.fromName(
|
||||
settings.mediaQualityMode),
|
||||
loading: state.isLoadingMore,
|
||||
favoriteKeys: favoriteKeys,
|
||||
viewedKeys: viewedKeys,
|
||||
@@ -309,6 +311,7 @@ class _FeedScreenState extends ConsumerState<FeedScreen> {
|
||||
for (final post in _selectedPosts(posts)) {
|
||||
if (!favoriteKeys.contains(post.cacheKey)) {
|
||||
await ref.read(favoriteServiceProvider).addFavorite(post);
|
||||
await _maybeAutoDownloadFavorite(ref, post);
|
||||
}
|
||||
}
|
||||
ref.invalidate(favoriteKeysProvider);
|
||||
@@ -398,6 +401,7 @@ class _FeedScreenState extends ConsumerState<FeedScreen> {
|
||||
.removeFavorite(post.id, post.providerId);
|
||||
} else {
|
||||
await ref.read(favoriteServiceProvider).addFavorite(post);
|
||||
await _maybeAutoDownloadFavorite(ref, post);
|
||||
}
|
||||
ref.invalidate(favoriteKeysProvider);
|
||||
ref.invalidate(favoritesControllerProvider);
|
||||
@@ -426,6 +430,13 @@ class _FeedScreenState extends ConsumerState<FeedScreen> {
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Future<void> _maybeAutoDownloadFavorite(WidgetRef ref, Post post) async {
|
||||
final settings =
|
||||
ref.read(appSettingsProvider).value ?? AppSettings.defaults;
|
||||
if (!settings.autoDownloadFavorites || !settings.allowDownloads) return;
|
||||
await ref.read(downloadManagerServiceProvider).start(post);
|
||||
}
|
||||
}
|
||||
|
||||
class _RefreshIntent extends Intent {
|
||||
@@ -448,13 +459,17 @@ class _FeedTitle extends StatelessWidget {
|
||||
),
|
||||
),
|
||||
const SizedBox(width: 12),
|
||||
Text(
|
||||
'Feed',
|
||||
style: theme.textTheme.titleMedium?.copyWith(
|
||||
color: theme.colorScheme.onSurfaceVariant,
|
||||
fontWeight: FontWeight.w600,
|
||||
),
|
||||
),
|
||||
Builder(builder: (context) {
|
||||
return Consumer(
|
||||
builder: (context, ref, _) => Text(
|
||||
ref.watch(appStringsProvider).feed,
|
||||
style: theme.textTheme.titleMedium?.copyWith(
|
||||
color: theme.colorScheme.onSurfaceVariant,
|
||||
fontWeight: FontWeight.w600,
|
||||
),
|
||||
),
|
||||
);
|
||||
}),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user