From front-end Superman, author Rong Ding
Introduction
When we want to draw a basic simple shape on the Canvas, using Canvas won't feel cumbersome. However, when any form of interaction is required on the Canvas, drawing complex graphics and changing pictures in specific situations, it will become very difficult to use the native canvas API.
Fabric aims to solve this problem.
https://github.com/fabricjs/fabric.js
Fabric.js is a powerful and simple Javascript HTML5 canvas library. Fabric provides an interactive object model on top of canvas elements. Fabric also has SVG to canvas (and canvas to SVG) parsers.
For convenience, I will explain how to use Fabric through vue project
1, Installation
yarn add fabric -S #or npm i fabric -S
You can also download the latest js file on the official website and import it through the script tag
2, Use
<!-- html --> <canvas id="canvas" width="500" height="500"></canvas>
2.1 draw a simple graph
Fabric offers 7 basic shapes:
- fabric.Circle (circle)
- fabric.Ellipse (ellipse)
- fabric.Line
- fabric.Polyline (multiple lines are drawn into graphics)
- fabric.triangle (triangle)
- fabric.Rect (rectangular)
- fabric.Polygon
- rectangle
// js //Introducing fabric import { fabric } from "fabric"; // Create a fabric instance let canvas = new fabric.Canvas("canvas"); //You can zoom out and rotate with the mouse // or // let canvas = new fabric.StaticCanvas("canvas");// Fabric object without mouse interaction // Create a rectangular object let rect = new fabric.Rect({ left: 200, //Distance to the left top: 200, //Distance from top fill: "green", //Fill color width: 200, //Rectangle width height: 200, //Rectangle height }); // Add a rectangle to the canvas canvas.add(rect);
You can see that the interface is filled with a green rectangle that can be zoomed in and out and rotated by the mouse. It is very convenient to configure the element style in the form of objects!
- Circles and triangles
// Create a circular object let circle = new fabric.Circle({ left: 0, //Distance to the left top: 0, //Distance from top fill: "red", //Fill color radius: 50, //Radius of circle }); // Create a triangle object let triangle = new fabric.Triangle({ left: 200, //Distance to the left top: 0, //Distance from top fill: "blue", //Fill color width: 100, //width height: 100, //height }); // Add a graphic shape to the canvas canvas.add(circle, triangle);
We can determine whether we can interact with related elements through the following attribute settings
canvas.selection = false; // Disable all selections rect.set("selectable", false); // Just disable the selection of this rectangle
2.2 drawing pictures
There are mainly two ways to draw by url and img tag
//Draw pictures by url fabric.Image.fromURL( //Local pictures need to be imported through require("./xxx.jpeg") "https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fimg.thaihot.com.cn%2Fuploadimg%2Fico%2F2021%2F0711%2F1625982535739193.jpg&refer=http%3A%2F%2Fimg.thaihot.com.cn&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1630940858&t=e1d24ff0a7eaeea2ff89cedf656a9374", (img) => { img.scale(0.5); canvas.add(img); } ); //You can also draw with labels let img = document.getElementById("img"); let image = new fabric.Image(img, { left: 100, top: 100, opacity: 0.8, }); canvas.add(image);
2.3 drawing through customized path
Before that, we need to understand the meaning of several parameters
- M: "move" moves to a point
- L: "line" draw lines x,y
- C: curve
- A: "arc" arc
- z: closed path (similar to creating selection in PS)
let customPath = new fabric.Path("M 0 0 L 300 100 L 170 100 z"); customPath.set({ left: 100, top: 100, fill: "green", }); canvas.add(customPath);
let customPath = new fabric.Path( "M 0 0 L 300 100 L 170 100 L 70 300 L 20 200 C136.19,2.98,128.98,0,121.32,0 z" );
It can be seen that through path drawing, we can make very complex graphics (but we usually don't use it. We usually use it to parse SVG and get the path recovery graphics)
animation
The first parameter is the attribute of the animation, the second parameter is the final position of the animation, and the third parameter is an optional object to specify the details of the animation: duration, callback, dynamic effect, etc.
The third parameter mainly includes
- Duration defaults to 500ms. Can be used to change the duration of the animation.
- from allows you to specify the starting value of the animation attribute (if we don't want to use the current value).
- onComplete the callback after the animation ends.
- easing dynamic effect function.
Absolute animation
let canvas = new fabric.Canvas("canvas");let rect = new fabric.Rect({ left: 400, //Distance from the left top: 200, / / distance from the top fill: "green", / / fill color width: 200, / / width height: 200, / / height}); rect.animate("left", 100, { onChange: canvas.renderAll.bind(canvas), duration: 1000,});canvas.add(rect);
Relative animation (the second parameter determines the final effect of animation through + =, - = and so on)
rect.animate("left", "+=100", { onChange: canvas.renderAll.bind(canvas), duration: 1000, });
rect.set({ angle: 45 }); rect.animate("angle", "-=90", { onChange: canvas.renderAll.bind(canvas), duration: 2000, });
Defines the animation's dynamic function
By default, the animation is executed using the ease in sine animation. If this is not what you need, fabric provides us with a lot of built-in animation effects. There are a lot of dynamic effects under fabric.util.ease. The commonly used ones include ease outbound, ease incubic, ease outbound cubic, ease inelastic, ease outbound elastic, ease inbound and ease outbound Expo
rect.animate("left", 100, { onChange: canvas.renderAll.bind(canvas), duration: 1000, easing: fabric.util.ease.easeOutBounce, });
image filters
At present, Fabric provides us with the following built-in filters
- BaseFilter basic filter
- Blur blur
- Brightness brightness
- ColorMatrix color matrix
- Contrast
- Convolute
- Gamma gamma
- Grayscale
- HueRotation hue rotation
- Invert inversion
- Noise
- Pixelate
- RemoveColor remove color
- Resize resize
- Saturation saturation
Single filter
fabric.Image.fromURL(require("./aaa.jpeg"), (img) => { img.scale(0.5); canvas.add(img); }); fabric.Image.fromURL(require("./aaa.jpeg"), (img) => { img.scale(0.5); // Add Filter img.filters.push(new fabric.Image.filters.Grayscale()); // After the picture is loaded, apply the filter effect img.applyFilters(); img.set({ left: 300, top: 250, }); canvas.add(img); });
Overlay filter
The "filters" attribute is an array. We can use the array method to perform any required operations: remove filters (pop, slice, shift), add filters (push, unshift, slice), and even combine multiple filters. When we call applyFilters, any filters in the "filters" array will be applied one by one, so let's try to create an image that is both color biased and bright.
fabric.Image.fromURL(require("./aaa.jpeg"), (img) => { img.scale(0.5); // Add Filter img.filters.push( new fabric.Image.filters.Grayscale(), new fabric.Image.filters.Sepia(), //Color deviation new fabric.Image.filters.Brightness({ brightness: 0.2 }) //brightness ); // After the picture is loaded, apply the filter effect img.applyFilters(); img.set({ left: 300, top: 250, }); canvas.add(img); });
You can see that the effects of multiple filters are superimposed. Of course, fabric also supports custom filters. After 500 likes in this article, I will update the advanced article of fabric. Thank you for your support~
colour
Whether you use hexadecimal, RGB or RGBA colors, Fabric can handle them very well
define color
new fabric.Color("#f55"); new fabric.Color("#aa3123"); new fabric.Color("356333"); new fabric.Color("rgb(100,50,100)"); new fabric.Color("rgba(100, 200, 30, 0.5)");
Color conversion
new fabric.Color('#f55').toRgb(); // "rgb(255,85,85)" new fabric.Color('rgb(100,100,100)').toHex(); // "646464" new fabric.Color('fff').toHex(); // "FFFFFF"
We can also overlay with another color or convert it to a grayscale version.
let redish = new fabric.Color("#f55"); let greenish = new fabric.Color("#5f5"); redish.overlayWith(greenish).toHex(); // "AAAA55" redish.toGrayscale().toHex(); // "A1A1A1"
Gradual change
Fabric supports gradients through the setGradient method and is defined on all objects. Calling setGradient('fill ', {...}) is like setting the "fill" value of an object.
let circle = new fabric.Circle({ left: 100, top: 100, radius: 50 }); circle.setGradient("fill", { // Where the gradient starts x1: 0, y1: 0, // Where the gradient ends x2: circle.width, y2: 0, //Gradient color colorStops: { // The gradient range (0,0.1,0.3,0.5,0.75,1) can be between 0-1 0: "red", 0.2: "orange", 0.4: "yellow", 0.6: "green", 0.8: "blue", 1: "purple" }, });
text
The fabric.Text object provides richer functions for text than canvas, including:
- Multi line support unfortunately, the native text method ignores creating a new line.
- Text alignment text alignmentleft, center, right. Useful when working with multiline text.
- Text background text background also supports text alignment.
- Text decoration underline, underline, through line.
- Line Highline height is useful when using multiline text.
- Character spacing Char spacing makes text more compact or spaced.
- The Subranges apply colors and attributes to children of text objects.
- Multi byte Multibyte supports emoticons.
- Interactive canvas editionon canvas editingyou can type text directly on the canvas.
let text = new fabric.Text( "hello everyone~This is Qianpu village\n I'm Rongding~\n A man who wants to be the king of development!", { left: 0, top: 200, fontFamily: "Comic Sans", //typeface fontSize: 50, //Font size fontWeight: 800, //Font thickness, you can use keywords ("normal", "bold") or numbers (100200400600800) shadow: "green 3px 3px 2px", //Text shadow, color, horizontal offset, vertical offset and blur size. underline: true, //Underline linethrough: true, //Delete line overline: true, //Upper scribe fontStyle: "italic", //Font style, normal or italic stroke: "#c3bfbf ", / / stroke color strokeWidth: 1, //Stroke width textAlign: "center", //text alignment lineHeight: 1.5, //Row height textBackgroundColor: "#91A8D0 ", / / text background color } ); canvas.add(text);
event
In fabric, the on method is used to initialize events, and the off method is used to delete events.
Common events are as follows
- "mouse:down" mouse pressed
- The "object:add" object is added
- after:render rendering is complete
There are also a lot of mouse events: "mouse:down", "mouse:move" and "mouse:up..." select relevant events: "before:selection:cleared", "selection:created". You can view the official documents for details
canvas.on("mouse:down", function(options) { canvas.clear(); let text = new fabric.Text("You ordered me~", { left: 200, top: 200, }); canvas.add(text); console.log(options.e.clientX, options.e.clientY); }); canvas.on("mouse:up", function(options) { this.text = "You didn't order me 0.0"; canvas.clear(); let text = new fabric.Text("You didn't order me 0.0", { left: 200, top: 200, }); canvas.add(text); console.log(options.e.clientX, options.e.clientY); });
Fabric allows you to attach listeners directly to objects in the canvas.
let rect = new fabric.Rect({ width: 100, height: 50, fill: "green" }); rect.on("selected", function() { console.log("Oh, roar~You chose me"); }); let circle = new fabric.Circle({ radius: 75, fill: "blue" }); circle.on("selected", function() { console.log("Ha ha ha~You chose me"); });
Free painting
If the isDrawingMode property of Fabric canvas is set to true, the free drawing mode can be realized. In this way, the clicks and movements on the canvas will be immediately interpreted as pencils or brushes.
let canvas = new fabric.Canvas("canvas"); canvas.isDrawingMode = true; canvas.freeDrawingBrush.color = "blue"; canvas.freeDrawingBrush.width = 5;
last
I'm glad to write this article. It's an article I use to summarize the knowledge points of fabric with great care. I hope this article will help you. At present, fabric is not very popular in China, but there are 20k stars on github, which is also a star project.
We often use canvas in our daily development, but its api will be very tired for dealing with complex business logic, so I share this article, hoping to help you.
Open source outposts share popular, interesting and practical open source projects on a daily basis. Participate in maintaining the open source technology resource library of 100000 + Star, including Python, Java, C/C + +, Go, JS, CSS, Node.js, PHP,. NET, etc.