Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: seperate nodes entry for backward compatibility #1427

Merged
merged 12 commits into from
Jul 1, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 12 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ Code like this:

```javascript
import * as THREE from 'three';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader.js';
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

align to three export

import { VRMLoaderPlugin } from '@pixiv/three-vrm';

const scene = new THREE.Scene();
Expand Down Expand Up @@ -131,25 +131,31 @@ loader.load(
### Use with WebGPURenderer

Starting from v3, we provide [WebGPURenderer](https://github.com/mrdoob/three.js/blob/master/examples/jsm/renderers/webgpu/WebGPURenderer.js) compatibility.
To use three-vrm with WebGPURenderer, specify the WebGPU-compatible `MToonNodeMaterialLoaderPlugin` for the `mtoonMaterialPlugin` option of `VRMLoaderPlugin`.
To use three-vrm with WebGPURenderer, specify the WebGPU-compatible `MToonNodeMaterial` for the `materialType` option of `MToonMaterialLoaderPlugin`.

`MToonNodeMaterial` only supports Three.js r161 or later.
The NodeMaterial system of Three.js is still under development, so we may break compatibility with older versions of Three.js more frequently than other parts of three-vrm.

```js
import { VRMLoaderPlugin, MToonNodeMaterialLoaderPlugin } from '@pixiv/three-vrm';
import { VRMLoaderPlugin } from '@pixiv/three-vrm';
import { MToonNodeMaterial } from '@pixiv/three-vrm/nodes';

// ...

