Home Game Development Set vertex shade of sprite in 3.5 – Cocos Creator

Set vertex shade of sprite in 3.5 – Cocos Creator

0
Set vertex shade of sprite in 3.5 – Cocos Creator

[ad_1]

Hello,

I couldn’t discover an updated instance of the way to set the vertices colours of a sprite in 3.5.
Can somebody clarify to me the way it’s accomplished, or hyperlink me an instance/doc that I may need missed ?
Thanks upfront.

If I adapt the older examples I discovered for the three.5 API, it offers one thing like this :

@ccclass("ColorSprite")
export class ColorSprite extends SpritePart {
  @property({ sort: [Color] })
  non-public colours: Color[] = [];


  protected _updateColor() {
    tremendous._updateColor();

    const vData = this.renderData.vertexFormat;
    let colorOffset = 5;
    for (let i = 0; i < 4; i++)  this.shade;
      const colorR = shade.r / 255;
      const colorG = shade.g / 255;
      const colorB = shade.b / 255;
      const colorA = this.node._uiProps.opacity;
      vData![colorOffset] = colorR;
      vData![colorOffset + 1] = colorG;
      vData![colorOffset + 2] = colorB;
      vData![colorOffset + 3] = colorA;
      colorOffset += 9;
    
  }
}

But this provides an error :

Uncaught TypeError: Cannot learn properties of undefined (studying ‘format’)
at updateOpacity (utils.ts:83:35)
at Batcher2D.stroll (batcher-2nd.ts:670:13)
at Batcher2D.stroll (batcher-2nd.ts:680:22)
at Batcher2D.stroll (batcher-2nd.ts:680:22)
at Batcher2D.replace (batcher-2nd.ts:204:18)
at Root.frameMove (root.ts:437:31)
at Director.tick (director.ts:715:25)
at callback (recreation.ts:838:26)

By the best way, the rationale I would like it is because I wish to apply a shader to a sprite that takes its sprite body by way of an atlas. Because of the atlas, I now not have entry to uv coordinates from 0 to 1 as a way to know the place I’m within the sprite within the fragment shader.
My thought to counter this was to make use of vertex shade interpolation to simulates a 0 to 1 coordinate.
If somebody has a greater thought for this, let me know.

Ok, I discovered the best way to do it :

import { _decorator, Sprite, Color } from 'cc';
const { ccclass, property } = _decorator;

@ccclass('ColorSprite')
export class ColorSprite extends Sprite {
    @property([Color])
    non-public colours: Array<Color> = [Color.WHITE, Color.WHITE, Color.WHITE, Color.WHITE];

    begin() {
        let colorOffset = 5;
        const vertexCount = this.renderData.vertexCount;
        if (vertexCount === 0) return;
        const vData = this.renderData.chunk.vb;
        const stride = this.renderData.floatStride;
        for(let i = 0; i < vertexCount; i++) {
            vData[colorOffset] = this.colours[i % 4].r / 255;
            vData[colorOffset + 1] = this.colours[i % 4].g / 255;
            vData[colorOffset + 2] = this.colours[i % 4].b / 255;
            vData[colorOffset + 3] = this.colours[i % 4].a / 255;
            colorOffset += stride;
        }
    }
}

It works nicely on sprites and labels that use ttf fonts. Both in 3.5 and three.6.
However, when a label makes use of a bitmap font, it appears to be like like one thing resets the vertices colours.
I don’t discover a method to counter that.
Any assist ?

I needed to learn a variety of supply recordsdata to discover a answer, however right here it’s :

import {
  _decorator,
  Color,
  Label,
} from "cc";
const { ccclass, property } = _decorator;

@ccclass("ColorBitmapFontLabel")
export class ColorBitmapFontLabel extends Label {
  @property([Color])
  non-public colours: Array<Color> = [Color.RED, Color.RED, Color.BLUE, Color.BLUE];

  non-public originalFillBuffer: Function;

  begin() {
    this.originalFillBuffer = this._assembler.fillBuffers;

    this._assembler.fillBuffers = (comp: Label, renderer) => {
      this.originalFillBuffer(comp, renderer);
      this.setVerticesColors();
    };
  }

  setVerticesColors() {
    let colorOffset = 5;
    const vertexCount = this.renderData.vertexCount;
    if (vertexCount === 0) return;
    const vData = this.renderData.chunk.vb;
    const stride = this.renderData.floatStride;
    for (let i = 0; i < vertexCount; i++) {
      vData[colorOffset] = this.colours[i % 4].r / 255;
      vData[colorOffset + 1] = this.colours[i % 4].g / 255;
      vData[colorOffset + 2] = this.colours[i % 4].b / 255;
      vData[colorOffset + 3] = this.colours[i % 4].a / 255;
      colorOffset += stride;
    }
  }
}

2 Likes

It does work on net platform.
Since we modify 2nd/UI-rendering course of in v3.6, rendering information of Label are saved in RenderEntity and transported to native to excute fillBuffers like net.
You would possibly attempt to overwrite setEntityColor in UIRenderer, recombine a shade and assign it to entity.shade. Then construct in one among native platforms and validate it.

1 Like

My goal is net solely. But thanks for the information.

[ad_2]

LEAVE A REPLY

Please enter your comment!
Please enter your name here