Clipper
By: Yubaraj Poudel
Tags: Flutter Widget, Flutter, Dart, Clipper, Custom Widget

Let's move one by one

class RectangularClipper extends CustomClipper<Rect> {

@override

Rect getClip(Size size) {

// TODO: implement getClip

Rect rectange = Rect.fromLTWH(0.0, 0.0, size.width, size.height);

return rectange;

}



@override

bool shouldReclip(CustomClipper<Rect> oldClipper) {

// TODO: implement shouldReclip

return true;

}

}

In the above snippet, it will just create a rectangular shape. By default the `size.width` here refers to the screen width.

Rectangular Clipper

Custom Clipper

class TriangleClipper extends CustomClipper<Path> {

@override

Path getClip(Size size) {

final path = Path();

path.lineTo(size.width / 2, size.height);

path.lineTo(size.width, 0.0);

path.close();

return path;

}



@override

bool shouldReclip(CustomClipper<Path> oldClipper) {

return true;

}

}

The path is very useful in generating the user choice type of clipper with different irregular shapes. `lineTo` function takes the two argument x and y 0.0 in x represent the right most place whereas 0.0 in y represent the topmost of the left of the screen.

Triangle Clipper

Pentagon Clipper

class PentagonClipper extends CustomClipper<Path> {

@override

Path getClip(Size size) {

final path = Path();

path.lineTo(0.0, size.height - 40);

path.lineTo(size.width / 2, size.height);

path.lineTo(size.width, size.height - 40);

path.lineTo(size.width, 0.0);

path.close();

return path;

}



@override

bool shouldReclip(CustomClipper<Path> oldClipper) {

return true;

}

}

PentagonClipper

Quadratic curves

Let’s merge all examples in a single file.

import 'dart:ui';



import 'package:flutter/material.dart';

/**

@Author: Yubaraj Poudel

@Since: 2019/05/06

@link: /**@Author: Yubaraj Poudel@Since: 2019/05/06@link: https://github.com/flutterchallenge/widgetchallenge **/

class RectangularClipper extends CustomClipper<Rect> {

@override

Rect getClip(Size size) {

// TODO: implement getClip

Rect rectange = Rect.fromLTWH(0.0, 0.0, size.width, size.height);

return rectange;

}



@override

bool shouldReclip(CustomClipper<Rect> oldClipper) {

// TODO: implement shouldReclip

return true;

}

}



class TriangleClipper extends CustomClipper<Path> {

@override

Path getClip(Size size) {

final path = Path();

path.lineTo(size.width / 2, size.height);

path.lineTo(size.width, 0.0);

path.close();

return path;

}



@override

bool shouldReclip(CustomClipper<Path> oldClipper) {

return true;

}

}



class PentagonClipper extends CustomClipper<Path> {

@override

Path getClip(Size size) {

final path = Path();

path.lineTo(0.0, size.height - 40);

path.lineTo(size.width / 2, size.height);

path.lineTo(size.width, size.height - 40);

path.lineTo(size.width, 0.0);

path.close();

return path;

}



@override

bool shouldReclip(CustomClipper<Path> oldClipper) {

return true;

}

}



class WaveClipper extends CustomClipper<Path> {

@override

Path getClip(Size size) {

var path = new Path();

path.lineTo(0.0, size.height - 20);



var firstStartPoint = Offset(size.width / 4, size.height);

var firstEndPoint = Offset(size.width / 2.25, size.height - 30.0);

path.quadraticBezierTo(firstStartPoint.dx, firstStartPoint.dy,

firstEndPoint.dx, firstEndPoint.dy);



var secondStartPoint =

Offset(size.width - (size.width / 3.25), size.height - 65);

var secondEndPoint = Offset(size.width, size.height - 40);

path.quadraticBezierTo(secondStartPoint.dx, secondStartPoint.dy,

secondEndPoint.dx, secondEndPoint.dy);



path.lineTo(size.width, size.height - 40);

path.lineTo(size.width, 0.0);

path.close();



return path;

}



@override

bool shouldReclip(CustomClipper<Path> oldClipper) {

// TODO: implement shouldReclip

return true;

}

}



//@Widgets

// Color container

_coloredContainer() => Container(color: Colors.teal, height: 200);

//----------------------------------

//triangle



_triangleWidget() =>

ClipPath(clipper: TriangleClipper(), child: _coloredContainer());



//Rectangle

_rectangeWidget() => ClipRect(

clipper: RectangularClipper(),

child: _coloredContainer(),

);



//pentagon

_pentagonWidget() => ClipPath(

clipper: PentagonClipper(),

child: _coloredContainer(),

);



//oval

_ovalWidget() => ClipOval(

child: _coloredContainer(),

);



//wave

_waveWidget() => ClipPath(

clipper: WaveClipper(),

child: _coloredContainer(),

);



class MyCustomClipper extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(

title: Text("Custom clippers"),

),

body: ListView(

children: <Widget>[

SizedBox(height: 8.0,),

Text("Triangle Clipper", style: TextStyle(fontSize: 16.0, fontWeight: FontWeight.bold), textAlign: TextAlign.center,),

SizedBox(height: 16.0,),

_triangleWidget(),

SizedBox(height: 16.0,),

Text("Rectangle Clipper", style: TextStyle(fontSize: 16.0, fontWeight: FontWeight.bold), textAlign: TextAlign.center),

SizedBox(height: 8.0,),

_rectangeWidget(),

SizedBox(height: 16.0,),

Text("Pentagon Clipper", style: TextStyle(fontSize: 16.0, fontWeight: FontWeight.bold), textAlign: TextAlign.center),

SizedBox(height: 8.0,),

_pentagonWidget(),

SizedBox(height: 16.0,),

Text("Oval Clipper", style: TextStyle(fontSize: 16.0, fontWeight: FontWeight.bold), textAlign: TextAlign.center),

SizedBox(height: 8.0,),

_ovalWidget(),

SizedBox(height: 8.0,),

Text("Wave Clipper", style: TextStyle(fontSize: 16.0, fontWeight: FontWeight.bold), textAlign: TextAlign.center),

SizedBox(height: 16.0,),

_waveWidget()

],

),

);

}

}

In the above example, the Clippers are used to generate different types of polygons.

If you like to help to build a better flutter community, we are happy to contain you as a contributor on widgetchallenge

https://github.com/flutterchallenge/widgetchallenge