💄 Optimize file viewer

This commit is contained in:
2025-07-30 00:29:26 +08:00
parent 97226ae96b
commit e4bb031138
3 changed files with 46 additions and 76 deletions

View File

@@ -122,7 +122,7 @@ class WebSocketService {
void _scheduleHeartbeat() {
_heartbeatTimer?.cancel();
_heartbeatTimer = Timer.periodic(const Duration(seconds: 3), (_) {
_heartbeatTimer = Timer.periodic(const Duration(seconds: 60), (_) {
_beatTheHeart();
});
}

View File

@@ -30,7 +30,7 @@ class CloudFileList extends HookConsumerWidget {
const CloudFileList({
super.key,
required this.files,
this.maxHeight = 360,
this.maxHeight = 560,
this.maxWidth = double.infinity,
this.minWidth,
this.disableZoomIn = false,
@@ -98,53 +98,8 @@ class CloudFileList extends HookConsumerWidget {
).padding(horizontal: 3);
}
final allImages =
!files.any(
(e) => e.mimeType == null || !e.mimeType!.startsWith('image'),
);
if (allImages) {
return ConstrainedBox(
constraints: BoxConstraints(maxHeight: maxHeight, minWidth: maxWidth),
child: AspectRatio(
aspectRatio: calculateAspectRatio(),
child: CarouselView(
itemExtent: math.min(
MediaQuery.of(context).size.width * 0.85,
maxWidth * 0.85,
),
itemSnapping: true,
shape: RoundedRectangleBorder(
borderRadius: const BorderRadius.all(Radius.circular(16)),
),
children: [
for (var i = 0; i < files.length; i++)
_CloudFileListEntry(
file: files[i],
heroTag: heroTags[i],
isImage: files[i].mimeType?.startsWith('image') ?? false,
disableZoomIn: disableZoomIn,
fit: BoxFit.cover,
),
],
onTap: (i) {
if (!(files[i].mimeType?.startsWith('image') ?? false)) {
return;
}
if (!disableZoomIn) {
context.pushTransparentRoute(
CloudFileZoomIn(item: files[i], heroTag: heroTags[i]),
rootNavigator: true,
);
}
},
),
),
);
}
return ConstrainedBox(
constraints: BoxConstraints(maxHeight: maxHeight, minWidth: maxWidth),
constraints: BoxConstraints(maxHeight: maxHeight),
child: AspectRatio(
aspectRatio: calculateAspectRatio(),
child: ListView.separated(
@@ -152,26 +107,49 @@ class CloudFileList extends HookConsumerWidget {
itemCount: files.length,
padding: EdgeInsets.symmetric(horizontal: 3),
itemBuilder: (context, index) {
return ClipRRect(
borderRadius: const BorderRadius.all(Radius.circular(16)),
child: _CloudFileListEntry(
file: files[index],
heroTag: heroTags[index],
isImage: files[index].mimeType?.startsWith('image') ?? false,
disableZoomIn: disableZoomIn,
onTap: () {
if (!(files[index].mimeType?.startsWith('image') ?? false)) {
return;
}
if (!disableZoomIn) {
context.pushTransparentRoute(
CloudFileZoomIn(
item: files[index],
heroTag: heroTags[index],
),
);
}
},
return AspectRatio(
aspectRatio:
files[index].fileMeta?['ratio'] is num
? files[index].fileMeta!['ratio'].toDouble()
: 1.0,
child: Stack(
children: [
ClipRRect(
borderRadius: const BorderRadius.all(Radius.circular(16)),
child: _CloudFileListEntry(
file: files[index],
heroTag: heroTags[index],
isImage:
files[index].mimeType?.startsWith('image') ?? false,
disableZoomIn: disableZoomIn,
onTap: () {
if (!(files[index].mimeType?.startsWith('image') ??
false)) {
return;
}
if (!disableZoomIn) {
context.pushTransparentRoute(
CloudFileZoomIn(
item: files[index],
heroTag: heroTags[index],
),
);
}
},
),
),
Positioned(
bottom: 12,
left: 16,
child: Text('${index + 1}/${files.length}')
.textColor(Colors.white)
.textShadow(
color: Colors.black54,
offset: Offset(1, 1),
blurRadius: 3,
),
),
],
),
);
},

View File

@@ -174,10 +174,6 @@ class PostItem extends HookConsumerWidget {
MediaQuery.of(context).size.width,
kWideScreenWidth,
),
minWidth: math.min(
MediaQuery.of(context).size.width,
kWideScreenWidth,
),
),
if (item.meta?['embeds'] != null)
...((item.meta!['embeds'] as List<dynamic>)
@@ -410,10 +406,6 @@ class PostItem extends HookConsumerWidget {
MediaQuery.of(context).size.width * 0.85,
kWideScreenWidth - 160,
),
minWidth: math.min(
MediaQuery.of(context).size.width * 0.9,
kWideScreenWidth - 160,
),
),
// Render embed links
if (item.meta?['embeds'] != null)