Compare commits

...

7 Commits

Author SHA1 Message Date
7fe26d0df0 🚀 Launch 1.2.1+16 2024-08-19 00:33:20 +08:00
80bade0e03 View posts posted by friends 2024-08-19 00:33:03 +08:00
b63db7fe76 👽 Support use realm alias instead of id 2024-08-19 00:14:09 +08:00
49f73f5f04 ⬆️ Support new attachments system 2024-08-18 22:51:52 +08:00
98749f42c0 ⬆️ Upgrade deps 2024-08-17 19:18:51 +08:00
f0e6bd64f4 ♻️ Refactor video player 2024-08-17 19:02:57 +08:00
3bea3a114a Post alias 2024-08-17 18:44:20 +08:00
39 changed files with 452 additions and 485 deletions

View File

@ -196,12 +196,6 @@ PODS:
- livekit_client (2.2.4): - livekit_client (2.2.4):
- Flutter - Flutter
- WebRTC-SDK (= 125.6422.04) - WebRTC-SDK (= 125.6422.04)
- media_kit_libs_ios_video (1.0.4):
- Flutter
- media_kit_native_event_loop (1.0.0):
- Flutter
- media_kit_video (0.0.1):
- Flutter
- nanopb (2.30910.0): - nanopb (2.30910.0):
- nanopb/decode (= 2.30910.0) - nanopb/decode (= 2.30910.0)
- nanopb/encode (= 2.30910.0) - nanopb/encode (= 2.30910.0)
@ -223,8 +217,6 @@ PODS:
- PromisesObjC (= 2.4.0) - PromisesObjC (= 2.4.0)
- protocol_handler_ios (0.0.1): - protocol_handler_ios (0.0.1):
- Flutter - Flutter
- screen_brightness_ios (0.1.0):
- Flutter
- SDWebImage (5.19.6): - SDWebImage (5.19.6):
- SDWebImage/Core (= 5.19.6) - SDWebImage/Core (= 5.19.6)
- SDWebImage/Core (5.19.6) - SDWebImage/Core (5.19.6)
@ -240,8 +232,9 @@ PODS:
- TOCropViewController (2.7.4) - TOCropViewController (2.7.4)
- url_launcher_ios (0.0.1): - url_launcher_ios (0.0.1):
- Flutter - Flutter
- volume_controller (0.0.1): - video_player_avfoundation (0.0.1):
- Flutter - Flutter
- FlutterMacOS
- wakelock_plus (0.0.1): - wakelock_plus (0.0.1):
- Flutter - Flutter
- WebRTC-SDK (125.6422.04) - WebRTC-SDK (125.6422.04)
@ -262,21 +255,17 @@ DEPENDENCIES:
- image_cropper (from `.symlinks/plugins/image_cropper/ios`) - image_cropper (from `.symlinks/plugins/image_cropper/ios`)
- image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`) - image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`)
- livekit_client (from `.symlinks/plugins/livekit_client/ios`) - livekit_client (from `.symlinks/plugins/livekit_client/ios`)
- media_kit_libs_ios_video (from `.symlinks/plugins/media_kit_libs_ios_video/ios`)
- media_kit_native_event_loop (from `.symlinks/plugins/media_kit_native_event_loop/ios`)
- media_kit_video (from `.symlinks/plugins/media_kit_video/ios`)
- package_info_plus (from `.symlinks/plugins/package_info_plus/ios`) - package_info_plus (from `.symlinks/plugins/package_info_plus/ios`)
- pasteboard (from `.symlinks/plugins/pasteboard/ios`) - pasteboard (from `.symlinks/plugins/pasteboard/ios`)
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`) - path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
- permission_handler_apple (from `.symlinks/plugins/permission_handler_apple/ios`) - permission_handler_apple (from `.symlinks/plugins/permission_handler_apple/ios`)
- pointer_interceptor_ios (from `.symlinks/plugins/pointer_interceptor_ios/ios`) - pointer_interceptor_ios (from `.symlinks/plugins/pointer_interceptor_ios/ios`)
- protocol_handler_ios (from `.symlinks/plugins/protocol_handler_ios/ios`) - protocol_handler_ios (from `.symlinks/plugins/protocol_handler_ios/ios`)
- screen_brightness_ios (from `.symlinks/plugins/screen_brightness_ios/ios`)
- share_plus (from `.symlinks/plugins/share_plus/ios`) - share_plus (from `.symlinks/plugins/share_plus/ios`)
- shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`) - shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`)
- sqflite (from `.symlinks/plugins/sqflite/darwin`) - sqflite (from `.symlinks/plugins/sqflite/darwin`)
- url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`) - url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`)
- volume_controller (from `.symlinks/plugins/volume_controller/ios`) - video_player_avfoundation (from `.symlinks/plugins/video_player_avfoundation/darwin`)
- wakelock_plus (from `.symlinks/plugins/wakelock_plus/ios`) - wakelock_plus (from `.symlinks/plugins/wakelock_plus/ios`)
SPEC REPOS: SPEC REPOS:
@ -335,12 +324,6 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/image_picker_ios/ios" :path: ".symlinks/plugins/image_picker_ios/ios"
livekit_client: livekit_client:
:path: ".symlinks/plugins/livekit_client/ios" :path: ".symlinks/plugins/livekit_client/ios"
media_kit_libs_ios_video:
:path: ".symlinks/plugins/media_kit_libs_ios_video/ios"
media_kit_native_event_loop:
:path: ".symlinks/plugins/media_kit_native_event_loop/ios"
media_kit_video:
:path: ".symlinks/plugins/media_kit_video/ios"
package_info_plus: package_info_plus:
:path: ".symlinks/plugins/package_info_plus/ios" :path: ".symlinks/plugins/package_info_plus/ios"
pasteboard: pasteboard:
@ -353,8 +336,6 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/pointer_interceptor_ios/ios" :path: ".symlinks/plugins/pointer_interceptor_ios/ios"
protocol_handler_ios: protocol_handler_ios:
:path: ".symlinks/plugins/protocol_handler_ios/ios" :path: ".symlinks/plugins/protocol_handler_ios/ios"
screen_brightness_ios:
:path: ".symlinks/plugins/screen_brightness_ios/ios"
share_plus: share_plus:
:path: ".symlinks/plugins/share_plus/ios" :path: ".symlinks/plugins/share_plus/ios"
shared_preferences_foundation: shared_preferences_foundation:
@ -363,8 +344,8 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/sqflite/darwin" :path: ".symlinks/plugins/sqflite/darwin"
url_launcher_ios: url_launcher_ios:
:path: ".symlinks/plugins/url_launcher_ios/ios" :path: ".symlinks/plugins/url_launcher_ios/ios"
volume_controller: video_player_avfoundation:
:path: ".symlinks/plugins/volume_controller/ios" :path: ".symlinks/plugins/video_player_avfoundation/darwin"
wakelock_plus: wakelock_plus:
:path: ".symlinks/plugins/wakelock_plus/ios" :path: ".symlinks/plugins/wakelock_plus/ios"
@ -399,9 +380,6 @@ SPEC CHECKSUMS:
image_cropper: 37d40f62177c101ff4c164906d259ea2c3aa70cf image_cropper: 37d40f62177c101ff4c164906d259ea2c3aa70cf
image_picker_ios: c560581cceedb403a6ff17f2f816d7fea1421fc1 image_picker_ios: c560581cceedb403a6ff17f2f816d7fea1421fc1
livekit_client: d079c5f040d4bf2b80440ff0ae997725a183e4bc livekit_client: d079c5f040d4bf2b80440ff0ae997725a183e4bc
media_kit_libs_ios_video: a5fe24bc7875ccd6378a0978c13185e1344651c1
media_kit_native_event_loop: e6b2ab20cf0746eb1c33be961fcf79667304fa2a
media_kit_video: 5da63f157170e5bf303bf85453b7ef6971218a2e
nanopb: 438bc412db1928dac798aa6fd75726007be04262 nanopb: 438bc412db1928dac798aa6fd75726007be04262
package_info_plus: 58f0028419748fad15bf008b270aaa8e54380b1c package_info_plus: 58f0028419748fad15bf008b270aaa8e54380b1c
pasteboard: 982969ebaa7c78af3e6cc7761e8f5e77565d9ce0 pasteboard: 982969ebaa7c78af3e6cc7761e8f5e77565d9ce0
@ -411,7 +389,6 @@ SPEC CHECKSUMS:
PromisesObjC: f5707f49cb48b9636751c5b2e7d227e43fba9f47 PromisesObjC: f5707f49cb48b9636751c5b2e7d227e43fba9f47
PromisesSwift: 9d77319bbe72ebf6d872900551f7eeba9bce2851 PromisesSwift: 9d77319bbe72ebf6d872900551f7eeba9bce2851
protocol_handler_ios: a5db8abc38526ee326988b808be621e5fd568990 protocol_handler_ios: a5db8abc38526ee326988b808be621e5fd568990
screen_brightness_ios: 715ca807df953bf676d339f11464e438143ee625
SDWebImage: a79252b60f4678812d94316c91da69ec83089c9f SDWebImage: a79252b60f4678812d94316c91da69ec83089c9f
share_plus: 8875f4f2500512ea181eef553c3e27dba5135aad share_plus: 8875f4f2500512ea181eef553c3e27dba5135aad
shared_preferences_foundation: fcdcbc04712aee1108ac7fda236f363274528f78 shared_preferences_foundation: fcdcbc04712aee1108ac7fda236f363274528f78
@ -419,7 +396,7 @@ SPEC CHECKSUMS:
SwiftyGif: 706c60cf65fa2bc5ee0313beece843c8eb8194d4 SwiftyGif: 706c60cf65fa2bc5ee0313beece843c8eb8194d4
TOCropViewController: 80b8985ad794298fb69d3341de183f33d1853654 TOCropViewController: 80b8985ad794298fb69d3341de183f33d1853654
url_launcher_ios: 5334b05cef931de560670eeae103fd3e431ac3fe url_launcher_ios: 5334b05cef931de560670eeae103fd3e431ac3fe
volume_controller: 531ddf792994285c9b17f9d8a7e4dcdd29b3eae9 video_player_avfoundation: 7c6c11d8470e1675df7397027218274b6d2360b3
wakelock_plus: 78ec7c5b202cab7761af8e2b2b3d0671be6c4ae1 wakelock_plus: 78ec7c5b202cab7761af8e2b2b3d0671be6c4ae1
WebRTC-SDK: c3d69a87e7185fad3568f6f3cff7c9ac5890acf3 WebRTC-SDK: c3d69a87e7185fad3568f6f3cff7c9ac5890acf3

View File

@ -17,6 +17,7 @@ import 'package:shared_preferences/shared_preferences.dart';
class PostEditorController extends GetxController { class PostEditorController extends GetxController {
late final SharedPreferences _prefs; late final SharedPreferences _prefs;
final aliasController = TextEditingController();
final titleController = TextEditingController(); final titleController = TextEditingController();
final descriptionController = TextEditingController(); final descriptionController = TextEditingController();
final contentController = TextEditingController(); final contentController = TextEditingController();
@ -30,9 +31,9 @@ class PostEditorController extends GetxController {
Rx<Realm?> realmZone = Rx(null); Rx<Realm?> realmZone = Rx(null);
Rx<DateTime?> publishedAt = Rx(null); Rx<DateTime?> publishedAt = Rx(null);
Rx<DateTime?> publishedUntil = Rx(null); Rx<DateTime?> publishedUntil = Rx(null);
RxList<int> attachments = RxList<int>.empty(growable: true); RxList<String> attachments = RxList<String>.empty(growable: true);
RxList<String> tags = RxList<String>.empty(growable: true); RxList<String> tags = RxList<String>.empty(growable: true);
Rx<int?> thumbnail = Rx(null); Rx<String?> thumbnail = Rx(null);
RxList<int> visibleUsers = RxList.empty(growable: true); RxList<int> visibleUsers = RxList.empty(growable: true);
RxList<int> invisibleUsers = RxList.empty(growable: true); RxList<int> invisibleUsers = RxList.empty(growable: true);
@ -115,12 +116,12 @@ class PostEditorController extends GetxController {
return showModalBottomSheet( return showModalBottomSheet(
context: context, context: context,
builder: (context) => AttachmentEditorPopup( builder: (context) => AttachmentEditorPopup(
usage: 'i.attachment', pool: 'interactive',
initialAttachments: attachments, initialAttachments: attachments,
onAdd: (int value) { onAdd: (String value) {
attachments.add(value); attachments.add(value);
}, },
onRemove: (int value) { onRemove: (String value) {
attachments.remove(value); attachments.remove(value);
}, },
), ),
@ -168,6 +169,7 @@ class PostEditorController extends GetxController {
} }
void currentClear() { void currentClear() {
aliasController.clear();
titleController.clear(); titleController.clear();
descriptionController.clear(); descriptionController.clear();
contentController.clear(); contentController.clear();
@ -197,16 +199,23 @@ class PostEditorController extends GetxController {
type = value.type; type = value.type;
editTo.value = value; editTo.value = value;
realmZone.value = value.realm;
isDraft.value = value.isDraft ?? false; isDraft.value = value.isDraft ?? false;
aliasController.text = value.alias ?? '';
titleController.text = value.body['title'] ?? ''; titleController.text = value.body['title'] ?? '';
descriptionController.text = value.body['description'] ?? ''; descriptionController.text = value.body['description'] ?? '';
contentController.text = value.body['content'] ?? ''; contentController.text = value.body['content'] ?? '';
publishedAt.value = value.publishedAt; publishedAt.value = value.publishedAt;
publishedUntil.value = value.publishedUntil; publishedUntil.value = value.publishedUntil;
tags.value = tags.value = List.from(
value.body['tags']?.map((x) => x['alias']).toList() ?? List.empty(); value.body['tags']?.map((x) => x['alias']).toList() ?? List.empty(),
growable: true,
);
tags.refresh(); tags.refresh();
attachments.value = value.body['attachments']?.cast<int>() ?? List.empty(); attachments.value = List.from(
value.body['attachments'] ?? List.empty(),
growable: true,
);
attachments.refresh(); attachments.refresh();
thumbnail.value = value.body['thumbnail']; thumbnail.value = value.body['thumbnail'];
@ -256,6 +265,7 @@ class PostEditorController extends GetxController {
Map<String, dynamic> get payload { Map<String, dynamic> get payload {
return { return {
'alias': aliasController.text,
'title': title, 'title': title,
'description': description, 'description': description,
'content': contentController.text, 'content': contentController.text,
@ -277,20 +287,33 @@ class PostEditorController extends GetxController {
set payload(Map<String, dynamic> value) { set payload(Map<String, dynamic> value) {
type = value['type']; type = value['type'];
tags.value = value['tags'].map((x) => x['alias']).toList().cast<String>(); tags.value = List.from(
value['tags'].map((x) => x['alias']).toList(),
growable: true,
);
aliasController.text = value['alias'] ?? '';
titleController.text = value['title'] ?? ''; titleController.text = value['title'] ?? '';
descriptionController.text = value['description'] ?? ''; descriptionController.text = value['description'] ?? '';
contentController.text = value['content'] ?? ''; contentController.text = value['content'] ?? '';
attachments.value = value['attachments'].cast<int>() ?? List.empty(); attachments.value = List.from(
value['attachments'] ?? List.empty(),
growable: true,
);
attachments.refresh(); attachments.refresh();
thumbnail.value = value['thumbnail']; thumbnail.value = value['thumbnail'];
visibility.value = value['visibility']; visibility.value = value['visibility'];
isDraft.value = value['is_draft']; isDraft.value = value['is_draft'];
if (value['visible_users'] != null) { if (value['visible_users'] != null) {
visibleUsers.value = value['visible_users'].cast<int>(); visibleUsers.value = List.from(
value['visible_users'],
growable: true,
);
} }
if (value['invisible_users'] != null) { if (value['invisible_users'] != null) {
invisibleUsers.value = value['invisible_users'].cast<int>(); invisibleUsers.value = List.from(
value['invisible_users'],
growable: true,
);
} }
if (value['published_at'] != null) { if (value['published_at'] != null) {
publishedAt.value = DateTime.parse(value['published_at']).toLocal(); publishedAt.value = DateTime.parse(value['published_at']).toLocal();
@ -319,6 +342,7 @@ class PostEditorController extends GetxController {
bool get isNotEmpty { bool get isNotEmpty {
return [ return [
aliasController.text.isNotEmpty,
titleController.text.isNotEmpty, titleController.text.isNotEmpty,
descriptionController.text.isNotEmpty, descriptionController.text.isNotEmpty,
contentController.text.isNotEmpty, contentController.text.isNotEmpty,

View File

@ -9,11 +9,12 @@ class PostListController extends GetxController {
/// The polling source modifier. /// The polling source modifier.
/// - `0`: default recommendations /// - `0`: default recommendations
/// - `1`: shuffle mode /// - `1`: friend mode
/// - `2`: shuffle mode
RxInt mode = 0.obs; RxInt mode = 0.obs;
/// The paging controller for infinite loading. /// The paging controller for infinite loading.
/// Only available when mode is `0`. /// Only available when mode is `0` or `1`.
PagingController<int, Post> pagingController = PagingController<int, Post> pagingController =
PagingController(firstPageKey: 0); PagingController(firstPageKey: 0);
@ -111,10 +112,23 @@ class PostListController extends GetxController {
author: author, author: author,
); );
} else { } else {
switch (mode.value) {
case 2:
resp = await provider.listRecommendations( resp = await provider.listRecommendations(
pageKey, pageKey,
channel: mode.value == 0 ? null : 'shuffle', channel: 'shuffle',
); );
break;
case 1:
resp = await provider.listRecommendations(
pageKey,
channel: 'friends',
);
break;
default:
resp = await provider.listRecommendations(pageKey);
break;
}
} }
} catch (e) { } catch (e) {
rethrow; rethrow;

View File

@ -6,7 +6,6 @@ import 'package:flutter/material.dart';
import 'package:flutter_acrylic/flutter_acrylic.dart'; import 'package:flutter_acrylic/flutter_acrylic.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:go_router/go_router.dart'; import 'package:go_router/go_router.dart';
import 'package:media_kit/media_kit.dart';
import 'package:protocol_handler/protocol_handler.dart'; import 'package:protocol_handler/protocol_handler.dart';
import 'package:provider/provider.dart'; import 'package:provider/provider.dart';
import 'package:solian/bootstrapper.dart'; import 'package:solian/bootstrapper.dart';
@ -32,7 +31,6 @@ import 'package:flutter_web_plugins/url_strategy.dart' show usePathUrlStrategy;
void main() async { void main() async {
WidgetsFlutterBinding.ensureInitialized(); WidgetsFlutterBinding.ensureInitialized();
MediaKit.ensureInitialized();
await Future.wait([ await Future.wait([
_initializeFirebase(), _initializeFirebase(),

View File

@ -5,11 +5,11 @@ class Attachment {
DateTime createdAt; DateTime createdAt;
DateTime updatedAt; DateTime updatedAt;
DateTime? deletedAt; DateTime? deletedAt;
String rid;
String uuid; String uuid;
int size; int size;
String name; String name;
String alt; String alt;
String usage;
String mimetype; String mimetype;
String hash; String hash;
int destination; int destination;
@ -24,11 +24,11 @@ class Attachment {
required this.createdAt, required this.createdAt,
required this.updatedAt, required this.updatedAt,
required this.deletedAt, required this.deletedAt,
required this.rid,
required this.uuid, required this.uuid,
required this.size, required this.size,
required this.name, required this.name,
required this.alt, required this.alt,
required this.usage,
required this.mimetype, required this.mimetype,
required this.hash, required this.hash,
required this.destination, required this.destination,
@ -43,19 +43,22 @@ class Attachment {
id: json['id'], id: json['id'],
createdAt: DateTime.parse(json['created_at']), createdAt: DateTime.parse(json['created_at']),
updatedAt: DateTime.parse(json['updated_at']), updatedAt: DateTime.parse(json['updated_at']),
deletedAt: json['deleted_at'] != null ? DateTime.parse(json['deleted_at']) : null, deletedAt: json['deleted_at'] != null
? DateTime.parse(json['deleted_at'])
: null,
rid: json['rid'],
uuid: json['uuid'], uuid: json['uuid'],
size: json['size'], size: json['size'],
name: json['name'], name: json['name'],
alt: json['alt'], alt: json['alt'],
usage: json['usage'],
mimetype: json['mimetype'], mimetype: json['mimetype'],
hash: json['hash'], hash: json['hash'],
destination: json['destination'], destination: json['destination'],
isAnalyzed: json['is_analyzed'], isAnalyzed: json['is_analyzed'],
metadata: json['metadata'], metadata: json['metadata'],
isMature: json['is_mature'], isMature: json['is_mature'],
account: json['account'] != null ? Account.fromJson(json['account']) : null, account:
json['account'] != null ? Account.fromJson(json['account']) : null,
accountId: json['account_id'], accountId: json['account_id'],
); );
@ -64,11 +67,11 @@ class Attachment {
'created_at': createdAt.toIso8601String(), 'created_at': createdAt.toIso8601String(),
'updated_at': updatedAt.toIso8601String(), 'updated_at': updatedAt.toIso8601String(),
'deleted_at': deletedAt?.toIso8601String(), 'deleted_at': deletedAt?.toIso8601String(),
'rid': rid,
'uuid': uuid, 'uuid': uuid,
'size': size, 'size': size,
'name': name, 'name': name,
'alt': alt, 'alt': alt,
'usage': usage,
'mimetype': mimetype, 'mimetype': mimetype,
'hash': hash, 'hash': hash,
'destination': destination, 'destination': destination,

View File

@ -8,6 +8,8 @@ class Post {
DateTime updatedAt; DateTime updatedAt;
DateTime? editedAt; DateTime? editedAt;
DateTime? deletedAt; DateTime? deletedAt;
String? alias;
String? areaAlias;
dynamic body; dynamic body;
List<Tag>? tags; List<Tag>? tags;
List<Category>? categories; List<Category>? categories;
@ -33,6 +35,8 @@ class Post {
required this.updatedAt, required this.updatedAt,
required this.editedAt, required this.editedAt,
required this.deletedAt, required this.deletedAt,
required this.alias,
required this.areaAlias,
required this.type, required this.type,
required this.body, required this.body,
required this.tags, required this.tags,
@ -60,6 +64,8 @@ class Post {
deletedAt: json['deleted_at'] != null deletedAt: json['deleted_at'] != null
? DateTime.parse(json['deleted_at']) ? DateTime.parse(json['deleted_at'])
: null, : null,
alias: json['alias'],
areaAlias: json['area_alias'],
type: json['type'], type: json['type'],
body: json['body'], body: json['body'],
tags: json['tags']?.map((x) => Tag.fromJson(x)).toList().cast<Tag>(), tags: json['tags']?.map((x) => Tag.fromJson(x)).toList().cast<Tag>(),
@ -101,6 +107,8 @@ class Post {
'updated_at': updatedAt.toIso8601String(), 'updated_at': updatedAt.toIso8601String(),
'edited_at': editedAt?.toIso8601String(), 'edited_at': editedAt?.toIso8601String(),
'deleted_at': deletedAt?.toIso8601String(), 'deleted_at': deletedAt?.toIso8601String(),
'alias': alias,
'area_alias': areaAlias,
'type': type, 'type': type,
'body': body, 'body': body,
'tags': tags, 'tags': tags,

View File

@ -148,7 +148,7 @@ class AttachmentUploaderController extends GetxController {
Future<void> uploadAttachmentWithCallback( Future<void> uploadAttachmentWithCallback(
Uint8List data, Uint8List data,
String path, String path,
String usage, String pool,
Map<String, dynamic>? metadata, Map<String, dynamic>? metadata,
Function(Attachment?) callback, Function(Attachment?) callback,
) async { ) async {
@ -158,7 +158,7 @@ class AttachmentUploaderController extends GetxController {
final result = await _rawUploadAttachment( final result = await _rawUploadAttachment(
data, data,
path, path,
usage, pool,
metadata, metadata,
onProgress: (progress) { onProgress: (progress) {
progressOfUpload.value = progress; progressOfUpload.value = progress;
@ -171,7 +171,7 @@ class AttachmentUploaderController extends GetxController {
Future<Attachment?> uploadAttachment( Future<Attachment?> uploadAttachment(
Uint8List data, Uint8List data,
String path, String path,
String usage, String pool,
Map<String, dynamic>? metadata, Map<String, dynamic>? metadata,
) async { ) async {
if (isUploading.value) throw Exception('uploading blocked'); if (isUploading.value) throw Exception('uploading blocked');
@ -180,7 +180,7 @@ class AttachmentUploaderController extends GetxController {
final result = await _rawUploadAttachment( final result = await _rawUploadAttachment(
data, data,
path, path,
usage, pool,
metadata, metadata,
onProgress: (progress) { onProgress: (progress) {
progressOfUpload.value = progress; progressOfUpload.value = progress;
@ -191,14 +191,14 @@ class AttachmentUploaderController extends GetxController {
} }
Future<Attachment?> _rawUploadAttachment( Future<Attachment?> _rawUploadAttachment(
Uint8List data, String path, String usage, Map<String, dynamic>? metadata, Uint8List data, String path, String pool, Map<String, dynamic>? metadata,
{Function(double)? onProgress, Function(dynamic err)? onError}) async { {Function(double)? onProgress, Function(dynamic err)? onError}) async {
final AttachmentProvider provider = Get.find(); final AttachmentProvider provider = Get.find();
try { try {
final result = await provider.createAttachment( final result = await provider.createAttachment(
data, data,
path, path,
usage, pool,
metadata, metadata,
onProgress: onProgress, onProgress: onProgress,
); );

View File

@ -88,22 +88,7 @@ class ChatCallProvider extends GetxController {
void initRoom() { void initRoom() {
initHardware(); initHardware();
room = Room(); room = Room(
listener = room.createListener();
WakelockPlus.enable();
}
void joinRoom(String url, String token) async {
if (isMounted.value) {
return;
} else {
isMounted.value = true;
}
try {
await room.connect(
url,
token,
roomOptions: const RoomOptions( roomOptions: const RoomOptions(
dynacast: true, dynacast: true,
adaptiveStream: true, adaptiveStream: true,
@ -126,6 +111,22 @@ class ChatCallProvider extends GetxController {
params: VideoParametersPresets.h1080_169, params: VideoParametersPresets.h1080_169,
), ),
), ),
);
listener = room.createListener();
WakelockPlus.enable();
}
void joinRoom(String url, String token) async {
if (isMounted.value) {
return;
} else {
isMounted.value = true;
}
try {
await room.connect(
url,
token,
fastConnectOptions: FastConnectOptions( fastConnectOptions: FastConnectOptions(
microphone: TrackOption(track: audioTrack.value), microphone: TrackOption(track: audioTrack.value),
camera: TrackOption(track: videoTrack.value), camera: TrackOption(track: videoTrack.value),
@ -152,7 +153,7 @@ class ChatCallProvider extends GetxController {
void onRoomDidUpdate() => sortParticipants(); void onRoomDidUpdate() => sortParticipants();
void setupRoom() { void setupRoom() {
if(isInitialized.value) return; if (isInitialized.value) return;
sortParticipants(); sortParticipants();
room.addListener(onRoomDidUpdate); room.addListener(onRoomDidUpdate);

View File

@ -20,22 +20,22 @@ class AttachmentProvider extends GetConnect {
httpClient.baseUrl = ServiceFinder.buildUrl('files', null); httpClient.baseUrl = ServiceFinder.buildUrl('files', null);
} }
final Map<int, Attachment> _cachedResponses = {}; final Map<String, Attachment> _cachedResponses = {};
Future<List<Attachment?>> listMetadata( Future<List<Attachment?>> listMetadata(
List<int> id, { List<String> rid, {
noCache = false, noCache = false,
}) async { }) async {
if (id.isEmpty) return List.empty(); if (rid.isEmpty) return List.empty();
List<Attachment?> result = List.filled(id.length, null); List<Attachment?> result = List.filled(rid.length, null);
List<int> pendingQuery = List.empty(growable: true); List<String> pendingQuery = List.empty(growable: true);
if (!noCache) { if (!noCache) {
for (var idx = 0; idx < id.length; idx++) { for (var idx = 0; idx < rid.length; idx++) {
if (_cachedResponses.containsKey(id[idx])) { if (_cachedResponses.containsKey(rid[idx])) {
result[idx] = _cachedResponses[id[idx]]; result[idx] = _cachedResponses[rid[idx]];
} else { } else {
pendingQuery.add(id[idx]); pendingQuery.add(rid[idx]);
} }
} }
} }
@ -52,12 +52,12 @@ class AttachmentProvider extends GetConnect {
rawOut.data!.map((x) => Attachment.fromJson(x)).toList(); rawOut.data!.map((x) => Attachment.fromJson(x)).toList();
for (final item in out) { for (final item in out) {
if (item.destination != 0 && item.isAnalyzed) { if (item.destination != 0 && item.isAnalyzed) {
_cachedResponses[item.id] = item; _cachedResponses[item.rid] = item;
} }
} }
for (var i = 0; i < out.length; i++) { for (var i = 0; i < out.length; i++) {
for (var j = 0; j < id.length; j++) { for (var j = 0; j < rid.length; j++) {
if (out[i].id == id[j]) { if (out[i].rid == rid[j]) {
result[j] = out[i]; result[j] = out[i];
} }
} }
@ -66,16 +66,16 @@ class AttachmentProvider extends GetConnect {
return result; return result;
} }
Future<Attachment?> getMetadata(int id, {noCache = false}) async { Future<Attachment?> getMetadata(String rid, {noCache = false}) async {
if (!noCache && _cachedResponses.containsKey(id)) { if (!noCache && _cachedResponses.containsKey(rid)) {
return _cachedResponses[id]!; return _cachedResponses[rid]!;
} }
final resp = await get('/attachments/$id/meta'); final resp = await get('/attachments/$rid/meta');
if (resp.statusCode == 200) { if (resp.statusCode == 200) {
final result = Attachment.fromJson(resp.body); final result = Attachment.fromJson(resp.body);
if (result.destination != 0 && result.isAnalyzed) { if (result.destination != 0 && result.isAnalyzed) {
_cachedResponses[id] = result; _cachedResponses[rid] = result;
} }
return result; return result;
} }
@ -84,7 +84,7 @@ class AttachmentProvider extends GetConnect {
} }
Future<Attachment> createAttachment( Future<Attachment> createAttachment(
Uint8List data, String path, String usage, Map<String, dynamic>? metadata, Uint8List data, String path, String pool, Map<String, dynamic>? metadata,
{Function(double)? onProgress}) async { {Function(double)? onProgress}) async {
final AuthProvider auth = Get.find(); final AuthProvider auth = Get.find();
if (auth.isAuthorized.isFalse) throw Exception('unauthorized'); if (auth.isAuthorized.isFalse) throw Exception('unauthorized');
@ -108,7 +108,7 @@ class AttachmentProvider extends GetConnect {
final payload = dio.FormData.fromMap({ final payload = dio.FormData.fromMap({
'alt': fileAlt, 'alt': fileAlt,
'file': filePayload, 'file': filePayload,
'usage': usage, 'pool': pool,
if (mimetypeOverride != null) 'mimetype': mimetypeOverride, if (mimetypeOverride != null) 'mimetype': mimetypeOverride,
'metadata': jsonEncode(metadata), 'metadata': jsonEncode(metadata),
}); });
@ -133,8 +133,7 @@ class AttachmentProvider extends GetConnect {
Future<Response> updateAttachment( Future<Response> updateAttachment(
int id, int id,
String alt, String alt, {
String usage, {
bool isMature = false, bool isMature = false,
}) async { }) async {
final AuthProvider auth = Get.find(); final AuthProvider auth = Get.find();
@ -144,7 +143,6 @@ class AttachmentProvider extends GetConnect {
var resp = await client.put('/attachments/$id', { var resp = await client.put('/attachments/$id', {
'alt': alt, 'alt': alt,
'usage': usage,
'is_mature': isMature, 'is_mature': isMature,
}); });
@ -169,7 +167,7 @@ class AttachmentProvider extends GetConnect {
return resp; return resp;
} }
void clearCache({int? id}) { void clearCache({String? id}) {
if (id != null) { if (id != null) {
_cachedResponses.remove(id); _cachedResponses.remove(id);
} else { } else {

View File

@ -9,13 +9,20 @@ class PostProvider extends GetConnect {
} }
Future<Response> listRecommendations(int page, Future<Response> listRecommendations(int page,
{int? realm, String? channel}) async { {String? realm, String? channel}) async {
GetConnect client;
final AuthProvider auth = Get.find();
final queries = [ final queries = [
'take=${10}', 'take=${10}',
'offset=$page', 'offset=$page',
if (realm != null) 'realmId=$realm', if (realm != null) 'realm=$realm',
]; ];
final resp = await get( if (auth.isAuthorized.value) {
client = auth.configureClient('co');
} else {
client = ServiceFinder.configureClient('co');
}
final resp = await client.get(
channel == null channel == null
? '/recommendations?${queries.join('&')}' ? '/recommendations?${queries.join('&')}'
: '/recommendations/$channel?${queries.join('&')}', : '/recommendations/$channel?${queries.join('&')}',
@ -45,14 +52,14 @@ class PostProvider extends GetConnect {
} }
Future<Response> listPost(int page, Future<Response> listPost(int page,
{int? realm, String? author, tag, category}) async { {String? realm, String? author, tag, category}) async {
final queries = [ final queries = [
'take=${10}', 'take=${10}',
'offset=$page', 'offset=$page',
if (tag != null) 'tag=$tag', if (tag != null) 'tag=$tag',
if (category != null) 'category=$category', if (category != null) 'category=$category',
if (author != null) 'author=$author', if (author != null) 'author=$author',
if (realm != null) 'realmId=$realm', if (realm != null) 'realm=$realm',
]; ];
final resp = await get('/posts?${queries.join('&')}'); final resp = await get('/posts?${queries.join('&')}');
if (resp.statusCode != 200) { if (resp.statusCode != 200) {

View File

@ -116,7 +116,7 @@ class _PersonalizeScreenState extends State<PersonalizeScreen> {
attachResult = await provider.createAttachment( attachResult = await provider.createAttachment(
await file.readAsBytes(), await file.readAsBytes(),
file.path, file.path,
'p.$position', 'avatar',
null, null,
); );
} catch (e) { } catch (e) {

View File

@ -5,6 +5,7 @@ import 'package:solian/providers/auth.dart';
import 'package:solian/router.dart'; import 'package:solian/router.dart';
import 'package:solian/screens/account/notification.dart'; import 'package:solian/screens/account/notification.dart';
import 'package:solian/theme.dart'; import 'package:solian/theme.dart';
import 'package:solian/widgets/account/signin_required_overlay.dart';
import 'package:solian/widgets/app_bar_title.dart'; import 'package:solian/widgets/app_bar_title.dart';
import 'package:solian/widgets/current_state_action.dart'; import 'package:solian/widgets/current_state_action.dart';
import 'package:solian/widgets/app_bar_leading.dart'; import 'package:solian/widgets/app_bar_leading.dart';
@ -27,20 +28,18 @@ class _HomeScreenState extends State<HomeScreen>
void initState() { void initState() {
super.initState(); super.initState();
_postController = PostListController(); _postController = PostListController();
_tabController = TabController(length: 2, vsync: this); _tabController = TabController(length: 3, vsync: this);
_tabController.addListener(() { _tabController.addListener(() {
switch (_tabController.index) {
case 0:
case 1:
if (_postController.mode.value == _tabController.index) return; if (_postController.mode.value == _tabController.index) return;
_postController.mode.value = _tabController.index; _postController.mode.value = _tabController.index;
_postController.reloadAllOver(); _postController.reloadAllOver();
}
}); });
} }
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
final AuthProvider auth = Get.find();
return Material( return Material(
color: Theme.of(context).colorScheme.surface, color: Theme.of(context).colorScheme.surface,
child: Scaffold( child: Scaffold(
@ -82,6 +81,7 @@ class _HomeScreenState extends State<HomeScreen>
controller: _tabController, controller: _tabController,
tabs: [ tabs: [
Tab(text: 'postListNews'.tr), Tab(text: 'postListNews'.tr),
Tab(text: 'postListFriends'.tr),
Tab(text: 'postListShuffle'.tr), Tab(text: 'postListShuffle'.tr),
], ],
), ),
@ -108,6 +108,23 @@ class _HomeScreenState extends State<HomeScreen>
), ),
]), ]),
), ),
Obx(() {
if (auth.isAuthorized.value) {
return RefreshIndicator(
onRefresh: () => _postController.reloadAllOver(),
child: CustomScrollView(slivers: [
PostWarpedListWidget(
controller: _postController.pagingController,
onUpdate: () => _postController.reloadAllOver(),
),
]),
);
} else {
return SigninRequiredOverlay(
onSignedIn: () => _postController.reloadAllOver(),
);
}
}),
PostShuffleSwiper(controller: _postController), PostShuffleSwiper(controller: _postController),
], ],
); );

View File

@ -65,7 +65,7 @@ class _PostPublishScreenState extends State<PostPublishScreen> {
final AttachmentUploaderController uploader = Get.find(); final AttachmentUploaderController uploader = Get.find();
if (uploader.queueOfUpload.any( if (uploader.queueOfUpload.any(
((x) => x.usage == 'i.attachment' && x.isUploading), ((x) => x.isUploading),
)) { )) {
context.showErrorDialog('attachmentUploadInProgress'.tr); context.showErrorDialog('attachmentUploadInProgress'.tr);
return; return;
@ -90,8 +90,8 @@ class _PostPublishScreenState extends State<PostPublishScreen> {
if (resp.statusCode != 200) { if (resp.statusCode != 200) {
context.showErrorDialog(resp.bodyString); context.showErrorDialog(resp.bodyString);
} else { } else {
_editorController.localClear();
_editorController.currentClear(); _editorController.currentClear();
_editorController.localClear();
AppRouter.instance.pop(resp.body); AppRouter.instance.pop(resp.body);
} }
@ -176,11 +176,20 @@ class _PostPublishScreenState extends State<PostPublishScreen> {
children: [ children: [
ListTile( ListTile(
tileColor: Theme.of(context).colorScheme.surfaceContainerLow, tileColor: Theme.of(context).colorScheme.surfaceContainerLow,
title: Text( title: Row(
children: [
Text(
_editorController.title ?? 'title'.tr, _editorController.title ?? 'title'.tr,
maxLines: 1, maxLines: 1,
overflow: TextOverflow.ellipsis, overflow: TextOverflow.ellipsis,
), ),
const SizedBox(width: 6),
if (_editorController.aliasController.text.isNotEmpty)
Badge(
label: Text('#${_editorController.aliasController.text}'),
),
],
),
subtitle: Text( subtitle: Text(
_editorController.description ?? 'description'.tr, _editorController.description ?? 'description'.tr,
maxLines: 2, maxLines: 2,
@ -255,6 +264,7 @@ class _PostPublishScreenState extends State<PostPublishScreen> {
), ),
], ],
), ),
if (_isBusy) const LinearProgressIndicator().animate().scaleX(),
Expanded( Expanded(
child: Row( child: Row(
crossAxisAlignment: CrossAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start,
@ -265,10 +275,6 @@ class _PostPublishScreenState extends State<PostPublishScreen> {
Expanded( Expanded(
child: ListView( child: ListView(
children: [ children: [
if (_isBusy)
const LinearProgressIndicator()
.animate()
.scaleX(),
Container( Container(
padding: const EdgeInsets.symmetric( padding: const EdgeInsets.symmetric(
horizontal: 16, horizontal: 16,

View File

@ -171,7 +171,7 @@ class _RealmPostListWidgetState extends State<RealmPostListWidget> {
Response resp; Response resp;
try { try {
resp = await provider.listPost(pageKey, realm: widget.realm.id); resp = await provider.listPost(pageKey, realm: widget.realm.alias);
} catch (e) { } catch (e) {
_pagingController.error = e; _pagingController.error = e;
return; return;

View File

@ -13,6 +13,7 @@ const i18nEnglish = {
'more': 'More', 'more': 'More',
'share': 'Share', 'share': 'Share',
'shareNoUri': 'Share text content', 'shareNoUri': 'Share text content',
'alias': 'Alias',
'feed': 'Feed', 'feed': 'Feed',
'unlink': 'Unlink', 'unlink': 'Unlink',
'feedSearch': 'Search Feed', 'feedSearch': 'Search Feed',
@ -124,6 +125,7 @@ const i18nEnglish = {
'postThumbnailAttachment': 'Attachment serial number', 'postThumbnailAttachment': 'Attachment serial number',
'postPinned': 'Pinned', 'postPinned': 'Pinned',
'postListNews': 'News', 'postListNews': 'News',
'postListFriends': 'Friends',
'postListShuffle': 'Random', 'postListShuffle': 'Random',
'postEditorModeStory': 'Post a post', 'postEditorModeStory': 'Post a post',
'postEditorModeArticle': 'Post an article', 'postEditorModeArticle': 'Post an article',

View File

@ -21,6 +21,7 @@ const i18nSimplifiedChinese = {
'more': '更多', 'more': '更多',
'share': '分享', 'share': '分享',
'shareNoUri': '分享文字内容', 'shareNoUri': '分享文字内容',
'alias': '别名',
'feed': '资讯', 'feed': '资讯',
'unlink': '移除链接', 'unlink': '移除链接',
'feedSearch': '搜索资讯', 'feedSearch': '搜索资讯',
@ -124,6 +125,7 @@ const i18nSimplifiedChinese = {
'articleDetail': '文章详情', 'articleDetail': '文章详情',
'draftBoxOpen': '打开草稿箱', 'draftBoxOpen': '打开草稿箱',
'postListNews': '新鲜事', 'postListNews': '新鲜事',
'postListFriends': '好友圈',
'postListShuffle': '打乱看', 'postListShuffle': '打乱看',
'postNew': '创建新帖子', 'postNew': '创建新帖子',
'postNewInRealmHint': '在领域 @realm 里发表新帖子', 'postNewInRealmHint': '在领域 @realm 里发表新帖子',

View File

@ -24,7 +24,6 @@ class AccountAvatar extends StatelessWidget {
if (content is String) { if (content is String) {
direct = content.startsWith('http'); direct = content.startsWith('http');
if (!isEmpty) isEmpty = content.isEmpty; if (!isEmpty) isEmpty = content.isEmpty;
if (!isEmpty) isEmpty = content.endsWith('/attachments/0');
} }
final url = direct final url = direct

View File

@ -16,10 +16,12 @@ class AttachmentAttrEditorDialog extends StatefulWidget {
}); });
@override @override
State<AttachmentAttrEditorDialog> createState() => _AttachmentAttrEditorDialogState(); State<AttachmentAttrEditorDialog> createState() =>
_AttachmentAttrEditorDialogState();
} }
class _AttachmentAttrEditorDialogState extends State<AttachmentAttrEditorDialog> { class _AttachmentAttrEditorDialogState
extends State<AttachmentAttrEditorDialog> {
final _altController = TextEditingController(); final _altController = TextEditingController();
bool _isBusy = false; bool _isBusy = false;
@ -33,11 +35,10 @@ class _AttachmentAttrEditorDialogState extends State<AttachmentAttrEditorDialog>
final resp = await provider.updateAttachment( final resp = await provider.updateAttachment(
widget.item.id, widget.item.id,
_altController.value.text, _altController.value.text,
widget.item.usage,
isMature: _isMature, isMature: _isMature,
); );
Get.find<AttachmentProvider>().clearCache(id: widget.item.id); Get.find<AttachmentProvider>().clearCache(id: widget.item.rid);
setState(() => _isBusy = false); setState(() => _isBusy = false);
return Attachment.fromJson(resp.body); return Attachment.fromJson(resp.body);

View File

@ -22,19 +22,19 @@ import 'package:solian/widgets/attachments/attachment_attr_editor.dart';
import 'package:solian/widgets/attachments/attachment_fullscreen.dart'; import 'package:solian/widgets/attachments/attachment_fullscreen.dart';
class AttachmentEditorPopup extends StatefulWidget { class AttachmentEditorPopup extends StatefulWidget {
final String usage; final String pool;
final bool singleMode; final bool singleMode;
final bool imageOnly; final bool imageOnly;
final bool autoUpload; final bool autoUpload;
final double? imageMaxWidth; final double? imageMaxWidth;
final double? imageMaxHeight; final double? imageMaxHeight;
final List<int>? initialAttachments; final List<String>? initialAttachments;
final void Function(int) onAdd; final void Function(String) onAdd;
final void Function(int) onRemove; final void Function(String) onRemove;
const AttachmentEditorPopup({ const AttachmentEditorPopup({
super.key, super.key,
required this.usage, required this.pool,
required this.onAdd, required this.onAdd,
required this.onRemove, required this.onRemove,
this.singleMode = false, this.singleMode = false,
@ -73,7 +73,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
_enqueueTaskBatch(medias.map((x) { _enqueueTaskBatch(medias.map((x) {
final file = File(x.path); final file = File(x.path);
return AttachmentUploadTask(file: file, usage: widget.usage); return AttachmentUploadTask(file: file, usage: widget.pool);
})); }));
} else { } else {
final media = await _imagePicker.pickMedia( final media = await _imagePicker.pickMedia(
@ -83,7 +83,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
if (media == null) return; if (media == null) return;
_enqueueTask( _enqueueTask(
AttachmentUploadTask(file: File(media.path), usage: widget.usage), AttachmentUploadTask(file: File(media.path), usage: widget.pool),
); );
} }
} }
@ -97,7 +97,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
final file = File(media.path); final file = File(media.path);
_enqueueTask( _enqueueTask(
AttachmentUploadTask(file: file, usage: widget.usage), AttachmentUploadTask(file: file, usage: widget.pool),
); );
} }
@ -113,7 +113,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
List<File> files = result.paths.map((path) => File(path!)).toList(); List<File> files = result.paths.map((path) => File(path!)).toList();
_enqueueTaskBatch(files.map((x) { _enqueueTaskBatch(files.map((x) {
return AttachmentUploadTask(file: x, usage: widget.usage); return AttachmentUploadTask(file: x, usage: widget.pool);
})); }));
} }
@ -131,7 +131,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
final file = File(media.path); final file = File(media.path);
_enqueueTask( _enqueueTask(
AttachmentUploadTask(file: file, usage: widget.usage), AttachmentUploadTask(file: file, usage: widget.pool),
); );
} }
@ -181,13 +181,11 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
WidgetsBinding.instance.addPostFrameCallback((_) => controller.dispose()); WidgetsBinding.instance.addPostFrameCallback((_) => controller.dispose());
if (input == null || input.isEmpty) return; if (input == null || input.isEmpty) return;
final value = int.tryParse(input);
if (value == null) return;
final AttachmentProvider attach = Get.find(); final AttachmentProvider attach = Get.find();
final result = await attach.getMetadata(value); final result = await attach.getMetadata(input);
if (result != null) { if (result != null) {
widget.onAdd(result.id); widget.onAdd(result.rid);
setState(() => _attachments.add(result)); setState(() => _attachments.add(result));
if (widget.singleMode) Navigator.pop(context); if (widget.singleMode) Navigator.pop(context);
} }
@ -202,11 +200,11 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
_uploadController.uploadAttachmentWithCallback( _uploadController.uploadAttachmentWithCallback(
data, data,
'Pasted Image', 'Pasted Image',
widget.usage, widget.pool,
null, null,
(item) { (item) {
if (item == null) return; if (item == null) return;
widget.onAdd(item.id); widget.onAdd(item.rid);
if (mounted) { if (mounted) {
setState(() => _attachments.add(item)); setState(() => _attachments.add(item));
if (widget.singleMode) Navigator.pop(context); if (widget.singleMode) Navigator.pop(context);
@ -413,11 +411,11 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
: () { : () {
_uploadController _uploadController
.performSingleTask(index) .performSingleTask(index)
.then((r) { .then((out) {
if (r == null) return; if (out == null) return;
widget.onAdd(r.id); widget.onAdd(out.rid);
if (mounted) { if (mounted) {
setState(() => _attachments.add(r)); setState(() => _attachments.add(out));
if (widget.singleMode) { if (widget.singleMode) {
Navigator.pop(context); Navigator.pop(context);
} }
@ -515,7 +513,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
), ),
onTap: () { onTap: () {
_deleteAttachment(element).then((_) { _deleteAttachment(element).then((_) {
widget.onRemove(element.id); widget.onRemove(element.rid);
setState(() => _attachments.removeAt(index)); setState(() => _attachments.removeAt(index));
}); });
}, },
@ -529,7 +527,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
), ),
), ),
onTap: () { onTap: () {
widget.onRemove(element.id); widget.onRemove(element.rid);
setState(() => _attachments.removeAt(index)); setState(() => _attachments.removeAt(index));
}, },
), ),
@ -560,7 +558,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
void _startUploading() { void _startUploading() {
_uploadController.performUploadQueue(onData: (r) { _uploadController.performUploadQueue(onData: (r) {
widget.onAdd(r.id); widget.onAdd(r.rid);
if (mounted) { if (mounted) {
setState(() => _attachments.add(r)); setState(() => _attachments.add(r));
if (widget.singleMode) Navigator.pop(context); if (widget.singleMode) Navigator.pop(context);
@ -584,7 +582,7 @@ class _AttachmentEditorPopupState extends State<AttachmentEditorPopup> {
if (_uploadController.isUploading.value) return; if (_uploadController.isUploading.value) return;
_enqueueTaskBatch(detail.files.map((x) { _enqueueTaskBatch(detail.files.map((x) {
final file = File(x.path); final file = File(x.path);
return AttachmentUploadTask(file: file, usage: widget.usage); return AttachmentUploadTask(file: file, usage: widget.pool);
})); }));
}, },
child: Column( child: Column(

View File

@ -67,7 +67,7 @@ class _AttachmentFullScreenState extends State<AttachmentFullScreen> {
Future<void> _saveToAlbum() async { Future<void> _saveToAlbum() async {
final url = ServiceFinder.buildUrl( final url = ServiceFinder.buildUrl(
'files', 'files',
'/attachments/${widget.item.id}', '/attachments/${widget.item.rid}',
); );
if (PlatformInfo.isWeb || PlatformInfo.isDesktop) { if (PlatformInfo.isWeb || PlatformInfo.isDesktop) {
@ -258,7 +258,7 @@ class _AttachmentFullScreenState extends State<AttachmentFullScreen> {
spacing: 6, spacing: 6,
children: [ children: [
Text( Text(
'#${widget.item.id}', '#${widget.item.rid}',
style: metaTextStyle, style: metaTextStyle,
), ),
if (widget.item.metadata?['width'] != null && if (widget.item.metadata?['width'] != null &&

View File

@ -1,14 +1,14 @@
import 'package:cached_network_image/cached_network_image.dart'; import 'package:cached_network_image/cached_network_image.dart';
import 'package:chewie/chewie.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_animate/flutter_animate.dart'; import 'package:flutter_animate/flutter_animate.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:media_kit/media_kit.dart';
import 'package:media_kit_video/media_kit_video.dart';
import 'package:solian/models/attachment.dart'; import 'package:solian/models/attachment.dart';
import 'package:solian/platform.dart'; import 'package:solian/platform.dart';
import 'package:solian/services.dart'; import 'package:solian/services.dart';
import 'package:solian/widgets/sized_container.dart'; import 'package:solian/widgets/sized_container.dart';
import 'package:url_launcher/url_launcher_string.dart'; import 'package:url_launcher/url_launcher_string.dart';
import 'package:video_player/video_player.dart';
class AttachmentItem extends StatefulWidget { class AttachmentItem extends StatefulWidget {
final String parentId; final String parentId;
@ -91,7 +91,7 @@ class _AttachmentItemState extends State<AttachmentItem> {
launchUrlString( launchUrlString(
ServiceFinder.buildUrl( ServiceFinder.buildUrl(
'files', 'files',
'/attachments/${widget.item.id}', '/attachments/${widget.item.rid}',
), ),
); );
}, },
@ -135,7 +135,7 @@ class _AttachmentItemImage extends StatelessWidget {
fit: fit, fit: fit,
imageUrl: ServiceFinder.buildUrl( imageUrl: ServiceFinder.buildUrl(
'files', 'files',
'/attachments/${item.id}', '/attachments/${item.rid}',
), ),
progressIndicatorBuilder: (context, url, downloadProgress) { progressIndicatorBuilder: (context, url, downloadProgress) {
return Center( return Center(
@ -231,17 +231,22 @@ class _AttachmentItemVideo extends StatefulWidget {
} }
class _AttachmentItemVideoState extends State<_AttachmentItemVideo> { class _AttachmentItemVideoState extends State<_AttachmentItemVideo> {
late final _player = Player( VideoPlayerController? _playerController;
configuration: const PlayerConfiguration(logLevel: MPVLogLevel.error), ChewieController? _chewieController;
);
late final _controller = VideoController(_player);
bool _showContent = false; bool _showContent = false;
void _startLoad() { Future<void> _startLoad() async {
_player.open( final ratio = widget.item.metadata?['ratio'] ?? 16 / 9;
Media(ServiceFinder.buildUrl('files', '/attachments/${widget.item.id}')), _playerController = VideoPlayerController.networkUrl(
play: false, Uri.parse(
ServiceFinder.buildUrl('files', '/attachments/${widget.item.rid}'),
),
);
_playerController!.initialize();
_chewieController = ChewieController(
aspectRatio: ratio,
videoPlayerController: _playerController!,
); );
setState(() => _showContent = true); setState(() => _showContent = true);
} }
@ -249,13 +254,22 @@ class _AttachmentItemVideoState extends State<_AttachmentItemVideo> {
@override @override
void initState() { void initState() {
super.initState(); super.initState();
_showContent = widget.autoload; if (widget.autoload) {
_startLoad();
}
}
@override
void dispose() {
_playerController?.dispose();
_chewieController?.dispose();
super.dispose();
} }
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
final ratio = widget.item.metadata?['ratio'] ?? 16 / 9; final ratio = widget.item.metadata?['ratio'] ?? 16 / 9;
if (!_showContent) { if (!_showContent || _chewieController == null) {
return GestureDetector( return GestureDetector(
child: AspectRatio( child: AspectRatio(
aspectRatio: ratio, aspectRatio: ratio,
@ -293,15 +307,8 @@ class _AttachmentItemVideoState extends State<_AttachmentItemVideo> {
); );
} }
return Video( return Chewie(
aspectRatio: ratio, controller: _chewieController!,
controller: _controller,
); );
} }
@override
void dispose() {
_player.dispose();
super.dispose();
}
} }

View File

@ -14,7 +14,7 @@ import 'package:solian/widgets/sized_container.dart';
class AttachmentList extends StatefulWidget { class AttachmentList extends StatefulWidget {
final String parentId; final String parentId;
final List<int> attachmentsId; final List<String> attachmentsId;
final bool isGrid; final bool isGrid;
final bool isForceGrid; final bool isForceGrid;
final bool autoload; final bool autoload;
@ -57,10 +57,12 @@ class _AttachmentListState extends State<AttachmentList> {
} }
attach.listMetadata(widget.attachmentsId).then((result) { attach.listMetadata(widget.attachmentsId).then((result) {
if (mounted) {
setState(() { setState(() {
_attachmentsMeta = result; _attachmentsMeta = result;
_isLoading = false; _isLoading = false;
}); });
}
_calculateAspectRatio(); _calculateAspectRatio();
}); });
} }
@ -111,6 +113,7 @@ class _AttachmentListState extends State<AttachmentList> {
showBadge: _attachmentsMeta.length > 1 && !widget.isGrid, showBadge: _attachmentsMeta.length > 1 && !widget.isGrid,
showBorder: widget.attachmentsId.length > 1, showBorder: widget.attachmentsId.length > 1,
showMature: _showMature, showMature: _showMature,
autoload: widget.autoload,
onReveal: (value) { onReveal: (value) {
setState(() => _showMature = value); setState(() => _showMature = value);
}, },
@ -138,8 +141,9 @@ class _AttachmentListState extends State<AttachmentList> {
); );
} }
final isNotPureImage = _attachmentsMeta final isNotPureImage = _attachmentsMeta.any(
.any((x) => x?.mimetype.split('/').firstOrNull != 'image'); (x) => x?.mimetype.split('/').firstOrNull != 'image',
);
if (widget.isGrid && (widget.isForceGrid || !isNotPureImage)) { if (widget.isGrid && (widget.isForceGrid || !isNotPureImage)) {
const radius = BorderRadius.all(Radius.circular(8)); const radius = BorderRadius.all(Radius.circular(8));
return GridView.builder( return GridView.builder(
@ -157,8 +161,10 @@ class _AttachmentListState extends State<AttachmentList> {
final element = _attachmentsMeta[idx]; final element = _attachmentsMeta[idx];
return Container( return Container(
decoration: BoxDecoration( decoration: BoxDecoration(
border: border: Border.all(
Border.all(color: Theme.of(context).dividerColor, width: 1), color: Theme.of(context).dividerColor,
width: 1,
),
borderRadius: radius, borderRadius: radius,
), ),
child: ClipRRect( child: ClipRRect(
@ -328,13 +334,13 @@ class AttachmentListEntry extends StatelessWidget {
} }
class AttachmentSelfContainedEntry extends StatefulWidget { class AttachmentSelfContainedEntry extends StatefulWidget {
final int id; final String rid;
final String parentId; final String parentId;
final bool isDense; final bool isDense;
const AttachmentSelfContainedEntry({ const AttachmentSelfContainedEntry({
super.key, super.key,
required this.id, required this.rid,
required this.parentId, required this.parentId,
this.isDense = false, this.isDense = false,
}); });
@ -353,10 +359,12 @@ class _AttachmentSelfContainedEntryState
final AttachmentProvider attachments = Get.find(); final AttachmentProvider attachments = Get.find();
return FutureBuilder( return FutureBuilder(
future: attachments.getMetadata(widget.id), future: attachments.getMetadata(widget.rid),
builder: (context, snapshot) { builder: (context, snapshot) {
if (!snapshot.hasData) { if (!snapshot.hasData) {
return const Text('Loading...'); return const Center(
child: CircularProgressIndicator(),
);
} }
return AttachmentListEntry( return AttachmentListEntry(

View File

@ -39,8 +39,8 @@ class ChatEvent extends StatelessWidget {
Widget _buildAttachment(BuildContext context, {bool isMinimal = false}) { Widget _buildAttachment(BuildContext context, {bool isMinimal = false}) {
final attachments = item.body['attachments'] != null final attachments = item.body['attachments'] != null
? List<int>.from(item.body['attachments'].map((x) => x)) ? List<String>.from(item.body['attachments'].map((x) => x))
: List<int>.empty(); : List<String>.empty();
if (attachments.isEmpty) return const SizedBox(); if (attachments.isEmpty) return const SizedBox();

View File

@ -59,7 +59,7 @@ class _ChatMessageInputState extends State<ChatMessageInput> {
final TextEditingController _textController = TextEditingController(); final TextEditingController _textController = TextEditingController();
final FocusNode _focusNode = FocusNode(); final FocusNode _focusNode = FocusNode();
final List<int> _attachments = List.empty(growable: true); final List<String> _attachments = List.empty(growable: true);
Event? _editTo; Event? _editTo;
Event? _replyTo; Event? _replyTo;
@ -68,7 +68,7 @@ class _ChatMessageInputState extends State<ChatMessageInput> {
showModalBottomSheet( showModalBottomSheet(
context: context, context: context,
builder: (context) => AttachmentEditorPopup( builder: (context) => AttachmentEditorPopup(
usage: 'm.attachment', pool: 'messaging',
initialAttachments: _attachments, initialAttachments: _attachments,
onAdd: (value) { onAdd: (value) {
setState(() { setState(() {
@ -103,7 +103,7 @@ class _ChatMessageInputState extends State<ChatMessageInput> {
final AttachmentUploaderController uploader = Get.find(); final AttachmentUploaderController uploader = Get.find();
if (uploader.queueOfUpload.any( if (uploader.queueOfUpload.any(
((x) => x.usage == 'm.attachment' && x.isUploading), ((x) => x.isUploading),
)) { )) {
context.showErrorDialog('attachmentUploadInProgress'.tr); context.showErrorDialog('attachmentUploadInProgress'.tr);
return; return;

View File

@ -131,7 +131,7 @@ class MarkdownTextContent extends StatelessWidget {
child: AttachmentSelfContainedEntry( child: AttachmentSelfContainedEntry(
isDense: true, isDense: true,
parentId: parentId, parentId: parentId,
id: int.parse(segments[1]), rid: segments[1],
), ),
), ),
).paddingSymmetric(vertical: 4); ).paddingSymmetric(vertical: 4);

View File

@ -19,7 +19,7 @@ class PostEditorCategoriesDialog extends StatelessWidget {
initialTags: controller.tags, initialTags: controller.tags,
hintText: 'postTagsPlaceholder'.tr, hintText: 'postTagsPlaceholder'.tr,
onUpdate: (value) { onUpdate: (value) {
controller.tags.value = value; controller.tags.value = List.from(value, growable: true);
controller.tags.refresh(); controller.tags.refresh();
}, },
), ),

View File

@ -14,12 +14,25 @@ class PostEditorOverviewDialog extends StatelessWidget {
content: Column( content: Column(
mainAxisSize: MainAxisSize.min, mainAxisSize: MainAxisSize.min,
children: [ children: [
TextField(
autofocus: true,
autocorrect: true,
controller: controller.aliasController,
decoration: InputDecoration(
isDense: true,
border: const OutlineInputBorder(),
hintText: 'alias'.tr,
),
onTapOutside: (_) => FocusManager.instance.primaryFocus?.unfocus(),
),
const SizedBox(height: 16),
TextField( TextField(
autofocus: true, autofocus: true,
autocorrect: true, autocorrect: true,
controller: controller.titleController, controller: controller.titleController,
decoration: InputDecoration( decoration: InputDecoration(
border: const UnderlineInputBorder(), isDense: true,
border: const OutlineInputBorder(),
hintText: 'title'.tr, hintText: 'title'.tr,
), ),
onTapOutside: (_) => FocusManager.instance.primaryFocus?.unfocus(), onTapOutside: (_) => FocusManager.instance.primaryFocus?.unfocus(),
@ -33,7 +46,8 @@ class PostEditorOverviewDialog extends StatelessWidget {
keyboardType: TextInputType.multiline, keyboardType: TextInputType.multiline,
controller: controller.descriptionController, controller: controller.descriptionController,
decoration: InputDecoration( decoration: InputDecoration(
border: const UnderlineInputBorder(), isDense: true,
border: const OutlineInputBorder(),
hintText: 'description'.tr, hintText: 'description'.tr,
), ),
onTapOutside: (_) => FocusManager.instance.primaryFocus?.unfocus(), onTapOutside: (_) => FocusManager.instance.primaryFocus?.unfocus(),

View File

@ -20,7 +20,7 @@ class _PostEditorThumbnailDialogState extends State<PostEditorThumbnailDialog> {
showModalBottomSheet( showModalBottomSheet(
context: context, context: context,
builder: (context) => AttachmentEditorPopup( builder: (context) => AttachmentEditorPopup(
usage: 'i.attachment', pool: 'interactive',
singleMode: true, singleMode: true,
imageOnly: true, imageOnly: true,
autoUpload: true, autoUpload: true,
@ -84,8 +84,7 @@ class _PostEditorThumbnailDialogState extends State<PostEditorThumbnailDialog> {
actions: [ actions: [
TextButton( TextButton(
onPressed: () { onPressed: () {
widget.controller.thumbnail.value = widget.controller.thumbnail.value = _attachmentController.text;
int.tryParse(_attachmentController.text);
Navigator.pop(context); Navigator.pop(context);
}, },
child: Text('confirm'.tr), child: Text('confirm'.tr),

View File

@ -42,24 +42,30 @@ class _PostActionState extends State<PostAction> {
Future<void> _doShare({bool noUri = false}) async { Future<void> _doShare({bool noUri = false}) async {
ShareResult result; ShareResult result;
String id;
final box = context.findRenderObject() as RenderBox?; final box = context.findRenderObject() as RenderBox?;
if (widget.item.alias?.isNotEmpty ?? false) {
id = '${widget.item.areaAlias}/${widget.item.alias}';
} else {
id = '${widget.item.id}';
}
if ((PlatformInfo.isAndroid || PlatformInfo.isIOS) && !noUri) { if ((PlatformInfo.isAndroid || PlatformInfo.isIOS) && !noUri) {
result = await Share.shareUri( result = await Share.shareUri(
Uri.parse('https://solsynth.dev/posts/${widget.item.id}'), Uri.parse('https://solsynth.dev/posts/$id'),
sharePositionOrigin: box!.localToGlobal(Offset.zero) & box.size, sharePositionOrigin: box!.localToGlobal(Offset.zero) & box.size,
); );
} else { } else {
final extraContent = [ final extraContent = <String?>[
widget.item.body['title'], widget.item.body['title'],
widget.item.body['description'], widget.item.body['description'],
]; ].where((x) => x != null && x.isNotEmpty).toList();
final isExtraNotEmpty = extraContent.any((x) => x != null); final isExtraNotEmpty = extraContent.any((x) => x != null);
result = await Share.share( result = await Share.share(
'postShareContent'.trParams({ 'postShareContent'.trParams({
'username': widget.item.author.nick, 'username': widget.item.author.nick,
'content': 'content':
'${extraContent.join('\n')}${isExtraNotEmpty ? '\n\n' : ''}${widget.item.body['content'] ?? 'no content'}', '${extraContent.join('\n')}${isExtraNotEmpty ? '\n\n' : ''}${widget.item.body['content'] ?? 'no content'}',
'link': 'https://solsynth.dev/posts/${widget.item.id}', 'link': 'https://solsynth.dev/posts/$id',
}), }),
subject: 'postShareSubject'.trParams({ subject: 'postShareSubject'.trParams({
'username': widget.item.author.nick, 'username': widget.item.author.nick,
@ -96,10 +102,28 @@ class _PostActionState extends State<PostAction> {
'postActionList'.tr, 'postActionList'.tr,
style: Theme.of(context).textTheme.headlineSmall, style: Theme.of(context).textTheme.headlineSmall,
), ),
Row(
children: [
Text( Text(
'#${widget.item.id.toString().padLeft(8, '0')}', '#${widget.item.id.toString().padLeft(8, '0')}',
style: Theme.of(context).textTheme.bodySmall, style: Theme.of(context).textTheme.bodySmall,
), ),
if (widget.item.alias?.isNotEmpty ?? false)
Text(
'·',
style: Theme.of(context).textTheme.bodySmall,
).paddingSymmetric(horizontal: 6),
if (widget.item.alias?.isNotEmpty ?? false)
Expanded(
child: Text(
'${widget.item.areaAlias}:${widget.item.alias}',
style: Theme.of(context).textTheme.bodySmall,
maxLines: 1,
overflow: TextOverflow.ellipsis,
),
),
],
),
], ],
).paddingOnly(left: 24, right: 24, top: 32, bottom: 16), ).paddingOnly(left: 24, right: 24, top: 32, bottom: 16),
if (_isBusy) const LinearProgressIndicator().animate().scaleX(), if (_isBusy) const LinearProgressIndicator().animate().scaleX(),

View File

@ -78,25 +78,19 @@ class _PostItemState extends State<PostItem> {
Widget _buildThumbnail() { Widget _buildThumbnail() {
if (widget.item.body['thumbnail'] == null) return const SizedBox(); if (widget.item.body['thumbnail'] == null) return const SizedBox();
const radius = BorderRadius.all(Radius.circular(8)); final border = BorderSide(
return AspectRatio(
aspectRatio: 16 / 9,
child: Container(
decoration: BoxDecoration(
border: Border.all(
color: Theme.of(context).dividerColor, color: Theme.of(context).dividerColor,
width: 0.3, width: 0.3,
), );
borderRadius: radius, return Container(
), decoration: BoxDecoration(border: Border(top: border, bottom: border)),
child: ClipRRect( child: AspectRatio(
borderRadius: radius, aspectRatio: 16 / 9,
child: AttachmentSelfContainedEntry( child: AttachmentSelfContainedEntry(
id: widget.item.body['thumbnail'], rid: widget.item.body['thumbnail'],
parentId: 'p${item.id}-thumbnail', parentId: 'p${item.id}-thumbnail',
), ),
), ),
),
); );
} }
@ -298,8 +292,8 @@ class _PostItemState extends State<PostItem> {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
final List<int> attachments = item.body['attachments'] is List final List<String> attachments = item.body['attachments'] is List
? item.body['attachments']?.cast<int>() ? item.body['attachments']?.cast<String>()
: List.empty(); : List.empty();
final hasAttachment = attachments.isNotEmpty; final hasAttachment = attachments.isNotEmpty;
@ -307,7 +301,7 @@ class _PostItemState extends State<PostItem> {
return Column( return Column(
crossAxisAlignment: CrossAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start,
children: [ children: [
_buildThumbnail().paddingSymmetric(horizontal: 12, vertical: 4), _buildThumbnail(),
_buildHeader().paddingSymmetric(horizontal: 12), _buildHeader().paddingSymmetric(horizontal: 12),
_buildHeaderDivider().paddingSymmetric(horizontal: 12), _buildHeaderDivider().paddingSymmetric(horizontal: 12),
Stack( Stack(
@ -381,7 +375,7 @@ class _PostItemState extends State<PostItem> {
closedBuilder: (_, openContainer) => Column( closedBuilder: (_, openContainer) => Column(
crossAxisAlignment: CrossAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start,
children: [ children: [
_buildThumbnail().paddingSymmetric(horizontal: 12, vertical: 4), _buildThumbnail().paddingOnly(bottom: 4),
Row( Row(
crossAxisAlignment: CrossAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start,
children: [ children: [

View File

@ -29,7 +29,7 @@ class _StickerUploadDialogState extends State<StickerUploadDialog> {
showModalBottomSheet( showModalBottomSheet(
context: context, context: context,
builder: (context) => AttachmentEditorPopup( builder: (context) => AttachmentEditorPopup(
usage: 'sticker', pool: 'sticker',
singleMode: true, singleMode: true,
imageOnly: true, imageOnly: true,
autoUpload: true, autoUpload: true,

View File

@ -11,8 +11,6 @@
#include <flutter_acrylic/flutter_acrylic_plugin.h> #include <flutter_acrylic/flutter_acrylic_plugin.h>
#include <flutter_secure_storage_linux/flutter_secure_storage_linux_plugin.h> #include <flutter_secure_storage_linux/flutter_secure_storage_linux_plugin.h>
#include <flutter_webrtc/flutter_web_r_t_c_plugin.h> #include <flutter_webrtc/flutter_web_r_t_c_plugin.h>
#include <media_kit_libs_linux/media_kit_libs_linux_plugin.h>
#include <media_kit_video/media_kit_video_plugin.h>
#include <pasteboard/pasteboard_plugin.h> #include <pasteboard/pasteboard_plugin.h>
#include <url_launcher_linux/url_launcher_plugin.h> #include <url_launcher_linux/url_launcher_plugin.h>
@ -32,12 +30,6 @@ void fl_register_plugins(FlPluginRegistry* registry) {
g_autoptr(FlPluginRegistrar) flutter_webrtc_registrar = g_autoptr(FlPluginRegistrar) flutter_webrtc_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "FlutterWebRTCPlugin"); fl_plugin_registry_get_registrar_for_plugin(registry, "FlutterWebRTCPlugin");
flutter_web_r_t_c_plugin_register_with_registrar(flutter_webrtc_registrar); flutter_web_r_t_c_plugin_register_with_registrar(flutter_webrtc_registrar);
g_autoptr(FlPluginRegistrar) media_kit_libs_linux_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "MediaKitLibsLinuxPlugin");
media_kit_libs_linux_plugin_register_with_registrar(media_kit_libs_linux_registrar);
g_autoptr(FlPluginRegistrar) media_kit_video_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "MediaKitVideoPlugin");
media_kit_video_plugin_register_with_registrar(media_kit_video_registrar);
g_autoptr(FlPluginRegistrar) pasteboard_registrar = g_autoptr(FlPluginRegistrar) pasteboard_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "PasteboardPlugin"); fl_plugin_registry_get_registrar_for_plugin(registry, "PasteboardPlugin");
pasteboard_plugin_register_with_registrar(pasteboard_registrar); pasteboard_plugin_register_with_registrar(pasteboard_registrar);

View File

@ -8,14 +8,11 @@ list(APPEND FLUTTER_PLUGIN_LIST
flutter_acrylic flutter_acrylic
flutter_secure_storage_linux flutter_secure_storage_linux
flutter_webrtc flutter_webrtc
media_kit_libs_linux
media_kit_video
pasteboard pasteboard
url_launcher_linux url_launcher_linux
) )
list(APPEND FLUTTER_FFI_PLUGIN_LIST list(APPEND FLUTTER_FFI_PLUGIN_LIST
media_kit_native_event_loop
) )
set(PLUGIN_BUNDLED_LIBRARIES) set(PLUGIN_BUNDLED_LIBRARIES)

View File

@ -18,17 +18,15 @@ import flutter_webrtc
import gal import gal
import livekit_client import livekit_client
import macos_window_utils import macos_window_utils
import media_kit_libs_macos_video
import media_kit_video
import package_info_plus import package_info_plus
import pasteboard import pasteboard
import path_provider_foundation import path_provider_foundation
import protocol_handler_macos import protocol_handler_macos
import screen_brightness_macos
import share_plus import share_plus
import shared_preferences_foundation import shared_preferences_foundation
import sqflite import sqflite
import url_launcher_macos import url_launcher_macos
import video_player_avfoundation
import wakelock_plus import wakelock_plus
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) { func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
@ -45,16 +43,14 @@ func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
GalPlugin.register(with: registry.registrar(forPlugin: "GalPlugin")) GalPlugin.register(with: registry.registrar(forPlugin: "GalPlugin"))
LiveKitPlugin.register(with: registry.registrar(forPlugin: "LiveKitPlugin")) LiveKitPlugin.register(with: registry.registrar(forPlugin: "LiveKitPlugin"))
MacOSWindowUtilsPlugin.register(with: registry.registrar(forPlugin: "MacOSWindowUtilsPlugin")) MacOSWindowUtilsPlugin.register(with: registry.registrar(forPlugin: "MacOSWindowUtilsPlugin"))
MediaKitLibsMacosVideoPlugin.register(with: registry.registrar(forPlugin: "MediaKitLibsMacosVideoPlugin"))
MediaKitVideoPlugin.register(with: registry.registrar(forPlugin: "MediaKitVideoPlugin"))
FPPPackageInfoPlusPlugin.register(with: registry.registrar(forPlugin: "FPPPackageInfoPlusPlugin")) FPPPackageInfoPlusPlugin.register(with: registry.registrar(forPlugin: "FPPPackageInfoPlusPlugin"))
PasteboardPlugin.register(with: registry.registrar(forPlugin: "PasteboardPlugin")) PasteboardPlugin.register(with: registry.registrar(forPlugin: "PasteboardPlugin"))
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin")) PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
ProtocolHandlerMacosPlugin.register(with: registry.registrar(forPlugin: "ProtocolHandlerMacosPlugin")) ProtocolHandlerMacosPlugin.register(with: registry.registrar(forPlugin: "ProtocolHandlerMacosPlugin"))
ScreenBrightnessMacosPlugin.register(with: registry.registrar(forPlugin: "ScreenBrightnessMacosPlugin"))
SharePlusMacosPlugin.register(with: registry.registrar(forPlugin: "SharePlusMacosPlugin")) SharePlusMacosPlugin.register(with: registry.registrar(forPlugin: "SharePlusMacosPlugin"))
SharedPreferencesPlugin.register(with: registry.registrar(forPlugin: "SharedPreferencesPlugin")) SharedPreferencesPlugin.register(with: registry.registrar(forPlugin: "SharedPreferencesPlugin"))
SqflitePlugin.register(with: registry.registrar(forPlugin: "SqflitePlugin")) SqflitePlugin.register(with: registry.registrar(forPlugin: "SqflitePlugin"))
UrlLauncherPlugin.register(with: registry.registrar(forPlugin: "UrlLauncherPlugin")) UrlLauncherPlugin.register(with: registry.registrar(forPlugin: "UrlLauncherPlugin"))
FVPVideoPlayerPlugin.register(with: registry.registrar(forPlugin: "FVPVideoPlayerPlugin"))
WakelockPlusMacosPlugin.register(with: registry.registrar(forPlugin: "WakelockPlusMacosPlugin")) WakelockPlusMacosPlugin.register(with: registry.registrar(forPlugin: "WakelockPlusMacosPlugin"))
} }

View File

@ -163,12 +163,6 @@ PODS:
- WebRTC-SDK (= 125.6422.04) - WebRTC-SDK (= 125.6422.04)
- macos_window_utils (1.0.0): - macos_window_utils (1.0.0):
- FlutterMacOS - FlutterMacOS
- media_kit_libs_macos_video (1.0.4):
- FlutterMacOS
- media_kit_native_event_loop (1.0.0):
- FlutterMacOS
- media_kit_video (0.0.1):
- FlutterMacOS
- nanopb (2.30910.0): - nanopb (2.30910.0):
- nanopb/decode (= 2.30910.0) - nanopb/decode (= 2.30910.0)
- nanopb/encode (= 2.30910.0) - nanopb/encode (= 2.30910.0)
@ -186,8 +180,6 @@ PODS:
- PromisesObjC (= 2.4.0) - PromisesObjC (= 2.4.0)
- protocol_handler_macos (0.0.1): - protocol_handler_macos (0.0.1):
- FlutterMacOS - FlutterMacOS
- screen_brightness_macos (0.1.0):
- FlutterMacOS
- share_plus (0.0.1): - share_plus (0.0.1):
- FlutterMacOS - FlutterMacOS
- shared_preferences_foundation (0.0.1): - shared_preferences_foundation (0.0.1):
@ -198,6 +190,9 @@ PODS:
- FlutterMacOS - FlutterMacOS
- url_launcher_macos (0.0.1): - url_launcher_macos (0.0.1):
- FlutterMacOS - FlutterMacOS
- video_player_avfoundation (0.0.1):
- Flutter
- FlutterMacOS
- wakelock_plus (0.0.1): - wakelock_plus (0.0.1):
- FlutterMacOS - FlutterMacOS
- WebRTC-SDK (125.6422.04) - WebRTC-SDK (125.6422.04)
@ -217,18 +212,15 @@ DEPENDENCIES:
- gal (from `Flutter/ephemeral/.symlinks/plugins/gal/darwin`) - gal (from `Flutter/ephemeral/.symlinks/plugins/gal/darwin`)
- livekit_client (from `Flutter/ephemeral/.symlinks/plugins/livekit_client/macos`) - livekit_client (from `Flutter/ephemeral/.symlinks/plugins/livekit_client/macos`)
- macos_window_utils (from `Flutter/ephemeral/.symlinks/plugins/macos_window_utils/macos`) - macos_window_utils (from `Flutter/ephemeral/.symlinks/plugins/macos_window_utils/macos`)
- media_kit_libs_macos_video (from `Flutter/ephemeral/.symlinks/plugins/media_kit_libs_macos_video/macos`)
- media_kit_native_event_loop (from `Flutter/ephemeral/.symlinks/plugins/media_kit_native_event_loop/macos`)
- media_kit_video (from `Flutter/ephemeral/.symlinks/plugins/media_kit_video/macos`)
- package_info_plus (from `Flutter/ephemeral/.symlinks/plugins/package_info_plus/macos`) - package_info_plus (from `Flutter/ephemeral/.symlinks/plugins/package_info_plus/macos`)
- pasteboard (from `Flutter/ephemeral/.symlinks/plugins/pasteboard/macos`) - pasteboard (from `Flutter/ephemeral/.symlinks/plugins/pasteboard/macos`)
- path_provider_foundation (from `Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin`) - path_provider_foundation (from `Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin`)
- protocol_handler_macos (from `Flutter/ephemeral/.symlinks/plugins/protocol_handler_macos/macos`) - protocol_handler_macos (from `Flutter/ephemeral/.symlinks/plugins/protocol_handler_macos/macos`)
- screen_brightness_macos (from `Flutter/ephemeral/.symlinks/plugins/screen_brightness_macos/macos`)
- share_plus (from `Flutter/ephemeral/.symlinks/plugins/share_plus/macos`) - share_plus (from `Flutter/ephemeral/.symlinks/plugins/share_plus/macos`)
- shared_preferences_foundation (from `Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin`) - shared_preferences_foundation (from `Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin`)
- sqflite (from `Flutter/ephemeral/.symlinks/plugins/sqflite/darwin`) - sqflite (from `Flutter/ephemeral/.symlinks/plugins/sqflite/darwin`)
- url_launcher_macos (from `Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos`) - url_launcher_macos (from `Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos`)
- video_player_avfoundation (from `Flutter/ephemeral/.symlinks/plugins/video_player_avfoundation/darwin`)
- wakelock_plus (from `Flutter/ephemeral/.symlinks/plugins/wakelock_plus/macos`) - wakelock_plus (from `Flutter/ephemeral/.symlinks/plugins/wakelock_plus/macos`)
SPEC REPOS: SPEC REPOS:
@ -280,12 +272,6 @@ EXTERNAL SOURCES:
:path: Flutter/ephemeral/.symlinks/plugins/livekit_client/macos :path: Flutter/ephemeral/.symlinks/plugins/livekit_client/macos
macos_window_utils: macos_window_utils:
:path: Flutter/ephemeral/.symlinks/plugins/macos_window_utils/macos :path: Flutter/ephemeral/.symlinks/plugins/macos_window_utils/macos
media_kit_libs_macos_video:
:path: Flutter/ephemeral/.symlinks/plugins/media_kit_libs_macos_video/macos
media_kit_native_event_loop:
:path: Flutter/ephemeral/.symlinks/plugins/media_kit_native_event_loop/macos
media_kit_video:
:path: Flutter/ephemeral/.symlinks/plugins/media_kit_video/macos
package_info_plus: package_info_plus:
:path: Flutter/ephemeral/.symlinks/plugins/package_info_plus/macos :path: Flutter/ephemeral/.symlinks/plugins/package_info_plus/macos
pasteboard: pasteboard:
@ -294,8 +280,6 @@ EXTERNAL SOURCES:
:path: Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin :path: Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin
protocol_handler_macos: protocol_handler_macos:
:path: Flutter/ephemeral/.symlinks/plugins/protocol_handler_macos/macos :path: Flutter/ephemeral/.symlinks/plugins/protocol_handler_macos/macos
screen_brightness_macos:
:path: Flutter/ephemeral/.symlinks/plugins/screen_brightness_macos/macos
share_plus: share_plus:
:path: Flutter/ephemeral/.symlinks/plugins/share_plus/macos :path: Flutter/ephemeral/.symlinks/plugins/share_plus/macos
shared_preferences_foundation: shared_preferences_foundation:
@ -304,6 +288,8 @@ EXTERNAL SOURCES:
:path: Flutter/ephemeral/.symlinks/plugins/sqflite/darwin :path: Flutter/ephemeral/.symlinks/plugins/sqflite/darwin
url_launcher_macos: url_launcher_macos:
:path: Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos :path: Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos
video_player_avfoundation:
:path: Flutter/ephemeral/.symlinks/plugins/video_player_avfoundation/darwin
wakelock_plus: wakelock_plus:
:path: Flutter/ephemeral/.symlinks/plugins/wakelock_plus/macos :path: Flutter/ephemeral/.symlinks/plugins/wakelock_plus/macos
@ -335,9 +321,6 @@ SPEC CHECKSUMS:
GoogleUtilities: ea963c370a38a8069cc5f7ba4ca849a60b6d7d15 GoogleUtilities: ea963c370a38a8069cc5f7ba4ca849a60b6d7d15
livekit_client: 95f3b71e6545845aa658a6df0a3a62dcc3471d7c livekit_client: 95f3b71e6545845aa658a6df0a3a62dcc3471d7c
macos_window_utils: 933f91f64805e2eb91a5bd057cf97cd097276663 macos_window_utils: 933f91f64805e2eb91a5bd057cf97cd097276663
media_kit_libs_macos_video: b3e2bbec2eef97c285f2b1baa7963c67c753fb82
media_kit_native_event_loop: 81fd5b45192b72f8b5b69eaf5b540f45777eb8d5
media_kit_video: c75b07f14d59706c775778e4dd47dd027de8d1e5
nanopb: 438bc412db1928dac798aa6fd75726007be04262 nanopb: 438bc412db1928dac798aa6fd75726007be04262
package_info_plus: fa739dd842b393193c5ca93c26798dff6e3d0e0c package_info_plus: fa739dd842b393193c5ca93c26798dff6e3d0e0c
pasteboard: 9b69dba6fedbb04866be632205d532fe2f6b1d99 pasteboard: 9b69dba6fedbb04866be632205d532fe2f6b1d99
@ -345,11 +328,11 @@ SPEC CHECKSUMS:
PromisesObjC: f5707f49cb48b9636751c5b2e7d227e43fba9f47 PromisesObjC: f5707f49cb48b9636751c5b2e7d227e43fba9f47
PromisesSwift: 9d77319bbe72ebf6d872900551f7eeba9bce2851 PromisesSwift: 9d77319bbe72ebf6d872900551f7eeba9bce2851
protocol_handler_macos: d10a6c01d6373389ffd2278013ab4c47ed6d6daa protocol_handler_macos: d10a6c01d6373389ffd2278013ab4c47ed6d6daa
screen_brightness_macos: 2d6d3af2165592d9a55ffcd95b7550970e41ebda
share_plus: 36537c04ce0c3e3f5bd297ce4318b6d5ee5fd6cf share_plus: 36537c04ce0c3e3f5bd297ce4318b6d5ee5fd6cf
shared_preferences_foundation: fcdcbc04712aee1108ac7fda236f363274528f78 shared_preferences_foundation: fcdcbc04712aee1108ac7fda236f363274528f78
sqflite: 673a0e54cc04b7d6dba8d24fb8095b31c3a99eec sqflite: 673a0e54cc04b7d6dba8d24fb8095b31c3a99eec
url_launcher_macos: 5f437abeda8c85500ceb03f5c1938a8c5a705399 url_launcher_macos: 5f437abeda8c85500ceb03f5c1938a8c5a705399
video_player_avfoundation: 7c6c11d8470e1675df7397027218274b6d2360b3
wakelock_plus: 4783562c9a43d209c458cb9b30692134af456269 wakelock_plus: 4783562c9a43d209c458cb9b30692134af456269
WebRTC-SDK: c3d69a87e7185fad3568f6f3cff7c9ac5890acf3 WebRTC-SDK: c3d69a87e7185fad3568f6f3cff7c9ac5890acf3

View File

@ -206,6 +206,14 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "2.0.3" version: "2.0.3"
chewie:
dependency: "direct main"
description:
name: chewie
sha256: "2243e41e79e865d426d9dd9c1a9624aa33c4ad11de2d0cd680f826e2cd30e879"
url: "https://pub.dev"
source: hosted
version: "1.8.3"
cli_util: cli_util:
dependency: transitive dependency: transitive
description: description:
@ -278,6 +286,14 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "3.0.5" version: "3.0.5"
csslib:
dependency: transitive
description:
name: csslib
sha256: "706b5707578e0c1b4b7550f64078f0a0f19dec3f50a178ffae7006b0a9ca58fb"
url: "https://pub.dev"
source: hosted
version: "1.0.0"
cupertino_icons: cupertino_icons:
dependency: "direct main" dependency: "direct main"
description: description:
@ -853,6 +869,14 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "1.0.5" version: "1.0.5"
html:
dependency: transitive
description:
name: html
sha256: "3a7812d5bcd2894edf53dfaf8cd640876cf6cef50a8f238745c8b8120ea74d3a"
url: "https://pub.dev"
source: hosted
version: "0.15.4"
http: http:
dependency: transitive dependency: transitive
description: description:
@ -1117,78 +1141,6 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "0.11.1" version: "0.11.1"
media_kit:
dependency: "direct main"
description:
name: media_kit
sha256: "3289062540e3b8b9746e5c50d95bd78a9289826b7227e253dff806d002b9e67a"
url: "https://pub.dev"
source: hosted
version: "1.1.10+1"
media_kit_libs_android_video:
dependency: transitive
description:
name: media_kit_libs_android_video
sha256: "9dd8012572e4aff47516e55f2597998f0a378e3d588d0fad0ca1f11a53ae090c"
url: "https://pub.dev"
source: hosted
version: "1.3.6"
media_kit_libs_ios_video:
dependency: transitive
description:
name: media_kit_libs_ios_video
sha256: b5382994eb37a4564c368386c154ad70ba0cc78dacdd3fb0cd9f30db6d837991
url: "https://pub.dev"
source: hosted
version: "1.1.4"
media_kit_libs_linux:
dependency: transitive
description:
name: media_kit_libs_linux
sha256: e186891c31daa6bedab4d74dcdb4e8adfccc7d786bfed6ad81fe24a3b3010310
url: "https://pub.dev"
source: hosted
version: "1.1.3"
media_kit_libs_macos_video:
dependency: transitive
description:
name: media_kit_libs_macos_video
sha256: f26aa1452b665df288e360393758f84b911f70ffb3878032e1aabba23aa1032d
url: "https://pub.dev"
source: hosted
version: "1.1.4"
media_kit_libs_video:
dependency: "direct main"
description:
name: media_kit_libs_video
sha256: "3688e0c31482074578652bf038ce6301a5d21e1eda6b54fc3117ffeb4bdba067"
url: "https://pub.dev"
source: hosted
version: "1.0.4"
media_kit_libs_windows_video:
dependency: transitive
description:
name: media_kit_libs_windows_video
sha256: "7bace5f35d9afcc7f9b5cdadb7541d2191a66bb3fc71bfa11c1395b3360f6122"
url: "https://pub.dev"
source: hosted
version: "1.0.9"
media_kit_native_event_loop:
dependency: transitive
description:
name: media_kit_native_event_loop
sha256: a605cf185499d14d58935b8784955a92a4bf0ff4e19a23de3d17a9106303930e
url: "https://pub.dev"
source: hosted
version: "1.0.8"
media_kit_video:
dependency: "direct main"
description:
name: media_kit_video
sha256: c048d11a19e379aebbe810647636e3fc6d18374637e2ae12def4ff8a4b99a882
url: "https://pub.dev"
source: hosted
version: "1.2.4"
meta: meta:
dependency: transitive dependency: transitive
description: description:
@ -1533,62 +1485,6 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "0.28.0" version: "0.28.0"
safe_local_storage:
dependency: transitive
description:
name: safe_local_storage
sha256: ede4eb6cb7d88a116b3d3bf1df70790b9e2038bc37cb19112e381217c74d9440
url: "https://pub.dev"
source: hosted
version: "1.0.2"
screen_brightness:
dependency: transitive
description:
name: screen_brightness
sha256: ed8da4a4511e79422fc1aa88138e920e4008cd312b72cdaa15ccb426c0faaedd
url: "https://pub.dev"
source: hosted
version: "0.2.2+1"
screen_brightness_android:
dependency: transitive
description:
name: screen_brightness_android
sha256: "3df10961e3a9e968a5e076fe27e7f4741fa8a1d3950bdeb48cf121ed529d0caf"
url: "https://pub.dev"
source: hosted
version: "0.1.0+2"
screen_brightness_ios:
dependency: transitive
description:
name: screen_brightness_ios
sha256: "99adc3ca5490b8294284aad5fcc87f061ad685050e03cf45d3d018fe398fd9a2"
url: "https://pub.dev"
source: hosted
version: "0.1.0"
screen_brightness_macos:
dependency: transitive
description:
name: screen_brightness_macos
sha256: "64b34e7e3f4900d7687c8e8fb514246845a73ecec05ab53483ed025bd4a899fd"
url: "https://pub.dev"
source: hosted
version: "0.1.0+1"
screen_brightness_platform_interface:
dependency: transitive
description:
name: screen_brightness_platform_interface
sha256: b211d07f0c96637a15fb06f6168617e18030d5d74ad03795dd8547a52717c171
url: "https://pub.dev"
source: hosted
version: "0.1.0"
screen_brightness_windows:
dependency: transitive
description:
name: screen_brightness_windows
sha256: "9261bf33d0fc2707d8cf16339ce25768100a65e70af0fcabaf032fc12408ba86"
url: "https://pub.dev"
source: hosted
version: "0.1.3"
sdp_transform: sdp_transform:
dependency: transitive dependency: transitive
description: description:
@ -1866,22 +1762,6 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "0.3.1" version: "0.3.1"
universal_platform:
dependency: transitive
description:
name: universal_platform
sha256: "64e16458a0ea9b99260ceb5467a214c1f298d647c659af1bff6d3bf82536b1ec"
url: "https://pub.dev"
source: hosted
version: "1.1.0"
uri_parser:
dependency: transitive
description:
name: uri_parser
sha256: "6543c9fd86d2862fac55d800a43e67c0dcd1a41677cb69c2f8edfe73bbcf1835"
url: "https://pub.dev"
source: hosted
version: "2.0.2"
url_launcher: url_launcher:
dependency: "direct main" dependency: "direct main"
description: description:
@ -1962,6 +1842,46 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "2.1.4" version: "2.1.4"
video_player:
dependency: "direct main"
description:
name: video_player
sha256: e30df0d226c4ef82e2c150ebf6834b3522cf3f654d8e2f9419d376cdc071425d
url: "https://pub.dev"
source: hosted
version: "2.9.1"
video_player_android:
dependency: transitive
description:
name: video_player_android
sha256: "4de50df9ee786f5891d3281e1e633d7b142ef1acf47392592eb91cba5d355849"
url: "https://pub.dev"
source: hosted
version: "2.6.0"
video_player_avfoundation:
dependency: transitive
description:
name: video_player_avfoundation
sha256: d1e9a824f2b324000dc8fb2dcb2a3285b6c1c7c487521c63306cc5b394f68a7c
url: "https://pub.dev"
source: hosted
version: "2.6.1"
video_player_platform_interface:
dependency: transitive
description:
name: video_player_platform_interface
sha256: "236454725fafcacf98f0f39af0d7c7ab2ce84762e3b63f2cbb3ef9a7e0550bc6"
url: "https://pub.dev"
source: hosted
version: "6.2.2"
video_player_web:
dependency: transitive
description:
name: video_player_web
sha256: "6dcdd298136523eaf7dfc31abaf0dfba9aa8a8dbc96670e87e9d42b6f2caf774"
url: "https://pub.dev"
source: hosted
version: "2.3.2"
vm_service: vm_service:
dependency: transitive dependency: transitive
description: description:
@ -1970,14 +1890,6 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "14.2.4" version: "14.2.4"
volume_controller:
dependency: transitive
description:
name: volume_controller
sha256: c71d4c62631305df63b72da79089e078af2659649301807fa746088f365cb48e
url: "https://pub.dev"
source: hosted
version: "2.0.8"
wakelock_plus: wakelock_plus:
dependency: "direct main" dependency: "direct main"
description: description:

View File

@ -2,7 +2,7 @@ name: solian
description: "The Solar Network App" description: "The Solar Network App"
publish_to: "none" publish_to: "none"
version: 1.2.1+14 version: 1.2.1+16
environment: environment:
sdk: ">=3.3.4 <4.0.0" sdk: ">=3.3.4 <4.0.0"
@ -45,9 +45,6 @@ dependencies:
sqflite: ^2.3.3+1 sqflite: ^2.3.3+1
protocol_handler: ^0.2.0 protocol_handler: ^0.2.0
markdown: ^7.2.2 markdown: ^7.2.2
media_kit: ^1.1.10+1
media_kit_video: ^1.2.4
media_kit_libs_video: ^1.0.4
pasteboard: ^0.2.0 pasteboard: ^0.2.0
desktop_drop: ^0.4.4 desktop_drop: ^0.4.4
badges: ^3.1.2 badges: ^3.1.2
@ -70,6 +67,8 @@ dependencies:
collection: ^1.18.0 collection: ^1.18.0
firebase_crashlytics: ^4.0.4 firebase_crashlytics: ^4.0.4
firebase_analytics: ^11.2.1 firebase_analytics: ^11.2.1
video_player: ^2.9.1
chewie: ^1.8.3
dev_dependencies: dev_dependencies:
flutter_test: flutter_test:

View File

@ -15,12 +15,9 @@
#include <flutter_webrtc/flutter_web_r_t_c_plugin.h> #include <flutter_webrtc/flutter_web_r_t_c_plugin.h>
#include <gal/gal_plugin_c_api.h> #include <gal/gal_plugin_c_api.h>
#include <livekit_client/live_kit_plugin.h> #include <livekit_client/live_kit_plugin.h>
#include <media_kit_libs_windows_video/media_kit_libs_windows_video_plugin_c_api.h>
#include <media_kit_video/media_kit_video_plugin_c_api.h>
#include <pasteboard/pasteboard_plugin.h> #include <pasteboard/pasteboard_plugin.h>
#include <permission_handler_windows/permission_handler_windows_plugin.h> #include <permission_handler_windows/permission_handler_windows_plugin.h>
#include <protocol_handler_windows/protocol_handler_windows_plugin_c_api.h> #include <protocol_handler_windows/protocol_handler_windows_plugin_c_api.h>
#include <screen_brightness_windows/screen_brightness_windows_plugin.h>
#include <share_plus/share_plus_windows_plugin_c_api.h> #include <share_plus/share_plus_windows_plugin_c_api.h>
#include <url_launcher_windows/url_launcher_windows.h> #include <url_launcher_windows/url_launcher_windows.h>
@ -43,18 +40,12 @@ void RegisterPlugins(flutter::PluginRegistry* registry) {
registry->GetRegistrarForPlugin("GalPluginCApi")); registry->GetRegistrarForPlugin("GalPluginCApi"));
LiveKitPluginRegisterWithRegistrar( LiveKitPluginRegisterWithRegistrar(
registry->GetRegistrarForPlugin("LiveKitPlugin")); registry->GetRegistrarForPlugin("LiveKitPlugin"));
MediaKitLibsWindowsVideoPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("MediaKitLibsWindowsVideoPluginCApi"));
MediaKitVideoPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("MediaKitVideoPluginCApi"));
PasteboardPluginRegisterWithRegistrar( PasteboardPluginRegisterWithRegistrar(
registry->GetRegistrarForPlugin("PasteboardPlugin")); registry->GetRegistrarForPlugin("PasteboardPlugin"));
PermissionHandlerWindowsPluginRegisterWithRegistrar( PermissionHandlerWindowsPluginRegisterWithRegistrar(
registry->GetRegistrarForPlugin("PermissionHandlerWindowsPlugin")); registry->GetRegistrarForPlugin("PermissionHandlerWindowsPlugin"));
ProtocolHandlerWindowsPluginCApiRegisterWithRegistrar( ProtocolHandlerWindowsPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("ProtocolHandlerWindowsPluginCApi")); registry->GetRegistrarForPlugin("ProtocolHandlerWindowsPluginCApi"));
ScreenBrightnessWindowsPluginRegisterWithRegistrar(
registry->GetRegistrarForPlugin("ScreenBrightnessWindowsPlugin"));
SharePlusWindowsPluginCApiRegisterWithRegistrar( SharePlusWindowsPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("SharePlusWindowsPluginCApi")); registry->GetRegistrarForPlugin("SharePlusWindowsPluginCApi"));
UrlLauncherWindowsRegisterWithRegistrar( UrlLauncherWindowsRegisterWithRegistrar(

View File

@ -12,18 +12,14 @@ list(APPEND FLUTTER_PLUGIN_LIST
flutter_webrtc flutter_webrtc
gal gal
livekit_client livekit_client
media_kit_libs_windows_video
media_kit_video
pasteboard pasteboard
permission_handler_windows permission_handler_windows
protocol_handler_windows protocol_handler_windows
screen_brightness_windows
share_plus share_plus
url_launcher_windows url_launcher_windows
) )
list(APPEND FLUTTER_FFI_PLUGIN_LIST list(APPEND FLUTTER_FFI_PLUGIN_LIST
media_kit_native_event_loop
) )
set(PLUGIN_BUNDLED_LIBRARIES) set(PLUGIN_BUNDLED_LIBRARIES)