fabric
Version:
Object model for HTML5 canvas, and SVG-to-canvas parser. Backed by jsdom and node-canvas.
351 lines (347 loc) • 8.81 kB
JavaScript
import {
Point,
FabricImage,
Group,
BaseFabricObject,
StaticCanvas,
} from 'fabric/node';
/**
* Updates the fromObject function of a class to return a version that can restore old data
* with values of originX and originY that are different from 'center', 'center'
* Used to upgrade from fabric 6 to fabric 7
* @param originalFn the original fromObject function of an object,
* @param defaultOriginX optional default value for non exported originX,
* @param defaultOriginY optional default value for non exported originY,
* @returns a wrapped fromObject function for the object
*/
export const originUpdaterWrapper = (
originalFn,
defaultOriginX = 'left',
defaultOriginY = 'top',
) =>
async function (serializedObject, ...args) {
// we default to left and top because those are defaults before deprecation
const { originX = defaultOriginX, originY = defaultOriginY } =
serializedObject;
// and we do not want to pass those properties on the object anymore
delete serializedObject.originX;
delete serializedObject.originY;
const originalObject = await originalFn.call(
this,
serializedObject,
...args,
);
const actualPosition = new Point(originalObject.left, originalObject.top);
originalObject.setPositionByOrigin(actualPosition, originX, originY);
return originalObject;
};
// @ts-expect-error the _fromObject parameter could be instantiated differently
BaseFabricObject._fromObject = originUpdaterWrapper(
BaseFabricObject._fromObject,
);
// FabricImage and Group do not use _fromObject
FabricImage.fromObject = originUpdaterWrapper(FabricImage.fromObject);
Group.fromObject = originUpdaterWrapper(Group.fromObject);
const json = {
version: '4.5.1',
objects: [
{
type: 'Path',
version: '4.5.1',
left: 213,
top: 163,
width: 180,
height: 180,
fill: '',
stroke: 'red',
strokeWidth: 2,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
{
type: 'Path',
version: '4.5.1',
left: 200,
top: 6,
width: 180,
height: 180,
fill: '',
stroke: 'red',
strokeWidth: 2,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
{
type: 'Path',
version: '4.5.1',
left: 18,
top: 164,
width: 180,
height: 180,
fill: '',
stroke: 'red',
strokeWidth: 2,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
{
type: 'Path',
version: '4.5.1',
left: 9,
top: 14,
width: 180,
height: 180,
fill: '',
stroke: 'red',
strokeWidth: 2,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
{
type: 'Text',
version: '4.5.1',
left: 10,
top: 14,
width: 180,
height: 180,
text: 'Text on a swirl textAlign right',
fontSize: 28,
textAlign: 'right',
charSpacing: 50,
path: {
type: 'Path',
version: '4.5.1',
originX: 'left',
originY: 'top',
left: -0.5,
top: -180.5,
width: 180,
height: 180,
fill: 'rgb(0,0,0)',
stroke: null,
strokeWidth: 1,
strokeDashArray: null,
strokeLineCap: 'butt',
strokeDashOffset: 0,
strokeLineJoin: 'miter',
strokeUniform: false,
strokeMiterLimit: 4,
scaleX: 1,
scaleY: 1,
angle: 0,
flipX: false,
flipY: false,
opacity: 1,
shadow: null,
visible: false,
backgroundColor: '',
fillRule: 'nonzero',
paintFirst: 'fill',
globalCompositeOperation: 'source-over',
skewX: 0,
skewY: 0,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
direction: 'ltr',
styles: {},
},
{
type: 'Text',
version: '4.5.1',
left: 15,
top: 165,
width: 180,
height: 180,
text: 'Text on a swirl textAlign left',
fontSize: 28,
charSpacing: 50,
path: {
type: 'Path',
version: '4.5.1',
originX: 'left',
originY: 'top',
left: -0.5,
top: -180.5,
width: 180,
height: 180,
fill: 'rgb(0,0,0)',
stroke: null,
strokeWidth: 1,
strokeDashArray: null,
strokeLineCap: 'butt',
strokeDashOffset: 0,
strokeLineJoin: 'miter',
strokeUniform: false,
strokeMiterLimit: 4,
scaleX: 1,
scaleY: 1,
angle: 0,
flipX: false,
flipY: false,
opacity: 1,
shadow: null,
visible: false,
backgroundColor: '',
fillRule: 'nonzero',
paintFirst: 'fill',
globalCompositeOperation: 'source-over',
skewX: 0,
skewY: 0,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
direction: 'ltr',
styles: {},
},
{
type: 'Text',
version: '4.5.1',
left: 201,
top: 9,
width: 180,
height: 180,
text: 'Text on a swirl textAlign center',
fontSize: 28,
textAlign: 'center',
charSpacing: 50,
path: {
type: 'Path',
version: '4.5.1',
originX: 'left',
originY: 'top',
left: -0.5,
top: -180.5,
width: 180,
height: 180,
fill: 'rgb(0,0,0)',
stroke: null,
strokeWidth: 1,
strokeDashArray: null,
strokeLineCap: 'butt',
strokeDashOffset: 0,
strokeLineJoin: 'miter',
strokeUniform: false,
strokeMiterLimit: 4,
scaleX: 1,
scaleY: 1,
angle: 0,
flipX: false,
flipY: false,
opacity: 1,
shadow: null,
visible: false,
backgroundColor: '',
fillRule: 'nonzero',
paintFirst: 'fill',
globalCompositeOperation: 'source-over',
skewX: 0,
skewY: 0,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
direction: 'ltr',
styles: {},
},
{
type: 'Text',
version: '4.5.1',
left: 213,
top: 164,
width: 180,
height: 180,
text: 'full text to understand better a Text on a swirl textAlign',
fontSize: 28,
charSpacing: 50,
path: {
type: 'Path',
version: '4.5.1',
originX: 'left',
originY: 'top',
left: -0.5,
top: -180.5,
width: 180,
height: 180,
fill: 'rgb(0,0,0)',
stroke: null,
strokeWidth: 1,
strokeDashArray: null,
strokeLineCap: 'butt',
strokeDashOffset: 0,
strokeLineJoin: 'miter',
strokeUniform: false,
strokeMiterLimit: 4,
scaleX: 1,
scaleY: 1,
angle: 0,
flipX: false,
flipY: false,
opacity: 1,
shadow: null,
visible: false,
backgroundColor: '',
fillRule: 'nonzero',
paintFirst: 'fill',
globalCompositeOperation: 'source-over',
skewX: 0,
skewY: 0,
path: [
['M', 0, 0],
['Q', 180, 0, 180, -101.25],
['Q', 180, -180, 90, -180],
['Q', 0, -180, 0, -112.5],
['Q', 0, -45, 78.75, -45],
['Q', 135, -45, 146.25, -90],
],
},
direction: 'ltr',
styles: {},
},
],
};
const canvas = new StaticCanvas();
await canvas.loadFromJSON(json);
canvas.includeDefaultValues = false;
console.log(JSON.stringify(canvas));