Sfoglia il codice sorgente

Merge branch 'zzd' of ssh://was.baoshi56.com:10022/var/git/bswas

 Conflicts:
	app/Http/Controllers/TestController.php
	laravel-echo-server.lock
	package-lock.json
LD 5 anni fa
parent
commit
1dc867daf3

+ 1 - 1
app/DeliveryAppointment.php

@@ -26,7 +26,7 @@ class DeliveryAppointment extends Model
         "date_period",
         "status",
     ];
-    //时段 映射date_period字段
+    //时段 映射date_period字段 必须有序 否则展示数据错乱
     const PERIOD=[
         0 => "9-11",
         1 => "13-17",

+ 1 - 6
app/DeliveryAppointmentCar.php

@@ -17,15 +17,10 @@ class DeliveryAppointmentCar extends Model
         "driver_name",
         "driver_phone",
         "appointment_number",
-        "status",
+        "delivery_time",
     ];
     public $timestamps=false;
 
-    const STATUS=[
-        0 => "待送",
-        1 => "已送"
-    ];
-
     public function deliveryAppointment()
     {   //预约信息
         return $this->belongsTo(DeliveryAppointment::class);

+ 42 - 0
app/Events/DeliveryAppointmentEvent.php

@@ -0,0 +1,42 @@
+<?php
+
+namespace App\Events;
+
+use App\DeliveryAppointmentCar;
+use Illuminate\Broadcasting\Channel;
+use Illuminate\Contracts\Broadcasting\ShouldBroadcast;
+use Illuminate\Foundation\Events\Dispatchable;
+use Illuminate\Queue\SerializesModels;
+
+class DeliveryAppointmentEvent implements ShouldBroadcast
+{
+    use Dispatchable, SerializesModels;
+
+    public $delivery;
+    /**
+     * Create a new event instance.
+     *
+     * @param DeliveryAppointmentCar $delivery
+     *
+     * @return void
+     */
+    public function __construct(DeliveryAppointmentCar $delivery)
+    {
+        $this->delivery = $delivery;
+    }
+
+    /**
+     * Get the channels the event should broadcast on.
+     *
+     * @return \Illuminate\Broadcasting\Channel|array
+     */
+    public function broadcastOn()
+    {
+        return new Channel('delivery');
+    }
+
+    public function broadcastAs()
+    {
+        return "car";
+    }
+}

+ 123 - 3
app/Http/Controllers/DeliveryAppointmentController.php

@@ -3,14 +3,12 @@
 namespace App\Http\Controllers;
 
 use App\CarType;
-use App\CommodityBarcode;
 use App\Components\AsyncResponse;
 use App\DeliveryAppointment;
 use App\DeliveryAppointmentCar;
-use App\DeliveryAppointmentDetail;
+use App\Events\DeliveryAppointmentEvent;
 use App\Imports\AppointmentDetail;
 use App\Services\common\ExportService;
-use App\Services\common\QueryService;
 use App\Warehouse;
 use Carbon\Carbon;
 use Carbon\CarbonPeriod;
@@ -287,4 +285,126 @@ class DeliveryAppointmentController extends Controller
         }
         return app(ExportService::class)->json($row,$list,"预约记录");
     }
