Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement HeroProperties #177

Merged
merged 2 commits into from Sep 3, 2019
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ Widget build(BuildContext context) {
return PhotoViewGalleryPageOptions(
imageProvider: AssetImage(widget.galleryItems[index].image),
initialScale: PhotoViewComputedScale.contained * 0.8,
heroTag: galleryItems[index].id,
heroAttributes: HeroAttributes(tag: galleryItems[index].id),
);
},
itemCount: galleryItems.length,
Expand Down
4 changes: 2 additions & 2 deletions example/lib/screens/examples/gallery/gallery_example.dart
Original file line number Diff line number Diff line change
Expand Up @@ -148,14 +148,14 @@ class _GalleryPhotoViewWrapperState extends State<GalleryPhotoViewWrapper> {
initialScale: PhotoViewComputedScale.contained,
minScale: PhotoViewComputedScale.contained * (0.5 + index / 10),
maxScale: PhotoViewComputedScale.covered * 1.1,
heroTag: item.id,
heroAttributes: HeroAttributes(tag: item.id),
)
: PhotoViewGalleryPageOptions(
imageProvider: AssetImage(item.resource),
initialScale: PhotoViewComputedScale.contained,
minScale: PhotoViewComputedScale.contained * (0.5 + index / 10),
maxScale: PhotoViewComputedScale.covered * 1.1,
heroTag: item.id,
heroAttributes: HeroAttributes(tag: item.id),
);
}
}
2 changes: 1 addition & 1 deletion example/lib/screens/examples/hero_example.dart
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ class HeroPhotoViewWrapper extends StatelessWidget {
backgroundDecoration: backgroundDecoration,
minScale: minScale,
maxScale: maxScale,
heroTag: "someTag",
heroAttributes: const HeroAttributes(tag: "someTag"),
));
}
}
43 changes: 21 additions & 22 deletions lib/photo_view.dart
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import 'src/photo_view_scale_state.dart';
import 'src/photo_view_typedefs.dart';
import 'src/photo_view_utils.dart';

