mirror of
https://github.com/n8n-io/n8n.git
synced 2025-03-05 20:50:17 -08:00
⚡ Add support for draw and allow font selection EditImage-Node
This commit is contained in:
parent
b81d175145
commit
02669c04f1
|
@ -4,17 +4,23 @@ import {
|
|||
} from 'n8n-core';
|
||||
import {
|
||||
IDataObject,
|
||||
ILoadOptionsFunctions,
|
||||
INodeExecutionData,
|
||||
INodePropertyOptions,
|
||||
INodeType,
|
||||
INodeTypeDescription,
|
||||
} from 'n8n-workflow';
|
||||
import * as gm from 'gm';
|
||||
import { file } from 'tmp-promise';
|
||||
import {
|
||||
parse as pathParse,
|
||||
} from 'path';
|
||||
import {
|
||||
writeFile as fsWriteFile,
|
||||
} from 'fs';
|
||||
import { promisify } from 'util';
|
||||
const fsWriteFileAsync = promisify(fsWriteFile);
|
||||
import * as getSystemFonts from 'get-system-fonts';
|
||||
|
||||
|
||||
export class EditImage implements INodeType {
|
||||
|
@ -57,6 +63,11 @@ export class EditImage implements INodeType {
|
|||
value: 'composite',
|
||||
description: 'Composite image on top of another one',
|
||||
},
|
||||
{
|
||||
name: 'Draw',
|
||||
value: 'draw',
|
||||
description: 'Draw on image',
|
||||
},
|
||||
{
|
||||
name: 'Get Information',
|
||||
value: 'information',
|
||||
|
@ -96,6 +107,140 @@ export class EditImage implements INodeType {
|
|||
},
|
||||
|
||||
|
||||
// ----------------------------------
|
||||
// draw
|
||||
// ----------------------------------
|
||||
{
|
||||
displayName: 'Primitive',
|
||||
name: 'primitive',
|
||||
type: 'options',
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
},
|
||||
},
|
||||
options: [
|
||||
{
|
||||
name: 'Line',
|
||||
value: 'line',
|
||||
},
|
||||
{
|
||||
name: 'Rectangle',
|
||||
value: 'rectangle',
|
||||
},
|
||||
],
|
||||
default: 'rectangle',
|
||||
description: 'The primitive to draw.',
|
||||
},
|
||||
{
|
||||
displayName: 'Color',
|
||||
name: 'color',
|
||||
type: 'color',
|
||||
default: '#ff000000',
|
||||
typeOptions: {
|
||||
showAlpha: true,
|
||||
},
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
},
|
||||
},
|
||||
description: 'The color of the primitive to draw',
|
||||
},
|
||||
{
|
||||
displayName: 'Start Position X',
|
||||
name: 'startPositionX',
|
||||
type: 'number',
|
||||
default: 50,
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
primitive: [
|
||||
'line',
|
||||
'rectangle',
|
||||
],
|
||||
},
|
||||
},
|
||||
description: 'X (horizontal) start position of the primitive.',
|
||||
},
|
||||
{
|
||||
displayName: 'Start Position Y',
|
||||
name: 'startPositionY',
|
||||
type: 'number',
|
||||
default: 50,
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
primitive: [
|
||||
'line',
|
||||
'rectangle',
|
||||
],
|
||||
},
|
||||
},
|
||||
description: 'Y (horizontal) start position of the primitive.',
|
||||
},
|
||||
{
|
||||
displayName: 'End Position X',
|
||||
name: 'endPositionX',
|
||||
type: 'number',
|
||||
default: 250,
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
primitive: [
|
||||
'line',
|
||||
'rectangle',
|
||||
],
|
||||
},
|
||||
},
|
||||
description: 'X (horizontal) end position of the primitive.',
|
||||
},
|
||||
{
|
||||
displayName: 'End Position Y',
|
||||
name: 'endPositionY',
|
||||
type: 'number',
|
||||
default: 250,
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
primitive: [
|
||||
'line',
|
||||
'rectangle',
|
||||
],
|
||||
},
|
||||
},
|
||||
description: 'Y (horizontal) end position of the primitive.',
|
||||
},
|
||||
{
|
||||
displayName: 'Corner Radius',
|
||||
name: 'cornerRadius',
|
||||
type: 'number',
|
||||
default: 0,
|
||||
displayOptions: {
|
||||
show: {
|
||||
operation: [
|
||||
'draw',
|
||||
],
|
||||
primitive: [
|
||||
'rectangle',
|
||||
],
|
||||
},
|
||||
},
|
||||
description: 'The radius of the corner to create round corners.',
|
||||
},
|
||||
|
||||
// ----------------------------------
|
||||
// text
|
||||
// ----------------------------------
|
||||
|
@ -501,7 +646,7 @@ export class EditImage implements INodeType {
|
|||
],
|
||||
},
|
||||
},
|
||||
description: 'The color to use for the background when image gets rotated by anything which is not a multiple of 90..',
|
||||
description: 'The color to use for the background when image gets rotated by anything which is not a multiple of 90.',
|
||||
},
|
||||
|
||||
|
||||
|
@ -558,6 +703,23 @@ export class EditImage implements INodeType {
|
|||
default: '',
|
||||
description: 'File name to set in binary data.',
|
||||
},
|
||||
{
|
||||
displayName: 'Font',
|
||||
name: 'font',
|
||||
type: 'options',
|
||||
displayOptions: {
|
||||
show: {
|
||||
'/operation': [
|
||||
'text',
|
||||
],
|
||||
},
|
||||
},
|
||||
typeOptions: {
|
||||
loadOptionsMethod: 'getFonts',
|
||||
},
|
||||
default: 'default',
|
||||
description: 'The font to use.',
|
||||
},
|
||||
{
|
||||
displayName: 'Format',
|
||||
name: 'format',
|
||||
|
@ -613,6 +775,40 @@ export class EditImage implements INodeType {
|
|||
};
|
||||
|
||||
|
||||
methods = {
|
||||
loadOptions: {
|
||||
async getFonts(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
|
||||
|
||||
// @ts-ignore
|
||||
const files = await getSystemFonts();
|
||||
const returnData: INodePropertyOptions[] = [];
|
||||
|
||||
files.forEach((file: string) => {
|
||||
const pathParts = pathParse(file);
|
||||
returnData.push({
|
||||
name: pathParts.name,
|
||||
value: file,
|
||||
});
|
||||
});
|
||||
|
||||
returnData.sort((a, b) => {
|
||||
if (a.name < b.name) { return -1; }
|
||||
if (a.name > b.name) { return 1; }
|
||||
return 0;
|
||||
});
|
||||
|
||||
returnData.unshift({
|
||||
name: 'default',
|
||||
value: 'default',
|
||||
});
|
||||
|
||||
return returnData;
|
||||
},
|
||||
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
async executeSingle(this: IExecuteSingleFunctions): Promise<INodeExecutionData> {
|
||||
const item = this.getInputData();
|
||||
|
||||
|
@ -670,7 +866,24 @@ export class EditImage implements INodeType {
|
|||
const positionY = this.getNodeParameter('positionY') as number;
|
||||
|
||||
gmInstance = gmInstance.crop(width, height, positionX, positionY);
|
||||
} else if (operation === 'information') {
|
||||
} else if (operation === 'draw') {
|
||||
const startPositionX = this.getNodeParameter('startPositionX') as number;
|
||||
const startPositionY = this.getNodeParameter('startPositionY') as number;
|
||||
const endPositionX = this.getNodeParameter('endPositionX') as number;
|
||||
const endPositionY = this.getNodeParameter('endPositionY') as number;
|
||||
const primitive = this.getNodeParameter('primitive') as string;
|
||||
const color = this.getNodeParameter('color') as string;
|
||||
|
||||
gmInstance = gmInstance.fill(color);
|
||||
|
||||
if (primitive === 'line') {
|
||||
gmInstance = gmInstance.drawLine(startPositionX, startPositionY, endPositionX, endPositionY);
|
||||
} else if (primitive === 'rectangle') {
|
||||
const cornerRadius = this.getNodeParameter('cornerRadius') as number;
|
||||
gmInstance = gmInstance.drawRectangle(startPositionX, startPositionY, endPositionX, endPositionY, cornerRadius || undefined);
|
||||
}
|
||||
|
||||
} else if (operation === 'information') {
|
||||
const imageData = await new Promise<IDataObject>((resolve, reject) => {
|
||||
gmInstance = gmInstance.identify((error, imageData) => {
|
||||
if (error) {
|
||||
|
@ -738,6 +951,10 @@ export class EditImage implements INodeType {
|
|||
// Combine the lines to a single string
|
||||
const renderText = lines.join('\n');
|
||||
|
||||
if (options.font && options.font !== 'default') {
|
||||
gmInstance = gmInstance.font(options.font as string);
|
||||
}
|
||||
|
||||
gmInstance = gmInstance
|
||||
.fill(fontColor)
|
||||
.fontSize(fontSize)
|
||||
|
|
|
@ -453,6 +453,7 @@
|
|||
"@types/redis": "^2.8.11",
|
||||
"@types/request-promise-native": "~1.0.15",
|
||||
"@types/ssh2-sftp-client": "^5.1.0",
|
||||
"@types/tmp": "^0.2.0",
|
||||
"@types/uuid": "^3.4.6",
|
||||
"@types/xml2js": "^0.4.3",
|
||||
"gulp": "^4.0.0",
|
||||
|
@ -471,6 +472,7 @@
|
|||
"cron": "^1.7.2",
|
||||
"eventsource": "^1.0.7",
|
||||
"formidable": "^1.2.1",
|
||||
"get-system-fonts": "^2.0.2",
|
||||
"glob-promise": "^3.4.0",
|
||||
"gm": "^1.23.1",
|
||||
"imap-simple": "^4.3.0",
|
||||
|
|
Loading…
Reference in a new issue