美文网首页
CocosCreator中,显示SpriteFrame的一部分

CocosCreator中,显示SpriteFrame的一部分

作者: 全新的饭 | 来源:发表于2022-10-28 17:36 被阅读0次

    说明

    将一个SpriteFrame横向均分x份,纵向均分成y份,显示其中的第n份。


    image.png

    如图,横向均分成3份,纵向均分成4份,显示(右侧小方块中)其中的第(2,1)个。(从0开始数,起点是左上,终点是右下)。

    // 左边显示的完整图
    this._sprite.spriteFrame = spriteFrame;     
    // 将给定图片分成若干份,显示其中的一份。
    const width = spriteFrame.width / 3;
    const height = spriteFrame.height / 4;
    const x = width*2;
    const y = height;
    const rect = new Rect(x, y, width, height);
    const sectionSprite = spriteFrame.clone();
    sectionSprite.rect = rect;
    this._sectionSprite.spriteFrame = sectionSprite;
    

    应用

    传入完整图片(SpriteFrame)、区域(宽、高、中心位置),将其划分成若干方块显示:CreateElements
    DivideImg.ts

    import { _decorator, Component, Node, SpriteFrame, CCInteger, Vec3, MATH_FLOAT_ARRAY, Rect, instantiate, Sprite } from 'cc';
    import { ImgElement } from './ImgElement';
    const { ccclass, property } = _decorator;
    
    @ccclass('DivideImg')
    export class DivideImg extends Component 
    {
        @property({ type: ImgElement, visible: true, displayName: 'Element模板' })
        private _elementTemplate: ImgElement;
        @property({ type: CCInteger, visible: true, displayName: '最小份数' })
        private _minCnt: number = 3;
    
        private _rowCnt: number;
        private _columnCnt: number;
        private _elementWidth: number;
        private _elementHeight: number;
        // 左下
        private _originalPos: Vec3;
    
        private _elements: ImgElement[];
    
        start()
        {
            this.init();
        }
    
        onDestroy()
        { 
            this.myDestroy();
        }
    
        private init(): void
        {
            this._elementTemplate.hide();
            this._elements = new Array<ImgElement>();
        }
        
        private myDestroy(): void
        {
            this.clearElements();
            this._elements = null;
        }
    
        public CreateElements(spriteFrame: SpriteFrame, width:number, height:number, centerPos:Vec3):void
        {
            // 删除原有Elements
            this.clearElements();
            // 算得数据:行份数、列份数、width,height,原点(左下)的位置
            this.refreshData(width, height, centerPos);
            // 创建各元素
            for (let index = 0; index < this._rowCnt * this._columnCnt; index++)
            { 
                const curElement = instantiate(this._elementTemplate.node).getComponent(ImgElement);
                curElement.node.setParent(this._elementTemplate.node.parent);
                curElement.init(index, this.createElementSprite(spriteFrame, index), this._elementWidth, this._elementHeight);
                this._elements.push(curElement);
            }
            // 设置各元素的位置(先都设置到原位)并显示
            for (const e of this._elements)
            { 
                e.setPos(e.index, this.getPos(e.index));
                e.show();
            }
        }
    
        private clearElements(): void
        { 
            if (this._elements)
            { 
                for (const e of this._elements)
                { 
                    e.myDestroy();
                }
                this._elements.splice(0, this._elements.length);
            }
        }
    
        private refreshData(width: number, height: number, centerPos: Vec3): void
        {
            if (width > height)
            { 
                this._rowCnt = this._minCnt;
                this._elementHeight = height / this._rowCnt;
                this._columnCnt = Math.round(width / this._elementHeight);
                this._elementWidth = width / this._columnCnt;
            }
            else
            { 
                this._columnCnt = this._minCnt;
                this._elementWidth = width / this._columnCnt;
                this._rowCnt = Math.round(height / this._elementWidth);
                this._elementHeight = height / this._rowCnt;
            }
            
            this._originalPos = new Vec3(centerPos.x - width / 2 + this._elementWidth / 2, centerPos.y - height / 2 + this._elementHeight / 2, centerPos.z);
        }
    
        private createElementSprite(spriteFrame: SpriteFrame, index: number): SpriteFrame
        { 
            const width = spriteFrame.width / this._columnCnt;
            const height = spriteFrame.height / this._rowCnt;
            const x = index % this._columnCnt;
            const y = this._rowCnt - 1 - Math.floor(index / this._columnCnt);
            const rect = new Rect(x*width, y*height, width, height);
            const elementSprite = spriteFrame.clone();
            elementSprite.rect = rect;
            return elementSprite;
        }
    
        // index方向:从左到右,从下到上,一行一行填充
        private getPos(index: number): Vec3
        { 
            const y = Math.floor(index / this._columnCnt);
            const x = index % this._columnCnt;
            const pos = new Vec3(this._originalPos.x + x * this._elementWidth, this._originalPos.y + y * this._elementHeight, this._originalPos.z);
            return pos;
        }
    }
    

    ImgElement.ts

    import { _decorator, Component, Node, Sprite, UITransform, SpriteFrame, Vec3, size, Size, rect, Rect } from 'cc';
    const { ccclass, property } = _decorator;
    
    @ccclass('ImgElement')
    export class ImgElement extends Component 
    {
        private _index: number;
        public get index(): number
        { 
            return this._index;
        }
        public _posIndex: number;
        public get posIndex(): number
        { 
            return this._posIndex;
        }
        @property({ type: Node, visible: true, displayName: '根节点' })
        private _root: Node;
        @property({ type: Sprite, visible: true, displayName: '图片' })
        private _sprite: Sprite;
        @property({ type: UITransform, visible: true, displayName: 'UITrans' })
        private _spriteTrans: UITransform;
    
        public init(index:number, spriteFrame:SpriteFrame, width:number, height:number): void
        {   
            this._index = index;
            this._posIndex = -1;
            this._sprite.spriteFrame = spriteFrame;
            this._spriteTrans.setContentSize(new Size(width, height));
        }
        
        public myDestroy(): void
        { 
            this._index = -1;
            this._posIndex = -1;
            this._sprite.spriteFrame = null;
            this._spriteTrans = null;
            this._root.destroy();
        }
    
        public setPos(posIndex:number, pos: Vec3)
        { 
            this._posIndex = posIndex;
            this._root.setWorldPosition(pos);
        }
    
        public isAtRightPos(): boolean
        { 
            return this._index == this.posIndex;
        }
    
        public hide(): void
        { 
            this._root.active = false;
        }
        public show(): void
        {
            this._root.active = true;
        }
    }
    

    相关文章

      网友评论

          本文标题:CocosCreator中,显示SpriteFrame的一部分

          本文链接:https://www.haomeiwen.com/subject/hvjftdtx.html