@@ -21,9 +21,17 @@ function collectMeshes(scene: THREE.Group): Set<THREE.Mesh> {
21
21
22
22
function combineMorph (
23
23
positionAttributes : ( THREE . BufferAttribute | THREE . InterleavedBufferAttribute ) [ ] ,
24
- binds : Iterable < VRMExpressionMorphTargetBind > ,
24
+ binds : Set < VRMExpressionMorphTargetBind > ,
25
25
morphTargetsRelative : boolean ,
26
- ) : THREE . BufferAttribute {
26
+ ) : THREE . BufferAttribute | THREE . InterleavedBufferAttribute {
27
+ // if there is only one morph target and the weight is 1.0, we can use the original as-is
28
+ if ( binds . size === 1 ) {
29
+ const bind = binds . values ( ) . next ( ) . value ! ;
30
+ if ( bind . weight === 1.0 ) {
31
+ return positionAttributes [ bind . index ] ;
32
+ }
33
+ }
34
+
27
35
const newArray = new Float32Array ( positionAttributes [ 0 ] . count * 3 ) ;
28
36
let weightSum = 0.0 ;
29
37
@@ -108,14 +116,18 @@ export function combineMorphs(vrm: VRMCore): void {
108
116
continue ;
109
117
}
110
118
119
+ // prevent cloning morph attributes
120
+ const originalMorphAttributes = mesh . geometry . morphAttributes ;
121
+ mesh . geometry . morphAttributes = { } ;
122
+
111
123
const geometry = mesh . geometry . clone ( ) ;
112
124
mesh . geometry = geometry ;
113
125
const morphTargetsRelative = geometry . morphTargetsRelative ;
114
126
115
- const hasPMorph = geometry . morphAttributes . position != null ;
116
- const hasNMorph = geometry . morphAttributes . normal != null ;
127
+ const hasPMorph = originalMorphAttributes . position != null ;
128
+ const hasNMorph = originalMorphAttributes . normal != null ;
117
129
118
- const morphAttributes : typeof geometry . morphAttributes = { } ;
130
+ const morphAttributes : typeof originalMorphAttributes = { } ;
119
131
const morphTargetDictionary : typeof mesh . morphTargetDictionary = { } ;
120
132
const morphTargetInfluences : typeof mesh . morphTargetInfluences = [ ] ;
121
133
@@ -130,10 +142,10 @@ export function combineMorphs(vrm: VRMCore): void {
130
142
let i = 0 ;
131
143
for ( const [ name , bindSet ] of nameBindSetMap ) {
132
144
if ( hasPMorph ) {
133
- morphAttributes . position [ i ] = combineMorph ( geometry . morphAttributes . position , bindSet , morphTargetsRelative ) ;
145
+ morphAttributes . position [ i ] = combineMorph ( originalMorphAttributes . position , bindSet , morphTargetsRelative ) ;
134
146
}
135
147
if ( hasNMorph ) {
136
- morphAttributes . normal [ i ] = combineMorph ( geometry . morphAttributes . normal , bindSet , morphTargetsRelative ) ;
148
+ morphAttributes . normal [ i ] = combineMorph ( originalMorphAttributes . normal , bindSet , morphTargetsRelative ) ;
137
149
}
138
150
139
151
expressionMap ?. [ name ] . addBind (
0 commit comments