解决 Uncaught TypeError: SpriteCanvasMaterial is not a constructor.


foreword

Last week, I bought the "Three.js Development Guide", the third edition. The grammar in it is not quite up to date, and it is a bit old. I can't blame the author entirely, because the iteration of three is really fast.


1. Alternative syntax

I have nothing to do in the past few days, and I have been in contact with Three before, so I quickly progressed to Chapter 6.
When I was advancing the section of using Canvas textures to add styles to sprites (Sprite), I checked the documentation in advance and found SpriteCanvasMaterialthis The syntax doesn't exist in the docs, but part of Three's syntax...even if it's active, you can't find it in the docs so I'm not sure if it's really deprecated.

But even if it is not in the source code, I can't justify it. I started looking for an alternative to this method.

Based on the description and source code in the book, it can be seen that this grammar generates materials based on DOM:

var getTexture = function (ctx) {
    
    
 // 此处绘制canvas, 无返回值;
};

createSprites();
render();

function createSprites() {
    
    
  var material = new THREE.SpriteCanvasMaterial({
    
    
    program: getTexture,
    color: 0xffffff
  });

  material.rotation = Math.PI;

  var range = 500;
  for (let i = 0; i < 1500; i++) {
    
    
    const sprite = new THREE.Sprite(material);
    sprite.position.set(Math.random() * range - range / 2, Math.random() * range - range / 2, Math.random() * range - range / 2);
    sprite.scale.set(0.1, 0.1, 0.1);
    scene.add(sprite);
  }
}

Then the material will be used to generate sprites. Since Canvas is used, there should be Canvas patterns on this material. I don’t know if it is a pattern based on textures.

new THREE.Sprite(material);This syntax has not been eliminated.

Then you only need a DOM元素process that can convert it into a material with textures. I remember that I have learned Three before CanvasTexture(). This syntax can be DOM元素generated by using Texture:

function createImageTexture() {
    
     // Canvas贴图直接用图片做
  const img = document.createElement('img');
  img.src = '../assets/textures/construction.jpg';

  const texture = new THREE.CanvasTexture(img);
  return texture;
}

Now that DOM元素the generated texture is available, a material is needed to carry the texture. Here we directly select the material for sprites. The name is for sprites:

const material = new THREE.SpriteMaterial({
    
     map: texture, color: 0xffffff });

In practice, if you want to add material to the elf, the elf will not appear when other materials are added to the elf.
By the way, paste the texture on it.

The material obtained in this way SpriteCanvasMaterialis the same as the material generated by the old syntax. Now use this material to generate the sprite:

const range = 500;
for (let i = 0; i < 1500; i++) {
    
    
  const sprite = new THREE.Sprite(material);
  sprite.position.set(Math.random() * range - range / 2, Math.random() * range - range / 2, Math.random() * range - range / 2);
  sprite.scale.set(0.8, 0.8, 0.8);
  scene.add(sprite);
}

insert image description here

I don't use Canvas as CanavsTexturea parameter but one img. In fact, texture maps THREE.CanvasTexture()can also be created based on elements. When creating an object, if the parameter passed in is an element, the object will create a new element internally, and the element's Content is drawn onto the element, and the element is returned as a texture map.HTMLImageElementCanvasTextureHTMLImageElement
CanvasTextureCanvasHTMLImageElement


Summarize

Guess you like

Origin blog.csdn.net/qq_52697994/article/details/130754676