+
+    /**
+     *  获取展览数据
+     */
+    public function getExhibitionList()
+    {
+        $this->gate("入库管理-客户预约-预约管理");
+        $list = [];
+        $hour = date("H");
+        $index = null;
+        foreach (DeliveryAppointment::PERIOD as $key=>$period){
+            $arr = explode("-",$period);
+            if (count($arr)!=2)continue;
+            if ($hour<$arr[1])$index = $key;
+        }
+        if ($index===null)$this->success([]);
+        DeliveryAppointmentCar::query()->whereHas("deliveryAppointment",function (Builder $query)use($index){
+            $query->where("appointment_date",date("Y-m-d"))->whereIn("status",[0,2])
+                ->where("date_period",">=",$index);
+        })->orderByDesc("id")->limit(10)->get()->each(function ($car)use(&$list){
+            $diff = $car->delivery_time ? (strtotime($car->delivery_time)+1799)-time() : 0;
+            $list[] = [
+                "license_plate_number" => $car->license_plate_number,
+                "driver_name" => $car->driver_name,
+                "driver_phone" => $car->driver_phone,
+                "diff" => $diff>0 ? $diff*1000 : 0,
+            ];
+        });
+        $result = ["list"=>$list];
+        $nextTime = DeliveryAppointment::PERIOD[$index+1] ?? null;
+        if ($nextTime){
+            $nextTime = explode("-",$nextTime)[0];
+            $timestamp = strtotime(date("Y-m-d")." ".$nextTime.":00:00");
+            $result["refresh"] = (($timestamp-time())*1000) ?? 1000;
+        }
+        $this->success($result);
+    }
+
+    public function getKey()
+    {
+        $this->success(app("DeliveryAppointmentService")->getKey());
+    }
+
+    /**
+     * 错误信息
+     *
+     * @return string
+     */
+    public function errMsg()
+    {
+        return <<<html
+<div style='font-weight: bold;color: red;margin: 500px auto;text-align: center;'>
+<span style='font-size: 200px;'>&times;</span><br>
+<span style='font-size: 50px'>二维码已过期,请重新扫描!</span><br><h1 style="color: #1b1e21;">如果多次扫描失败,请联系管理人员检查!</h1>
+</div>"
+html;
+    }
+
+    /**
+     * 检查key有效性
+     *
+     * @param string $key
+     * @param int $offset
+     *
+     * @return bool
+     */
+    private function check($key,$offset):bool
+    {
+        if (!$key)return false;
+        $key = base64_decode($key);
+        $ch = app("DeliveryAppointmentService")->getKey();
+        $len = strlen($ch);
+        $timeLen = strlen($key)-$len;
+        if (substr($key,0,$len)!=$ch)return false;
+        $time = substr($key,$len)+$offset;
+        $thisTime = (integer)substr(time(),$timeLen*-1);
+        if ($thisTime>$time)return false;
+        return true;
+    }
+    /**
+     * 进入预约界面填写预约码
+     */
+    public function delivery()
+    {
+        if (!$this->check(request("k"),65))return $this->errMsg();
+        return view("store.deliveryAppointment.delivery",["k"=>request("k")]);
+    }
+
+    /**
+     * 验证预约码
+     *
+     */
+    public function checkAppointment()
+    {
+        if (!$this->check(request("k"),180))return ["status"=>406];
+        $number = request("number");
+        if (!$number)return ["status"=>417];
+        $period = app("DeliveryAppointmentService")->getPeriod();
+        if ($period===false)return ["status"=>416]; //非法时段扫码
+        $car = DeliveryAppointmentCar::query()->whereNull("delivery_time")
+            ->where("appointment_number",$number)->whereHas("deliveryAppointment",function (Builder $query)use($period){
+                $query->where("appointment_date",date("Y-m-d"))
+                ->where("date_period",$period)->where("status",0);
+            })->first();
+        if (!$car)return ["status"=>417];
+        $car->update(["delivery_time"=>date("Y-m-d H:i:s")]);
+        /** @var DeliveryAppointmentCar $car */
+        event(new DeliveryAppointmentEvent($car));
+        app("DeliveryAppointmentService")->checkFull($car->delivery_appointment_id);
+        return ["status"=>200,"k"=>$car->delivery_appointment_id];
+    }
+
+    public function successMsg()
+    {
+        if (!request("k"))return view("exception.404");
+        /** @var \stdClass $appointment */
+        $appointment = DeliveryAppointment::query()->with(["cars"=>function($query){
+            /** @var Builder $query */
+            $query->whereNull("delivery_time");
+        }])->find(request("k"));
+        return view("store.deliveryAppointment.deliverySuccess",["cars"=>$appointment->cars]);
+    }
 }

+ 8 - 0
app/Http/Controllers/TestController.php

@@ -19,6 +19,8 @@ use App\Console\Commands\SyncWMSOrderTask;
 use App\Console\Commands\WasSyncWmsAsnInformation;
 use App\DeliveryAppointment;
 use App\Events\BroadcastToStation;
+use App\DeliveryAppointmentCar;
+use App\Events\DeliveryAppointmentEvent;
 use App\Exceptions\ErrorException;
 use App\Events\CancelOrder;
 use App\Events\SendEmailEvent;
