Skip to content

Commit 56c7875

Browse files
committed
Vuejs error making GS freeze
* fixed the given demo which was freezing making widgets and not removing items. PROBLEM: let grid = ref(null); grid.value = GridStack.init() was causing proxy so all items were cloned and code compares node = node instead of ids...
1 parent fd60fd1 commit 56c7875

File tree

4 files changed

+173
-5
lines changed

4 files changed

+173
-5
lines changed

demo/index.html

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ <h1>Demos</h1>
2727
<li><a href="two_vertical.html">Two grids Vertical</a></li>
2828
<li><a href="vue2js.html">Vue2.js</a></li>
2929
<li><a href="vue3js.html">Vue3.js</a></li>
30+
<li><a href="vue3js_v-for.html">Vue3 with v-for</a></li>
3031
<li><a href="web-comp.html">Web Component</a></li>
3132
<li><a href="web1.html">Website demo 1</a></li>
3233
<li><a href="web2.html">Website demo 2</a></li>

demo/vue3js.html

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
<main id="app">
1212
<h1>How to integrate GridStack.js with Vue.js</h1>
1313
<p>
14-
As with any virtualDOM-based framework, you need to check if Vue has
14+
As with any virtual DOM based framework, you need to check if Vue has
1515
rendered the DOM (or any updates to it) <strong>before</strong> you
1616
initialize GridStack or call its methods. As a basic example, check this
1717
component's <code>mounted</code> hook.
@@ -35,7 +35,7 @@ <h1>How to integrate GridStack.js with Vue.js</h1>
3535
setup() {
3636
let count = ref(0);
3737
let info = ref("");
38-
let grid = null;
38+
let grid = null; // DO NOT use ref(NULL) as proxies GS will break all logic when comparing structures... see https://github.com/gridstack/gridstack.js/issues/2115
3939
const items = [
4040
{ x: 2, y: 1, h: 2 },
4141
{ x: 2, y: 4, w: 3 },
@@ -45,7 +45,7 @@ <h1>How to integrate GridStack.js with Vue.js</h1>
4545
];
4646

4747
onMounted(() => {
48-
grid = GridStack.init({
48+
grid = GridStack.init({ // DO NOT user grid.value = GridStack.init(), see above
4949
float: true,
5050
cellHeight: "70px",
5151
minRow: 1,

demo/vue3js_v-for.html

Lines changed: 163 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,163 @@
1+
<!DOCTYPE html>
2+
<html lang="en">
3+
<head>
4+
<meta charset="UTF-8" />
5+
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
6+
<title>Vue3 v-for Gridstack</title>
7+
<link rel="stylesheet" href="demo.css"/>
8+
<script src="../dist/gridstack-all.js"></script>
9+
</head>
10+
<body>
11+
<main id="app">
12+
<h1>How to integrate GridStack.js with Vue.js</h1>
13+
<p>
14+
As with any virtual DOM based framework, you need to check if Vue has
15+
rendered the DOM (or any updates to it) <strong>before</strong> you
16+
initialize GridStack or call its methods. As a basic example, check this
17+
component's <code>mounted</code> hook.
18+
</p>
19+
<p>
20+
If your app requires more complex render logic than the inline template
21+
in `addWidget`, consider
22+
<a
23+
href="https://github.com/gridstack/gridstack.js/tree/master/doc#makewidgetel"
24+
>makeWidget</a
25+
>
26+
to let Vue deal with DOM rendering.
27+
</p>
28+
<button type="button" @click="addNewWidget2()">Add Widget pos [0,0]</button>
29+
<button type="button" @click="removeLastWidget()">Remove Last Widget</button>
30+
<br>
31+
<br>
32+
<button type="button" @click="changeFloat()">Float: {{gridFloat}}</button>
33+
34+
<div>{{ info }}</div>
35+
<br>
36+
<div><b :style="{color: color}">{{ gridInfo }}</b></div>
37+
<br>
38+
39+
<div class="grid-stack">
40+
<div v-for="(w, indexs) in items" class="grid-stack-item" :gs-x="w.x" :gs-y="w.y" :gs-w="w.w" :gs-h="w.h" :gs-id="w.id" :id="w.id">
41+
<div class="grid-stack-item-content">
42+
<button @click="remove(w)">remove</button>
43+
{{w}}
44+
</div>
45+
</div>
46+
</div>
47+
48+
</main>
49+
<script type="module">
50+
import { createApp, ref, onMounted, nextTick } from "https://cdn.jsdelivr.net/npm/vue@3.0.11/dist/vue.esm-browser.js";
51+
52+
createApp({
53+
setup() {
54+
let count = ref(0);
55+
let info = ref("");
56+
let gridFloat = ref(false);
57+
let color = ref("black");
58+
let gridInfo = ref("");
59+
let grid = null; // DO NOT use ref(NULL) as proxies GS will break all logic when comparing structures... see https://github.com/gridstack/gridstack.js/issues/2115
60+
let items = ref([]);
61+
62+
onMounted(() => {
63+
grid = GridStack.init({ // DO NOT user grid.value = GridStack.init(), see above
64+
float: false,
65+
cellHeight: "70px",
66+
minRow: 1,
67+
});
68+
grid.on("dragstop", function (event, element) {
69+
const node = element.gridstackNode;
70+
info.value = `you just dragged node #${node.id} to ${node.x},${node.y} – good job!`;
71+
});
72+
grid.on('change', onChange);
73+
// gridFloat.value = grid.float();
74+
});
75+
76+
function changeFloat() {
77+
gridFloat.value = !gridFloat.value;
78+
grid.float(gridFloat.value);
79+
}
80+
81+
function onChange(event, changeItems) {
82+
updateInfo();
83+
// update item position
84+
changeItems.forEach(item => {
85+
var widget = items.value.find(w => w.id == item.id);
86+
if (!widget) {
87+
alert("Widget not found: " + item.id);
88+
return;
89+
}
90+
widget.x = item.x;
91+
widget.y = item.y;
92+
widget.w = item.w;
93+
widget.h = item.h;
94+
});
95+
}
96+
97+
98+
function addNewWidget2() {
99+
const node = items[count.value] || { x: 0, y: 0, w: 2, h: 2 };
100+
node.id = 'w_'+ (count.value++);
101+
// grid.addWidget(node);
102+
items.value.push(node);
103+
nextTick(()=>{
104+
grid.makeWidget(node.id);
105+
updateInfo();
106+
});
107+
}
108+
109+
function removeLastWidget() {
110+
if (count.value == 0) return;
111+
var id = `w_${count.value-1}`;
112+
var index = items.value.findIndex(w => w.id == id);
113+
if (index < 0) return;
114+
var removed = items.value[index];
115+
remove(removed);
116+
}
117+
118+
function remove(widget) {
119+
var index = items.value.findIndex(w => w.id == widget.id);
120+
items.value.splice(index, 1);
121+
const selector = `#${widget.id}`;
122+
grid.removeWidget(selector, false);
123+
updateInfo();
124+
}
125+
126+
function updateInfo() {
127+
color.value = grid.engine.nodes.length == items.value.length ? "black" : "red";
128+
gridInfo.value = `Grid engine: ${grid.engine.nodes.length}, widgets: ${items.value.length}`;
129+
130+
}
131+
132+
return {
133+
info,
134+
items,
135+
addNewWidget2,
136+
removeLastWidget,
137+
onChange,
138+
grid,
139+
gridInfo,
140+
remove,
141+
gridFloat,
142+
changeFloat,
143+
color
144+
};
145+
},
146+
147+
watch: {
148+
/**
149+
* Clear the info text after a two second timeout. Clears previous timeout first.
150+
*/
151+
info: function (newVal) {
152+
if (newVal.length === 0) return;
153+
154+
window.clearTimeout(this.timerId);
155+
this.timerId = window.setTimeout(() => {
156+
this.info = "";
157+
}, 2000);
158+
},
159+
},
160+
}).mount("#app");
161+
</script>
162+
</body>
163+
</html>

doc/CHANGES.md

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,8 @@ Change log
55
<!-- DON'T EDIT THIS SECTION, INSTEAD RE-RUN doctoc TO UPDATE -->
66
**Table of Contents** *generated with [DocToc](http://doctoc.herokuapp.com/)*
77

8-
- [7.1.2-dev (2022-12-29)](#712-2022-12-29)
8+
- [7.1.2-dev (TBD)](#712-dev-tbd)
9+
- [7.1.2 (2022-12-29)](#712-2022-12-29)
910
- [7.1.1 (2022-11-13)](#711-2022-11-13)
1011
- [7.1.0 (2022-10-23)](#710-2022-10-23)
1112
- [7.0.1 (2022-10-14)](#701-2022-10-14)
@@ -77,7 +78,10 @@ Change log
7778

7879
<!-- END doctoc generated TOC please keep comment here to allow auto update -->
7980

80-
## 7.1.2-dev (2022-12-29)
81+
## 7.1.2-dev (TBD)
82+
* fix [#1936](https://github.com/gridstack/gridstack.js/issues/1936) some styles left behind after a drag
83+
84+
## 7.1.2 (2022-12-29)
8185
* fix [#939](https://github.com/gridstack/gridstack.js/issues/2039) 'prototype' undefined error for dd-gridstack.js
8286
* add [#939](https://github.com/gridstack/gridstack.js/issues/2105) disable/enable are methods now recursive by default
8387
* add better `GridStackEventHandlerCallback` spelled out types

0 commit comments

Comments
 (0)