♿ Share post as image on web
This commit is contained in:
parent
a6b17f2c05
commit
1abc65f8fa
@ -484,5 +484,6 @@
|
|||||||
"authMaximumAuthStepsDesc": "The maximum number of authentication steps when logging in, higher value is more secure, lower value is more convenient; default is 2",
|
"authMaximumAuthStepsDesc": "The maximum number of authentication steps when logging in, higher value is more secure, lower value is more convenient; default is 2",
|
||||||
"auditLog": "Audit log",
|
"auditLog": "Audit log",
|
||||||
"shareImage": "Share as image",
|
"shareImage": "Share as image",
|
||||||
"shareImageFooter": "Only on the Solar Network"
|
"shareImageFooter": "Only on the Solar Network",
|
||||||
|
"fileSavedAt": "File saved at @path"
|
||||||
}
|
}
|
||||||
|
@ -480,5 +480,6 @@
|
|||||||
"authMaximumAuthStepsDesc": "登陆时最多的验证步数,值越高则越安全,反之则会相对方便;默认设置为 2",
|
"authMaximumAuthStepsDesc": "登陆时最多的验证步数,值越高则越安全,反之则会相对方便;默认设置为 2",
|
||||||
"auditLog": "活动日志",
|
"auditLog": "活动日志",
|
||||||
"shareImage": "分享图片",
|
"shareImage": "分享图片",
|
||||||
"shareImageFooter": "上 Solar Network 看更多有趣帖子"
|
"shareImageFooter": "上 Solar Network 看更多有趣帖子",
|
||||||
|
"fileSavedAt": "文件保存于 @path"
|
||||||
}
|
}
|
||||||
|
@ -49,6 +49,7 @@ class _AttachmentListState extends State<AttachmentList> {
|
|||||||
bool _isLoading = true;
|
bool _isLoading = true;
|
||||||
bool _showMature = false;
|
bool _showMature = false;
|
||||||
|
|
||||||
|
// ignore: unused_field
|
||||||
double _aspectRatio = 1;
|
double _aspectRatio = 1;
|
||||||
|
|
||||||
List<Attachment?> _attachments = List.empty();
|
List<Attachment?> _attachments = List.empty();
|
||||||
|
@ -1,4 +1,3 @@
|
|||||||
import 'dart:io';
|
|
||||||
import 'dart:math';
|
import 'dart:math';
|
||||||
|
|
||||||
import 'package:file_saver/file_saver.dart';
|
import 'package:file_saver/file_saver.dart';
|
||||||
@ -7,9 +6,6 @@ import 'package:flutter/material.dart';
|
|||||||
import 'package:flutter_animate/flutter_animate.dart';
|
import 'package:flutter_animate/flutter_animate.dart';
|
||||||
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:intl/intl.dart';
|
|
||||||
import 'package:path/path.dart' as path;
|
|
||||||
import 'package:path_provider/path_provider.dart';
|
|
||||||
import 'package:screenshot/screenshot.dart';
|
import 'package:screenshot/screenshot.dart';
|
||||||
import 'package:share_plus/share_plus.dart';
|
import 'package:share_plus/share_plus.dart';
|
||||||
import 'package:solian/exts.dart';
|
import 'package:solian/exts.dart';
|
||||||
@ -113,16 +109,17 @@ class _PostActionState extends State<PostAction> {
|
|||||||
maxHeight: double.infinity,
|
maxHeight: double.infinity,
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
final directory = await getApplicationDocumentsDirectory();
|
|
||||||
final imageFile = await File(
|
final filename = 'share_post#${widget.item.id}';
|
||||||
'${directory.path}/share_image_${DateFormat('yyyy-MM-dd-HH-mm-ss').format(DateTime.now())}.png',
|
|
||||||
).create();
|
|
||||||
await imageFile.writeAsBytes(image);
|
|
||||||
|
|
||||||
if (PlatformInfo.isAndroid || PlatformInfo.isIOS) {
|
if (PlatformInfo.isAndroid || PlatformInfo.isIOS) {
|
||||||
final box = context.findRenderObject() as RenderBox?;
|
final box = context.findRenderObject() as RenderBox?;
|
||||||
|
|
||||||
final file = XFile(imageFile.path);
|
final file = XFile.fromData(
|
||||||
|
image,
|
||||||
|
mimeType: 'image/png',
|
||||||
|
name: filename,
|
||||||
|
);
|
||||||
await Share.shareXFiles(
|
await Share.shareXFiles(
|
||||||
[file],
|
[file],
|
||||||
subject: 'postShareSubject'.trParams({
|
subject: 'postShareSubject'.trParams({
|
||||||
@ -132,15 +129,14 @@ class _PostActionState extends State<PostAction> {
|
|||||||
sharePositionOrigin: box!.localToGlobal(Offset.zero) & box.size,
|
sharePositionOrigin: box!.localToGlobal(Offset.zero) & box.size,
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
await FileSaver.instance.saveAs(
|
final filepath = await FileSaver.instance.saveFile(
|
||||||
name: path.basename(imageFile.path),
|
name: filename,
|
||||||
ext: path.extension(imageFile.path),
|
ext: 'png',
|
||||||
mimeType: MimeType.png,
|
mimeType: MimeType.png,
|
||||||
file: imageFile,
|
bytes: image,
|
||||||
);
|
);
|
||||||
|
context.showSnackbar('fileSavedAt'.trParams({'path': filepath}));
|
||||||
}
|
}
|
||||||
|
|
||||||
await imageFile.delete();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import 'package:flutter/gestures.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:infinite_scroll_pagination/infinite_scroll_pagination.dart';
|
import 'package:infinite_scroll_pagination/infinite_scroll_pagination.dart';
|
||||||
@ -73,9 +74,30 @@ class PostListEntryWidget extends StatelessWidget {
|
|||||||
required this.onUpdate,
|
required this.onUpdate,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
void _openActions(BuildContext context) {
|
||||||
|
final AuthProvider auth = Get.find();
|
||||||
|
if (auth.isAuthorized.isFalse) return;
|
||||||
|
|
||||||
|
showModalBottomSheet(
|
||||||
|
useRootNavigator: true,
|
||||||
|
context: context,
|
||||||
|
builder: (context) => PostAction(item: item),
|
||||||
|
).then((value) {
|
||||||
|
if (value is Future) {
|
||||||
|
value.then((_) {
|
||||||
|
onUpdate();
|
||||||
|
});
|
||||||
|
} else if (value != null) {
|
||||||
|
onUpdate();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return GestureDetector(
|
return TapRegion(
|
||||||
|
child: GestureDetector(
|
||||||
|
onLongPress: () => _openActions(context),
|
||||||
child: PostItem(
|
child: PostItem(
|
||||||
key: Key('p${item.id}'),
|
key: Key('p${item.id}'),
|
||||||
item: item,
|
item: item,
|
||||||
@ -100,23 +122,11 @@ class PostListEntryWidget extends StatelessWidget {
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
).paddingSymmetric(vertical: 8),
|
).paddingSymmetric(vertical: 8),
|
||||||
onLongPress: () {
|
),
|
||||||
final AuthProvider auth = Get.find();
|
onTapInside: (event) {
|
||||||
if (auth.isAuthorized.isFalse) return;
|
if (event.buttons == kSecondaryMouseButton) {
|
||||||
|
_openActions(context);
|
||||||
showModalBottomSheet(
|
|
||||||
useRootNavigator: true,
|
|
||||||
context: context,
|
|
||||||
builder: (context) => PostAction(item: item),
|
|
||||||
).then((value) {
|
|
||||||
if (value is Future) {
|
|
||||||
value.then((_) {
|
|
||||||
onUpdate();
|
|
||||||
});
|
|
||||||
} else if (value != null) {
|
|
||||||
onUpdate();
|
|
||||||
}
|
}
|
||||||
});
|
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -6,6 +6,8 @@ PODS:
|
|||||||
- FlutterMacOS
|
- FlutterMacOS
|
||||||
- device_info_plus (0.0.1):
|
- device_info_plus (0.0.1):
|
||||||
- FlutterMacOS
|
- FlutterMacOS
|
||||||
|
- file_saver (0.0.1):
|
||||||
|
- FlutterMacOS
|
||||||
- file_selector_macos (0.0.1):
|
- file_selector_macos (0.0.1):
|
||||||
- FlutterMacOS
|
- FlutterMacOS
|
||||||
- Firebase/Analytics (11.2.0):
|
- Firebase/Analytics (11.2.0):
|
||||||
@ -230,6 +232,7 @@ DEPENDENCIES:
|
|||||||
- connectivity_plus (from `Flutter/ephemeral/.symlinks/plugins/connectivity_plus/darwin`)
|
- connectivity_plus (from `Flutter/ephemeral/.symlinks/plugins/connectivity_plus/darwin`)
|
||||||
- desktop_drop (from `Flutter/ephemeral/.symlinks/plugins/desktop_drop/macos`)
|
- desktop_drop (from `Flutter/ephemeral/.symlinks/plugins/desktop_drop/macos`)
|
||||||
- device_info_plus (from `Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos`)
|
- device_info_plus (from `Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos`)
|
||||||
|
- file_saver (from `Flutter/ephemeral/.symlinks/plugins/file_saver/macos`)
|
||||||
- file_selector_macos (from `Flutter/ephemeral/.symlinks/plugins/file_selector_macos/macos`)
|
- file_selector_macos (from `Flutter/ephemeral/.symlinks/plugins/file_selector_macos/macos`)
|
||||||
- firebase_analytics (from `Flutter/ephemeral/.symlinks/plugins/firebase_analytics/macos`)
|
- firebase_analytics (from `Flutter/ephemeral/.symlinks/plugins/firebase_analytics/macos`)
|
||||||
- firebase_core (from `Flutter/ephemeral/.symlinks/plugins/firebase_core/macos`)
|
- firebase_core (from `Flutter/ephemeral/.symlinks/plugins/firebase_core/macos`)
|
||||||
@ -288,6 +291,8 @@ EXTERNAL SOURCES:
|
|||||||
:path: Flutter/ephemeral/.symlinks/plugins/desktop_drop/macos
|
:path: Flutter/ephemeral/.symlinks/plugins/desktop_drop/macos
|
||||||
device_info_plus:
|
device_info_plus:
|
||||||
:path: Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos
|
:path: Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos
|
||||||
|
file_saver:
|
||||||
|
:path: Flutter/ephemeral/.symlinks/plugins/file_saver/macos
|
||||||
file_selector_macos:
|
file_selector_macos:
|
||||||
:path: Flutter/ephemeral/.symlinks/plugins/file_selector_macos/macos
|
:path: Flutter/ephemeral/.symlinks/plugins/file_selector_macos/macos
|
||||||
firebase_analytics:
|
firebase_analytics:
|
||||||
@ -349,6 +354,7 @@ SPEC CHECKSUMS:
|
|||||||
connectivity_plus: ddd7f30999e1faaef5967c23d5b6d503d10434db
|
connectivity_plus: ddd7f30999e1faaef5967c23d5b6d503d10434db
|
||||||
desktop_drop: 69eeff437544aa619c8db7f4481b3a65f7696898
|
desktop_drop: 69eeff437544aa619c8db7f4481b3a65f7696898
|
||||||
device_info_plus: f1aae8670672f75c4c8850ecbe0b2ddef62b0a22
|
device_info_plus: f1aae8670672f75c4c8850ecbe0b2ddef62b0a22
|
||||||
|
file_saver: 44e6fbf666677faf097302460e214e977fdd977b
|
||||||
file_selector_macos: cc3858c981fe6889f364731200d6232dac1d812d
|
file_selector_macos: cc3858c981fe6889f364731200d6232dac1d812d
|
||||||
Firebase: 98e6bf5278170668a7983e12971a66b2cd57fc8c
|
Firebase: 98e6bf5278170668a7983e12971a66b2cd57fc8c
|
||||||
firebase_analytics: 30ff72f6d4847ff0b479d8edd92fc8582e719072
|
firebase_analytics: 30ff72f6d4847ff0b479d8edd92fc8582e719072
|
||||||
|
@ -2,7 +2,7 @@ name: solian
|
|||||||
description: "The Solar Network App"
|
description: "The Solar Network App"
|
||||||
publish_to: "none"
|
publish_to: "none"
|
||||||
|
|
||||||
version: 1.3.7+12
|
version: 1.3.8+12
|
||||||
|
|
||||||
environment:
|
environment:
|
||||||
sdk: ">=3.3.4 <4.0.0"
|
sdk: ">=3.3.4 <4.0.0"
|
||||||
|
@ -111,14 +111,13 @@
|
|||||||
<meta content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" name="viewport">
|
<meta content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" name="viewport">
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body oncontextmenu="return false;">
|
||||||
<picture id="splash">
|
<picture id="splash">
|
||||||
<source srcset="splash/img/light-1x.png 1x, splash/img/light-2x.png 2x, splash/img/light-3x.png 3x, splash/img/light-4x.png 4x" media="(prefers-color-scheme: light)">
|
<source srcset="splash/img/light-1x.png 1x, splash/img/light-2x.png 2x, splash/img/light-3x.png 3x, splash/img/light-4x.png 4x" media="(prefers-color-scheme: light)">
|
||||||
<source srcset="splash/img/dark-1x.png 1x, splash/img/dark-2x.png 2x, splash/img/dark-3x.png 3x, splash/img/dark-4x.png 4x" media="(prefers-color-scheme: dark)">
|
<source srcset="splash/img/dark-1x.png 1x, splash/img/dark-2x.png 2x, splash/img/dark-3x.png 3x, splash/img/dark-4x.png 4x" media="(prefers-color-scheme: dark)">
|
||||||
<img class="center" aria-hidden="true" src="splash/img/light-1x.png" alt="">
|
<img class="center" aria-hidden="true" src="splash/img/light-1x.png" alt="">
|
||||||
</picture>
|
</picture>
|
||||||
|
|
||||||
|
|
||||||
<script src="flutter_bootstrap.js" async=""></script>
|
<script src="flutter_bootstrap.js" async=""></script>
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user