first functionable
This commit is contained in:
91
src/components/KeyValueEditor.vue
Normal file
91
src/components/KeyValueEditor.vue
Normal file
@@ -0,0 +1,91 @@
|
||||
<script setup lang="ts">
|
||||
import { Trash2, Plus } from 'lucide-vue-next';
|
||||
import type { KeyValue } from '../stores/requestStore';
|
||||
|
||||
const props = defineProps<{
|
||||
modelValue: KeyValue[];
|
||||
title?: string;
|
||||
}>();
|
||||
|
||||
const emit = defineEmits(['update:modelValue']);
|
||||
|
||||
const addRow = () => {
|
||||
const newData = [...props.modelValue, {
|
||||
id: crypto.randomUUID(),
|
||||
key: '',
|
||||
value: '',
|
||||
enabled: true
|
||||
}];
|
||||
emit('update:modelValue', newData);
|
||||
};
|
||||
|
||||
const removeRow = (index: number) => {
|
||||
const newData = [...props.modelValue];
|
||||
newData.splice(index, 1);
|
||||
emit('update:modelValue', newData);
|
||||
};
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="flex flex-col h-full">
|
||||
<div class="flex-1 overflow-y-auto p-4">
|
||||
<table class="w-full text-left border-collapse">
|
||||
<thead>
|
||||
<tr class="text-xs text-slate-500 border-b border-slate-800">
|
||||
<th class="pb-2 pl-2 font-medium w-8"></th>
|
||||
<th class="pb-2 font-medium w-1/3">Key</th>
|
||||
<th class="pb-2 font-medium">Value</th>
|
||||
<th class="pb-2 w-8"></th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr
|
||||
v-for="(item, index) in modelValue"
|
||||
:key="item.id"
|
||||
class="group"
|
||||
>
|
||||
<td class="py-1 pl-2 align-middle">
|
||||
<input
|
||||
type="checkbox"
|
||||
v-model="item.enabled"
|
||||
class="rounded bg-slate-800 border-slate-700 text-indigo-500 focus:ring-indigo-500/50 focus:ring-offset-0"
|
||||
>
|
||||
</td>
|
||||
<td class="py-1 pr-2 align-middle">
|
||||
<input
|
||||
type="text"
|
||||
v-model="item.key"
|
||||
placeholder="Key"
|
||||
class="w-full bg-transparent border-b border-transparent hover:border-slate-700 focus:border-indigo-500 focus:outline-none py-1 px-1 text-sm text-slate-300 transition-colors"
|
||||
>
|
||||
</td>
|
||||
<td class="py-1 pr-2 align-middle">
|
||||
<input
|
||||
type="text"
|
||||
v-model="item.value"
|
||||
placeholder="Value"
|
||||
class="w-full bg-transparent border-b border-transparent hover:border-slate-700 focus:border-indigo-500 focus:outline-none py-1 px-1 text-sm text-slate-300 transition-colors"
|
||||
>
|
||||
</td>
|
||||
<td class="py-1 align-middle text-right">
|
||||
<button
|
||||
@click="removeRow(index)"
|
||||
class="p-1 text-slate-600 hover:text-rose-400 opacity-0 group-hover:opacity-100 transition-all"
|
||||
title="Remove"
|
||||
>
|
||||
<Trash2 class="w-4 h-4" />
|
||||
</button>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<button
|
||||
@click="addRow"
|
||||
class="mt-2 flex items-center text-xs text-slate-500 hover:text-indigo-400 transition-colors px-2 py-1"
|
||||
>
|
||||
<Plus class="w-3 h-3 mr-1" /> Add Item
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
Reference in New Issue
Block a user