| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290 |
- <template>
- <view class="page">
- <u-navbar :title="isEdit ? '编辑餐盒' : '新建餐盒'" :autoBack="true" :placeholder="true" :border-bottom="true"></u-navbar>
- <view class="section-head">规格1</view>
- <view class="form">
- <view class="row">
- <text class="label">餐盒名称</text>
- <input class="input" v-model="form.name" placeholder="请输入" placeholder-class="ph" />
- </view>
- <view class="row">
- <text class="label">餐盒价格</text>
- <input class="input" v-model="form.price" type="digit" placeholder="请输入金额 元" placeholder-class="ph" />
- </view>
- <view class="row link" @click="goBind">
- <text class="label">已绑商品</text>
- <view class="right">
- <text class="action">{{ form.bindCount ? `已绑${form.bindCount}个` : '去绑定' }}</text>
- <u-icon name="arrow-right" color="#C7C6CA" size="24"></u-icon>
- </view>
- </view>
- <view class="row link last" @click="pickImage">
- <text class="label">餐盒图片</text>
- <view class="right">
- <image v-if="form.image" class="thumb" :src="form.image" mode="aspectFill" @click.stop="previewImage"></image>
- <template v-else>
- <text class="action">去上传</text>
- <u-icon name="arrow-right" color="#C7C6CA" size="24"></u-icon>
- </template>
- </view>
- </view>
- </view>
- <view class="footer">
- <view :class="['primary-btn', saving ? 'disabled' : '']" @click="onSave">{{ saving ? '保存中...' : '保存' }}</view>
- </view>
- </view>
- </template>
- <script>
- import configService from '@/common/service/config.service';
- import merchantDishApi, { mapMealBoxItem } from '@/api/merchantDish.js';
- export default {
- data() {
- return {
- isEdit: false,
- saving: false,
- uploadAction: configService.apiUrl + '/sys/common/upload',
- imageHttp: configService.apiUrl + '/',
- form: {
- id: null,
- name: '',
- price: '',
- image: '',
- bindIds: [],
- bindCount: 0,
- status: 1,
- sort: 0
- }
- };
- },
- onLoad(query) {
- if (query.id) {
- this.isEdit = true;
- this.form.id = query.id;
- this.loadDetail(query.id);
- }
- },
- methods: {
- /** 供绑定页回写选中商品 */
- applyBindIds(ids) {
- this.form.bindIds = ids || [];
- this.form.bindCount = this.form.bindIds.length;
- },
- loadDetail(id) {
- uni.showLoading({ title: '加载中' });
- Promise.all([
- merchantDishApi.mealBoxDetail(id),
- merchantDishApi.mealBoxPackages(id)
- ])
- .then(([detailRes, pkgRes]) => {
- if (detailRes.data.code === 200 && detailRes.data.result) {
- const item = mapMealBoxItem(detailRes.data.result);
- this.form = {
- ...this.form,
- id: item.id,
- name: item.name || '',
- price: item.price != null && item.price !== '' ? String(item.price) : '',
- image: item.image || '',
- status: item.status != null ? item.status : 1,
- sort: item.sort || 0
- };
- }
- if (pkgRes.data.code === 200) {
- const pkgs = pkgRes.data.result || [];
- this.form.bindIds = pkgs.map((p) => p.packageId).filter(Boolean);
- this.form.bindCount = this.form.bindIds.length;
- }
- })
- .finally(() => uni.hideLoading());
- },
- pickImage() {
- uni.chooseImage({
- count: 1,
- sizeType: ['compressed'],
- sourceType: ['album', 'camera'],
- success: (res) => {
- const filePath = (res.tempFilePaths || [])[0];
- if (!filePath) return;
- uni.showLoading({ title: '上传中' });
- uni.uploadFile({
- url: this.uploadAction,
- filePath,
- name: 'file',
- formData: { biz: 'temp' },
- success: (uploadRes) => {
- try {
- const data = typeof uploadRes.data === 'string' ? JSON.parse(uploadRes.data) : uploadRes.data;
- if (data && data.success !== false && data.message) {
- this.form.image = this.imageHttp + data.message;
- } else if (data && data.url) {
- this.form.image = data.url;
- } else {
- this.$tip.toast((data && data.message) || '上传失败');
- }
- } catch (e) {
- this.$tip.toast('上传失败');
- }
- },
- fail: () => {
- this.$tip.toast('上传失败');
- },
- complete: () => uni.hideLoading()
- });
- }
- });
- },
- previewImage() {
- if (!this.form.image) return;
- uni.previewImage({ urls: [this.form.image] });
- },
- goBind() {
- const boxId = this.form.id || 'new';
- uni.navigateTo({
- url: `/pages/merchantDish/settings/box-bind?id=${boxId}&from=form`,
- success: (res) => {
- res.eventChannel.emit('initBind', {
- bindIds: this.form.bindIds || []
- });
- },
- events: {
- onBindConfirm: (data) => {
- this.applyBindIds((data && data.bindIds) || []);
- }
- }
- });
- },
- onSave() {
- if (!this.form.name) {
- uni.showToast({ title: '请输入餐盒名称', icon: 'none' });
- return;
- }
- if (this.saving) return;
- this.saving = true;
- const packageIds = this.form.bindIds || [];
- const base = {
- boxName: this.form.name,
- boxPrice: Number(this.form.price || 0),
- boxImage: this.form.image || '',
- status: this.form.status != null ? this.form.status : 1,
- sort: this.form.sort || 0
- };
- const done = (res) => {
- const ok = res.data.code === 200;
- this.$tip.toast(res.data.message || (ok ? '保存成功' : '保存失败'));
- if (ok) setTimeout(() => uni.navigateBack(), 400);
- };
- if (!this.isEdit) {
- merchantDishApi
- .mealBoxAdd({ ...base, packageIds })
- .then(done)
- .finally(() => {
- this.saving = false;
- });
- return;
- }
- merchantDishApi
- .mealBoxEdit({ id: this.form.id, ...base })
- .then((res) => {
- if (res.data.code !== 200) {
- done(res);
- return null;
- }
- return merchantDishApi.mealBoxBind(this.form.id, packageIds);
- })
- .then((res) => {
- if (res) done(res);
- })
- .finally(() => {
- this.saving = false;
- });
- }
- }
- };
- </script>
- <style lang="scss" scoped>
- .page {
- min-height: 100vh;
- background: #f7f8fa;
- padding-bottom: 160rpx;
- }
- .section-head {
- padding: 20rpx 24rpx;
- font-size: 30rpx;
- font-weight: 600;
- color: #333;
- background: #eef3f8;
- }
- .form {
- background: #fff;
- }
- .row {
- display: flex;
- align-items: center;
- min-height: 96rpx;
- padding: 0 24rpx;
- border-bottom: 1rpx solid #f0f0f0;
- &.last {
- border-bottom: none;
- }
- &.link:active {
- background: #fafafa;
- }
- .label {
- width: 180rpx;
- font-size: 28rpx;
- color: #333;
- flex-shrink: 0;
- }
- .input {
- flex: 1;
- text-align: right;
- font-size: 28rpx;
- color: #333;
- }
- .right {
- flex: 1;
- display: flex;
- align-items: center;
- justify-content: flex-end;
- }
- .action {
- font-size: 28rpx;
- color: #999;
- margin-right: 4rpx;
- }
- .thumb {
- width: 72rpx;
- height: 72rpx;
- border-radius: 8rpx;
- background: #eee;
- }
- }
- .ph {
- color: #c0c4cc;
- }
- .footer {
- position: fixed;
- left: 0;
- right: 0;
- bottom: 0;
- z-index: 20;
- padding: 20rpx 40rpx calc(20rpx + env(safe-area-inset-bottom));
- background: #fff;
- }
- .primary-btn {
- height: 88rpx;
- line-height: 88rpx;
- text-align: center;
- color: #fff;
- font-size: 32rpx;
- border-radius: 44rpx;
- background: linear-gradient( 89deg, #10ABFE 0%, #2260F6 100%);
- &.disabled {
- opacity: 0.6;
- }
- }
- </style>
|