@@ -171,6 +173,12 @@ class TestController extends Controller
     public function tt1(){
        $a = DeliveryAppointment::query()->with("cars")->with("details")->get();
        dd($a);
+        $nextTime = DeliveryAppointment::PERIOD[1];
+        $nextTime = explode("-",$nextTime)[1];
+        $timestamp = strtotime(date("Y-m-d")." ".$nextTime.":00:00");
+        $result["refresh"] = ($timestamp-time())*1000;
+        dd($result);
+        return view("store.deliveryAppointment.delivery",["k"=>"15661461456"]);
     }
     public function assignBatch(){
         $batches = collect([

+ 1 - 1
app/Http/Middleware/VerifyCsrfToken.php

@@ -19,6 +19,6 @@ class VerifyCsrfToken extends Middleware
      * @var array
      */
     protected $except = [
-        //
+        'store/deliveryAppointment/delivery',
     ];
 }

+ 63 - 1
app/Services/DeliveryAppointmentService.php

@@ -9,6 +9,7 @@ use App\Traits\ServiceAppAop;
 use App\DeliveryAppointment;
 use Illuminate\Database\Eloquent\Builder;
 use Illuminate\Support\Facades\Auth;
+use phpDocumentor\Reflection\Types\Integer;
 
 class DeliveryAppointmentService
 {
@@ -51,7 +52,7 @@ class DeliveryAppointmentService
             ($cubicMeter*config("appointment.production_capacity.cubic_meter")));
         $coefficient = config("appointment.production_capacity.coefficient");
         if ($amount && ($need/$amount < $coefficient)){
-            $need *= 1-(($coefficient-($need/$amount))*($rpcc/100));
+            $need *= 1+(($coefficient-($need/$amount))*($rpcc/100));
         }
         return $need;
     }
@@ -97,4 +98,65 @@ class DeliveryAppointmentService
         }
         if ($insert)DeliveryAppointmentDetail::query()->insert($insert);
     }
+
+    /**
+     * 获取一个KEY值用于验证二维码
+     *
+     * @return string
+     */
+    public function getKey()
+    {
+        $y = date("y");
+        $m = date("m");
+        $d = date("d");
+        $k1 = substr(env("APP_KEY"),7,2);
+        $k2 = substr(env("APP_KEY"),10,2);
+        $k3 = substr(env("APP_KEY"),15,2);
+        return md5($k3.$y.$k2.$m.$k1.$d);
+    }
+
+    /**
+     * 验证key值
+     *
+     * @param string $key
+     * @return bool
+     */
+    public function checkKey(string $key):bool
+    {
+        if ($key!=$this->getKey())return false;
+        return true;
+    }
+
+    /**
+     * 获取当前时段
+     *
+     * @param int|null $hour
+     *
+     * @return int|bool
+     */
+    public function getPeriod($hour=null)
+    {
+        if (!$hour)$hour = date("H");
+        foreach (DeliveryAppointment::PERIOD as $key=>$period){
+            $arr = explode("-",$period);
+            if (count($arr)!=2)continue;
+            if ($hour>=$arr[0] && $hour<$arr[1])return $key;
+        }
+        return false;
+    }
+
+    /**
+     * 验证预约单完整性修改状态
+     *
+     * @param integer $id
+     */
+    public function checkFull($id)
+    {
+        /** @var DeliveryAppointment|\stdClass $delivery */
+        $delivery = DeliveryAppointment::query()->withCount(["cars"=>function($query){
+            /** @var Builder $query */
+            $query->whereNull("delivery_time");
+        }])->find($id);
+        if ($delivery->cars_count == 0)$delivery->update(["status"=>2]);
+    }
 }

+ 34 - 0
database/migrations/2021_03_15_150311_change_delivery_appointment_cars_table.php

@@ -0,0 +1,34 @@
+<?php
+
+use Illuminate\Database\Migrations\Migration;
+use Illuminate\Database\Schema\Blueprint;
+use Illuminate\Support\Facades\Schema;
+
+class ChangeDeliveryAppointmentCarsTable extends Migration
+{
+    /**
+     * Run the migrations.
+     *
+     * @return void
+     */
+    public function up()
+    {
+        Schema::table('delivery_appointment_cars', function (Blueprint $table) {
+            $table->dateTime("delivery_time")->nullable()->comment("送达时间");
+            $table->dropColumn("status");
+        });
+    }
+
+    /**
+     * Reverse the migrations.
+     *
+     * @return void
+     */
+    public function down()
+    {
+        Schema::table('delivery_appointment_cars', function (Blueprint $table) {
+            $table->dropColumn("delivery_time");
+            $table->tinyInteger("status")->default(0)->comment("状态");
+        });
+    }
+}

