This commit is contained in:
parent
6fb4775043
commit
78ff1953ad
@ -4,12 +4,14 @@ import 'package:flutter/services.dart';
|
|||||||
import 'package:f0ckapp/providers/MediaProvider.dart';
|
import 'package:f0ckapp/providers/MediaProvider.dart';
|
||||||
import 'package:f0ckapp/providers/ThemeProvider.dart';
|
import 'package:f0ckapp/providers/ThemeProvider.dart';
|
||||||
import 'package:f0ckapp/screens/MediaGrid.dart';
|
import 'package:f0ckapp/screens/MediaGrid.dart';
|
||||||
|
import 'package:f0ckapp/utils/AppVersion.dart';
|
||||||
|
|
||||||
import 'package:provider/provider.dart';
|
import 'package:provider/provider.dart';
|
||||||
|
|
||||||
void main() async {
|
void main() async {
|
||||||
WidgetsFlutterBinding.ensureInitialized();
|
WidgetsFlutterBinding.ensureInitialized();
|
||||||
await SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp]);
|
await SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp]);
|
||||||
|
await AppVersion.init();
|
||||||
|
|
||||||
runApp(
|
runApp(
|
||||||
MultiProvider(
|
MultiProvider(
|
||||||
|
@ -49,8 +49,10 @@ class MediaProvider extends ChangeNotifier {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void setMediaItems(List<MediaItem> mediaItems) {
|
void setMediaItems(List<MediaItem> mediaItems) {
|
||||||
_mediaItems = mediaItems;
|
if (_mediaItems != mediaItems) {
|
||||||
notifyListeners();
|
_mediaItems = mediaItems;
|
||||||
|
notifyListeners();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void addMediaItems(List<MediaItem> newItems) {
|
void addMediaItems(List<MediaItem> newItems) {
|
||||||
@ -58,10 +60,10 @@ class MediaProvider extends ChangeNotifier {
|
|||||||
notifyListeners();
|
notifyListeners();
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<void> loadMedia({bool reload = false}) async {
|
Future<void> loadMedia({bool reload = false, bool notify = true}) async {
|
||||||
if (_isLoading) return;
|
if (_isLoading) return;
|
||||||
_isLoading = true;
|
_isLoading = true;
|
||||||
notifyListeners();
|
if (notify) notifyListeners();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
final newMedia = await fetchMedia(
|
final newMedia = await fetchMedia(
|
||||||
@ -81,7 +83,7 @@ class MediaProvider extends ChangeNotifier {
|
|||||||
debugPrint('Fehler beim Laden der Medien: $e');
|
debugPrint('Fehler beim Laden der Medien: $e');
|
||||||
} finally {
|
} finally {
|
||||||
_isLoading = false;
|
_isLoading = false;
|
||||||
notifyListeners();
|
if(notify) notifyListeners();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -21,6 +21,7 @@ class DetailView extends StatefulWidget {
|
|||||||
class _DetailViewState extends State<DetailView> {
|
class _DetailViewState extends State<DetailView> {
|
||||||
late PageController _pageController;
|
late PageController _pageController;
|
||||||
bool isLoading = false;
|
bool isLoading = false;
|
||||||
|
int _currentIndex = 0;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
@ -30,8 +31,16 @@ class _DetailViewState extends State<DetailView> {
|
|||||||
final initialIndex = provider.mediaItems.indexWhere(
|
final initialIndex = provider.mediaItems.indexWhere(
|
||||||
(item) => item.id == widget.initialItemId,
|
(item) => item.id == widget.initialItemId,
|
||||||
);
|
);
|
||||||
|
|
||||||
_pageController = PageController(initialPage: initialIndex);
|
_pageController = PageController(initialPage: initialIndex);
|
||||||
|
|
||||||
|
_currentIndex = initialIndex;
|
||||||
|
_pageController.addListener(() {
|
||||||
|
setState(() {
|
||||||
|
_currentIndex = _pageController.page?.round() ?? 0;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
_preloadAdjacentMedia(initialIndex);
|
_preloadAdjacentMedia(initialIndex);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -97,10 +106,12 @@ class _DetailViewState extends State<DetailView> {
|
|||||||
PageTransformer(
|
PageTransformer(
|
||||||
controller: _pageController,
|
controller: _pageController,
|
||||||
pages: provider.mediaItems.map((item) {
|
pages: provider.mediaItems.map((item) {
|
||||||
|
int itemIndex = provider.mediaItems.indexOf(item);
|
||||||
|
|
||||||
return SafeArea(
|
return SafeArea(
|
||||||
child: SmartRefreshIndicator(
|
child: SmartRefreshIndicator(
|
||||||
onRefresh: _loadMoreMedia,
|
onRefresh: _loadMoreMedia,
|
||||||
child: _buildMediaItem(item),
|
child: _buildMediaItem(item, _currentIndex == itemIndex),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}).toList(),
|
}).toList(),
|
||||||
@ -129,7 +140,7 @@ class _DetailViewState extends State<DetailView> {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
Widget _buildMediaItem(MediaItem item) {
|
Widget _buildMediaItem(MediaItem item, bool isActive) {
|
||||||
final provider = Provider.of<MediaProvider>(context);
|
final provider = Provider.of<MediaProvider>(context);
|
||||||
|
|
||||||
return SingleChildScrollView(
|
return SingleChildScrollView(
|
||||||
@ -143,7 +154,7 @@ class _DetailViewState extends State<DetailView> {
|
|||||||
errorWidget: (context, url, error) => Icon(Icons.error),
|
errorWidget: (context, url, error) => Icon(Icons.error),
|
||||||
)
|
)
|
||||||
else
|
else
|
||||||
VideoWidget(details: item, isActive: true),
|
VideoWidget(details: item, isActive: isActive),
|
||||||
const SizedBox(height: 20),
|
const SizedBox(height: 20),
|
||||||
Text(
|
Text(
|
||||||
item.mime,
|
item.mime,
|
||||||
|
@ -3,6 +3,7 @@ import 'package:cached_network_image/cached_network_image.dart';
|
|||||||
import 'package:provider/provider.dart';
|
import 'package:provider/provider.dart';
|
||||||
import 'package:f0ckapp/screens/DetailView.dart';
|
import 'package:f0ckapp/screens/DetailView.dart';
|
||||||
import 'package:f0ckapp/providers/MediaProvider.dart';
|
import 'package:f0ckapp/providers/MediaProvider.dart';
|
||||||
|
import 'package:f0ckapp/utils/AppVersion.dart';
|
||||||
|
|
||||||
class MediaGrid extends StatefulWidget {
|
class MediaGrid extends StatefulWidget {
|
||||||
const MediaGrid({super.key});
|
const MediaGrid({super.key});
|
||||||
@ -27,7 +28,7 @@ class _MediaGridState extends State<MediaGrid> {
|
|||||||
_scrollController.addListener(() {
|
_scrollController.addListener(() {
|
||||||
if (_scrollController.position.pixels >=
|
if (_scrollController.position.pixels >=
|
||||||
_scrollController.position.maxScrollExtent - 100) {
|
_scrollController.position.maxScrollExtent - 100) {
|
||||||
provider.loadMedia();
|
provider.loadMedia(notify: false);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -41,8 +42,12 @@ class _MediaGridState extends State<MediaGrid> {
|
|||||||
key: scaffoldKey,
|
key: scaffoldKey,
|
||||||
appBar: AppBar(
|
appBar: AppBar(
|
||||||
//centerTitle: true,
|
//centerTitle: true,
|
||||||
title: Text('f0ck v1.0.27+27'),
|
title: Text('fApp v${AppVersion.version}'),
|
||||||
actions: [
|
actions: [
|
||||||
|
IconButton(
|
||||||
|
icon: Icon(provider.random ? Icons.shuffle_on_outlined : Icons.shuffle),
|
||||||
|
onPressed: () => provider.toggleRandom(),
|
||||||
|
),
|
||||||
IconButton(
|
IconButton(
|
||||||
icon: const Icon(Icons.menu),
|
icon: const Icon(Icons.menu),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
@ -103,62 +108,6 @@ class _MediaGridState extends State<MediaGrid> {
|
|||||||
padding: EdgeInsets.all(0),
|
padding: EdgeInsets.all(0),
|
||||||
child: Image.asset('assets/images/menu.webp', fit: BoxFit.cover),
|
child: Image.asset('assets/images/menu.webp', fit: BoxFit.cover),
|
||||||
),
|
),
|
||||||
/*ListTile(
|
|
||||||
title: Text(
|
|
||||||
'All',
|
|
||||||
style: TextStyle(
|
|
||||||
fontWeight: provider.type == 'alles'
|
|
||||||
? FontWeight.bold
|
|
||||||
: FontWeight.normal,
|
|
||||||
color: provider.type == 'alles' ? Colors.blue : Colors.white,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
onTap: () {
|
|
||||||
provider.setType('all');
|
|
||||||
},
|
|
||||||
),
|
|
||||||
ListTile(
|
|
||||||
title: Text(
|
|
||||||
'Images',
|
|
||||||
style: TextStyle(
|
|
||||||
fontWeight: provider.type == 'image'
|
|
||||||
? FontWeight.bold
|
|
||||||
: FontWeight.normal,
|
|
||||||
color: provider.type == 'image' ? Colors.blue : Colors.white,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
onTap: () {
|
|
||||||
provider.setType('image');
|
|
||||||
},
|
|
||||||
),
|
|
||||||
ListTile(
|
|
||||||
title: Text(
|
|
||||||
'Videos',
|
|
||||||
style: TextStyle(
|
|
||||||
fontWeight: provider.type == 'video'
|
|
||||||
? FontWeight.bold
|
|
||||||
: FontWeight.normal,
|
|
||||||
color: provider.type == 'video' ? Colors.blue : Colors.white,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
onTap: () {
|
|
||||||
provider.setType('video');
|
|
||||||
},
|
|
||||||
),
|
|
||||||
ListTile(
|
|
||||||
title: Text(
|
|
||||||
'Audio',
|
|
||||||
style: TextStyle(
|
|
||||||
fontWeight: provider.type == 'audio'
|
|
||||||
? FontWeight.bold
|
|
||||||
: FontWeight.normal,
|
|
||||||
color: provider.type == 'audio' ? Colors.blue : Colors.white,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
onTap: () {
|
|
||||||
provider.setType('audio');
|
|
||||||
},
|
|
||||||
),*/
|
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@ -187,6 +136,7 @@ class _MediaGridState extends State<MediaGrid> {
|
|||||||
child: Consumer<MediaProvider>(
|
child: Consumer<MediaProvider>(
|
||||||
builder: (context, mediaProvider, child) {
|
builder: (context, mediaProvider, child) {
|
||||||
return GridView.builder(
|
return GridView.builder(
|
||||||
|
key: PageStorageKey('mediaGrid'),
|
||||||
controller: _scrollController,
|
controller: _scrollController,
|
||||||
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
|
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
|
||||||
crossAxisCount: mediaProvider.crossAxisCount == 0
|
crossAxisCount: mediaProvider.crossAxisCount == 0
|
||||||
|
10
lib/utils/AppVersion.dart
Normal file
10
lib/utils/AppVersion.dart
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
import 'package:package_info_plus/package_info_plus.dart';
|
||||||
|
|
||||||
|
class AppVersion {
|
||||||
|
static String version = "";
|
||||||
|
|
||||||
|
static Future<void> init() async {
|
||||||
|
PackageInfo packageInfo = await PackageInfo.fromPlatform();
|
||||||
|
version = '${packageInfo.version}+${packageInfo.buildNumber}';
|
||||||
|
}
|
||||||
|
}
|
@ -5,11 +5,13 @@
|
|||||||
import FlutterMacOS
|
import FlutterMacOS
|
||||||
import Foundation
|
import Foundation
|
||||||
|
|
||||||
|
import package_info_plus
|
||||||
import path_provider_foundation
|
import path_provider_foundation
|
||||||
import sqflite_darwin
|
import sqflite_darwin
|
||||||
import video_player_avfoundation
|
import video_player_avfoundation
|
||||||
|
|
||||||
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
|
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
|
||||||
|
FPPPackageInfoPlusPlugin.register(with: registry.registrar(forPlugin: "FPPPackageInfoPlusPlugin"))
|
||||||
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
|
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
|
||||||
SqflitePlugin.register(with: registry.registrar(forPlugin: "SqflitePlugin"))
|
SqflitePlugin.register(with: registry.registrar(forPlugin: "SqflitePlugin"))
|
||||||
FVPVideoPlayerPlugin.register(with: registry.registrar(forPlugin: "FVPVideoPlayerPlugin"))
|
FVPVideoPlayerPlugin.register(with: registry.registrar(forPlugin: "FVPVideoPlayerPlugin"))
|
||||||
|
24
pubspec.lock
24
pubspec.lock
@ -272,6 +272,22 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.0"
|
version: "2.1.0"
|
||||||
|
package_info_plus:
|
||||||
|
dependency: "direct main"
|
||||||
|
description:
|
||||||
|
name: package_info_plus
|
||||||
|
sha256: "7976bfe4c583170d6cdc7077e3237560b364149fcd268b5f53d95a991963b191"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "8.3.0"
|
||||||
|
package_info_plus_platform_interface:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: package_info_plus_platform_interface
|
||||||
|
sha256: "6c935fb612dff8e3cc9632c2b301720c77450a126114126ffaafe28d2e87956c"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "3.2.0"
|
||||||
path:
|
path:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -541,6 +557,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.1.1"
|
version: "1.1.1"
|
||||||
|
win32:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: win32
|
||||||
|
sha256: "329edf97fdd893e0f1e3b9e88d6a0e627128cc17cc316a8d67fda8f1451178ba"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "5.13.0"
|
||||||
xdg_directories:
|
xdg_directories:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -16,7 +16,7 @@ publish_to: 'none' # Remove this line if you wish to publish to pub.dev
|
|||||||
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
|
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
|
||||||
# In Windows, build-name is used as the major, minor, and patch parts
|
# In Windows, build-name is used as the major, minor, and patch parts
|
||||||
# of the product and file versions while build-number is used as the build suffix.
|
# of the product and file versions while build-number is used as the build suffix.
|
||||||
version: 1.0.27+27
|
version: 1.0.28+28
|
||||||
|
|
||||||
environment:
|
environment:
|
||||||
sdk: ^3.9.0-100.2.beta
|
sdk: ^3.9.0-100.2.beta
|
||||||
@ -38,6 +38,7 @@ dependencies:
|
|||||||
cached_network_image: ^3.4.1
|
cached_network_image: ^3.4.1
|
||||||
cached_video_player_plus: ^3.0.3
|
cached_video_player_plus: ^3.0.3
|
||||||
provider: ^6.1.5
|
provider: ^6.1.5
|
||||||
|
package_info_plus: ^8.3.0
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
flutter_test:
|
flutter_test:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user