Merge branches 'master' and 'xzj' of https://gitee.com/darlk/ShengTangManage into xzj

This commit is contained in:
xiezhijun
2021-03-08 18:00:43 +08:00
15 changed files with 315 additions and 174 deletions

View File

@ -3,6 +3,7 @@ package com.stdiet.web.controller.custom;
import com.stdiet.common.core.controller.BaseController;
import com.stdiet.common.core.domain.AjaxResult;
import com.stdiet.common.core.page.TableDataInfo;
import com.stdiet.common.utils.StringUtils;
import com.stdiet.custom.domain.SysRecipesTemplate;
import com.stdiet.custom.service.ISysRecipesTemplateService;
import org.springframework.beans.factory.annotation.Autowired;
@ -10,6 +11,7 @@ import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
import java.util.List;
import java.util.Map;
/**
* 食谱模板
@ -46,7 +48,11 @@ public class SysRecipesTemplateController extends BaseController {
@PreAuthorize("@ss.hasPermi('recipes:template:edit')")
@PostMapping("/add")
public AjaxResult add(@RequestBody SysRecipesTemplate sysRecipesTemplate) {
return toAjax(iSysRecipesTemplateService.insertRecipsesTemplate(sysRecipesTemplate));
Map<String, Long> result = iSysRecipesTemplateService.insertRecipsesTemplate(sysRecipesTemplate);
if (StringUtils.isEmpty(result)) {
return AjaxResult.error();
}
return AjaxResult.success(result);
}
/**

View File

@ -3,6 +3,7 @@ package com.stdiet.custom.service;
import com.stdiet.custom.domain.SysRecipesTemplate;
import java.util.List;
import java.util.Map;
/**
* 食谱计划Service接口
@ -14,7 +15,7 @@ public interface ISysRecipesTemplateService {
List<SysRecipesTemplate> selectRecipesTemplateListByCondition(SysRecipesTemplate sysRecipesTemplate);
int insertRecipsesTemplate(SysRecipesTemplate sysRecipesTemplate);
Map<String, Long> insertRecipsesTemplate(SysRecipesTemplate sysRecipesTemplate);
int updateRecipesTemplate(SysRecipesTemplate sysRecipesTemplate);

View File

@ -1,5 +1,6 @@
package com.stdiet.custom.service.impl;
import com.stdiet.common.utils.StringUtils;
import com.stdiet.custom.domain.SysRecipes;
import com.stdiet.custom.domain.SysRecipesDaily;
import com.stdiet.custom.domain.SysRecipesDailyDishes;

View File

@ -12,7 +12,9 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* 食谱计划Service业务层处理
@ -36,7 +38,7 @@ public class SysRecipesTemplateServiceImpl implements ISysRecipesTemplateService
}
@Override
public int insertRecipsesTemplate(SysRecipesTemplate sysRecipesTemplate) {
public Map<String, Long> insertRecipsesTemplate(SysRecipesTemplate sysRecipesTemplate) {
SysRecipesPlan sysRecipesPlan = new SysRecipesPlan();
sysRecipesPlan.setStartNumDay(1);
sysRecipesPlan.setEndNumDay(7);
@ -47,9 +49,17 @@ public class SysRecipesTemplateServiceImpl implements ISysRecipesTemplateService
sysRecipesTemplate.setCreateBy(SecurityUtils.getUsername());
sysRecipesTemplate.setCreateTime(DateUtils.getNowDate());
sysRecipesTemplate.setPlanId(sysRecipesPlan.getId());
return sysRecipesTemplateMapper.insertRecipsesTemplate(sysRecipesTemplate);
int rows = sysRecipesTemplateMapper.insertRecipsesTemplate(sysRecipesTemplate);
if(rows > 0) {
Map<String, Long> result = new HashMap<>();
result.put("id", sysRecipesTemplate.getId());
result.put("planId", sysRecipesPlan.getId());
return result;
} else {
return null;
}
}
return 0;
return null;
}
@Override

View File

@ -144,7 +144,7 @@
<insert id="bashAddDishes" >
insert into sys_customer_menu_dishes (menu_id, type, dishes_id, remark, detail) values
<foreach collection="list" separator="," item="item" index="index">
(#{item.menuId}, #{item.type}, #{item.dishesId}, #{remark}, #{item.detail, jdbcType=OTHER, typeHandler=com.stdiet.custom.typehandler.ArrayJsonHandler})
(#{item.menuId}, #{item.type}, #{item.dishesId}, #{item.remark}, #{item.detail, jdbcType=OTHER, typeHandler=com.stdiet.custom.typehandler.ArrayJsonHandler})
</foreach>
</insert>

View File

@ -12,10 +12,10 @@
>
<div class="msg-info" v-for="(info, idx) in basicInfo" :key="idx">
<text-info
v-for="con in info"
:title="con.title"
:key="con.title"
:value="data[con.value]"
v-for="i in info"
:title="i.title"
:key="i.title"
:value="data[i.value]"
extraclass="text-info-extra"
/>
</div>

View File

@ -17,7 +17,7 @@
class="copyBtn"
:data-clipboard-text="copyValue"
@click="handleOnRecipesLinkClick"
>客户食谱链接
>食谱链接
</el-button>
<el-popover placement="top" trigger="click" v-if="cusOutId" style="margin: 0 12px">
<VueQr :text="copyValue" :logoSrc="logo" size="256" />

View File

@ -0,0 +1,119 @@
<template>
<el-dialog
:title="title"
:visible.sync="visible"
width="520px"
append-to-body
>
<el-form ref="form" :model="form" :rules="rules" label-width="80px">
<el-form-item label="模板名称" prop="name" label-width="100px">
<el-input v-model="form.name" placeholder="请输入模板名称" />
</el-form-item>
<el-form-item label="营养师" prop="nutritionistId" label-width="100px">
<el-select v-model="form.nutritionistId" placeholder="请选择营养师">
<el-option
v-for="dict in nutritionistIdOptions"
:key="dict.dictValue"
:label="dict.dictLabel"
:value="dict.dictValue"
></el-option>
</el-select>
</el-form-item>
<el-form-item label="营养师助理" prop="nutriAssisId" label-width="100px">
<el-select v-model="form.nutriAssisId" placeholder="请选择营养师助理">
<el-option
v-for="dict in nutriAssisIdOptions"
:key="dict.dictValue"
:label="dict.dictLabel"
:value="dict.dictValue"
></el-option>
</el-select>
</el-form-item>
<el-form-item label="备注" prop="remark" label-width="100px">
<el-input
v-model="form.remark"
:rows="4"
type="textarea"
placeholder="请输入内容"
/>
</el-form-item>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button type="primary" @click="submitForm"> </el-button>
<el-button @click="cancel"> </el-button>
</div>
</el-dialog>
</template>
<script>
import { mapState } from "vuex";
export default {
name: "TemplateDialog",
data() {
return {
title: "",
form: {
cusId: 0,
id: null,
name: null,
nutriAssisId: null,
nutritionistId: null,
remark: null,
},
// 表单校验
rules: {
name: [{ required: true, message: "请输入模板名称", trigger: "blur" }],
nutritionistId: [
{ required: true, message: "请选择营养师", trigger: "blur" },
],
nutriAssisId: [
{ required: true, message: "请选择营养师助理", trigger: "blur" },
],
},
visible: false,
};
},
computed: {
...mapState({
//营养师
nutritionistIdOptions: (state) =>
state.global.nutritionistIdOptions.slice(1),
//营养师助理
nutriAssisIdOptions: (state) => state.global.nutriAssisIdOptions.slice(1),
}),
},
methods: {
showDialog(data) {
this.visible = true;
this.reset();
if (data) {
this.title = "修改模板";
this.form = data;
} else {
this.title = "创建模板";
}
},
submitForm() {
this.$refs["form"].validate((valid) => {
if (valid) {
this.$emit("onConfirm", this.form);
this.visible = false;
}
});
},
reset() {
this.form = {
cusId: 0,
id: null,
name: null,
nutriAssisId: null,
nutritionistId: null,
remark: null,
};
this.resetForm("form");
},
cancel() {
this.visible = false;
},
},
};
</script>

View File

@ -14,6 +14,7 @@ import { getDicts } from "@/api/system/dict/data";
const oriState = {
cusId: undefined,
name: undefined,
planId: undefined,
temId: undefined,
recipesId: undefined,
@ -107,6 +108,7 @@ const mutations = {
const actions = {
async init({ commit, dispatch }, payload) {
//
// console.log(payload);
const planResponse = await getRecipesPlan(payload.planId);
const {
@ -261,14 +263,15 @@ const actions = {
async saveRecipes({ commit, dispatch, state }, payload) {
const { recipesData, cusId, planId } = state;
const params = {
cusId,
planId,
cusId: payload.cusId !== undefined ? payload.cusId : cusId,
planId: payload.planId || planId,
menus: recipesData.map((menu, idx) => ({
numDay: menu.numDay,
cusId,
dishes: menu.dishes.map(dObj => ({
dishesId: dObj.dishesId,
type: dObj.type,
remark: dObj.remark,
detail: dObj.igdList.map(igd => ({
id: igd.id,
weight: igd.weight,
@ -282,11 +285,14 @@ const actions = {
const result = await addRecipesApi(params);
if (result.code === 200) {
const recipesId = result.data;
commit("updateStateData", { recipesId });
dispatch("getRecipesInfo", { recipesId });
if (!payload.planId) {
// 非保存模板
commit("updateStateData", { recipesId });
dispatch("getRecipesInfo", { recipesId });
}
payload.callback &&
payload.callback({
name: state.healthyData.name,
name: state.name,
planId: state.planId
});
}

View File

@ -3,58 +3,84 @@
class="recipes_aspect_wrapper"
:style="`height: ${collapse ? 30 : 200}px`"
>
<div class="header">
<span class="font_size_style">
字体大小
<el-select
v-model="mFontSize"
size="mini"
style="width: 80px"
@change="handleOnSizeChange"
>
<el-option
v-for="size in fontSizeOpts"
:key="size.value"
:label="size.label"
:value="size.value"
/>
</el-select>
</span>
<el-button size="mini" v-if="!recipesId" @click="handleOnBack"
>返回</el-button
>
<el-popover
placement="bottom"
trigger="click"
title="修改审核状态"
style="margin-right: 12px"
v-hasPermi="['recipes:plan:review']"
>
<div>
<el-button size="mini" type="success" @click="hanldeOnReveiwChange(2)"
>审核通过</el-button
<div class="header" v-loading="loading">
<div class="header_btns">
<span>
<el-button
size="mini"
v-if="!!recipesId"
type="primary"
icon="el-icon-document-copy"
@click="handleOnTemplateClick"
>
<el-button size="mini" type="danger" @click="hanldeOnReveiwChange(1)"
>未审核通过</el-button
另存为模板
</el-button>
</span>
<span>
<span class="font_size_style">
字体大小
<el-select
v-model="mFontSize"
size="mini"
style="width: 80px"
@change="handleOnSizeChange"
>
<el-option
v-for="size in fontSizeOpts"
:key="size.value"
:label="size.label"
:value="size.value"
/>
</el-select>
</span>
<el-button size="mini" v-if="!recipesId" @click="handleOnBack"
>返回</el-button
>
</div>
<el-button
slot="reference"
size="mini"
v-if="reviewStatus"
:type="reviewStatus === 1 ? 'danger' : 'success'"
>
{{ reviewStatus === 1 ? "未审核" : "已审核" }}
</el-button>
</el-popover>
<el-popover
placement="bottom"
trigger="click"
title="修改审核状态"
style="margin-right: 12px"
v-hasPermi="['recipes:plan:review']"
>
<div>
<el-button
size="mini"
type="success"
@click="hanldeOnReveiwChange(2)"
>审核通过</el-button
>
<el-button
size="mini"
type="danger"
@click="hanldeOnReveiwChange(1)"
>未审核通过</el-button
>
</div>
<el-button
slot="reference"
size="mini"
v-if="reviewStatus"
:type="reviewStatus === 1 ? 'danger' : 'success'"
>
{{ reviewStatus === 1 ? "未审核" : "已审核" }}
</el-button>
</el-popover>
<el-button
v-if="!recipesId"
size="mini"
type="primary"
@click="handleOnSave"
>生成食谱</el-button
>
</span>
</div>
<el-button
v-if="!recipesId"
size="mini"
type="primary"
@click="handleOnSave"
>生成食谱</el-button
type="text"
@click="handleCollapseClick"
class="collapse_btn"
>
<el-button size="mini" type="text" @click="handleCollapseClick">
{{ `${collapse ? "展开" : "收起"}` }}
<em
class="el-icon-arrow-down arrow_icon"
@ -91,23 +117,29 @@
width="500px"
/>
</div>
<!-- 模板 -->
<TemplateDialog ref="templateRef" @onConfirm="handleOnCopy" />
</div>
</template>
<script>
import BarChart from "./BarChart";
import PieChart from "./PieChart";
import { addRecipesTemplate } from "@/api/custom/recipesTemplate";
import { createNamespacedHelpers } from "vuex";
const { mapActions, mapState, mapMutations } = createNamespacedHelpers(
"recipes"
);
import TemplateDialog from "@/components/TemplateDialog";
export default {
name: "RecipesAspectCom",
components: {
BarChart,
PieChart,
TemplateDialog,
},
data() {
return {
loading: false,
mFontSize: 12,
fontSizeOpts: [
{ value: 12, label: "12" },
@ -152,6 +184,29 @@ export default {
handleOnBack() {
this.updateStateData({ recipesData: [] });
},
handleOnTemplateClick() {
this.$refs.templateRef.showDialog();
},
handleOnCopy(form) {
this.loading = true;
addRecipesTemplate(form).then((response) => {
if (response.code === 200) {
const { planId, id } = response.data;
this.saveRecipes({
cusId: 0,
planId,
callback: () => {
this.$message.success(`另存为模板「${form.name}」成功`);
this.loading = false;
// window.open(
// "/recipes/build/" + form.name + "/" + planId + "?temId=" + id,
// "_blank"
// );
},
});
}
});
},
...mapActions(["saveRecipes", "updateReviewStatus"]),
...mapMutations(["updateStateData", "updateFontSize"]),
},
@ -165,6 +220,19 @@ export default {
.header {
text-align: right;
height: 30px;
display: flex;
align-items: center;
.header_btns {
display: flex;
align-items: center;
justify-content: space-between;
flex: 1;
}
.collapse_btn {
width: 42px;
}
.arrow_icon {
transition: all 0.3s;

View File

@ -77,8 +77,9 @@
icon="el-icon-delete"
class="fun_button"
@click="handleOnDelete(scope.row)"
>删除</el-button
>
删除
</el-button>
</div>
<div>
<el-button
@ -87,15 +88,18 @@
icon="el-icon-document-copy"
class="fun_button"
@click="handleOnCopy(scope.row)"
>复制</el-button
>
复制
</el-button>
<el-button
type="primary"
size="mini"
icon="el-icon-document-copy"
class="fun_button"
@click="handleOnSetting(scope.row)"
>修改餐类</el-button
>
修改餐类
</el-button>
</div>
</div>
<div class="pointer_style" slot="reference">
@ -415,9 +419,6 @@ export default {
handleParentClick(e) {
// 校验某天
this.setCurrentDay({ currentDay: this.num });
VueScrollTo.scrollTo(`#recipes${this.num}`, 500, {
container: "#recipes_content",
});
},
spanMethod({ row, column, rowIndex, columnIndex }) {
if (columnIndex === 0) {
@ -440,6 +441,9 @@ export default {
e.stopPropagation();
// 取消高亮
this.resetCurrentDay({ currentDay: this.num });
VueScrollTo.scrollTo(`#recipes${this.num}`, 500, {
container: "#recipes_content",
});
},
handleOnAdd() {
// console.log(this.num);

View File

@ -40,8 +40,11 @@ export default {
};
},
mounted() {
this.$store.dispatch("global/init", {});
//
this.init({
planId: this.planId,
name: this.name,
temId: this.temId,
}).catch((err) => {
this.$message.error(err.message);

View File

@ -1,5 +1,7 @@
export function getProcessMenuData(menuData) {
return menuData.reduce((arr, cur) => {
// const igdPlanData = {};
const menuList = menuData.reduce((arr, cur) => {
if (
cur.dishesId > -1 &&
cur.name &&
@ -39,4 +41,5 @@ export function getProcessMenuData(menuData) {
}
return arr;
}, []);
return menuList;
}

View File

@ -180,49 +180,7 @@
/>
<!-- 添加或修改食材对话框 -->
<el-dialog :title="title" :visible.sync="open" width="520px" append-to-body>
<el-form ref="form" :model="form" :rules="rules" label-width="80px">
<el-form-item label="模板名称" prop="name" label-width="100px">
<el-input v-model="form.name" placeholder="请输入模板名称" />
</el-form-item>
<el-form-item label="营养师" prop="nutritionistId" label-width="100px">
<el-select v-model="form.nutritionistId" placeholder="请选择营养师">
<el-option
v-for="dict in nutritionistIdOptions"
:key="dict.dictValue"
:label="dict.dictLabel"
:value="dict.dictValue"
></el-option>
</el-select>
</el-form-item>
<el-form-item
label="营养师助理"
prop="nutriAssisId"
label-width="100px"
>
<el-select v-model="form.nutriAssisId" placeholder="请选择营养师助理">
<el-option
v-for="dict in nutriAssisIdOptions"
:key="dict.dictValue"
:label="dict.dictLabel"
:value="dict.dictValue"
></el-option>
</el-select>
</el-form-item>
<el-form-item label="备注" prop="remark" label-width="100px">
<el-input
v-model="form.remark"
:rows="4"
type="textarea"
placeholder="请输入内容"
/>
</el-form-item>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button type="primary" @click="submitForm"> </el-button>
<el-button @click="cancel"> </el-button>
</div>
</el-dialog>
<TemplateDialog ref="templateDialogRef" @onConfirm="handleOnConfirm" />
</div>
</template>
@ -233,10 +191,9 @@ import {
updateRecipesTemplate,
deleteRecipesTemplate,
} from "@/api/custom/recipesTemplate";
import store from "@/store";
import { mapState } from "vuex";
import TemplateDialog from "@/components/TemplateDialog";
import { mapGetters, mapState } from "vuex";
const userId = store.getters && store.getters.userId;
export default {
name: "recipesTemplate",
data() {
@ -266,18 +223,6 @@ export default {
},
open: false,
title: "",
// 表单参数
form: {},
// 表单校验
rules: {
name: [{ required: true, message: "请输入模板名称", trigger: "blur" }],
nutritionistId: [
{ required: true, message: "请选择营养师", trigger: "blur" },
],
nutriAssisId: [
{ required: true, message: "请选择营养师助理", trigger: "blur" },
],
},
//订单对于所有计划安排数据
allRecipesPlanList: [],
//订单弹窗状态
@ -295,10 +240,12 @@ export default {
};
},
components: {
TemplateDialog,
// "order-dialog": OrderDetail,
// body_sign_dialog: BodySignDetail,
},
computed: {
// ...mapGetters(["userId"]),
...mapState({
//营养师
nutritionistIdOptions: (state) =>
@ -340,9 +287,7 @@ export default {
},
/** 新增按钮操作 */
handleAdd() {
this.reset();
this.open = true;
this.title = "添加模板";
this.$refs.templateDialogRef.showDialog();
},
/** 搜索按钮操作 */
handleQuery() {
@ -354,22 +299,6 @@ export default {
this.resetForm("queryForm");
this.handleQuery();
},
// 取消按钮
cancel() {
this.open = false;
this.reset();
},
// 表单重置
reset() {
this.form = {
id: null,
name: null,
remark: null,
nutritionistId: null,
nutriAssisId: null,
};
this.resetForm("form");
},
/** 导出按钮操作 */
handleExport() {
const queryParams = this.queryParams;
@ -402,10 +331,7 @@ export default {
.catch(() => {});
},
handleOnTemplateEdit(data) {
this.open = true;
this.title = "修改模板";
this.reset();
this.form = data;
this.$refs.templateDialogRef.showDialog(data);
},
handleOnRecipesEdit(data) {
// console.log(data);
@ -427,29 +353,24 @@ export default {
return this.selectDictLabel(this.nutriAssisIdOptions, row.nutriAssisId);
},
/** 提交按钮 */
submitForm() {
this.$refs["form"].validate((valid) => {
if (valid) {
this.form.cusId = 0;
if (this.form.id != null) {
updateRecipesTemplate(this.form).then((response) => {
if (response.code === 200) {
this.msgSuccess("修改成功");
this.open = false;
this.getList();
}
});
} else {
addRecipesTemplate(this.form).then((response) => {
if (response.code === 200) {
this.msgSuccess("新增成功");
this.open = false;
this.getList();
}
});
handleOnConfirm(form) {
if (form.id != null) {
updateRecipesTemplate(form).then((response) => {
if (response.code === 200) {
this.msgSuccess("修改成功");
this.open = false;
this.getList();
}
}
});
});
} else {
addRecipesTemplate(form).then((response) => {
if (response.code === 200) {
this.msgSuccess("新增成功");
this.open = false;
this.getList();
}
});
}
},
},
};

View File

@ -268,7 +268,6 @@ import {
updateWxDistribution,
exportWxDistribution,
} from "@/api/custom/wxDistribution";
import { getOptions } from "@/api/custom/order";
import { listWxAccount } from "@/api/custom/wxAccount";
import { mapState } from "vuex";
export default {