Pation
Pation

Reputation: 159

How to use clip path with sliver app bar in flutter

Can anyone explain me how to change clip path of sliver app bar in flutter

Upvotes: 1

Views: 1324

Answers (2)

Yasin Ege
Yasin Ege

Reputation: 723

You can use that, my design supporting auto resize clip path and working perfectly

import 'package:flutter/material.dart';

import 'package:unfpa/base/base_stateful_state.dart';

import 'package:unfpa/utils/constants.dart';
import 'package:unfpa/utils/custom_clip_path.dart';
import 'package:unfpa/utils/custom_clip_path_two.dart';

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

  @override
  _TestWidgetState createState() => _TestWidgetState();
}

class _TestWidgetState extends BaseStatefulState<TestWidget> {
  final ScrollController _sliverScrollController = ScrollController();
  ValueNotifier<bool> isPinned = ValueNotifier(false);

  Size size;

  @override
  void initState() {
    super.initState();

    _sliverScrollController.addListener(() {
      if (!isPinned.value &&
          _sliverScrollController.hasClients &&
          _sliverScrollController.offset > kToolbarHeight) {
        isPinned.value = true;
      } else if (isPinned.value &&
          _sliverScrollController.hasClients &&
          _sliverScrollController.offset < kToolbarHeight) {
        isPinned.value = false;
      }
    });
  }

  @override
  Widget build(BuildContext context) {
    size = MediaQuery.of(context).size;

    return Scaffold(
        backgroundColor: Colors.white,
        body: CustomScrollView(
          controller: _sliverScrollController,
          slivers: <Widget>[
            ValueListenableBuilder(
                valueListenable: isPinned,
                builder: (context, value, child) {
                  return SliverAppBar(
                    elevation: 0,
                    backgroundColor: Colors.red,
                    leading: IconButton(
                        iconSize: 48,
                        color: Colors.white,
                        icon: Icon(Icons.close),
                        onPressed: () => Navigator.of(context).pop()),
                    primary: true,
                    pinned: true,
                    stretch: true,
                    title: Visibility(
                      visible: value,
                      child: Text(
                        "Sliver AppBar Title",
                        style: TextStyle(
                          fontWeight: FontWeight.w700,
                          fontSize: 22.0,
                          color: Colors.white,
                        ),
                      ),
                    ),
                    titleSpacing: 0,
                  );
                }),
            SliverList(
                delegate: SliverChildListDelegate([
              Column(
                crossAxisAlignment: CrossAxisAlignment.stretch,
                children: [
                  Container(
                    transform: Matrix4.translationValues(0.0, -2.0, 0.0),
                    alignment: Alignment.center,
                    child: ClipPath(
                      clipper: ClipPathClass(),
                      child: Container(
                        padding: EdgeInsets.only(bottom:20),
                        width: size.width,
                        color: Colors.yellow,
                        child: Container(
                          margin: EdgeInsets.symmetric(
                              horizontal: 25),
                          child: Column(
                            mainAxisSize: MainAxisSize.min,
                            crossAxisAlignment: CrossAxisAlignment.start,
                            children: <Widget>[
                              SizedBox(height: kToolbarTopMargin),
                              Text(
                                "Expanded Sliver title",
                                style: TextStyle(
                                  fontSize: 30.0,
                                  color: Colors.white,
                                ),
                              ),
                              SizedBox(
                                height: 5,
                              ),
                              Text(
                                "Expanded sliver description",
                                style: TextStyle(
                                  fontSize: 17,
                                  color: Colors.white,
                                  height: 1.3,
                                  fontWeight: FontWeight.w700,
                                ),
                              )
                            ],
                          ),
                        ),
                      ),
                    ),
                  ),
                ],
              )
            ])),
          ],
        ));
  }
}
CustomClipPathClass
import 'package:flutter/material.dart';

class ClipPathClass extends CustomClipper<Path> {
  @override
  Path getClip(Size size) {
    var path = Path();
    path.lineTo(0.0, size.height - 30);

    var firstControlPoint = Offset(size.width / 4, size.height);
    var firstPoint = Offset(size.width / 2, size.height);
    path.quadraticBezierTo(firstControlPoint.dx, firstControlPoint.dy,
        firstPoint.dx, firstPoint.dy);

    var secondControlPoint = Offset(size.width - (size.width / 4), size.height);
    var secondPoint = Offset(size.width, size.height - 30);
    path.quadraticBezierTo(secondControlPoint.dx, secondControlPoint.dy,
        secondPoint.dx, secondPoint.dy);

    path.lineTo(size.width, 0.0);
    path.close();

    return path;
  }

  @override
  bool shouldReclip(CustomClipper<Path> oldClipper) => false;
}

Upvotes: 1

Pation
Pation

Reputation: 159

class MyClipper extends CustomClipper<Path> {
  @override Path getClip(Size size) {
    final radius = 32.0;
    final r = Offset.zero & size; 
    final r1 = Rect.fromCircle(center: r.bottomRight - Offset(radius, radius * 2), radius: radius); 
    final r2 = Rect.fromCircle(center: r.bottomLeft + Offset(radius, 0), radius: radius);
    return Path() 
      ..moveTo(r.topLeft.dx, r.topLeft.dy)
      ..lineTo(r.topRight.dx, r.topRight.dy) 
      ..arcTo(r1, 0, pi / 2, false) 
      ..arcTo(r2, -pi / 2, -pi / 2, false);
  }

  @override bool shouldReclip(covariant CustomClipper<Path> oldClipper) => true;
}

Answer owner: pskink

Upvotes: 1

Related Questions