228 lines
7.8 KiB
PHP
228 lines
7.8 KiB
PHP
<div class="table-responsive p-1" id="spec-{{$name}}">
|
|
<input type="hidden" name="{{$name}}" value="{{ json_encode($value, JSON_UNESCAPED_UNICODE) }}">
|
|
<table class="table table-bordered table-hover">
|
|
<thead>
|
|
<tr>
|
|
@foreach($headers as $item)
|
|
<td>{{ $item }}</td>
|
|
@endforeach
|
|
<td></td>
|
|
</tr>
|
|
</thead>
|
|
<tbody>
|
|
@foreach($value as $index => $item)
|
|
<tr data-id="{{ $item['name'] }}">
|
|
<td rowspan="{{count($item['values']) + 2}}" class="editable">{{ $item['name'] }}</td>
|
|
</tr>
|
|
@foreach($item['values'] as $subItem)
|
|
<tr data-pid="{{ $item['name'] }}">
|
|
<td class="editable">{{ $subItem }}</td>
|
|
<td>
|
|
<button type="button" class="btn btn-sm btn-outline-danger delete-item-button">
|
|
<i class="fa fa-trash"></i>
|
|
</button>
|
|
</td>
|
|
</tr>
|
|
@endforeach
|
|
<tr data-pid="{{$item['name']}}">
|
|
<td>
|
|
<input type="text" class="form-control add-item-input" placeholder="填写 {{ $headers[$index] }}">
|
|
</td>
|
|
<td>
|
|
<button type="button" class="btn btn-sm btn-outline-primary add-item-button">
|
|
<i class="fa fa-plus"></i>
|
|
</button>
|
|
</td>
|
|
</tr>
|
|
@endforeach
|
|
<tr>
|
|
<td colspan="{{ count($headers) }}">
|
|
<input type="text" class="form-control add-attr-input" placeholder="添加 {{ $headers[0] }}">
|
|
</td>
|
|
<td>
|
|
<button type="button" class="btn btn-sm btn-outline-warning add-attr-button">
|
|
<i class="fa fa-plus"></i>
|
|
</button>
|
|
</td>
|
|
</tr>
|
|
</tbody>
|
|
</table>
|
|
</div>
|
|
<style>
|
|
.table {
|
|
text-align: center;
|
|
}
|
|
.table td {
|
|
vertical-align: middle;
|
|
}
|
|
.editable {
|
|
color: #586cb1;
|
|
cursor: pointer;
|
|
}
|
|
</style>
|
|
<script>
|
|
var type = JSON.parse('{!! json_encode($type) !!}')
|
|
var keys = JSON.parse('{!! json_encode($keys) !!}')
|
|
var headers = JSON.parse('{!! json_encode($headers) !!}')
|
|
var element = $('#spec-{{$name}}')
|
|
|
|
// 添加父级属性
|
|
element.on('click', '.add-attr-button', function () {
|
|
var value = $('.add-attr-input').val()
|
|
if (!value) {
|
|
return Dcat.swal.warning(`请填写 ${headers.name}`)
|
|
}
|
|
|
|
addGroup(value)
|
|
|
|
$('.add-attr-input').val('')
|
|
updateInputValue()
|
|
})
|
|
// 添加子属性
|
|
.on('click', '.add-item-button', function () {
|
|
var tr = $(this).parents('tr')
|
|
var pid = tr.data('pid')
|
|
var values = {}
|
|
var inputs = tr.find('input.add-item-input')
|
|
for(let i = 0; i < keys.length; i++) {
|
|
let item = inputs.eq(i)[0]
|
|
let key = keys[i]
|
|
values[key] = inputs.eq(i).val()
|
|
}
|
|
addItem(pid, values)
|
|
// 清空输入框
|
|
inputs.each((key, item) => {
|
|
item.value = ''
|
|
})
|
|
|
|
updateInputValue()
|
|
})
|
|
// 删除子属性
|
|
.on('click', '.delete-item-button', function () {
|
|
var tr = $(this).parents('tr')
|
|
var pid = tr.data('pid')
|
|
var parent = $('tr[data-id="'+pid+'"]')
|
|
var parentTd = parent.find('td').first()
|
|
parentTd.attr('rowspan', parseInt(parentTd.attr('rowspan')) - 1)
|
|
tr.remove()
|
|
|
|
// 子属性全部删除, 删除父级属性
|
|
if (element.find(`tr[data-pid="${pid}"]`).length <= 1) {
|
|
element.find(`tr[data-pid="${pid}"]`).remove()
|
|
element.find(`tr[data-id="${pid}"]`).remove()
|
|
}
|
|
|
|
updateInputValue()
|
|
})
|
|
// 修改
|
|
.on('click', '.editable', function () {
|
|
var td = $(this)
|
|
var tr = td.parents('tr')
|
|
var value = td.html()
|
|
Dcat.swal.fire({
|
|
input: 'text',
|
|
inputValue: value,
|
|
showCancelButton: true,
|
|
cancelButtonText: '取消',
|
|
confirmButtonText: '确定',
|
|
}).then(result => {
|
|
if (result.value !== undefined && result.value) {
|
|
// 修改父级属性
|
|
if (tr.attr('data-id')) {
|
|
var pid = tr.attr('data-id')
|
|
$('tr[data-pid="'+pid+'"]').attr('data-pid', result.value)
|
|
tr.attr('data-id', result.value)
|
|
}
|
|
td.html(result.value)
|
|
|
|
updateInputValue()
|
|
}
|
|
})
|
|
})
|
|
// 重新生成
|
|
.on('click', '.generate-button', function () {
|
|
var trs = $(this).parents('table').find('tr[data-id]')
|
|
for (let i = 0; i < type.length; i++) {
|
|
let item = type[i]
|
|
|
|
// 生成父级属性
|
|
if (element.find(`tr[data-id="${item.name}"]`).length === 0) {
|
|
addGroup(item.name)
|
|
}
|
|
// 生成子级属性
|
|
for (let k = 0; k < item.values.length; k++) {
|
|
let subItem = item.values[k]
|
|
let baseKey = keys[0]
|
|
if (element.find(`tr[data-pid="${item.name}"]`).find(`td[data-name="${subItem[baseKey]}"]`).length == 0) {
|
|
let values = {}
|
|
for(let j = 0; j < keys.length; j++) {
|
|
let key = keys[j]
|
|
values[key] = subItem[key] ?? ''
|
|
}
|
|
addItem(item.name, values)
|
|
}
|
|
}
|
|
|
|
}
|
|
updateInputValue()
|
|
})
|
|
|
|
function addGroup(id) {
|
|
var tr = element.find('.add-attr-button').parents('tr')
|
|
var html = `<tr data-id="${id}">`
|
|
html += `<td rowspan="${keys.length}" class="editable">${id}</td>`
|
|
html += '</tr>'
|
|
html += `<tr data-pid="${id}">`
|
|
for (let i = 1; i < headers.length; i++) {
|
|
html += `<td><input type="text" class="form-control add-item-input" placeholder="填写 ${headers[i]}"></td>`
|
|
}
|
|
html += '<td><button type="button" class="btn btn-sm btn-outline-primary add-item-button"><i class="fa fa-plus"></i></button></td>'
|
|
html += '</tr>'
|
|
tr.before(html)
|
|
}
|
|
|
|
function addItem(id, values) {
|
|
var tr = element.find(`tr[data-id="${id}"]`)
|
|
|
|
// 构造 html
|
|
var html = `<tr data-pid="${id}">`;
|
|
Object.keys(values).forEach(key => {
|
|
let value = values[key]
|
|
html += `<td class="editable" data-${key}="${value}">${value}</td>`
|
|
})
|
|
for(let i = 0; i < values.length; i++) {
|
|
html += `<td class="editable">${values[i]}</td>`
|
|
}
|
|
html += '<td><button type="button" class="btn btn-sm btn-outline-danger delete-item-button"><i class="fa fa-trash"></i></button></td></tr>'
|
|
|
|
// 修改 rowspan
|
|
var parentTd = tr.find('td').first()
|
|
parentTd.attr('rowspan', parseInt(parentTd.attr('rowspan')) + 1)
|
|
|
|
// 追加 html
|
|
$(`tr[data-pid="${id}"]:last`).before(html)
|
|
}
|
|
|
|
// 整合表格里面的值
|
|
function formatValue() {
|
|
var values = []
|
|
var tr = element.find('tr[data-id]')
|
|
for (let i = 0; i < tr.length; i++) {
|
|
var item = tr.eq(i)
|
|
var id = item.data('id')
|
|
var subTr = element.find(`[data-pid="${id}"]:not(:last)`)
|
|
var subValues = []
|
|
subTr.each((key, ele) => {
|
|
subValues.push($(ele).find('td:first-child').html())
|
|
})
|
|
values.push({name: id, values: subValues})
|
|
}
|
|
console.log(values)
|
|
return values
|
|
}
|
|
|
|
function updateInputValue() {
|
|
element.find('input[name="{{$name}}"]').val(JSON.stringify(formatValue()))
|
|
}
|
|
</script>
|