+ 0 - 0
package-lock.json


+ 1 - 0
package.json

@@ -26,6 +26,7 @@
   },
   "dependencies": {
     "bootstrap-select": "^1.13.18",
+    "davidshimjs-qrcodejs": "0.0.2",
     "echarts": "^4.9.0",
     "element-ui": "^2.14.1",
     "jquery.cookie": "^1.4.1",

+ 1 - 0
resources/js/utilities/qrcode.js

@@ -0,0 +1 @@
+window.QRCode = require("davidshimjs-qrcodejs");

+ 146 - 0
resources/views/store/deliveryAppointment/delivery.blade.php

@@ -0,0 +1,146 @@
+<!DOCTYPE html>
+<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
+<head>
+    <meta charset="utf-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1">
+    <link rel="icon" href="{{asset('icon/faviconc.ico')}}" type="image/x-icon"/>
+
+    <title>填写预约码-客户预约</title>
+    <style>
+        html{
+            height: 100%;
+            width: 100%;
+        }
+        body{
+            text-align:center;
+            height: 100%;
+            width: 100%;
+        }
+        .center{
+            margin:0 auto;
+            position: fixed;
+            top: 50%;
+            left: 50%;
+            width:50%;
+            height: 50%;
+            -webkit-transform: translateX(-50%) translateY(-50%);
+        }
+        #msg{
+            width:266px;
+            position: fixed;
+            z-index:999;
+            top: 49%;
+            margin-top:-80px;
+            left:50%;
+            margin-left:-133px;
+            background:#fff;
+            box-shadow:5px 5px 8px #999;
+            font-size:17px;
+            color:red;
+            border:1px solid #f8f8f8;
+            text-align: center;
+            line-height: 2rem;
+            display:inline-block;
+            padding-bottom:20px;
+            border-radius:5px;
+        }
+        #msg_top {
+            background: #f8f8f8;
+            padding: 5px 15px 5px 20px;
+            text-align: left;
+        }
+        #msg_top span{
+            font-size:22px;
+            float:right;
+            cursor:pointer;
+        }
+        #msg_cont{
+            padding:15px 20px 20px;
+            text-align:left;
+        }
+        #msg_clear{
+            background:#8fc31f;
+            float:right;
+        }
+        .msg_btn{
+            display:inline-block;
+            color:#fff;
+            padding:1px 15px;
+            border-radius:2px;
+            margin-right:15px;
+            cursor:pointer;
+        }
+        .label{
+            font-size: 1.2em;
+            font-weight: bold;
+            margin-bottom: 50px;
+        }
+        .btn{
+            width: 50%;
+            height: 40px;
+            margin-top: 50px;
+            color: #fff;
+            background-color: #28a745;
+            border-color: #28a745;
+            border-radius: 5px;
+        }
+        .input{
+            display: block;
+            width: 100%;
+            font-weight: 400;
+            color: #495057;
+            background-color: #fff;
+            background-clip: padding-box;
+            border: 1px solid #1b1e21;
+            transition: border-color .15s ease-in-out,box-shadow .15s ease-in-out;
+            height: calc(1.5em + .5rem + 2px);
+            padding: .25rem .5rem;
+            font-size: .875rem;
+            line-height: 1.5;
+            border-radius: .3rem;
+        }
+    </style>
+</head>
+<body>
+<div class="center">
+    <div>
+        <div class="label">下方填写您的预约码</div>
+        <label><input type="number" class="input" id="appointment_number" oninput="if(value.length>6)value=value.slice(0,6)"></label>
+    </div>
+    <div>
+        <button type="button" class="btn" onclick="submit()"> 确 认 </button>
+    </div>
+</div>
+</body>
+<script type="text/javascript">
+    //重绘弹窗样式
+    function alert(e){
+        let dom = document.createElement('div');
+        dom.innerHTML = '<div id="msg"><div id="msg_top">提示</div><div id="msg_cont">'+e+
+        '</div><div class="msg_close msg_btn" id="msg_clear">确定</div></div>';
+        document.querySelector('body').appendChild(dom);
+        document.getElementById('msg_clear').addEventListener('click', function() {
+            document.getElementById("msg").remove();
+        }, false);
+    }
+    function submit() {
+        let xhr = new XMLHttpRequest();
+        let url = "{{url('store/deliveryAppointment/delivery')}}";
+        let number = document.getElementById("appointment_number").value;
+        if (!number)return;
+        let data = "number="+number+"&k={{$k}}";
+        xhr.open("POST",url,true);
+        xhr.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
+        xhr.onreadystatechange = function() {
+            if (xhr.readyState === 4 && (xhr.status === 200 || xhr.status === 304)) {
+                let res = JSON.parse(xhr.responseText);
+                if (res.status === 406)window.location.href = "{{url('store/deliveryAppointment/errMsg')}}";
+                if (res.status === 417)alert("无效预约码!");
+                if (res.status === 416)alert("当前时间禁止送货!");
+                if (res.status === 200)window.location.href = "{{url('store/deliveryAppointment/successMsg?k=')}}"+res.k;
+            }
+        };
+        xhr.send(data);
+    }
+</script>
+</html>

