feat(mobile): pinch to zoom on asset grid (#2905)

This commit is contained in:
Fynn Petersen-Frey 2023-06-22 04:13:23 +02:00 committed by GitHub
parent 2c924e4c1c
commit 7f44d508dc
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23

View file

@ -1,3 +1,6 @@
import 'dart:math';
import 'package:flutter/gestures.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
@ -51,6 +54,12 @@ class ImmichAssetGrid extends HookConsumerWidget {
final enableHeroAnimations = useState(false); final enableHeroAnimations = useState(false);
final transitionDuration = ModalRoute.of(context)?.transitionDuration; final transitionDuration = ModalRoute.of(context)?.transitionDuration;
final perRow = useState(
assetsPerRow ?? settings.getSetting(AppSettingsEnum.tilesPerRow)!,
);
final scaleFactor = useState(7.0 - perRow.value);
final baseScaleFactor = useState(7.0 - perRow.value);
useEffect( useEffect(
() { () {
// Wait for transition to complete, then re-enable // Wait for transition to complete, then re-enable
@ -80,22 +89,43 @@ class ImmichAssetGrid extends HookConsumerWidget {
onWillPop: onWillPop, onWillPop: onWillPop,
child: HeroMode( child: HeroMode(
enabled: enableHeroAnimations.value, enabled: enableHeroAnimations.value,
child: ImmichAssetGridView( child: RawGestureDetector(
onRefresh: onRefresh, gestures: {
assetsPerRow: assetsPerRow ?? CustomScaleGestureRecognizer:
settings.getSetting(AppSettingsEnum.tilesPerRow), GestureRecognizerFactoryWithHandlers<
listener: listener, CustomScaleGestureRecognizer>(
showStorageIndicator: showStorageIndicator ?? () => CustomScaleGestureRecognizer(),
settings.getSetting(AppSettingsEnum.storageIndicator), (CustomScaleGestureRecognizer scale) {
renderList: renderList, scale.onStart = (details) {
margin: margin, baseScaleFactor.value = scaleFactor.value;
selectionActive: selectionActive, };
preselectedAssets: preselectedAssets,
canDeselect: canDeselect, scale.onUpdate = (details) {
dynamicLayout: dynamicLayout ?? scaleFactor.value =
settings.getSetting(AppSettingsEnum.dynamicLayout), max(min(5.0, baseScaleFactor.value * details.scale), 1.0);
showMultiSelectIndicator: showMultiSelectIndicator, if (7 - scaleFactor.value.toInt() != perRow.value) {
visibleItemsListener: visibleItemsListener, perRow.value = 7 - scaleFactor.value.toInt();
}
};
scale.onEnd = (details) {};
})
},
child: ImmichAssetGridView(
onRefresh: onRefresh,
assetsPerRow: perRow.value,
listener: listener,
showStorageIndicator: showStorageIndicator ??
settings.getSetting(AppSettingsEnum.storageIndicator),
renderList: renderList,
margin: margin,
selectionActive: selectionActive,
preselectedAssets: preselectedAssets,
canDeselect: canDeselect,
dynamicLayout: dynamicLayout ??
settings.getSetting(AppSettingsEnum.dynamicLayout),
showMultiSelectIndicator: showMultiSelectIndicator,
visibleItemsListener: visibleItemsListener,
),
), ),
), ),
); );
@ -113,3 +143,11 @@ class ImmichAssetGrid extends HookConsumerWidget {
); );
} }
} }
/// accepts a gesture even though it should reject it (because child won)
class CustomScaleGestureRecognizer extends ScaleGestureRecognizer {
@override
void rejectGesture(int pointer) {
acceptGesture(pointer);
}
}