Skip to content

Commit

Permalink
Merge pull request LanarsInc#44 from LanarsInc/develop
Browse files Browse the repository at this point in the history
Release 3.0.0
  • Loading branch information
vizhan-lanars authored Nov 15, 2022
2 parents 27cf585 + b82696e commit f55db56
Show file tree
Hide file tree
Showing 6 changed files with 192 additions and 173 deletions.
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,12 @@
## 3.0.0 - 15.11.2022
* **Breaking change**. Remove BuildContext in favor of OverlayState
* **Breaking change**. Add multi direction swipe for DismissType.onSwipe by [mofadillah](https://github.com/mofadillah) 'dismissDirection' change type from DismissDirection to List<DismissDirection>
* Enhancement: Add TextAlign parameter to CustomSnackBar widget by [ayoubrajabi](https://github.com/ayoubrajabi)
* Bugfix [#35](https://github.com/LanarsInc/top-snackbar-flutter/issues/35) Snackbar stuck on status bar

## 2.1.1 - 07.07.2022
* Fix dismissible widget dismissed error

## 2.1.0 - 04.07.2022
* Enhancement: Add `safeAreaValues` parameter by [LeGoffMael](https://github.com/LeGoffMael)
* Enhancement: Make `top_snackbar_flutter` dismissible by swipe with parameters `dismissType` and `dismissDirection` by [LeGoffMael](https://github.com/LeGoffMael)
Expand Down
75 changes: 39 additions & 36 deletions example/lib/main.dart
Original file line number Diff line number Diff line change
Expand Up @@ -4,23 +4,23 @@ import 'package:top_snackbar_flutter/tap_bounce_container.dart';
import 'package:top_snackbar_flutter/top_snack_bar.dart';

void main() {
runApp(MyApp());
runApp(const MyApp());
}

class MyApp extends StatefulWidget {
const MyApp({Key key}) : super(key: key);

@override
_MyAppState createState() => _MyAppState();
MyAppState createState() => MyAppState();
}

class _MyAppState extends State<MyApp> {
class MyAppState extends State<MyApp> {
AnimationController localAnimationController;

@override
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData(
primaryColor: Colors.orangeAccent,
),
theme: ThemeData(primaryColor: Colors.orangeAccent),
home: Builder(
builder: (BuildContext context) {
return Scaffold(
Expand All @@ -32,74 +32,77 @@ class _MyAppState extends State<MyApp> {
TapBounceContainer(
onTap: () {
showTopSnackBar(
context,
CustomSnackBar.info(
Overlay.of(context),
const CustomSnackBar.info(
message:
"There is some information. You need to do something with that",
'There is some information. You need to do something with that',
),
);
},
child: buildButton(context, "Show info"),
child: buildButton(context, 'Show info'),
),
SizedBox(height: 24),
const SizedBox(height: 24),
TapBounceContainer(
onTap: () {
showTopSnackBar(
context,
CustomSnackBar.success(
Overlay.of(context),
const CustomSnackBar.success(
message:
"Good job, your release is successful. Have a nice day",
'Good job, your release is successful. Have a nice day',
),
);
},
child: buildButton(context, "Show success"),
child: buildButton(context, 'Show success'),
),
SizedBox(height: 24),
const SizedBox(height: 24),
TapBounceContainer(
onTap: () {
showTopSnackBar(
context,
CustomSnackBar.error(
Overlay.of(context),
const CustomSnackBar.error(
message:
"Something went wrong. Please check your credentials and try again",
'Something went wrong. Please check your credentials and try again',
),
);
},
child: buildButton(context, "Show error"),
child: buildButton(context, 'Show error'),
),
SizedBox(height: 48),
const SizedBox(height: 48),
TapBounceContainer(
onTap: () {
showTopSnackBar(
context,
CustomSnackBar.info(
message: "Persistent SnackBar",
Overlay.of(context),
const CustomSnackBar.info(
message: 'Persistent SnackBar',
),
persistent: true,
onAnimationControllerInit: (controller) =>
localAnimationController = controller,
onAnimationControllerInit: (controller) {
localAnimationController = controller;
},
);
},
child: buildButton(context, "Show persistent SnackBar"),
child: buildButton(context, 'Show persistent SnackBar'),
),
SizedBox(height: 24),
const SizedBox(height: 24),
TapBounceContainer(
onTap: () => localAnimationController.reverse(),
child: buildButton(context, "Dismiss persistent SnackBar"),
child: buildButton(context, 'Dismiss persistent SnackBar'),
),
SizedBox(height: 24),
const SizedBox(height: 24),
TapBounceContainer(
onTap: () {
showTopSnackBar(
context,
CustomSnackBar.info(message: "Try to swipe me left"),
Overlay.of(context),
const CustomSnackBar.info(
message: 'Try to swipe me left',
),
dismissType: DismissType.onSwipe,
dismissDirection: DismissDirection.endToStart,
dismissDirection: [DismissDirection.endToStart],
);
},
child: buildButton(
context,
"Show swiped dismissible SnackBar",
'Show swiped dismissible SnackBar',
),
),
],
Expand All @@ -121,7 +124,7 @@ class _MyAppState extends State<MyApp> {
color: Colors.grey.withOpacity(0.4),
spreadRadius: 6,
blurRadius: 10,
offset: Offset(0, 3),
offset: const Offset(0, 3),
),
],
),
Expand All @@ -130,7 +133,7 @@ class _MyAppState extends State<MyApp> {
child: Center(
child: Text(
text,
style: TextStyle(
style: const TextStyle(
color: Colors.white,
fontSize: 16,
fontWeight: FontWeight.w600,
Expand Down
60 changes: 31 additions & 29 deletions lib/custom_snack_bar.dart
Original file line number Diff line number Diff line change
Expand Up @@ -4,26 +4,13 @@ import 'package:flutter/material.dart';

/// Popup widget that you can use by default to show some information
class CustomSnackBar extends StatefulWidget {
final String message;
final Widget icon;
final Color backgroundColor;
final TextStyle textStyle;
final int maxLines;
final int iconRotationAngle;
final List<BoxShadow> boxShadow;
final BorderRadius borderRadius;
final double iconPositionTop;
final double iconPositionLeft;
final EdgeInsetsGeometry messagePadding;
final double textScaleFactor;

const CustomSnackBar.success({
Key? key,
required this.message,
this.messagePadding = const EdgeInsets.symmetric(horizontal: 24),
this.icon = const Icon(
Icons.sentiment_very_satisfied,
color: const Color(0x15000000),
color: Color(0x15000000),
size: 120,
),
this.textStyle = const TextStyle(
Expand All @@ -39,15 +26,16 @@ class CustomSnackBar extends StatefulWidget {
this.boxShadow = kDefaultBoxShadow,
this.borderRadius = kDefaultBorderRadius,
this.textScaleFactor = 1.0,
});
this.textAlign = TextAlign.center,
}) : super(key: key);

const CustomSnackBar.info({
Key? key,
required this.message,
this.messagePadding = const EdgeInsets.symmetric(horizontal: 24),
this.icon = const Icon(
Icons.sentiment_neutral,
color: const Color(0x15000000),
color: Color(0x15000000),
size: 120,
),
this.textStyle = const TextStyle(
Expand All @@ -63,15 +51,16 @@ class CustomSnackBar extends StatefulWidget {
this.boxShadow = kDefaultBoxShadow,
this.borderRadius = kDefaultBorderRadius,
this.textScaleFactor = 1.0,
});
this.textAlign = TextAlign.center,
}) : super(key: key);

const CustomSnackBar.error({
Key? key,
required this.message,
this.messagePadding = const EdgeInsets.symmetric(horizontal: 24),
this.icon = const Icon(
Icons.error_outline,
color: const Color(0x15000000),
color: Color(0x15000000),
size: 120,
),
this.textStyle = const TextStyle(
Expand All @@ -87,13 +76,28 @@ class CustomSnackBar extends StatefulWidget {
this.boxShadow = kDefaultBoxShadow,
this.borderRadius = kDefaultBorderRadius,
this.textScaleFactor = 1.0,
});
this.textAlign = TextAlign.center,
}) : super(key: key);

final String message;
final Widget icon;
final Color backgroundColor;
final TextStyle textStyle;
final int maxLines;
final int iconRotationAngle;
final List<BoxShadow> boxShadow;
final BorderRadius borderRadius;
final double iconPositionTop;
final double iconPositionLeft;
final EdgeInsetsGeometry messagePadding;
final double textScaleFactor;
final TextAlign textAlign;

@override
_CustomSnackBarState createState() => _CustomSnackBarState();
CustomSnackBarState createState() => CustomSnackBarState();
}

class _CustomSnackBarState extends State<CustomSnackBar> {
class CustomSnackBarState extends State<CustomSnackBar> {
@override
Widget build(BuildContext context) {
final theme = Theme.of(context);
Expand All @@ -111,7 +115,7 @@ class _CustomSnackBarState extends State<CustomSnackBar> {
Positioned(
top: widget.iconPositionTop,
left: widget.iconPositionLeft,
child: Container(
child: SizedBox(
height: 95,
child: Transform.rotate(
angle: widget.iconRotationAngle * pi / 180,
Expand All @@ -124,10 +128,8 @@ class _CustomSnackBarState extends State<CustomSnackBar> {
padding: widget.messagePadding,
child: Text(
widget.message,
style: theme.textTheme.bodyText2?.merge(
widget.textStyle,
),
textAlign: TextAlign.center,
style: theme.textTheme.bodyText2?.merge(widget.textStyle),
textAlign: widget.textAlign,
overflow: TextOverflow.ellipsis,
maxLines: widget.maxLines,
textScaleFactor: widget.textScaleFactor,
Expand All @@ -140,13 +142,13 @@ class _CustomSnackBarState extends State<CustomSnackBar> {
}
}

const kDefaultBoxShadow = const [
const kDefaultBoxShadow = [
BoxShadow(
color: Colors.black26,
offset: Offset(0.0, 8.0),
offset: Offset(0, 8),
spreadRadius: 1,
blurRadius: 30,
),
];

const kDefaultBorderRadius = const BorderRadius.all(Radius.circular(12));
const kDefaultBorderRadius = BorderRadius.all(Radius.circular(12));
28 changes: 15 additions & 13 deletions lib/tap_bounce_container.dart
Original file line number Diff line number Diff line change
@@ -1,32 +1,34 @@
import 'dart:async';

import 'package:flutter/cupertino.dart';

/// Widget for nice tap effect. It decrease widget scale while tapping
class TapBounceContainer extends StatefulWidget {
final Widget child;
final VoidCallback? onTap;

TapBounceContainer({
const TapBounceContainer({
Key? key,
required this.child,
this.onTap,
});
}) : super(key: key);

final Widget child;
final VoidCallback? onTap;

@override
_TapBounceContainerState createState() => _TapBounceContainerState();
TapBounceContainerState createState() => TapBounceContainerState();
}

class _TapBounceContainerState extends State<TapBounceContainer>
class TapBounceContainerState extends State<TapBounceContainer>
with SingleTickerProviderStateMixin {
late double _scale;
late AnimationController _controller;

final animationDuration = Duration(milliseconds: 200);
final animationDuration = const Duration(milliseconds: 200);

@override
void initState() {
_controller = AnimationController(
vsync: this,
duration: animationDuration,
lowerBound: 0.0,
upperBound: 0.04,
)..addListener(() {
if (mounted) {
Expand Down Expand Up @@ -63,17 +65,17 @@ class _TapBounceContainerState extends State<TapBounceContainer>
}
}

void _onTapUp(TapUpDetails details) async {
Future<void> _onTapUp(TapUpDetails details) async {
await _closeSnackBar();
}

void _onPanEnd(DragEndDetails details) async {
Future<void> _onPanEnd(DragEndDetails details) async {
await _closeSnackBar();
}

Future _closeSnackBar() async {
Future<void> _closeSnackBar() async {
if (mounted) {
_controller.reverse();
unawaited(_controller.reverse());
await Future.delayed(animationDuration);
widget.onTap?.call();
}
Expand Down
Loading

0 comments on commit f55db56

Please sign in to comment.