+ 33 - 0
resources/views/store/deliveryAppointment/deliverySuccess.blade.php

@@ -0,0 +1,33 @@
+<!DOCTYPE html>
+<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
+<head>
+    <meta charset="utf-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1">
+    <link rel="icon" href="{{asset('icon/faviconc.ico')}}" type="image/x-icon"/>
+
+    <title>送货成功-客户预约</title>
+    <link href="{{ mix('css/app.css') }}" rel="stylesheet">
+    <style>
+        .font{
+            margin-top: 15%;
+            font-size: 6em;
+        }
+    </style>
+</head>
+<body>
+    <div class="container-fluid h-100 text-center">
+        <div class="text-success h1 font w-100">
+            <span class="fa fa-check-circle"></span>
+        </div>
+        <span class="h2 font-weight-bold">送货成功</span>
+        <div class="mt-5">
+            @foreach($cars as $car)
+            <div class="w-100 mt-2">
+                <span class="fa fa-circle text-info"></span>&nbsp;&nbsp;
+                待扫&nbsp;&nbsp;{{$car->license_plate_number}}
+            </div>
+            @endforeach
+        </div>
+    </div>
+</body>
+</html>

+ 307 - 1
resources/views/store/deliveryAppointment/exhibition.blade.php

@@ -1 +1,307 @@
-<?php
+<!DOCTYPE html>
+<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
+<head>
+    <meta charset="utf-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1">
+    <link rel="icon" href="{{asset('icon/faviconc.ico')}}" type="image/x-icon"/>
+    <!-- CSRF Token -->
+    <meta name="csrf-token" content="{{ csrf_token() }}">
+
+    <title>入库区终端-客户预约</title>
+    <link href="{{ mix('css/app.css') }}" rel="stylesheet">
+    <style>
+        html{
+            background: white;
+            height: 100%;
+            width: 100%;
+        }
+        .h-20{
+            height: 20%;
+        }
+        .h-40{
+            height: 40%;
+        }
+        .h-5{
+            height: 5%;
+        }
+        .text-line{
+            line-height: 1;
+            font-size: 1.5em;
+        }
+        #msg{
+            width:266px;
+            position: fixed;
+            z-index:999;
+            top: 49%;
+            margin-top:-80px;
+            left:50%;
+            margin-left:-133px;
+            background:#fff;
+            box-shadow:5px 5px 8px #999;
+            font-size:17px;
+            color:#666;
+            border:1px solid #f8f8f8;
+            text-align: center;
+            line-height: 2rem;
+            display:inline-block;
+            padding-bottom:20px;
+            border-radius:5px;
+        }
+        #msg_top {
+            background: #f8f8f8;
+            padding: 5px 15px 5px 20px;
+            text-align: left;
+        }
+        #msg_top span{
+            font-size:22px;
+            float:right;
+            cursor:pointer;
+        }
+        #msg_cont{
+            padding:15px 20px 20px;
+            text-align:left;
+        }
+        #msg_clear{
+            background:#8fc31f;
+            float:right;
+        }
+        #msg_success{
+            background:#2a9055;
+            float:right;
+        }
+        .msg_btn{
+            display:inline-block;
+            color:#fff;
+            padding:1px 15px;
+            border-radius:2px;
+            margin-right:15px;
+            cursor:pointer;
+        }
+    </style>
+</head>
+<body onload="initLoad()" class="h-100">
+    <div class="container-fluid h-100 d-none" id="container">
+        <div class="offset-1 h1 font-weight-bold h-100">
+            <div class="h-5"></div>
+            <div class="w-100 h-40">
+                <div class="row h-20 mt-0" v-for="(data,i) in list" :class="data.is_delivery ? 'text-success' : 'text-primary'" v-if="i<5">
+                    <div class="col-3 text-line">@{{ data.license_plate_number }}</div>
+                    <div class="col-2 text-line">@{{ data.driver_name }}</div>
+                    <div class="col-3 text-line">@{{ data.driver_phone }}</div>
+                    <div class="col-2 text-line">
+                        <span v-if="data.is_delivery">已送达</span>
+                    </div>
+                </div>
+            </div>
+            <div class="row h-40 mt-0">
+                <div class="col-5">
+                    <div class="h-20 mt-0 row" v-for="(data,i) in list" :class="data.is_delivery ? 'text-success' : 'text-primary'" v-if="i>4">
+                        <div class="col-7 text-line">@{{ data.license_plate_number }}</div>
+                        <div class="col-5 text-line">
+                            <span class="ml-3">@{{ data.driver_name }}</span>
+                        </div>
+                    </div>
+                </div>
+                <div class="col-6">
+                    <div class="mt-4" id="code"></div>
+                </div>
+            </div>
+        </div>
+    </div>
+</body>
+<script src="{{ mix('js/app.js') }}"></script>
+<script src="{{ mix('js/utilities/qrcode.js') }}"></script>
+<script type="text/javascript">
+    //初始化询问
+    function initLoad() {
+        alert("是否需要开启全屏?");
+    }
+    //重绘弹窗样式
+    function alert(e){
+        $("body").append('<div id="msg"><div id="msg_top">设置<span class="msg_close">×</span></div><div id="msg_cont">'+e+
+            '</div><div class="msg_close msg_btn" id="msg_clear">取消</div><div class="msg_close msg_btn" id="msg_success" onclick="launchFullScreen()">确定</div></div>');
+        $(".msg_close").click(function (){
+            $("#msg").remove();
+        });
+    }
+    //全屏
+    function launchFullScreen() {
+        let element = window.document.body;
+        if (element.requestFullscreen) {
+            element.requestFullscreen();
+        } else if (element.mozRequestFullScreen) {
+            element.mozRequestFullScreen();
+        } else if (element.webkitRequestFullscreen) {
+            element.webkitRequestFullscreen();
+        } else if (element.msRequestFullscreen) {
+            element.msRequestFullscreen();
+        }
+    }
+    new Vue({
+        el:"#container",
+        data:{
+            list:[],
+            key:"",
+            baseUrl:"{{url('store/deliveryAppointment/delivery?k=')}}",
+            QrCode : null,
+        },
+        mounted(){
+            $("#container").removeClass("d-none");
+            this._initData();
+            this._getKey();
+            this._broadcast();
+            setTimeout(()=>{
+                //刷新密匙
+                this._getKey()
+            },this._getDiffDate());
+            setInterval(()=>{
+                this._createQrCode(this.baseUrl+this.base64());
+            },60000);
+        },
+        methods:{
+            _broadcast(){
+                initEcho();
+                window.Echo.channel('{{config('database.redis.options.prefix')}}delivery').listen('.car',(res)=>{
+                    if (this.list.length>=10) this.list = this.list.splice(0,9);
+                    res = res.delivery;
+                    if (this.list.every((data,i)=>{
+                        if (data.license_plate_number === res.license_plate_number){
+                            this.$set(this.list[i],"is_delivery",true);
+                            return false;
+                        }
+                        return true;
+                    }))this.list.unshift({
+                        "license_plate_number"  : res.license_plate_number,
+                        "driver_name"           : res.driver_name,
+                        "driver_phone"          : res.driver_phone,
+                        "is_delivery"           : true,
+                    });
+                    setTimeout(()=>{
+                        this.list.some((data,i)=>{
+                            if (data.license_plate_number === res.license_plate_number) {
+                                this.$set(this.list[i],"is_delivery",false);
+                                return true;
+                            }
+                        });
+                    },1800000);
+                })
+            },
+            //初始化数据
+            _initData(){
+                let url = "{{url('store/deliveryAppointment/getExhibitionList')}}";
+                window.tempTip.postBasicRequest(url,{},res=>{
+                    if (res.list){
+                        let data = res.list;
+                        data.forEach((item,i)=>{
+                            if (item.diff){
+                                data[i].is_delivery = true;
+                                setTimeout(()=>{
+                                    this.list.some((data,i)=>{
+                                        if (data.license_plate_number === item.license_plate_number) {
+                                            this.$set(this.list[i],"is_delivery",false);
+                                            return true;
+                                        }
+                                    });
+                                },item.diff);
+                            }
+                        });
+                        this.list = data;
+                    }
+                    //判断下次刷新数据的时间
+                    let refreshVal = res.refresh ? res.refresh : this._getDiffDate();
+                    setTimeout(()=>{
+                        this._initData();
+                    },refreshVal);
+                });
+            },
+            //获取密匙
+            _getKey(){
+                let url = "{{url('store/deliveryAppointment/getKey')}}";
+                window.tempTip.postBasicRequest(url,{},res=>{
+                    this.key = res;
+                    this._createQrCode(this.baseUrl+this.base64());
+                });
+            },
+            //生成二维码
+            _createQrCode(text){
+                if (!this.QrCode){
+                    let dom = document.getElementById("code");
+                    let height = dom.parentNode.offsetHeight<dom.parentNode.offsetWidth ? dom.parentNode.offsetHeight : dom.parentNode.offsetWidth;
+                    this.QrCode = new QRCode(dom,{
+                            text: text,
+                            width: height*1.4,
+                            height: height,
+                            colorDark : "#000000",
+                            colorLight : "#ffffff",
+                        }
+                    );
+                }else{
+                    this.QrCode.clear();
+                    this.QrCode.makeCode(text);
+                }
+            },
+            //获取当前时间距离明天0点的时间差  毫秒
+            _getDiffDate(){
+                let now = new Date();
+                let dateTime = now.getTime();
+                let yy = now.getFullYear();
+                let mm = now.getMonth() + 1;
+                let dd = now.getDate();
+                let clock = yy + "-";
+                if(mm < 10) clock += "0";
+                clock += mm + "-";
+                if(dd < 10) clock += "0";
+                clock += dd+" 00:00:00";
+                let timestamp = new Date(clock).getTime()+(24*60*60*1000);
+                return timestamp-dateTime;
+            },
+            //加密
+            base64(){
+                let _keyStr= "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
+                let output = "";
+                let chr1, chr2, chr3, enc1, enc2, enc3, enc4;
+                let i = 0;
+                let str = Math.floor(new Date().getTime()/1000).toString();
+                str = str.slice(str.length-8);
+                let input = this._utf8_encode(this.key+str);
+                while (i < input.length) {
+                    chr1 = input.charCodeAt(i++);
+                    chr2 = input.charCodeAt(i++);
+                    chr3 = input.charCodeAt(i++);
+                    enc1 = chr1 >> 2;
+                    enc2 = ((chr1 & 3) << 4) | (chr2 >> 4);
+                    enc3 = ((chr2 & 15) << 2) | (chr3 >> 6);
+                    enc4 = chr3 & 63;
+                    if (isNaN(chr2)) {
+                        enc3 = enc4 = 64;
+                    } else if (isNaN(chr3)) {
+                        enc4 = 64;
+                    }
+                    output = output +
+                        _keyStr.charAt(enc1) + _keyStr.charAt(enc2) +
+                        _keyStr.charAt(enc3) + _keyStr.charAt(enc4);
+                }
+                return output;
+            },
+            _utf8_encode (string) {
+                string = string.replace(/\r\n/g,"\n");
+                let utftext = "";
+                for (let n = 0; n < string.length; n++) {
+                    let c = string.charCodeAt(n);
+                    if (c < 128) {
+                        utftext += String.fromCharCode(c);
+                    } else if((c > 127) && (c < 2048)) {
+                        utftext += String.fromCharCode((c >> 6) | 192);
+                        utftext += String.fromCharCode((c & 63) | 128);
+                    } else {
+                        utftext += String.fromCharCode((c >> 12) | 224);
+                        utftext += String.fromCharCode(((c >> 6) & 63) | 128);
+                        utftext += String.fromCharCode((c & 63) | 128);
+                    }
+                }
+                return utftext;
+            }
+        },
+    });
+</script>
+</html>

