<template>
    <div>
        <el-table :data="tableData" style="width: 100%" class="elementTable">
            <el-table-column prop="val" label="值" width="180"></el-table-column>
            <el-table-column prop="desc" label="描述"></el-table-column>
        </el-table>
        <div style="margin: 14px 0;">
            <span style="font-size: 14px;">选择融合方式</span>
            <el-select v-model="value" placeholder="请选择" @change="changeCom" size="small">
                <el-option v-for="item in options" :key="item.value" :label="item.label"
                           :value="item.value"></el-option>
            </el-select>
        </div>
        <canvas :id="id" width="740" height="400" tabindex="0"/>
    </div>
</template>

<script lang="ts">
    import { SGraphItem, SGraphScene, SGraphView } from "@persagy-web/graph/lib";
    import { SColor, SCompositeType, SPainter, SRect } from "@persagy-web/draw/lib"
    import { Component, Vue } from "vue-property-decorator";
    import { v1 as uuid } from "uuid";

    class Circle extends SGraphItem {
        /** 融合方式 默认。在目标图像上显示源图像。 */
        _composite = SCompositeType.SourceOver;
        get composite(): SCompositeType {
            return this._composite;
        }

        set composite(v: SCompositeType) {
            this._composite = v;
            this.update();
        }

        /**
         * 构造函数
         *
         * @param parent    Item 图像引擎
         * @param com       融合方式
         */
        constructor(parent: SGraphItem | null, com: SCompositeType) {
            super(parent);
            this.composite = com ? SCompositeType.SourceOver : com;
        }

        /**
         * 矩形数据类型绘制
         */
        boundingRect(): SRect {
            return new SRect(-500, -500, 1500, 1500);
        }

        /**
         * Item 绘制操作
         *
         * @param painter 绘制对象
         */
        onDraw(painter: SPainter): void {
            painter.brush.color = SColor.Blue;
            painter.pen.color = SColor.Transparent;
            painter.drawRect(0, 0, 1000, 1000);
            //融合属性
            painter.composite = this.composite;
            painter.brush.color = SColor.Red;
            //绘制圆形
            painter.drawCircle(0, 0, 500);
        }
    }

    @Component
    export default class CompositeCanvas extends Vue {
        view: SGraphView | undefined;
        id: string = uuid();
        value: SCompositeType = SCompositeType.SourceOver;
        options = [{
            value: SCompositeType.DestinationAtop,
            label: 'DestinationAtop'
        }, {
            value: SCompositeType.DestinationIn,
            label: 'DestinationIn'
        }, {
            value: SCompositeType.DestinationOut,
            label: 'DestinationOut'
        }, {
            value: SCompositeType.DestinationOver,
            label: 'DestinationOver'
        }, {
            value: SCompositeType.SourceAtop,
            label: 'SourceAtop'
        }, {
            value: SCompositeType.SourceIn,
            label: 'SourceIn'
        }, {
            value: SCompositeType.SourceOver,
            label: 'SourceOver'
        }, {
            value: SCompositeType.SourceOut,
            label: 'SourceOut'
        }, {
            value: SCompositeType.Xor,
            label: 'Xor'
        }, {
            value: SCompositeType.Lighter,
            label: 'Lighter'
        }, {
            value: SCompositeType.Copy,
            label: 'Copy'
        }];
        circle: Circle | undefined;
        tableData = [{
            val: 'source-over',
            desc: '默认。在目标图像上显示源图像。'
        }, {
            val: 'source-atop',
            desc: '在目标图像顶部显示源图像。源图像位于目标图像之外的部分是不可见的。'
        },
            {
                val: 'source-in',
                desc: '在目标图像中显示源图像。只有目标图像之内的源图像部分会显示，目标图像是透明的。'
            },
            {
                val: 'source-out',
                desc: '在目标图像之外显示源图像。只有目标图像之外的源图像部分会显示，目标图像是透明的。'
            },
            {
                val: 'destination-over',
                desc: '在源图像上显示目标图像。'
            },
            {
                val: 'destination-atop',
                desc: '在源图像顶部显示目标图像。目标图像位于源图像之外的部分是不可见的。'
            },
            {
                val: 'destination-in',
                desc: '在源图像中显示目标图像。只有源图像之内的目标图像部分会被显示，源图像是透明的。'
            },
            {
                val: 'destination-out',
                desc: '在源图像之外显示目标图像。只有源图像之外的目标图像部分会被显示，源图像是透明的。'
            },
            {
                val: 'lighter',
                desc: '显示源图像 + 目标图像。'
            },
            {
                val: 'copy',
                desc: '显示源图像。忽略目标图像。'
            },
            {
                val: 'xor',
                desc: '使用异或操作对源图像与目标图像进行组合。'
            }
        ];

        mounted(): void {
            this.init()
        };

        init(): void {
            this.view = new SGraphView(this.id);
            const scene = new SGraphScene();
            this.circle = new Circle(null, SCompositeType.SourceOut);
            scene.addItem(this.circle);
            this.view.scene = scene;
            this.view.fitSceneToView();
            this.view.scalable = false;
        };

        changeCom(val: SCompositeType): void {
            if (this.circle) {
                this.circle.composite = val;
            }
        }
    }
</script>
