feat: [approval] 결재선 드롭다운 직접 배치 및 양식 본문 자동 채움
- 새기안/수정 화면에 결재선 드롭다운 추가 (모달 없이 빠른 선택) - 양식 선택 시 body_template HTML 자동 채움 (편집기 자동 활성화) - 모달 닫을 때 외부 드롭다운 동기화 - ApprovalForm 모델 fillable에 body_template 추가
This commit is contained in:
@@ -58,10 +58,22 @@ class="w-full px-3 py-2 border border-gray-300 rounded-lg text-sm focus:outline-
|
||||
<div class="mb-4">
|
||||
<div class="flex items-center justify-between mb-1">
|
||||
<label class="block text-sm font-medium text-gray-700">결재선</label>
|
||||
<button type="button" onclick="openApprovalLineModal()"
|
||||
class="px-3 py-1.5 bg-blue-50 text-blue-600 hover:bg-blue-100 rounded-lg text-xs font-medium transition">
|
||||
결재선 설정
|
||||
</button>
|
||||
<div class="flex items-center gap-2">
|
||||
<select id="quick-line-select" onchange="applyQuickLine(this.value)"
|
||||
class="px-2 py-1.5 border border-gray-300 rounded-lg text-xs focus:outline-none focus:ring-2 focus:ring-blue-500"
|
||||
style="min-width: 160px;">
|
||||
<option value="">결재선 선택</option>
|
||||
@foreach($lines as $line)
|
||||
<option value="{{ $line->id }}" {{ ($approval->line_id ?? '') == $line->id ? 'selected' : '' }}>
|
||||
{{ $line->name }} ({{ count($line->steps ?? []) }}단계)
|
||||
</option>
|
||||
@endforeach
|
||||
</select>
|
||||
<button type="button" onclick="openApprovalLineModal()"
|
||||
class="px-3 py-1.5 bg-blue-50 text-blue-600 hover:bg-blue-100 rounded-lg text-xs font-medium transition whitespace-nowrap">
|
||||
세부 설정
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div id="approval-line-summary" class="p-3 bg-gray-50 rounded-lg border border-gray-200 flex items-center">
|
||||
<span class="text-sm text-gray-400">결재선이 설정되지 않았습니다.</span>
|
||||
@@ -191,6 +203,8 @@ class="px-6 py-2 bg-blue-600 hover:bg-blue-700 text-white rounded-lg text-sm fon
|
||||
<script>
|
||||
let quillInstance = null;
|
||||
var summarySortableInstance = null;
|
||||
const formBodyTemplates = @json($forms->pluck('body_template', 'id'));
|
||||
const linesData = @json($lines);
|
||||
|
||||
function toggleEditor() {
|
||||
const useEditor = document.getElementById('useEditor').checked;
|
||||
@@ -254,6 +268,12 @@ function closeApprovalLineModal() {
|
||||
document.getElementById('approval-line-modal').style.display = 'none';
|
||||
document.body.style.overflow = '';
|
||||
updateApprovalLineSummary();
|
||||
|
||||
// 모달 내부 결재선 선택과 외부 드롭다운 동기화
|
||||
const editorEl = document.getElementById('approval-line-editor');
|
||||
if (editorEl && editorEl._x_dataStack) {
|
||||
document.getElementById('quick-line-select').value = editorEl._x_dataStack[0].selectedLineId || '';
|
||||
}
|
||||
}
|
||||
|
||||
function updateApprovalLineSummary() {
|
||||
@@ -323,6 +343,44 @@ function initSummarySortable() {
|
||||
});
|
||||
}
|
||||
|
||||
function applyQuickLine(lineId) {
|
||||
const editorEl = document.getElementById('approval-line-editor');
|
||||
if (!editorEl || !editorEl._x_dataStack) return;
|
||||
const alpineData = editorEl._x_dataStack[0];
|
||||
|
||||
if (!lineId) {
|
||||
alpineData.selectedLineId = '';
|
||||
alpineData.steps = [];
|
||||
} else {
|
||||
alpineData.selectedLineId = lineId;
|
||||
alpineData.loadLine();
|
||||
}
|
||||
|
||||
setTimeout(updateApprovalLineSummary, 100);
|
||||
}
|
||||
|
||||
function applyBodyTemplate(formId) {
|
||||
const template = formBodyTemplates[formId];
|
||||
if (!template) return;
|
||||
|
||||
// edit에서는 항상 confirm (기존 본문이 있을 가능성 높음)
|
||||
const bodyContent = getBodyContent();
|
||||
if (bodyContent.trim()) {
|
||||
if (!confirm('현재 본문 내용을 양식 템플릿으로 교체하시겠습니까?')) return;
|
||||
}
|
||||
|
||||
const useEditorEl = document.getElementById('useEditor');
|
||||
if (!useEditorEl.checked) {
|
||||
useEditorEl.checked = true;
|
||||
toggleEditor();
|
||||
}
|
||||
|
||||
if (quillInstance) {
|
||||
quillInstance.root.innerHTML = template;
|
||||
}
|
||||
document.getElementById('body').value = template;
|
||||
}
|
||||
|
||||
document.addEventListener('keydown', function(e) {
|
||||
if (e.key === 'Escape') {
|
||||
const modal = document.getElementById('approval-line-modal');
|
||||
@@ -342,6 +400,11 @@ function initSummarySortable() {
|
||||
|
||||
// Alpine 초기화 후 기존 결재선 요약 표시
|
||||
setTimeout(updateApprovalLineSummary, 200);
|
||||
|
||||
// 양식 변경 시 본문 템플릿 자동 채움
|
||||
document.getElementById('form_id').addEventListener('change', function() {
|
||||
applyBodyTemplate(this.value);
|
||||
});
|
||||
});
|
||||
|
||||
async function updateApproval(action) {
|
||||
|
||||
Reference in New Issue
Block a user