+ 3 - 0
resources/views/store/deliveryAppointment/menu.blade.php

@@ -10,6 +10,9 @@
                 <li class="nav-item">
                     <a target="store/deliveryAppointment/list" class="nav-link" href="{{url('store/deliveryAppointment/list')}}" :class="{active:isActive('list',3)}">预约管理</a>
                 </li> @endcan
+                <li class="nav-item">
+                    <a target="_blank" class="nav-link" href="{{url('store/deliveryAppointment/exhibition')}}" :class="{active:isActive('exhibition',3)}">入库区终端</a>
+                </li>
             </ul>
         </div>
     </div>

+ 1 - 1
resources/views/store/deliveryAppointment/success.blade.php

@@ -29,7 +29,7 @@
                     <span class="badge badge-pill badge-info">{{$car->appointment_number}}</span>
                 </span><br>
                 <span class="mt-1">预约时间:{{$appointment->appointment_date}}&nbsp;&nbsp;{{$appointment->period}}</span>
-                <span class="ml-4 mt-1">司机:{{$appointment->driver_name ?? '未知'}}</span>
+                <span class="ml-4 mt-1">司机:{{$car->driver_name ?? '未知'}}</span>
             </div>
             @endforeach
             <div class="mt-5">

+ 1 - 1
resources/views/waybill/index.blade.php

