{"id":18020046,"url":"https://github.com/polygonjs/plugins_tutorials","last_synced_at":"2025-04-04T17:12:12.674Z","repository":{"id":109050801,"uuid":"423582557","full_name":"polygonjs/plugins_tutorials","owner":"polygonjs","description":"Short examples on how to create plugins for Polygonjs","archived":false,"fork":false,"pushed_at":"2022-05-02T17:36:09.000Z","size":403,"stargazers_count":0,"open_issues_count":0,"forks_count":1,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-04-01T19:49:01.862Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/polygonjs.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null}},"created_at":"2021-11-01T18:58:55.000Z","updated_at":"2021-11-04T09:32:27.000Z","dependencies_parsed_at":"2023-03-22T12:16:51.389Z","dependency_job_id":null,"html_url":"https://github.com/polygonjs/plugins_tutorials","commit_stats":{"total_commits":13,"total_committers":1,"mean_commits":13.0,"dds":0.0,"last_synced_commit":"d95216ae8aebde0d1b21f76fd2f0e09eef1551c8"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/polygonjs%2Fplugins_tutorials","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/polygonjs%2Fplugins_tutorials/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/polygonjs%2Fplugins_tutorials/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/polygonjs%2Fplugins_tutorials/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/polygonjs","download_url":"https://codeload.github.com/polygonjs/plugins_tutorials/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247217222,"owners_count":20903009,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-10-30T05:13:24.202Z","updated_at":"2025-04-04T17:12:12.658Z","avatar_url":"https://github.com/polygonjs.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# How to add custom nodes to Polygonjs\n\n[Polygonjs](https://polygonjs.com) is node-based WebGL engine. It is [open-source](https://github.com/polygonjs/polygonjs) and allows you to create and import your own nodes.\n\nThis repository explains how to do so, it's very simple:\n\n\n## First, set up your project:\n\n- 1. Create a new folder.\n- 2. Start polygonjs with `npx polygonjs-editor`.\n- 3. Open your browser at `http://localhost:8091/` to open the editor.\n- 4. Save the default scene, either with `Ctrl+S` or from the top menu `File -\u003e Save`\n- 5. When prompted, install the dependencies with `npm install` or `yarn`.\n- 6. Once the dependencies are installed, click `Save again`.\n\n## Then, you can create a custom node:\n\nHere we are going to create a custom SOP node, which is specialized to manipulate geometries. So let's create it inside a `sop` folder:\n\n- 1. Add the folders `src/engine/nodes/sop`.\n- 2. Inside the `sop` folder, create a file called `TransformCustom.js`. You should now have this file structure:\n\n![File Structure](https://github.com/polygonjs/plugins_tutorials/blob/main/public/files.jpg?raw=true)\n\n- 3. Then copy the content of the file from [what's in the repo](https://github.com/polygonjs/plugins_tutorials/blob/main/src/engine/nodes/sop/TransformCustom.js). It looks like this:\n\n``` js\nimport {TypedSopNode} from '@polygonjs/polygonjs/dist/src/engine/nodes/sop/_Base';\nimport {NodeParamsConfig, ParamConfig} from '@polygonjs/polygonjs/dist/src/engine/nodes/utils/params/ParamsConfig';\nclass TransformCustomSopParamsConfig extends NodeParamsConfig {\n    height = ParamConfig.FLOAT(1);\n}\nconst ParamsConfig = new TransformCustomSopParamsConfig();\n\nexport class TransformCustomSopNode extends TypedSopNode {\n    paramsConfig = ParamsConfig;\n    static type() {\n        // This is the type of the node. All nodes within a specific context (such as SOP, COP, OBJ) must have a unique type.\n        return 'transformCustom';\n    }\n\n    initializeNode() {\n        // You can set properties of the nodes at initialization here, such as the number of inputs\n        this.io.inputs.setCount(1);\n    }\n\n    cook(inputContents) {\n        // This is where the core of the node is. We'll process its inputs (inputContents)\n        // then modify them\n        const coreGroup = inputContents[0]\n        for(let object of coreGroup.objects()){\n            // here we update the y position of the object by this.pv.y, which is the value of the parameter height;\n            object.position.y += this.pv.height;\n            object.updateMatrix();\n        }\n        this.setCoreGroup(coreGroup);\n    }\n}\n```\n\nOr **if you prefer using typescript**, you can also write your nodes with it.\n\n\u003cdetails\u003e\n\u003csummary\u003eShow typescript example\u003c/summary\u003e\n\nThe file is [almost the same](https://github.com/polygonjs/plugins_tutorials/blob/main/src/engine/nodes/sop/TransformCustomInTS.ts):\n\n\n``` ts\nimport { CoreGroup } from '@polygonjs/polygonjs/dist/src/core/geometry/Group';\nimport {TypedSopNode} from '@polygonjs/polygonjs/dist/src/engine/nodes/sop/_Base';\nimport {NodeParamsConfig, ParamConfig} from '@polygonjs/polygonjs/dist/src/engine/nodes/utils/params/ParamsConfig';\nclass TransformCustomSopParamsConfig extends NodeParamsConfig {\n    height = ParamConfig.FLOAT(1);\n}\nconst ParamsConfig = new TransformCustomSopParamsConfig();\n\nexport class TransformCustomInTSSopNode extends TypedSopNode\u003cTransformCustomSopParamsConfig\u003e {\n    paramsConfig = ParamsConfig;\n    static type() {\n        // This is the type of the node. All nodes within a specific context (such as SOP, COP, OBJ) must have a unique type.\n        return 'transformCustomInTS';\n    }\n\n    initializeNode() {\n        // You can set properties of the nodes at initialization here, such as the number of inputs\n        this.io.inputs.setCount(1);\n    }\n\n    override cook(inputContents:CoreGroup[]) {\n        // This is where the core of the node is. We'll process its inputs (inputContents)\n        // then modify them\n        const coreGroup = inputContents[0]\n        for(let object of coreGroup.objects()){\n            // here we update the y position of the object by this.pv.y, which is the value of the parameter height;\n            object.position.y += this.pv.height;\n            object.updateMatrix();\n        }\n        this.setCoreGroup(coreGroup);\n    }\n}\n```\n\nThe main differences between writing your node with javascript and typescript are:\n\n- you need to give the parameter object as template: `TypedSopNode\u003cTransformCustomSopParamsConfig\u003e`. This allows the calls to a parameter ( `node.p.height` ) and to a parameter value ( `node.pv.height` ) to predict the type those return.\n- you need to give the argument type of the cook method. For a [SOP node](https://polygonjs.com/docs/nodes/sop), this is: `cook(inputContents:CoreGroup[])`.\n\n\n\u003c/details\u003e\n\n\n\n## And once the node is created, you need to register it, so that it can be accessible from the UI:\n\n- 1. in the file [src/polygonjs/scenes/scene_01/PolyConfig.js](https://github.com/polygonjs/plugins_tutorials/blob/main/src/polygonjs/scenes/scene_01/PolyConfig.js), add the following line at the top:\n```js\nimport {TransformCustomSopNode} from '../../../engine/nodes/sop/TransformCustom'\n```\n- 2. And inside the function `configurePolygonjs`, add this line:\n``` js\npoly.nodesRegister.register(TransformCustomSopNode, 'myNodes');\n```\n\n- 3. And reload the page of the editor. You should now be able to load your custom nodes:\n\n![Custom node loaded](https://github.com/polygonjs/plugins_tutorials/blob/main/public/registered_node.jpg?raw=true)\n\n## What's next?\n\nNow that you see how easy it is to extend Polygonjs, have a look at all the nodes you can take inspiration from in the core library:\n\n- [Actor nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/actor)\n- [Anim nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/anim)\n- [Audio nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/audio)\n- [Compositing/Texture nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/cop)\n- [Event nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/event)\n- [GLSL nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/gl)\n- [Material nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/mat)\n- [Object nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/obj)\n- [Post processing nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/post)\n- [Renderer nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/rop)\n- [Geometry/Surface nodes](https://github.com/polygonjs/polygonjs/tree/master/src/engine/nodes/sop)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpolygonjs%2Fplugins_tutorials","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fpolygonjs%2Fplugins_tutorials","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpolygonjs%2Fplugins_tutorials/lists"}