export 'src/hero_attributes.dart';
export 'src/photo_view_computed_scale.dart';
export 'src/photo_view_controller.dart';
export 'src/photo_view_scale_state.dart';
Expand All @@ -30,10 +31,12 @@ export 'src/photo_view_typedefs.dart';
/// backgroundDecoration: BoxDecoration(color: Colors.black),
/// gaplessPlayback: false,
/// customSize: MediaQuery.of(context).size,
/// heroTag: "someTag",
/// heroAttributes: const HeroAttributes(
/// tag: "someTag",
/// transitionOnUserGestures: true,
/// ),
/// scaleStateChangedCallback: this.onScaleStateChanged,
/// enableRotation: true,
/// transitionOnUserGestures: true,
/// controller: controller,
/// minScale: PhotoViewComputedScale.contained * 0.8,
/// maxScale: PhotoViewComputedScale.covered * 1.8,
Expand All @@ -58,10 +61,12 @@ export 'src/photo_view_typedefs.dart';
/// backgroundDecoration: BoxDecoration(color: Colors.black),
/// gaplessPlayback: false,
/// customSize: MediaQuery.of(context).size,
/// heroTag: "someTag",
/// heroAttributes: const HeroAttributes(
/// tag: "someTag",
/// transitionOnUserGestures: true,
/// ),
/// scaleStateChangedCallback: this.onScaleStateChanged,
/// enableRotation: true,
/// transitionOnUserGestures: true,
/// controller: controller,
/// minScale: PhotoViewComputedScale.contained * 0.8,
/// maxScale: PhotoViewComputedScale.covered * 1.8,
Expand Down Expand Up @@ -91,8 +96,9 @@ export 'src/photo_view_typedefs.dart';
/// (`true`), or briefly show nothing (`false`), when the [imageProvider]
/// changes.By default it's set to `false`.
///
/// To use within an hero animation, specify [heroTag]. When [heroTag] is
/// specified, the image provider retrieval process should be sync.
/// To use within an hero animation, specify [heroAttributes]. When
/// [heroAttributes] is specified, the image provider retrieval process should
/// be sync.
///
/// Sample using hero animation:
/// ```
Expand All @@ -109,7 +115,7 @@ export 'src/photo_view_typedefs.dart';
/// ...
/// child: PhotoView(
/// imageProvider: AssetImage("assets/large-image.jpg"),
/// heroTag: "someTag",
/// heroAttributes: const HeroAttributes(tag: "someTag"),
/// )
/// ```
///
Expand Down Expand Up @@ -223,10 +229,9 @@ class PhotoView extends StatefulWidget {
this.backgroundDecoration,
this.gaplessPlayback = false,
this.customSize,
this.heroTag,
this.heroAttributes,
this.scaleStateChangedCallback,
this.enableRotation = false,
this.transitionOnUserGestures = false,
this.controller,
this.scaleStateController,
this.maxScale,
Expand All @@ -252,10 +257,9 @@ class PhotoView extends StatefulWidget {
@required this.childSize,
this.backgroundDecoration,
this.customSize,
this.heroTag,
this.heroAttributes,
this.scaleStateChangedCallback,
this.enableRotation = false,
this.transitionOnUserGestures = false,
this.controller,
this.scaleStateController,
this.maxScale,
Expand Down Expand Up @@ -290,8 +294,9 @@ class PhotoView extends StatefulWidget {
/// by default it is `MediaQuery.of(context).size`.
final Size customSize;

/// Assists the activation of a hero animation within [PhotoView]
final Object heroTag;
/// Attributes that are going to be passed to [PhotoViewImageWrapper]'s
/// [Hero]. Leave this property undefined if you don't want a hero animation.
final HeroAttributes heroAttributes;

/// A [Function] to be called whenever the scaleState changes, this heappens when the user double taps the content ou start to pinch-in.
final PhotoViewScaleStateChangedCallback scaleStateChangedCallback;
Expand All @@ -305,11 +310,6 @@ class PhotoView extends StatefulWidget {
/// The size of the custom [child]. [PhotoView] uses this value to compute the relation between the child and the container's size to calculate the scale value.
final Size childSize;

/// The value specified to homonimous option givento to [Hero]. Sets [Hero.transitionOnUserGestures] in the internal hero.
///
/// Should only be set when [PhotoView.heroTag] is set
final bool transitionOnUserGestures;

/// Defines the maximum size in which the image will be allowed to assume, it
/// is proportional to the original image size. Can be either a double (absolute value) or a
/// [PhotoViewComputedScale], that can be multiplied by a double
Expand Down Expand Up @@ -485,7 +485,7 @@ class _PhotoViewState extends State<PhotoView>
customChild: widget.child,
backgroundDecoration: widget.backgroundDecoration,
enableRotation: widget.enableRotation,
heroTag: widget.heroTag,
heroAttributes: widget.heroAttributes,
delegate: PhotoViewControllerDelegate(
controller: _controller,
scaleStateController: _scaleStateController,
Expand All @@ -505,7 +505,7 @@ class _PhotoViewState extends State<PhotoView>
}

Widget _buildImage(BuildContext context) {
return widget.heroTag == null
return widget.heroAttributes == null
? _buildWithFuture(context)
: _buildSync(context);
}
Expand Down Expand Up @@ -535,8 +535,7 @@ class _PhotoViewState extends State<PhotoView>
backgroundDecoration: widget.backgroundDecoration,
gaplessPlayback: widget.gaplessPlayback,
enableRotation: widget.enableRotation,
heroTag: widget.heroTag,
transitionOnUserGestures: widget.transitionOnUserGestures,
heroAttributes: widget.heroAttributes,
delegate: PhotoViewControllerDelegate(
basePosition: widget.basePosition ?? Alignment.center,
controller: _controller,
Expand Down
30 changes: 12 additions & 18 deletions lib/photo_view_gallery.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ library photo_view_gallery;
import 'package:flutter/widgets.dart';

import 'photo_view.dart';
import 'src/hero_attributes.dart';
import 'src/photo_view_controller.dart';
import 'src/photo_view_image_wrapper.dart';
import 'src/photo_view_scale_state.dart';
Expand All @@ -19,26 +20,26 @@ typedef PhotoViewGalleryBuilder = PhotoViewGalleryPageOptions Function(
///
/// Some of [PhotoView] consturctor options are passed direct to [PhotoViewGallery] cosntructor. Those options will affect the gallery in a whole.
///
/// Some of the options may be defined to each image individually, such as `initialScale` or `heroTag`. Those must be passed via each [PhotoViewGalleryPageOptions].
/// Some of the options may be defined to each image individually, such as `initialScale` or `heroAttributes`. Those must be passed via each [PhotoViewGalleryPageOptions].
///
/// Example of usage as a list of options:
/// ```
/// PhotoViewGallery(
/// pageOptions: <PhotoViewGalleryPageOptions>[
/// PhotoViewGalleryPageOptions(
/// imageProvider: AssetImage("assets/gallery1.jpg"),
/// heroTag: "tag1",
/// heroAttributes: const HeroAttributes(tag: "tag1"),
/// ),
/// PhotoViewGalleryPageOptions(
/// imageProvider: AssetImage("assets/gallery2.jpg"),
/// heroTag: "tag2",
/// heroAttributes: const HeroAttributes(tag: "tag2"),
/// maxScale: PhotoViewComputedScale.contained * 0.3
/// ),
/// PhotoViewGalleryPageOptions(
/// imageProvider: AssetImage("assets/gallery3.jpg"),
/// minScale: PhotoViewComputedScale.contained * 0.8,
/// maxScale: PhotoViewComputedScale.covered * 1.1,
/// heroTag: "tag3",
/// heroAttributes: const HeroAttributes(tag: "tag3"),
/// ),
/// ],
/// loadingChild: widget.loadingChild,
Expand All @@ -58,7 +59,7 @@ typedef PhotoViewGalleryBuilder = PhotoViewGalleryPageOptions Function(
/// initialScale: PhotoViewComputedScale.contained * 0.8,
/// minScale: PhotoViewComputedScale.contained * 0.8,
/// maxScale: PhotoViewComputedScale.covered * 1.1,
/// heroTag: galleryItems[index].id,
/// heroAttributes: HeroAttributes(tag: galleryItems[index].id),
/// );
/// },
/// itemCount: galleryItems.length,
Expand All @@ -82,7 +83,6 @@ class PhotoViewGallery extends StatefulWidget {
this.onPageChanged,
this.scaleStateChangedCallback,
this.enableRotation = false,
this.transitionOnUserGestures = false,
this.scrollPhysics,
this.scrollDirection = Axis.horizontal,
}) : _isBuilder = false,
Expand All @@ -107,7 +107,6 @@ class PhotoViewGallery extends StatefulWidget {
this.onPageChanged,
this.scaleStateChangedCallback,
this.enableRotation = false,
this.transitionOnUserGestures = false,
this.scrollPhysics,
this.scrollDirection = Axis.horizontal,
}) : _isBuilder = true,
Expand Down Expand Up @@ -155,9 +154,6 @@ class PhotoViewGallery extends StatefulWidget {
/// Mirror to [PhotoView.enableRotation]
final bool enableRotation;

/// Mirror to [PhotoView.transitionOnUserGestures]
final bool transitionOnUserGestures;

Copy link
Author

@ghost ghost Aug 29, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems like this is a negative side effect of this PR. Previously, the user could define transitionOnUserGestures to all PhotoViewGallery pages, but now they must define it to each page. However, I think most people use PhotoViewGallery.builder(), so they won't need to define transitionOnUserGestures more than once, anyway.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, not that bad, but since it is a breaking change, this is gonna require a major version, thanks.

/// The axis along which the [PageView] scrolls. Mirror to [PageView.scrollDirection]
final Axis scrollDirection;

Expand Down Expand Up @@ -230,10 +226,9 @@ class _PhotoViewGalleryState extends State<PhotoViewGallery> {
controller: pageOption.controller,
scaleStateController: pageOption.scaleStateController,
customSize: widget.customSize,
heroTag: pageOption.heroTag,
heroAttributes: pageOption.heroAttributes,
scaleStateChangedCallback: scaleStateChangedCallback,
enableRotation: widget.enableRotation,
transitionOnUserGestures: widget.transitionOnUserGestures,
initialScale: pageOption.initialScale,
minScale: pageOption.minScale,
maxScale: pageOption.maxScale,
Expand All @@ -250,10 +245,9 @@ class _PhotoViewGalleryState extends State<PhotoViewGallery> {
scaleStateController: pageOption.scaleStateController,
gaplessPlayback: widget.gaplessPlayback,
customSize: widget.customSize,
heroTag: pageOption.heroTag,
heroAttributes: pageOption.heroAttributes,
scaleStateChangedCallback: scaleStateChangedCallback,
enableRotation: widget.enableRotation,
transitionOnUserGestures: widget.transitionOnUserGestures,
initialScale: pageOption.initialScale,
minScale: pageOption.minScale,
maxScale: pageOption.maxScale,
Expand Down Expand Up @@ -284,7 +278,7 @@ class PhotoViewGalleryPageOptions {
PhotoViewGalleryPageOptions(
{Key key,
@required this.imageProvider,
this.heroTag,
this.heroAttributes,
this.minScale,
this.maxScale,
this.initialScale,
Expand All @@ -301,7 +295,7 @@ class PhotoViewGalleryPageOptions {
PhotoViewGalleryPageOptions.customChild(
{@required this.child,
@required this.childSize,
this.heroTag,
this.heroAttributes,
this.minScale,
this.maxScale,
this.initialScale,
Expand All @@ -318,8 +312,8 @@ class PhotoViewGalleryPageOptions {
/// Mirror to [PhotoView.imageProvider]
final ImageProvider imageProvider;

/// Mirror to [PhotoView.heroTag
final Object heroTag;
/// Mirror to [PhotoView.heroAttributes]
final HeroAttributes heroAttributes;

/// Mirror to [PhotoView.minScale]
final dynamic minScale;
Expand Down
30 changes: 30 additions & 0 deletions lib/src/hero_attributes.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
import 'package:flutter/material.dart';

import 'photo_view_image_wrapper.dart';

/// Data class that holds the attributes that are going to be passed to
/// [PhotoViewImageWrapper]'s [Hero].
class HeroAttributes {
const HeroAttributes({
@required this.tag,
this.createRectTween,
this.flightShuttleBuilder,
this.placeholderBuilder,
this.transitionOnUserGestures = false,
}) : assert(tag != null);

/// Mirror to [Hero.tag]
final Object tag;

/// Mirror to [Hero.createRectTween]
final CreateRectTween createRectTween;

/// Mirror to [Hero.flightShuttleBuilder]
final HeroFlightShuttleBuilder flightShuttleBuilder;

/// Mirror to [Hero.placeholderBuilder]
final HeroPlaceholderBuilder placeholderBuilder;

/// Mirror to [Hero.transitionOnUserGestures]
final bool transitionOnUserGestures;
}
Loading