@@ -124,7 +124,7 @@
                             </table>
                         </div>
                     </td>
-                    <td class="td-warm">@{{waybill.type}} <span class="badge badge-sm bg-warning" v-if="waybill.collect_fee">到付</span></td>
+                    <td class="td-warm">@{{waybill.type}} <span class="badge badge-sm bg-warning" v-if="waybill.collect_fee && waybill.collect_fee>0">到付</span></td>
                     <td class="td-warm">@{{waybill.owner}}</td>
                     <td class="td-warm toptd" :title="waybill.remark? '置顶备注:'+waybill.remark :''">@{{waybill.source_bill}}</td>
                     <td class="td-warm">

+ 10 - 0
routes/web.php

@@ -20,6 +20,7 @@ Route::get('/', function () {
 Route::any('test/{method}', 'TestController@method'); //测试
 
 Auth::routes();
+
 Route::get('/home', 'HomeController@index')->name('home');
 Route::get('/homeTemp', 'HomeController@home');
 
@@ -424,8 +425,17 @@ Route::group(['prefix'=>'store'],function(){
         Route::post('submitAppointment','DeliveryAppointmentController@submitAppointment');
         Route::get('showAppointmentInfo','DeliveryAppointmentController@showAppointmentInfo');
         Route::get('list','DeliveryAppointmentController@list');
+        Route::get('delivery','DeliveryAppointmentController@delivery');
+        Route::get('errMsg','DeliveryAppointmentController@errMsg');
+        Route::get('successMsg','DeliveryAppointmentController@successMsg');
+        Route::post('delivery','DeliveryAppointmentController@checkAppointment');
         Route::post('cancel','DeliveryAppointmentController@cancel');
         Route::any('export','DeliveryAppointmentController@export');
+        Route::post('getExhibitionList','DeliveryAppointmentController@getExhibitionList');
+        Route::post('getKey','DeliveryAppointmentController@getKey');
+        Route::get('exhibition',function (){
+            return view("store.deliveryAppointment.exhibition");
+        });
         Route::group(['prefix'=>'appointment'],function(){
             Route::post('import','DeliveryAppointmentController@import');
         });

+ 1 - 0
webpack.mix.js

@@ -24,6 +24,7 @@ mix.copy('resources/js/queryForm/queryForm.js','public/js/queryForm/queryForm.js
 mix.copy('resources/js/queryForm/export.js','public/js/queryForm/export.js');
 mix.js('resources/js/queryForm/header.js','public/js/queryForm/header.js');
 mix.js('resources/js/utilities/barcode.js','public/js/utilities/barcode.js');
+mix.js('resources/js/utilities/qrcode.js','public/js/utilities/qrcode.js');
 
 mix.copy('resources/sound/','public/sound');
 mix.js('resources/js/elementUi.js','public/js/element-ui.js')