420 lines
22 KiB
HTML
420 lines
22 KiB
HTML
<!DOCTYPE html>
|
||
<html class="x-admin-sm">
|
||
|
||
<head>
|
||
<meta charset="UTF-8">
|
||
<title>菜谱管理</title>
|
||
<meta name="renderer" content="webkit">
|
||
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
|
||
<meta name="viewport" content="width=device-width,user-scalable=yes, minimum-scale=0.4, initial-scale=0.8,target-densitydpi=low-dpi" />
|
||
<link rel="stylesheet" href="/x_admin/css/font.css">
|
||
<link rel="stylesheet" href="/x_admin/css/xadmin.css">
|
||
<script type="text/javascript" src="/x_admin/lib/layui/layui.js" charset="utf-8"></script>
|
||
<script type="text/javascript" src="/x_admin/js/xadmin.js"></script>
|
||
<script type="text/javascript" src="/x_admin/js/jq.js"></script>
|
||
<style>
|
||
.step-container {
|
||
display: flex;
|
||
margin-bottom: 15px;
|
||
border: 1px solid #eee;
|
||
padding: 15px;
|
||
border-radius: 4px;
|
||
}
|
||
.step-content {
|
||
flex: 1;
|
||
padding-right: 15px;
|
||
}
|
||
.step-image {
|
||
width: 200px;
|
||
display: flex;
|
||
flex-direction: column;
|
||
align-items: center;
|
||
}
|
||
.step-preview {
|
||
max-width: 100%;
|
||
max-height: 150px;
|
||
margin-bottom: 10px;
|
||
display: none;
|
||
}
|
||
.step-buttons {
|
||
display: flex;
|
||
justify-content: space-between;
|
||
margin-top: 10px;
|
||
}
|
||
</style>
|
||
</head>
|
||
<body>
|
||
<div class="layui-fluid">
|
||
<div class="layui-row">
|
||
<form class="layui-form layui-form-pane">
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red">☆</span>菜谱标题
|
||
</label>
|
||
<div class="layui-input-inline" style="width: 80%;">
|
||
<input type="text" id="recipe_title" name="recipe_title" required lay-verify="required" autocomplete="off" class="layui-input">
|
||
</div>
|
||
</div>
|
||
<!-- 图片选择器html部分 -->
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red">★</span>选择封面
|
||
</label>
|
||
<div class="layui-input-inline">
|
||
<div class="layui-btn" onclick="openImageManager('preview_img', 'cove_img')">点击选择</div>
|
||
<input type="hidden" id="cove_img" name="cove_img">
|
||
</div>
|
||
</div>
|
||
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red"></span>预览
|
||
</label>
|
||
<div class="layui-input-inline">
|
||
<img id="preview_img" style="max-width: 200px; display: none; border: 1px solid #eee; margin-top: 10px;" src="" alt="">
|
||
</div>
|
||
</div>
|
||
<!-- 图片选择器html部分 -->
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red">☆</span>菜谱类型
|
||
</label>
|
||
<div class="layui-input-inline" style="width: 80%;">
|
||
<select name="recipe_type" lay-verify="required" id="recipe_type">
|
||
<option value="0">请选择菜谱类型</option>
|
||
{volist name="result" id="vo"}
|
||
<option value="{$vo.id}">{$vo.name}</option>
|
||
{/volist}
|
||
</select>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red">☆</span>菜谱描述
|
||
</label>
|
||
<div class="layui-input-inline" style="width: 80%;">
|
||
<textarea name="recipe_desc" id="recipe_desc" required lay-verify="required" placeholder="请输入菜谱描述" class="layui-textarea"></textarea>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red">☆</span>食材
|
||
</label>
|
||
<div class="layui-input-inline" style="width: 80%;">
|
||
<div id="ingredients_container">
|
||
<div class="layui-form-item ingredient-item" style="margin-bottom: 10px;">
|
||
<div class="layui-inline">
|
||
<input type="text" name="ingredient_name[]" placeholder="食材名称" autocomplete="off" class="layui-input ingredient-name" style="width: 150px; display: inline-block;">
|
||
<div class="ingredient-suggest" style="position: absolute; z-index: 999; display: none; width: 150px; max-height: 200px; overflow-y: auto; border: 1px solid #d2d2d2; background: #fff;"></div>
|
||
<input type="text" name="ingredient_amount[]" placeholder="用量(g)" autocomplete="off" class="layui-input" style="width: 100px; display: inline-block; margin-left: 10px;">
|
||
<button type="button" class="layui-btn layui-btn-danger layui-btn-xs remove-ingredient" style="margin-left: 10px;">删除</button>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
<button type="button" id="add_ingredient" class="layui-btn layui-btn-xs">添加食材</button>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="layui-form-item">
|
||
<label class="layui-form-label" style="width: 120px; text-align: right;">
|
||
<span class="x-red">☆</span>步骤
|
||
</label>
|
||
<div class="layui-input-inline" style="width: 80%;">
|
||
<div id="steps_container">
|
||
<div class="step-container">
|
||
<div class="step-content">
|
||
<label class="layui-form-label" style="width: auto; padding: 9px 5px; text-align: left;">步骤1</label>
|
||
<textarea name="step_desc[]" placeholder="请输入步骤描述" class="layui-textarea"></textarea>
|
||
</div>
|
||
<div class="step-image">
|
||
<img class="step-preview" src="" alt="步骤图片预览">
|
||
<input type="hidden" class="step-image-id" name="step_image[]" value="">
|
||
<div class="step-buttons">
|
||
<button type="button" class="layui-btn layui-btn-xs select-step-image">选择图片</button>
|
||
<button type="button" class="layui-btn layui-btn-danger layui-btn-xs remove-step">删除步骤</button>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
<button type="button" id="add_step" class="layui-btn layui-btn-xs">添加步骤</button>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="layui-form-item" style="display: flex;flex-direction: row;justify-content: center;">
|
||
<button class="layui-btn" lay-filter="add" lay-submit="" style="width: 150px;">增加</button>
|
||
</div>
|
||
</form>
|
||
</div>
|
||
</div>
|
||
<script>
|
||
// 图片选择器js部分~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||
// 全局变量存储当前操作的预览和隐藏字段ID
|
||
var currentImageSelection = {
|
||
previewId: '',
|
||
hiddenFieldId: ''
|
||
};
|
||
// 打开图片管理器函数
|
||
function openImageManager(previewId, hiddenFieldId) {
|
||
// 存储当前操作的ID
|
||
currentImageSelection.previewId = previewId;
|
||
currentImageSelection.hiddenFieldId = hiddenFieldId;
|
||
|
||
// 打开图片管理窗口
|
||
xadmin.open('图片管理', '/k/admin/pic', '80%', '80%');
|
||
}
|
||
// 接收从图片管理窗口返回的参数
|
||
function receiveParamFromIframe(param) {
|
||
if(param.length > 0 && currentImageSelection.previewId && currentImageSelection.hiddenFieldId){
|
||
// 更新预览图片
|
||
var img = document.getElementById(currentImageSelection.previewId);
|
||
img.src = param[1];
|
||
img.style.display = 'block';
|
||
|
||
// 更新隐藏字段值
|
||
document.getElementById(currentImageSelection.hiddenFieldId).value = param[0];
|
||
|
||
// 重置当前操作的ID
|
||
currentImageSelection.previewId = '';
|
||
currentImageSelection.hiddenFieldId = '';
|
||
} else {
|
||
layer.msg('图片选择失败');
|
||
}
|
||
}
|
||
// 图片选择器js部分~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||
$(document).ready(function(){
|
||
var stepCounter = 1;
|
||
var ingredientCounter = 1;
|
||
|
||
// 添加食材
|
||
$('#add_ingredient').on('click', function() {
|
||
ingredientCounter++;
|
||
var html = `
|
||
<div class="layui-form-item ingredient-item" style="margin-bottom: 10px;">
|
||
<div class="layui-inline">
|
||
<input type="text" name="ingredient_name[]" placeholder="食材名称" autocomplete="off" class="layui-input ingredient-name" style="width: 150px; display: inline-block;">
|
||
<div class="ingredient-suggest" style="position: absolute; z-index: 999; display: none; width: 150px; max-height: 200px; overflow-y: auto; border: 1px solid #d2d2d2; background: #fff;"></div>
|
||
<input type="text" name="ingredient_amount[]" placeholder="用量(g)" autocomplete="off" class="layui-input" style="width: 100px; display: inline-block; margin-left: 10px;">
|
||
<button type="button" class="layui-btn layui-btn-danger layui-btn-xs remove-ingredient" style="margin-left: 10px;">删除</button>
|
||
</div>
|
||
</div>
|
||
`;
|
||
$('#ingredients_container').append(html);
|
||
});
|
||
|
||
// 食材名称输入自动完成
|
||
$(document).on('input', '.ingredient-name', function() {
|
||
var input = $(this);
|
||
var keyword = input.val().trim();
|
||
var suggestBox = input.next('.ingredient-suggest');
|
||
|
||
if (keyword.length < 1) {
|
||
suggestBox.hide();
|
||
return;
|
||
}
|
||
console.log(keyword)
|
||
// 发送AJAX请求
|
||
$.ajax({
|
||
url: '/k/a/cookbook/find_food_list',
|
||
dataType:"json", //返回格式为json
|
||
async:true,//请求是否异步,默认为异步,这也是ajax重要特性
|
||
data:{"id":"value"}, //参数值
|
||
data: {'search_data': keyword},
|
||
type: 'POST',
|
||
success: function(res) {
|
||
if (res.code === 0 && res.data && res.data.length > 0) {
|
||
var html = '';
|
||
res.data.forEach(function(item) {
|
||
html += '<div class="suggest-item" style="padding: 5px 10px; cursor: pointer;" data-id="' + item.id + '" data-name="' + item.food_name + '" data-kcal="' + item.Calorie_val + '">' + item.food_name + '</div>';
|
||
});
|
||
suggestBox.html(html).show();
|
||
} else {
|
||
suggestBox.hide();
|
||
}
|
||
},
|
||
error: function() {
|
||
suggestBox.hide();
|
||
}
|
||
});
|
||
});
|
||
|
||
// 点击建议项填充到输入框
|
||
$(document).on('click', '.suggest-item', function() {
|
||
var id = $(this).data('id');
|
||
var name = $(this).data('name');
|
||
var kcal = $(this).data('kcal');
|
||
|
||
var parentDiv = $(this).closest('.layui-inline');
|
||
parentDiv.find('.ingredient-name').val(name).data('id', id).data('kcal', kcal);
|
||
parentDiv.find('.ingredient-suggest').hide();
|
||
});
|
||
|
||
// 点击其他地方隐藏建议框并清空输入框
|
||
$(document).on('click', function(e) {
|
||
if (!$(e.target).closest('.ingredient-suggest').length && !$(e.target).hasClass('ingredient-name')) {
|
||
$('.ingredient-suggest').hide();
|
||
// 清空未选择食材的输入框
|
||
$('.ingredient-name').each(function() {
|
||
if (!$(this).data('id')) { // 如果没有选择过食材(没有data-id)
|
||
$(this).val(''); // 清空输入框
|
||
}
|
||
});
|
||
}
|
||
});
|
||
|
||
// 删除食材
|
||
$(document).on('click', '.remove-ingredient', function() {
|
||
if($('.ingredient-item').length > 1) {
|
||
$(this).closest('.ingredient-item').remove();
|
||
} else {
|
||
layer.msg('至少保留一个食材');
|
||
}
|
||
});
|
||
|
||
// 添加步骤
|
||
$('#add_step').on('click', function() {
|
||
stepCounter++;
|
||
var html = `
|
||
<div class="step-container">
|
||
<div class="step-content">
|
||
<label class="layui-form-label" style="width: auto; padding: 9px 5px; text-align: left;">步骤${stepCounter}</label>
|
||
<textarea name="step_desc[]" placeholder="请输入步骤描述" class="layui-textarea"></textarea>
|
||
</div>
|
||
<div class="step-image">
|
||
<img class="step-preview" src="" alt="步骤图片预览">
|
||
<input type="hidden" class="step-image-id" name="step_image[]" value="">
|
||
<div class="step-buttons">
|
||
<button type="button" class="layui-btn layui-btn-xs select-step-image">选择图片</button>
|
||
<button type="button" class="layui-btn layui-btn-danger layui-btn-xs remove-step">删除步骤</button>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
`;
|
||
$('#steps_container').append(html);
|
||
});
|
||
|
||
// 为步骤选择图片
|
||
$(document).on('click', '.select-step-image', function() {
|
||
var container = $(this).closest('.step-container');
|
||
var previewImg = container.find('.step-preview');
|
||
var hiddenInput = container.find('.step-image-id');
|
||
|
||
// 为元素设置唯一ID
|
||
var previewId = 'step-preview-' + Math.random().toString(36).substr(2, 9);
|
||
var hiddenId = 'step-image-' + Math.random().toString(36).substr(2, 9);
|
||
|
||
previewImg.attr('id', previewId);
|
||
hiddenInput.attr('id', hiddenId);
|
||
|
||
// 打开图片管理器
|
||
openImageManager(previewId, hiddenId);
|
||
});
|
||
|
||
// 删除步骤
|
||
$(document).on('click', '.remove-step', function() {
|
||
if($('.step-container').length > 1) {
|
||
$(this).closest('.step-container').remove();
|
||
// 重新编号步骤
|
||
$('.step-container').each(function(index) {
|
||
$(this).find('.layui-form-label').text('步骤' + (index + 1));
|
||
});
|
||
stepCounter--;
|
||
} else {
|
||
layer.msg('至少保留一个步骤');
|
||
}
|
||
});
|
||
|
||
// 表单提交时收集数据
|
||
layui.use(['form', 'layer'], function() {
|
||
var form = layui.form,
|
||
layer = layui.layer;
|
||
|
||
// 监听提交
|
||
form.on('submit(add)', function(data) {
|
||
// 显示加载中
|
||
var loadIndex = layer.load(1);
|
||
|
||
// 收集表单数据
|
||
var formData = {
|
||
cook_label: $('#recipe_type').val(),
|
||
title: $('#recipe_title').val(),
|
||
description: $('#recipe_desc').val(),
|
||
cover: $('#cove_img').val(), // 封面图片ID
|
||
foodList: [],
|
||
stepList: []
|
||
};
|
||
|
||
// 收集食材数据
|
||
$('.ingredient-item').each(function() {
|
||
var nameInput = $(this).find('.ingredient-name');
|
||
var amountInput = $(this).find('input[placeholder="用量(g)"]');
|
||
|
||
var id = nameInput.data('id');
|
||
var name = nameInput.val();
|
||
var weight = amountInput.val();
|
||
|
||
if (id && name && weight && weight > 0) {
|
||
formData.foodList.push({
|
||
id: id,
|
||
name: name,
|
||
weight: weight
|
||
});
|
||
}
|
||
});
|
||
|
||
// 收集步骤数据
|
||
$('.step-container').each(function() {
|
||
var desc = $(this).find('textarea').val();
|
||
var imageId = $(this).find('.step-image-id').val();
|
||
|
||
if (desc && desc.trim() !== '') {
|
||
formData.stepList.push({
|
||
pic_list: [imageId] || [],
|
||
description: desc.trim()
|
||
});
|
||
}
|
||
});
|
||
|
||
// 调试输出
|
||
console.log('提交数据:', formData);
|
||
|
||
// 发送AJAX请求
|
||
$.ajax({
|
||
url: "/k/a/cookbook/add_cookbook_action",
|
||
type: "POST",
|
||
data: JSON.stringify(formData),
|
||
contentType: "application/json",
|
||
success: function(res) {
|
||
layer.close(loadIndex);
|
||
if (res.code === 0) {
|
||
layer.alert("添加成功", {icon: 1}, function() {
|
||
xadmin.close();
|
||
xadmin.father_reload();
|
||
});
|
||
} else {
|
||
layer.alert("添加失败:" + res.msg, {icon: 2});
|
||
}
|
||
},
|
||
error: function() {
|
||
layer.close(loadIndex);
|
||
layer.alert("请求失败,请稍后再试", {icon: 2});
|
||
}
|
||
});
|
||
return false;
|
||
});
|
||
});
|
||
//加载提示开启
|
||
function load() {
|
||
var index = layer.load(1, {
|
||
shade: [0.1, '#fff'] //0.1透明度的白色背景
|
||
});
|
||
}
|
||
// 关闭加载提示
|
||
function c_load() {
|
||
layer.close(layer.index)
|
||
}
|
||
});
|
||
</script>
|
||
</body>
|
||
</html> |