management/src/views/invoicing/operation_in.vue

586 lines
25 KiB
Vue

<template>
<div class="app-container">
<div class="head-container">
<el-form ref="queryForm" :model="queryForm" :rules="queryRules" label-position="left" label-width="80px">
<!-- <el-form-item label="入库内容">
<div class="shop_type_box">
<div class="item" v-for="item in inTabs" :key="item.value"
:class="{ active: inTabValue == item.value }" @click="tabChange(item.value, item.type)">
<div class="s_title">{{ item.label }}</div>
<div class="active_dot">
<i class="el-icon-check"></i>
</div>
</div>
</div>
</el-form-item> -->
<!-- <el-form-item label="入库类型" v-if="inTabValue == 'goods'">
<div class="shop_type_box">
<div class="item" v-for="(item, index) in shopTypes" :key="index"
:class="{ active: shopTypesActive == index }" @click="changeTypeEnum(index)">
<div class="s_title">{{ item.label }}</div>
<div class="active_dot">
<i class="el-icon-check"></i>
</div>
</div>
</div>
</el-form-item>
<el-form-item label="入库类型" v-else>
<div class="shop_type_box">
<div class="item" v-for="(item, index) in shopTypes2" :key="index"
:class="{ active: shopTypesActive == index }" @click="changeTypeEnum(index)">
<div class="s_title">{{ item.label }}</div>
<div class="active_dot">
<i class="el-icon-check"></i>
</div>
</div>
</div>
</el-form-item> -->
<el-row>
<el-col :span="8">
<el-form-item label="供应商">
<el-select v-model="queryForm.purveyorId" placeholder="请选择供应商" clearable
style="width: 220px;" @change="changeTypeEnum">
<el-option :label="item.purveyorName" :value="item.id" v-for="item in purveyorList"
:key="item.id"></el-option>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="入库时间" prop="time">
<el-date-picker v-model="queryForm.time" type="date" format="yyyy-MM-dd"
value-format="yyyy-MM-dd" placeholder="选择日期" style="width: 220px;">
</el-date-picker>
</el-form-item>
</el-col>
</el-row>
<el-row v-if="shopTypes[shopTypesActive].value == 'purveyor'">
<el-col :span="8">
<el-form-item label="应付金额">
<el-input v-model="queryForm.totalAmount" placeholder="请输入应收金额"
style="width: 220px;"></el-input>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="实付金额">
<el-input v-model="queryForm.paidAmount" placeholder="请输入实收金额"
style="width: 220px;"></el-input>
</el-form-item>
</el-col>
</el-row>
<el-row v-if="shopTypes[shopTypesActive].value == 'purveyor'">
<el-col :span="8">
<el-form-item label="付款时间">
<el-date-picker v-model="queryForm.paidAt" type="date" format="yyyy-MM-dd"
value-format="yyyy-MM-dd" placeholder="选择日期" style="width: 220px;">
</el-date-picker>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="批号">
<el-input v-model="queryForm.batchNumber" placeholder="请输入批号"
style="width: 220px;"></el-input>
</el-form-item>
</el-col>
</el-row>
<el-row>
<el-col :span="8">
<el-form-item label="欠款金额">
<el-input v-model="queryForm.waitAmount" disabled style="width: 220px;"></el-input>
</el-form-item>
</el-col> <el-col :span="8">
<el-form-item label="备注">
<el-input v-model="queryForm.remark" placeholder="请输入备注" style="width: 220px;"></el-input>
</el-form-item>
</el-col>
</el-row>
<el-form-item>
<el-button type="primary" @click="$refs.ConsumableList.show(tableData.list)"
v-if="inTabValue == 'consumable'">选择耗材</el-button>
<el-button type="primary" @click="$refs.shopList.show(tableData.list)" v-else>选择商品</el-button>
</el-form-item>
<el-autocomplete v-model="autocompletename" :fetch-suggestions="querySearchAsync"
:value-key="inTabValue == 'goods' ? 'name' : 'conName'"
:placeholder="inTabValue == 'goods' ? '商品搜索' : '耗材搜索'" @select="handleSelect"
style="width: 500px;"></el-autocomplete>
</el-form>
</div>
<div class="head-container">
<el-button type="primary" plain v-if="inTabValue == 'consumable'">
共{{ tableData.list.length }}种耗材,金额合计<span style="color: red;">¥{{ queryForm.totalAmount }}</span>
</el-button>
<el-button type="primary" plain v-else>
共{{ tableData.list.length }}种商品,金额合计<span style="color: red;">¥{{ queryForm.totalAmount }}</span>
</el-button>
</div>
<div class="head-container">
<el-table :data="tableData.list" v-if="inTabValue == 'consumable'">
<el-table-column label="耗材名称" prop="conName">
<template v-slot="scope">
{{ scope.row.conName }}
</template>
</el-table-column>
<el-table-column label="进价">
<template v-slot="scope">
<el-input-number v-model="scope.row.price" :min="0" controls-position="right"
@change="consCountTotal($event, scope.row, 'price')"></el-input-number>
<div class="tips">原价¥{{ scope.row.costPrice }}/{{ scope.row.conUnit }}</div>
</template>
</el-table-column>
<el-table-column label="单位">
<template v-slot="scope">
<el-select @change="consCountTotal($event, scope.row, 'unit')" v-model="scope.row.unit"
:placeholder="scope.row.conUnit">
<el-option :label="scope.row.conUnit" :value="scope.row.conUnit"> </el-option>
<el-option :label="scope.row.conUnitTwo" :value="scope.row.conUnitTwo"
v-if="scope.row.conUnitTwo"> </el-option>
</el-select>
<div class="tips"> &nbsp;</div>
</template>
</el-table-column>
<el-table-column label="数量">
<template v-slot="scope">
<el-input-number v-model="scope.row.stockNumber" :min="0" :step="1" step-strictly
controls-position="right"
@change="consCountTotal($event, scope.row, 'stockNumber')"></el-input-number>
<div class="tips">入库前:{{ scope.row.number }}{{ scope.row.conUnit }}
</div>
</template>
</el-table-column>
<el-table-column label="小计">
<template v-slot="scope">
<!-- <el-input-number v-model="scope.row.totalAmount" :min="0" scope.row.price , scope.row.stockNumber
controls-position="right"></el-input-number> -->
<el-input :value="formatDecimal(testform(scope.row))" readonly style="width: 100px;" />
</template>
</el-table-column>
<!-- <el-table-column label="变动后剩余库存">
<template v-slot="scope">
{{ scope.row.stockNumber + scope.row.number }}{{ scope.row.conUnit }}
</template>
</el-table-column> -->
<el-table-column label="操作" width="80">
<template v-slot="scope">
<el-button type="text"
@click="tableData.list.splice(scope.$index, 1), spliceclick()">删除</el-button>
</template>
</el-table-column>
</el-table>
<el-table :data="tableData.list" v-else>
<el-table-column type="index" width="50"></el-table-column>
<el-table-column label="商品名称" prop="name">
<template v-slot="scope">
<div class="name_wrap">
<span class="name">{{ scope.row.name }}</span>
<span v-if="scope.row.specSnap">({{ scope.row.specSnap }})</span>
<!-- <el-tag type="info" v-if="scope.row.specSnap" size="mini">{{ scope.row.specSnap }}</el-tag> -->
</div>
</template>
</el-table-column>
<el-table-column label="进价">
<template v-slot="scope">
<el-input-number v-model="scope.row.costPrice" :min="0" controls-position="right"
@change="modifyPrice($event, scope.row, 'costPrice')"></el-input-number>
<div class="tips">成本价¥{{ scope.row.costPrice }}/{{ scope.row.unitName }}</div>
</template>
</el-table-column>
<el-table-column label="数量">
<template v-slot="scope">
<el-input-number v-model="scope.row.number" :min="0" :step="1" step-strictly
controls-position="right"
@change="modifyPrice($event, scope.row, 'number', 'totalAmount')"></el-input-number>
<div class="tips">入库前:{{ scope.row.stockNumber }}{{ scope.row.unitName }}</div>
</template>
</el-table-column>
<el-table-column label="小计">
<template v-slot="scope">
<!-- <el-input-number v-model="scope.row.totalAmount" :min="0"
controls-position="right"></el-input-number> -->
<el-input :value="scope.row.costPrice * scope.row.number" readonly style="width: 100px;" />
</template>
</el-table-column>
<el-table-column label="变动后剩余库存">
<template v-slot="scope">
{{ scope.row.stockNumber + scope.row.number }}{{ scope.row.unitName }}
</template>
</el-table-column>
<el-table-column label="操作" width="80">
<template v-slot="scope">
<el-button type="text"
@click="tableData.list.splice(scope.$index, 1), spliceclick()">删除</el-button>
</template>
</el-table-column>
</el-table>
</div>
<div>
<el-button type="primary" @click="submitHandle" :loading="queryFormLoading">确定</el-button>
</div>
<!-- 选择商品 -->
<shopList ref="shopList" @success="selectShop" />
<!-- 选择耗材 -->
<ConsumableList ref="ConsumableList" @success="selectConsumable" />
<el-dialog :visible.sync="showResult" :show-close="false" :close-on-press-escape="false"
:close-on-click-modal="false">
<el-result icon="success" title="入库提交成功" :subTitle="`共操作${tableData.list.length}件商品`">
<template slot="extra">
<el-button type="primary" size="medium" @click="resetHandle">创建新的入库单</el-button>
<router-link to="/invoicing/operating_record">
<el-button size="medium">历史提交</el-button>
</router-link>
</template>
</el-result>
</el-dialog>
</div>
</template>
<script>
import dayjs from 'dayjs'
import shopList from './components/shopList'
import ConsumableList from './components/consumableList'
import { tbConsInfoGet, tbProductlist } from "@/api/invoicing";
import { tbShopPurveyorGet, tbProductStockOperateOutAndOn, stockInOut } from '@/api/invoicing'
import { formatDecimal } from '@/utils'
export default {
name:'operation_in',
components: {
shopList,
ConsumableList
},
data() {
return {
formatDecimal,
inTabValue: 'consumable',
inTabs: [
{
label: '商品入库',
value: 'goods',
type: 'purveyor'
},
{
label: '耗材入库',
value: 'consumable',
type: 'in'
}
],
shopTypesActive: 0,
shopTypes: [
{
label: '供应商入库',
value: 'purveyor'
},
{
label: '其他入库',
value: 'purchase'
}
],
shopTypes2: [
{
label: '供应商入库',
value: 'purveyor'
},
],
resetForm: '',
queryFormLoading: false,
queryForm: {
batchNumber: '',
list: [],
paidAmount: 0,
paidAt: '',
purveyorId: '',
purveyorName: '',
remark: '',
time: dayjs().format('YYYY-MM-DD'),
totalAmount: 0,
type: 'in',
shopId: localStorage.getItem('shopId')
},
queryRules: {
purveyorId: [
{
required: true,
message: '请选择供应商',
trigger: 'change'
}
],
time: [
{
required: true,
message: ' ',
trigger: 'change'
}
]
},
purveyorList: [],
tableData: {
list: []
},
showResult: false,
autocompletename: '',
restaurants: [],
timeout: null
}
},
mounted() {
this.resetForm = { ...this.queryForm }
this.tbShopPurveyorGet()
},
methods: {
async querySearchAsync(queryString, cb) {//快捷搜索
let res = null
if (this.inTabValue == 'goods') {
res = await tbProductlist({
page: 0,
size: 20,
name: queryString ? queryString : '',
shopId: localStorage.getItem('shopId'),
sort: 'id',
})
} else {
res = await tbConsInfoGet({
page: 0,
size: 20,
shopId: localStorage.getItem('shopId'),
conName: queryString ? queryString : ''
})
}
this.restaurants = res.content
if (res.content.length == 0) {//给个提示没有搜到
this.$message('无此商品');
return false
}
var uniqueArray = this.restaurants.filter(item1 =>
!this.tableData.list.some(item2 => item2.productId == item1.id)
);
clearTimeout(this.timeout);
this.timeout = setTimeout(() => {
cb(uniqueArray);
}, 1000 * Math.random());
},
testform(d) {
let p = 1
if (d.unit && d.unit == d.conUnitTwo) {
p = d.conUnitTwoConvert
}
return d.price * d.stockNumber * p
},
handleSelect(item) {//选定后清空
this.autocompletename = ''
if (this.inTabValue == 'goods') {
this.selectShop([item])
} else {
this.selectConsumable([item])
}
},
//删除计算
spliceclick() {
var zong = 0
if (this.inTabValue == 'goods') {
this.tableData.list.forEach(ele => {
zong += ele.costPrice * ele.number
})
} else {
this.tableData.list.forEach(ele => {
zong += ele.price * ele.stockNumber
})
}
this.queryForm.totalAmount = formatDecimal(zong)
},
// 选择商品
selectShop(res) {
let arr = []
res.forEach(item => {
item.skuList.forEach(i => {
arr.push({
name: item.name,
unitName: item.unitName,
productId: item.id,
number: 0,
totalAmount: '',
...i
})
})
})
this.tableData.list = [...this.tableData.list, ...arr]
},
// 切换入库内容
tabChange(value, type) {
console.log(value, type)
this.shopTypesActive = type == 'in' ? 0 : 1
this.inTabValue = value
this.resetHandle()
this.$refs.shopList.reset()//清除选项
this.$refs.ConsumableList.reset()//清除选项
},
// 切换类型
changeTypeEnum(index) {
let filterd= this.purveyorList.filter(ele=>ele.id == index)
this.queryForm.waitAmount = filterd[0].waitAmount
this.inTabs.forEach((i) => {
if (i.value == this.inTabValue) {
this.queryForm.type = i.type
}
})
if (this.inTabValue == 'consumable') {
return false
}
//商品入库是否显示应付实付
if (this.queryForm.purveyorId) {
this.shopTypesActive = 0
} else {
this.shopTypesActive = 1
}
},
// 计算耗材总价
consCountTotal(cvalue, row, key1, key2 = undefined) {
if (cvalue == undefined) {
setTimeout(() => {
row[key1] = 0
let zong = 0
this.tableData.list.forEach(ele => {
zong += ele.price * ele.stockNumber
})
this.queryForm.totalAmount = formatDecimal(zong)
}, 10)
} else {
row[key1] = cvalue
let zong = 0
this.tableData.list.forEach(ele => {
let p = 1
if (ele.unit && ele.conUnitTwo == ele.unit) {
p = ele.conUnitTwoConvert
}
zong += ele.price * ele.stockNumber * p
})
this.queryForm.totalAmount = formatDecimal(zong)
}
},
// 计算商品总价
modifyPrice(cvalue, row, key1, key2 = undefined) {
if (cvalue == undefined) {
setTimeout(() => {
row[key1] = 0
row[key2] = 0
let zong = 0
this.tableData.list.forEach(ele => {
zong += ele.costPrice * ele.number
})
this.queryForm.totalAmount = formatDecimal(zong)
}, 10)
} else {
row[key1] = cvalue
row[key2] = cvalue
let zong = 0
this.tableData.list.forEach(ele => {
zong += ele.costPrice * ele.number
})
this.queryForm.totalAmount = formatDecimal(zong)
}
},
// 提交
submitHandle() {
if (this.tableData.list.length == 0) {
switch (this.inTabValue) {
case 'goods':
this.$message('请先选择商品!');
break;
case 'consumable':
this.$message('请先选择耗材!');
break;
default:
break;
}
return false
}
this.$refs.queryForm.validate(async valid => {
if (valid) {
try {
this.queryFormLoading = true
switch (this.inTabValue) {
case 'goods':
this.queryForm.list = this.tableData.list
await tbProductStockOperateOutAndOn(this.queryForm)
break;
case 'consumable':
this.queryForm.accountsPayable = this.queryForm.totalAmount
this.queryForm.actualPayment = this.queryForm.paidAmount
this.queryForm.paymentTime = this.queryForm.paidAt
this.queryForm.supplierId = this.queryForm.purveyorId
this.queryForm.list = this.tableData.list
await stockInOut(this.queryForm)
break;
default:
break;
}
this.queryFormLoading = false
this.$message({
message: '入库提交成功',
type: 'success'
})
this.resetHandle()//初始化
// this.showResult = true
// this.$refs.shopList.reset()//清除选项
// this.$refs.ConsumableList.reset()//清除选项
} catch (error) {
console.log(error)
this.queryFormLoading = false
}
}
})
},
// 选择耗材
selectConsumable(res) {
let arr = res.map(item => {
item.number = formatDecimal(item.stockNumber - item.stockConsume, 2, true)
item.stockNumber = 0
item.costPrice = item.price
item.conInfoId = item.id
return item
})
this.tableData.list = [...this.tableData.list, ...arr]
},
// 初始化
resetHandle() {
this.showResult = false
this.queryForm = { ...this.resetForm }
if (this.inTabValue == 'goods') {
this.queryForm.type = 'purveyor'
} else {
this.queryForm.type = this.inTabs.find(item => item.value == this.inTabValue).type
}
this.tableData.list = []
this.$refs.queryForm.resetFields()
this.$refs.queryForm.resetFields()
},
// 获取供应商列表
async tbShopPurveyorGet() {
try {
const res = await tbShopPurveyorGet({
shopId: localStorage.getItem('shopId'),
page: 0,
size: 100
})
this.purveyorList = res.content
} catch (error) {
console.log(error)
}
}
}
}
</script>
<style scoped lang="scss">
.name_wrap {
display: flex;
align-items: center;
.name {
margin-right: 10px;
}
}
</style>