I'm trying to build an application on KonvaJS with the Vue library.
I've got a group layer where I'm drawing a circle and placing images inside this group.
<v-group
v-for="item in listGroup_Logo"
:key="item.name"
:ref="item.name"
:config="item"
@dblclick="check"
@dragstart="handleDragStart"
@dragend="handleDragEnd"
>
<v-circle
v-for="item in listCircle_Logo"
:key="item.name"
:ref="item.name"
:config="item"
@dragstart="handleDragStart"
@dragend="handleDragEnd"
/>
<v-image
v-for="item in listLogo"
@dragstart="handleDragStart"
@dragend="handleDragEnd"
:ref="item.name"
:key="item.name"
:config="item"
:keyup.delete="deleteItemFromKey"
/>
</v-group>
The goal is to clip the images as per the circle/group area. Also, the end user can resize the group element collectively. As you can see below, resizing the group effects the circle strokes.
To achieve this I defined the basic configuration dataset listGroup_Logo
to be passed inside the group layer, so this config data renders at the initial rendering.
listGroup_Logo: [
{
clipFunc: (ctx) => {
ctx.arc(50, 50, 30, 0, Math.PI * 2, false);
},
draggable: true,
x: 50,
y: 50,
name: "Group1676367620342",
type: "group",
},
],
To add drag and drop functionality I'm tracking @mousedown
and @touchstart
events at v-stage
component and defined a method handleMousedown
to do the further modifications.
I'm trying to fetch the x and y positions along with the scaleX
and scaleY
values and trying to update the circle configs:
this.listCircle_Logo[objIndex] = e.target.attrs;
let scaleX =
typeof e.target.attrs.scaleX === "undefined"
? 1
: e.target.attrs.scaleX;
let scaleY =
typeof e.target.attrs.scaleY === "undefined"
? 1
: e.target.attrs.scaleY;
let obj = {
clipFunc: (ctx) => {
ctx.arc(
50 * scaleX,
50 * scaleY,
30 * scaleX,
0,
Math.PI * 2,
false
);
},
};
this.listGroup_Logo[0].clipFunc = obj.clipFunc;
But the circle is not updating its values. See the image below:
I've made a sandbox for my code. You can find it here: https://codesandbox.io/s/bold-fog-ivccnt?file=/src/App.vue
Please advise on how to resize the entire group without disturbing the strokes or circles.
You may need to change the clipping of your group every time you transform circle:
handleTransform(e) {
this.listGroup_Logo[0].clipFunc = (ctx) => {
ctx.save();
ctx.scale(e.target.scaleX(), e.target.scaleY())
ctx.arc(
e.target.x() / e.target.scaleX(),
e.target.y() / e.target.scaleY(),
30,
0,
Math.PI * 2,
false
);
ctx.restore();
};
},
https://codesandbox.io/s/dreamy-hugle-8zqcci?file=/src/App.vue
Also for a bit better view I added strokeScaleEnabled: false
to circle and ignoreStroke: true
to transformer.