// Register a VRMLoaderPlugin
loader.register((parser) => {

// create a WebGPU compatible MToon loader plugin
const mtoonMaterialPlugin = new MToonNodeMaterialLoaderPlugin(parser);
// create a WebGPU compatible MToonMaterialLoaderPlugin
const mtoonMaterialPlugin = new MToonMaterialLoaderPlugin(parser, {

// set the material type to MToonNodeMaterial
materialType: MToonNodeMaterial,

});

return new VRMLoaderPlugin(parser, {

// Specify the MToon loader plugin to use in the VRMLoaderPlugin instance
// Specify the MToonMaterialLoaderPlugin to use in the VRMLoaderPlugin instance
mtoonMaterialPlugin,

});
Expand Down
20 changes: 17 additions & 3 deletions bin/build.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -55,11 +55,25 @@ async function buildPackage(absWorkingDir) {
* @param {'esm' | 'cjs'} format
*/
const entryPoints = (format) => {
let outFilename = filename + (format === 'esm' ? '.module' : '');
outFilename += DEV ? '' : '.min';
/**
* Add suffix according to the format to the given basename of the output file.
* @param {string} base Basename of the output file
* @returns {string} `<base>[.module][.min]`
*/
const addSuffix = (base) => {
let outFilename = base + (format === 'esm' ? '.module' : '');
return outFilename + (DEV ? '' : '.min');
};

const needsNodesBuild = ['@pixiv/three-vrm', '@pixiv/three-vrm-materials-mtoon'].includes(packageJson.name);
const extraEntryPoints = needsNodesBuild
? { [addSuffix('nodes/index')]: 'src/nodes/index.ts' }
: {};

return {
entryPoints: {
[outFilename]: 'src/index.ts',
[addSuffix(filename)]: 'src/index.ts',
...extraEntryPoints,
},
format,
};
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import * as THREE from 'three';
import { GLTF, GLTFLoaderPlugin, GLTFParser } from 'three/examples/jsm/loaders/GLTFLoader';
import { GLTF, GLTFLoaderPlugin, GLTFParser } from 'three/examples/jsm/loaders/GLTFLoader.js';
import { GLTF as GLTFSchema } from '@gltf-transform/core';
import { VRMCVRMAnimation } from '@pixiv/types-vrmc-vrm-animation-1.0';
import type { VRMHumanBoneName } from '@pixiv/three-vrm-core';
Expand Down
17 changes: 8 additions & 9 deletions packages/three-vrm-materials-mtoon/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,26 +11,25 @@ MToon (toon material) module for @pixiv/three-vrm
## WebGPU Support

Starting from v3, we provide [WebGPURenderer](https://github.com/mrdoob/three.js/blob/master/examples/jsm/renderers/webgpu/WebGPURenderer.js) compatibility.
To use three-vrm with WebGPURenderer, specify the WebGPU-compatible `MToonNodeMaterialLoaderPlugin` for the `mtoonMaterialPlugin` option of `VRMLoaderPlugin`.
To use MToon with WebGPURenderer, specify the WebGPU-compatible `MToonNodeMaterial` for the `materialType` option of `MToonMaterialLoaderPlugin`.

`MToonNodeMaterial` only supports Three.js r161 or later.
The NodeMaterial system of Three.js is still under development, so we may break compatibility with older versions of Three.js more frequently than other parts of three-vrm.

```js
import { VRMLoaderPlugin, MToonNodeMaterialLoaderPlugin } from '@pixiv/three-vrm';
import { MToonMaterialLoaderPlugin } from '@pixiv/three-vrm-materials-mtoon';
import { MToonNodeMaterial } from '@pixiv/three-vrm-materials-mtoon/nodes';

// ...

// Register a VRMLoaderPlugin
// Register a MToonMaterialLoaderPlugin with MToonNodeMaterial
loader.register((parser) => {

// create a WebGPU compatible MToon loader plugin
const mtoonMaterialPlugin = new MToonNodeMaterialLoaderPlugin(parser);
// create a WebGPU compatible MToonMaterialLoaderPlugin
return new MToonMaterialLoaderPlugin(parser, {

return new VRMLoaderPlugin(parser, {

// Specify the MToon loader plugin to use in the VRMLoaderPlugin instance
mtoonMaterialPlugin,
// set the material type to MToonNodeMaterial
materialType: MToonNodeMaterial,

});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,8 @@
"imports": {
"three": "https://cdn.jsdelivr.net/npm/three@0.164.1/build/three.module.js",
"three/addons/": "https://cdn.jsdelivr.net/npm/three@0.164.1/examples/jsm/",
"@pixiv/three-vrm-materials-mtoon": "../lib/three-vrm-materials-mtoon.module.js"
"@pixiv/three-vrm-materials-mtoon": "../lib/three-vrm-materials-mtoon.module.js",
"@pixiv/three-vrm-materials-mtoon/nodes": "../lib/nodes/index.module.js"
}
}
</script>
Expand All @@ -34,7 +35,7 @@
import * as THREE from 'three';
import { OrbitControls } from 'three/addons/controls/OrbitControls.js';
import WebGPURenderer from 'three/addons/renderers/webgpu/WebGPURenderer.js';
import { MToonNodeMaterial } from '@pixiv/three-vrm-materials-mtoon';
import { MToonNodeMaterial } from '@pixiv/three-vrm-materials-mtoon/nodes';

// renderer
const renderer = new WebGPURenderer();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,10 @@
<script type="importmap">
{
"imports": {
"three": "https://cdn.jsdelivr.net/npm/three@0.164.1/build/three.module.js",
"three/addons/": "https://cdn.jsdelivr.net/npm/three@0.164.1/examples/jsm/",
"@pixiv/three-vrm-materials-mtoon": "../lib/three-vrm-materials-mtoon.module.js"
"three": "https://cdn.jsdelivr.net/npm/three@0.164.0/build/three.module.js",
"three/addons/": "https://cdn.jsdelivr.net/npm/three@0.164.0/examples/jsm/",
"@pixiv/three-vrm-materials-mtoon": "../lib/three-vrm-materials-mtoon.module.js",
"@pixiv/three-vrm-materials-mtoon/nodes": "../lib/nodes/index.module.js"
}
}
</script>
Expand All @@ -35,7 +36,8 @@
import { GLTFLoader } from 'three/addons/loaders/GLTFLoader.js';
import { OrbitControls } from 'three/addons/controls/OrbitControls.js';
import WebGPURenderer from 'three/addons/renderers/webgpu/WebGPURenderer.js';
import { MToonNodeMaterialLoaderPlugin } from '@pixiv/three-vrm-materials-mtoon';
import { MToonMaterialLoaderPlugin } from '@pixiv/three-vrm-materials-mtoon';
import { MToonNodeMaterial } from '@pixiv/three-vrm-materials-mtoon/nodes';

// renderer
const renderer = new WebGPURenderer();
Expand Down Expand Up @@ -67,8 +69,14 @@

loader.register( ( parser ) => {

const plugin = new MToonNodeMaterialLoaderPlugin( parser );
return plugin;

// create a WebGPU compatible MToonMaterialLoaderPlugin
return new MToonMaterialLoaderPlugin( parser, {

// set the material type to MToonNodeMaterial
materialType: MToonNodeMaterial,

} );

} );

Expand Down
5 changes: 5 additions & 0 deletions packages/three-vrm-materials-mtoon/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,11 @@
"import": "./lib/three-vrm-materials-mtoon.module.js",
"require": "./lib/three-vrm-materials-mtoon.cjs"
},
"./nodes": {
"types": "./types/nodes/index.d.ts",
"import": "./lib/nodes/index.module.js",
"require": "./lib/nodes/index.cjs"
},
"./package.json": "./package.json"
},
"repository": {
Expand Down
77 changes: 60 additions & 17 deletions packages/three-vrm-materials-mtoon/src/MToonMaterialLoaderPlugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,13 @@ import * as THREE from 'three';
import * as V1MToonSchema from '@pixiv/types-vrmc-materials-mtoon-1.0';
import type { GLTF, GLTFLoader, GLTFLoaderPlugin, GLTFParser } from 'three/examples/jsm/loaders/GLTFLoader.js';
import type { MToonMaterialParameters } from './MToonMaterialParameters';
import { MToonMaterialOutlineWidthMode } from './MToonMaterialOutlineWidthMode';
import type { MToonMaterialOutlineWidthMode } from './MToonMaterialOutlineWidthMode';
import { GLTFMToonMaterialParamsAssignHelper } from './GLTFMToonMaterialParamsAssignHelper';
import { MToonMaterialLoaderPluginOptions } from './MToonMaterialLoaderPluginOptions';
import type { MToonMaterialLoaderPluginOptions } from './MToonMaterialLoaderPluginOptions';
import type { MToonMaterialDebugMode } from './MToonMaterialDebugMode';
import { GLTF as GLTFSchema } from '@gltf-transform/core';
import { MToonMaterial } from './MToonMaterial';
import type { MToonNodeMaterialLoaderPlugin } from './nodes/MToonNodeMaterialLoaderPlugin';
import type { MToonNodeMaterial } from './nodes/MToonNodeMaterial';

/**
* Possible spec versions it recognizes.
Expand All @@ -18,24 +18,56 @@ const POSSIBLE_SPEC_VERSIONS = new Set(['1.0', '1.0-beta']);
/**
* A loader plugin of {@link GLTFLoader} for the extension `VRMC_materials_mtoon`.
*
* This plugin is for uses with WebGLRenderer.
* To use MToon in WebGPURenderer, use {@link MToonNodeMaterialLoaderPlugin} instead.
* This plugin is for uses with WebGLRenderer by default.
* To use MToon in WebGPURenderer, set {@link materialType} to {@link MToonNodeMaterial}.
*
* @example to use with WebGPURenderer
* ```js
* import { MToonMaterialLoaderPlugin } from '@pixiv/three-vrm-materials-mtoon';
* import { MToonNodeMaterial } from '@pixiv/three-vrm-materials-mtoon/nodes';
*
* // ...
*
* // Register a MToonMaterialLoaderPlugin with MToonNodeMaterial
* loader.register((parser) => {
*
* // create a WebGPU compatible MToonMaterialLoaderPlugin
* return new MToonMaterialLoaderPlugin(parser, {
*
* // set the material type to MToonNodeMaterial
* materialType: MToonNodeMaterial,
*
* });
*
* });
* ```
*/
export class MToonMaterialLoaderPlugin implements GLTFLoaderPlugin {
public static EXTENSION_NAME = 'VRMC_materials_mtoon';

/**
* The type of the material that this plugin will generate.
*
* If you are using this plugin with WebGPU, set this to {@link MToonNodeMaterial}.
*
* @default MToonMaterial
*/
public materialType: typeof THREE.Material;

/**
* This value will be added to `renderOrder` of every meshes who have MaterialsMToon.
* The final renderOrder will be sum of this `renderOrderOffset` and `renderQueueOffsetNumber` for each materials.
* `0` by default.
*
* @default 0
*/
public renderOrderOffset: number;

/**
* There is a line of the shader called "comment out if you want to PBR absolutely" in VRM0.0 MToon.
* When this is true, the material enables the line to make it compatible with the legacy rendering of VRM.
* Usually not recommended to turn this on.
* `false` by default.
*
* @default false
*/
public v0CompatShade: boolean;

Expand All @@ -44,6 +76,8 @@ export class MToonMaterialLoaderPlugin implements GLTFLoaderPlugin {
* You can visualize several components for diagnosis using debug mode.
*
* See: {@link MToonMaterialDebugMode}
*
* @default 'none'
*/
public debugMode: MToonMaterialDebugMode;

Expand All @@ -62,6 +96,7 @@ export class MToonMaterialLoaderPlugin implements GLTFLoaderPlugin {
public constructor(parser: GLTFParser, options: MToonMaterialLoaderPluginOptions = {}) {
this.parser = parser;

this.materialType = options.materialType ?? MToonMaterial;
this.renderOrderOffset = options.renderOrderOffset ?? 0;
this.v0CompatShade = options.v0CompatShade ?? false;
this.debugMode = options.debugMode ?? 'none';
Expand All @@ -80,7 +115,7 @@ export class MToonMaterialLoaderPlugin implements GLTFLoaderPlugin {
public getMaterialType(materialIndex: number): typeof THREE.Material | null {
const v1Extension = this._getMToonExtension(materialIndex);
if (v1Extension) {
return MToonMaterial;
return this.materialType;
}

return null;
Expand Down Expand Up @@ -248,6 +283,22 @@ export class MToonMaterialLoaderPlugin implements GLTFLoaderPlugin {
}
}

/**
* Check whether the material should generate outline or not.
* @param surfaceMaterial The material to check
* @returns True if the material should generate outline
*/
private _shouldGenerateOutline(surfaceMaterial: THREE.Material): boolean {
// we might receive MToonNodeMaterial as well as MToonMaterial
// so we're gonna duck type to check if it's compatible with MToon type outlines
return (
typeof (surfaceMaterial as any).outlineWidthMode === 'string' &&
(surfaceMaterial as any).outlineWidthMode !== 'none' &&
typeof (surfaceMaterial as any).outlineWidthFactor === 'number' &&
(surfaceMaterial as any).outlineWidthFactor > 0.0
);
}

/**
* Generate outline for the given mesh, if it needs.
*
Expand All @@ -265,15 +316,7 @@ export class MToonMaterialLoaderPlugin implements GLTFLoaderPlugin {
return;
}

// check whether we really have to prepare outline or not
// we might receive MToonNodeMaterial as well as MToonMaterial
// so we're gonna duck type to check if it's compatible with MToon type outlines
if (
typeof (surfaceMaterial as any).outlineWidthMode !== 'string' ||
(surfaceMaterial as any).outlineWidthMode === 'none' ||
typeof (surfaceMaterial as any).outlineWidthFactor !== 'number' ||
(surfaceMaterial as any).outlineWidthFactor <= 0.0
) {
if (!this._shouldGenerateOutline(surfaceMaterial)) {
return;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,18 +1,31 @@
import type * as THREE from 'three';
import type { MToonMaterialDebugMode } from './MToonMaterialDebugMode';
import type { MToonNodeMaterial } from './nodes/MToonNodeMaterial';

export interface MToonMaterialLoaderPluginOptions {
/**
* The type of the material that the loader plugin will generate.
*
* If you are using this plugin with WebGPU, set this to {@link MToonNodeMaterial}.
*
* @default MToonMaterial
*/
materialType?: typeof THREE.Material;

/**
* This value will be added to `renderOrder` of every meshes who have MToonMaterial.
* The final `renderOrder` will be sum of this `renderOrderOffset` and `renderQueueOffsetNumber` for each materials.
* `0` by default.
*
* @default 0
*/
renderOrderOffset?: number;

/**
* There is a line of the shader called "comment out if you want to PBR absolutely" in VRM0.0 MToon.
* When this is true, the material enables the line to make it compatible with the legacy rendering of VRM.
* Usually not recommended to turn this on.
* `false` by default.
*
* @default false
*/
v0CompatShade?: boolean;

Expand All @@ -21,6 +34,8 @@ export interface MToonMaterialLoaderPluginOptions {
* You can visualize several components for diagnosis using debug mode.
*
* See: {@link MToonMaterialDebugMode}
*
* @default 'none'
*/
debugMode?: MToonMaterialDebugMode;
}
2 changes: 0 additions & 2 deletions packages/three-vrm-materials-mtoon/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,3 @@ export { MToonMaterial } from './MToonMaterial';
export { MToonMaterialDebugMode } from './MToonMaterialDebugMode';
export { MToonMaterialOutlineWidthMode } from './MToonMaterialOutlineWidthMode';
export type { MToonMaterialParameters } from './MToonMaterialParameters';

export * from './nodes';
Loading
Loading