@dolphinweex/weex-harmony 0.1.80 → 0.1.82
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -22,11 +22,13 @@
|
|
|
22
22
|
v-for="(item, index) in data.list"
|
|
23
23
|
:key="item.id"
|
|
24
24
|
class="grid-item"
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
25
|
+
:class="{
|
|
26
|
+
'being-dragged': draggingIndex === index,
|
|
27
|
+
hidden: isDragClone && draggingIndex === index,
|
|
28
|
+
disabled: item.disabled === true,
|
|
29
|
+
deleted: item.deleted
|
|
30
|
+
}"
|
|
31
|
+
v-show="!item.deleted"
|
|
30
32
|
:data-index="index"
|
|
31
33
|
@touchstart="(e) => onTouchStart(e, index)"
|
|
32
34
|
@touchmove="onTouchMove"
|
|
@@ -37,9 +39,9 @@
|
|
|
37
39
|
<div class="box" :class="{ shaking: isEditing }">
|
|
38
40
|
<div class="thumb-wrap">
|
|
39
41
|
<img class="thumb" :src="item.imageSrc" alt="" />
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
42
|
+
<button class="delete-btn"
|
|
43
|
+
:style="{ fontSize : data.deleteBtnSize && data.deleteBtnSize * 4 || 16 * 4 }"
|
|
44
|
+
@click.stop="requestDelete(index, item)">×</button>
|
|
43
45
|
</div>
|
|
44
46
|
<div
|
|
45
47
|
class="label-row"
|
|
@@ -76,11 +78,22 @@
|
|
|
76
78
|
v-model="editInputValue"
|
|
77
79
|
:placeholder="data.inputPlaceholder || ''"
|
|
78
80
|
/>
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
81
|
+
<div class="modal-actions">
|
|
82
|
+
<text class="btn cancel" @click="onEditCancel">取消</text>
|
|
83
|
+
<div class="btn-divider"></div>
|
|
84
|
+
<text class="btn confirm" @click="onEditConfirm">确认</text>
|
|
85
|
+
</div>
|
|
86
|
+
</div>
|
|
87
|
+
</div>
|
|
88
|
+
<div v-if="showDeleteConfirm" class="modal-mask">
|
|
89
|
+
<div class="modal">
|
|
90
|
+
<div class="modal-title">温馨提示</div>
|
|
91
|
+
<div class="modal-content">删除所选关注视角后,相关的智能场景将执行失败</div>
|
|
92
|
+
<div class="modal-actions">
|
|
93
|
+
<text class="btn cancel" @click="onDeleteCancel">取消</text>
|
|
94
|
+
<div class="btn-divider"></div>
|
|
95
|
+
<text class="btn confirm" @click="onDeleteConfirmAction">确定</text>
|
|
96
|
+
</div>
|
|
84
97
|
</div>
|
|
85
98
|
</div>
|
|
86
99
|
</div>
|
|
@@ -132,6 +145,8 @@
|
|
|
132
145
|
showEditDialog: false,
|
|
133
146
|
editInputValue: '',
|
|
134
147
|
editIndex: null,
|
|
148
|
+
showDeleteConfirm: false,
|
|
149
|
+
pendingDeleteIndex: null,
|
|
135
150
|
scale: weex.config.env.scale
|
|
136
151
|
};
|
|
137
152
|
},
|
|
@@ -161,6 +176,25 @@
|
|
|
161
176
|
if (this.isTouchDragging || this.longPressTimer || this.secondLongPressTimer) return;
|
|
162
177
|
this.$emit('onClickEvent', { item, index });
|
|
163
178
|
},
|
|
179
|
+
|
|
180
|
+
requestDelete(index, item) {
|
|
181
|
+
const targetItem = this.data.list[index];
|
|
182
|
+
if (!targetItem || targetItem.deleted) return;
|
|
183
|
+
this.pendingDeleteIndex = index;
|
|
184
|
+
this.showDeleteConfirm = true;
|
|
185
|
+
},
|
|
186
|
+
|
|
187
|
+
onDeleteCancel() {
|
|
188
|
+
this.showDeleteConfirm = false;
|
|
189
|
+
this.pendingDeleteIndex = null;
|
|
190
|
+
},
|
|
191
|
+
|
|
192
|
+
onDeleteConfirmAction() {
|
|
193
|
+
if (this.pendingDeleteIndex === null) return;
|
|
194
|
+
const item = this.data.list[this.pendingDeleteIndex];
|
|
195
|
+
this.onDelete(this.pendingDeleteIndex, item);
|
|
196
|
+
this.onDeleteCancel();
|
|
197
|
+
},
|
|
164
198
|
|
|
165
199
|
onEditClick(item, index) {
|
|
166
200
|
// 点击编辑按钮:弹出编辑名称对话框
|
|
@@ -175,16 +209,19 @@
|
|
|
175
209
|
},
|
|
176
210
|
|
|
177
211
|
/**
|
|
178
|
-
* @description
|
|
212
|
+
* @description 校验输入内容,仅允许中文/英文/数字,且去除前后空白。
|
|
179
213
|
* @param {string} value 当前输入值
|
|
180
|
-
* @returns {string}
|
|
214
|
+
* @returns {{ valid: boolean, message?: string, value?: string }}
|
|
181
215
|
*/
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
216
|
+
validateLabelInput(value) {
|
|
217
|
+
const trimmedValue = (value || '').trim();
|
|
218
|
+
if (!trimmedValue) {
|
|
219
|
+
return { valid: false, message: '视角名称不能为空' };
|
|
220
|
+
}
|
|
221
|
+
if (/[^a-zA-Z0-9\u4e00-\u9fa5]/.test(trimmedValue)) {
|
|
222
|
+
return { valid: false, message: '视角名称只能输入中文、英文和数字' };
|
|
223
|
+
}
|
|
224
|
+
return { valid: true, value: trimmedValue };
|
|
188
225
|
},
|
|
189
226
|
|
|
190
227
|
showToast(message) {
|
|
@@ -199,20 +236,28 @@
|
|
|
199
236
|
},
|
|
200
237
|
|
|
201
238
|
onEditConfirm() {
|
|
202
|
-
const
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
// 2. 检查是否为空
|
|
206
|
-
if (!newLabel) {
|
|
207
|
-
this.showToast('不支持为空');
|
|
239
|
+
const validation = this.validateLabelInput(this.editInputValue);
|
|
240
|
+
if (!validation.valid) {
|
|
241
|
+
this.showToast(validation.message);
|
|
208
242
|
return;
|
|
209
243
|
}
|
|
244
|
+
const newLabel = validation.value;
|
|
245
|
+
|
|
210
246
|
// 3. 检查长度
|
|
211
247
|
if (newLabel.length > 8) {
|
|
212
248
|
// 长度超限:提示并阻止后续更新和关闭逻辑
|
|
213
249
|
this.showToast('限8个字符以内名称,请重新输入');
|
|
214
250
|
return;
|
|
215
251
|
}
|
|
252
|
+
const duplicateExists = this.data.list && this.data.list.some((it, idx) => {
|
|
253
|
+
if (idx === this.editIndex) return false;
|
|
254
|
+
if (!it || it.deleted) return false;
|
|
255
|
+
return String(it.label || '') === newLabel;
|
|
256
|
+
});
|
|
257
|
+
if (duplicateExists) {
|
|
258
|
+
this.showToast('已存在此视角');
|
|
259
|
+
return;
|
|
260
|
+
}
|
|
216
261
|
if (this.editIndex !== null && this.data.list && this.data.list[this.editIndex]) {
|
|
217
262
|
this.$set(this.data.list[this.editIndex], 'label', newLabel);
|
|
218
263
|
// 通知外部(可选)
|
|
@@ -230,15 +275,20 @@
|
|
|
230
275
|
* @param {object} item 列表项数据
|
|
231
276
|
*/
|
|
232
277
|
onDelete(index, item) {
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
this
|
|
278
|
+
const currentItem = this.data.list[index];
|
|
279
|
+
if (!currentItem) return;
|
|
280
|
+
this.$emit('onDeleteEvent', { item: currentItem, index });
|
|
281
|
+
this.$set(currentItem, 'deleted', true);
|
|
236
282
|
this.$nextTick(this.measureItemSize);
|
|
237
283
|
},
|
|
238
284
|
|
|
239
285
|
onTouchStart(e, index) {
|
|
240
286
|
if (!e.changedTouches || e.changedTouches.length === 0) return;
|
|
241
|
-
|
|
287
|
+
const targetItem = this.data.list[index];
|
|
288
|
+
if (targetItem && targetItem.deleted) {
|
|
289
|
+
return;
|
|
290
|
+
}
|
|
291
|
+
this.measureItemSize();
|
|
242
292
|
const touch = e.changedTouches[0];
|
|
243
293
|
this.touchStartX = touch.pageX;
|
|
244
294
|
this.touchStartY = touch.pageY;
|
|
@@ -395,7 +445,9 @@
|
|
|
395
445
|
const gridItems = Array.from(this.$el.querySelectorAll('.grid-item'));
|
|
396
446
|
let targetIndex = null;
|
|
397
447
|
for (let i = 0; i < gridItems.length; i++) {
|
|
398
|
-
|
|
448
|
+
if (i === this.draggingIndex) continue;
|
|
449
|
+
const listItem = this.data.list[i];
|
|
450
|
+
if (listItem && listItem.deleted) continue;
|
|
399
451
|
const rect = gridItems[i].getBoundingClientRect();
|
|
400
452
|
const centerX = (rect.left + rect.right) / 2;
|
|
401
453
|
const centerY = (rect.top + rect.bottom) / 2;
|
|
@@ -421,11 +473,15 @@
|
|
|
421
473
|
},
|
|
422
474
|
getListData(callback) {
|
|
423
475
|
const list = Array.isArray(this.data && this.data.list) ? this.data.list : [];
|
|
424
|
-
const arr =
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
476
|
+
const arr = [];
|
|
477
|
+
list.forEach((it) => {
|
|
478
|
+
if (!it || it.deleted) return;
|
|
479
|
+
arr.push({
|
|
480
|
+
id: String((it && (it.id != null ? it.id : '')) || ''),
|
|
481
|
+
label: String((it && (it.label != null ? it.label : '')) || ''),
|
|
482
|
+
imageSrc: (it && it.imageSrc) || ''
|
|
483
|
+
});
|
|
484
|
+
});
|
|
429
485
|
const payload = { listData: arr, list: arr };
|
|
430
486
|
if (typeof callback === 'function') {
|
|
431
487
|
try { callback(payload); } catch (e) { /* ignore */ }
|
|
@@ -512,8 +568,6 @@
|
|
|
512
568
|
flex-direction: row;
|
|
513
569
|
justify-content: center;
|
|
514
570
|
gap: 8px;
|
|
515
|
-
}
|
|
516
|
-
.edit-icon {
|
|
517
571
|
}
|
|
518
572
|
.drag-clone {
|
|
519
573
|
box-sizing: border-box;
|
|
@@ -539,7 +593,6 @@
|
|
|
539
593
|
max-width: 60vw;
|
|
540
594
|
background: #fff;
|
|
541
595
|
border-radius: 24px;
|
|
542
|
-
padding: 16px;
|
|
543
596
|
box-shadow: 0 8px 20px rgba(0,0,0,0.18);
|
|
544
597
|
}
|
|
545
598
|
.modal-title {
|
|
@@ -548,9 +601,18 @@
|
|
|
548
601
|
color: #222;
|
|
549
602
|
margin: 24px 0 24px 0px;
|
|
550
603
|
text-align: center;
|
|
604
|
+
font-weight: 500;
|
|
605
|
+
}
|
|
606
|
+
.modal-content {
|
|
607
|
+
font-size: 24px;
|
|
608
|
+
color: #333;
|
|
609
|
+
text-align: center;
|
|
610
|
+
padding-bottom: 16px;
|
|
611
|
+
padding: 10px 16px;
|
|
551
612
|
}
|
|
552
613
|
.modal-input {
|
|
553
|
-
width:
|
|
614
|
+
width: 90%;
|
|
615
|
+
margin: 10px auto;
|
|
554
616
|
box-sizing: border-box;
|
|
555
617
|
border: 2px solid #e8e8e8;
|
|
556
618
|
border-radius: 8px;
|
|
@@ -562,21 +624,22 @@
|
|
|
562
624
|
border-color: #1677ff;
|
|
563
625
|
}
|
|
564
626
|
.modal-actions {
|
|
627
|
+
border-top:1px solid #ccc;
|
|
565
628
|
margin-top: 14px;
|
|
566
629
|
display: flex;
|
|
567
630
|
align-items: center;
|
|
568
631
|
flex-direction: row;
|
|
569
632
|
width: 100%;
|
|
570
|
-
justify-content: space-
|
|
633
|
+
justify-content: space-evenly;
|
|
571
634
|
}
|
|
572
635
|
.btn {
|
|
573
|
-
padding:
|
|
636
|
+
padding: 20px 24px;
|
|
574
637
|
font-size: 30px;
|
|
575
638
|
color:#46a2df
|
|
576
639
|
}
|
|
577
640
|
.btn-divider {
|
|
578
641
|
width: 1px;
|
|
579
|
-
height:
|
|
580
|
-
background: #
|
|
642
|
+
height: 100%;
|
|
643
|
+
background: #ccc;
|
|
581
644
|
}
|
|
582
645
|
</style>
|
package/src/.DS_Store
DELETED
|
Binary file
|
package/src/components/.DS_Store
DELETED
|
Binary file
|