245 lines
		
	
	
		
			12 KiB
		
	
	
	
		
			PHP
		
	
	
	
			
		
		
	
	
			245 lines
		
	
	
		
			12 KiB
		
	
	
	
		
			PHP
		
	
	
	
<?php include ("./link/session.php") ?>
 | 
						|
<!doctype html>
 | 
						|
<html lang="uft-8">
 | 
						|
<head>
 | 
						|
    <?php include ("./public/head.inc") ?>
 | 
						|
    <link href="assets/plugins/nouislider/css/nouislider.min.css" rel="stylesheet">
 | 
						|
</head>
 | 
						|
<body>
 | 
						|
<?php include ("./public/menu.inc") ?>
 | 
						|
    <div data-simplebar>
 | 
						|
        <main class="page-content insta360" id="app" v-cloak>
 | 
						|
            <div class="row">
 | 
						|
                <div class="col-lg-6 lp-equal-height-container">
 | 
						|
                    <div class="card lp-equal-height-item mb-0">
 | 
						|
                        <div class="card-header bg-transparent">
 | 
						|
                            <div class="p-2 mb-0 d-flex align-items-end">
 | 
						|
                                <cn>Insta360预览</cn>
 | 
						|
                                <en>Insta360 Preview</en>
 | 
						|
                            </div>
 | 
						|
                        </div>
 | 
						|
                        <div class="card-body lp-align-center">
 | 
						|
                            <div class="row">
 | 
						|
                                <div class="col-lg-12 mt-2">
 | 
						|
                                    <img :src="chnImgUrl" class="card-img" alt="...">
 | 
						|
                                </div>
 | 
						|
                            </div>
 | 
						|
                        </div>
 | 
						|
                    </div>
 | 
						|
                </div>
 | 
						|
                <div class="col-lg-6 lp-equal-height-container">
 | 
						|
                    <div class="lp-equal-height-item mb-0">
 | 
						|
                        <div class="d-flex flex-column h-100">
 | 
						|
                            <div class="flex-fill pb-2">
 | 
						|
                                <div class="card h-100">
 | 
						|
                                    <div class="card-body d-flex align-items-center">
 | 
						|
                                        <ptz-direct :arrow-class="'arrow-direct'" :home-class="'home-direct'" :gop="5" :sticks="['up','down','left','right','home']"
 | 
						|
                                                    :zoom-val="ptz.z" :zoom-min="100" :zoom-max="400"
 | 
						|
                                                    @ptz-move="handlePtzMove" @zoom-change="handleZoomChange" @call-preset="handleCallPreset" @set-preset="handleSetPreset"></ptz-direct>
 | 
						|
                                    </div>
 | 
						|
                                </div>
 | 
						|
                            </div>
 | 
						|
                            <div class="flex-fill">
 | 
						|
                                <div class="card h-100">
 | 
						|
                                    <div class="card-body">
 | 
						|
                                        <div class="row h-100 d-flex align-items-center">
 | 
						|
                                            <div class="col-lg-8 offset-lg-2">
 | 
						|
                                                <div class="row">
 | 
						|
                                                    <div class="col-lg-4 text-center">
 | 
						|
                                                        <cn>自动跟踪</cn>
 | 
						|
                                                        <en>auto track</en>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 text-center">
 | 
						|
                                                        <cn>白板跟踪</cn>
 | 
						|
                                                        <en>whiteboard</en>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 text-center">
 | 
						|
                                                        <cn>俯拍模式</cn>
 | 
						|
                                                        <en>Overhead</en>
 | 
						|
                                                    </div>
 | 
						|
                                                </div>
 | 
						|
                                                <hr>
 | 
						|
                                                <div class="row">
 | 
						|
                                                    <div class="col-lg-4 lp-align-center">
 | 
						|
                                                        <bs-switch v-model="options.tracking" @switch-change="onUsbCamOptionChange"></bs-switch>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 lp-align-center">
 | 
						|
                                                        <bs-switch v-model="options.whiteboard" @switch-change="onUsbCamOptionChange"></bs-switch>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 lp-align-center">
 | 
						|
                                                        <bs-switch v-model="options.overhead" @switch-change="onUsbCamOptionChange"></bs-switch>
 | 
						|
                                                    </div>
 | 
						|
                                                </div>
 | 
						|
                                            </div>
 | 
						|
                                            <div class="col-lg-8 offset-lg-2 mt-2">
 | 
						|
                                                <div class="row">
 | 
						|
                                                    <div class="col-lg-4 text-center">
 | 
						|
                                                        <cn>桌面模式</cn>
 | 
						|
                                                        <en>desktop mode</en>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 text-center">
 | 
						|
                                                        HDR
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 text-center">
 | 
						|
                                                        <cn>镜像</cn>
 | 
						|
                                                        <en>mirror</en>
 | 
						|
                                                    </div>
 | 
						|
                                                </div>
 | 
						|
                                                <hr>
 | 
						|
                                                <div class="row">
 | 
						|
                                                    <div class="col-lg-4 lp-align-center">
 | 
						|
                                                        <bs-switch v-model="options.deskview" @switch-change="onUsbCamOptionChange"></bs-switch>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 lp-align-center">
 | 
						|
                                                        <bs-switch v-model="options.hdr" @switch-change="onUsbCamOptionChange"></bs-switch>
 | 
						|
                                                    </div>
 | 
						|
                                                    <div class="col-lg-4 lp-align-center">
 | 
						|
                                                        <bs-switch v-model="options.mirror" @switch-change="onUsbCamOptionChange"></bs-switch>
 | 
						|
                                                    </div>
 | 
						|
                                                </div>
 | 
						|
                                            </div>
 | 
						|
                                        </div>
 | 
						|
                                    </div>
 | 
						|
                                </div>
 | 
						|
                            </div>
 | 
						|
                        </div>
 | 
						|
                    </div>
 | 
						|
                </div>
 | 
						|
            </div>
 | 
						|
        </main>
 | 
						|
    </div>
 | 
						|
<?php include ("./public/foot.inc") ?>
 | 
						|
 | 
						|
<script type="module">
 | 
						|
    import { rpc } from "./assets/js/lp.utils.js";
 | 
						|
    import { useDefaultConf } from "./assets/js/vue.hooks.js";
 | 
						|
    import { ignoreCustomElementPlugin,filterKeywordPlugin,bootstrapSwitchComponent,ptzDirectComponent } from "./assets/js/vue.helper.js"
 | 
						|
    import vue from "./assets/js/vue.build.js";
 | 
						|
 | 
						|
    const {createApp,ref,reactive,watchEffect,onMounted,nextTick} = vue;
 | 
						|
    const app = createApp({
 | 
						|
        components:{
 | 
						|
            "bs-switch" : bootstrapSwitchComponent,
 | 
						|
            "ptz-direct": ptzDirectComponent,
 | 
						|
        },
 | 
						|
        setup(props,context) {
 | 
						|
 | 
						|
            const { defaultConf } = useDefaultConf();
 | 
						|
 | 
						|
            const state = {
 | 
						|
                chnIndex: ref(-1),
 | 
						|
                chnImgUrl: ref("assets/img/nosignal.jpg"),
 | 
						|
                ptz: reactive({ p: 0, t: 0, z: 300 }),
 | 
						|
                options: reactive({tracking: false, whiteboard: false, overhead: false, deskview: false, hdr: false, mirror: false}),
 | 
						|
                stepP: 0,
 | 
						|
                stepT: 0,
 | 
						|
                timerId: 0
 | 
						|
            }
 | 
						|
 | 
						|
            const unwatch = watchEffect(()=>{
 | 
						|
                if(defaultConf.length > 0) {
 | 
						|
                    for(let i=0;i<defaultConf.length;i++) {
 | 
						|
                        if(defaultConf[i].type !== "usb")
 | 
						|
                            continue;
 | 
						|
                        state.chnIndex.value = i;
 | 
						|
                    }
 | 
						|
                    updateChnImage();
 | 
						|
                    unwatch();
 | 
						|
                }
 | 
						|
            })
 | 
						|
 | 
						|
            const updateChnImage = () => {
 | 
						|
                if(defaultConf[state.chnIndex.value].enable)
 | 
						|
                    state.chnImgUrl.value = "snap/snap" + state.chnIndex.value + ".jpg?rnd=" + Math.random();
 | 
						|
                else
 | 
						|
                    state.chnImgUrl.value = "assets/img/nosignal.jpg";
 | 
						|
 | 
						|
                setTimeout(() => { rpc( "enc.snap" ) },200)
 | 
						|
                setTimeout(updateChnImage,500);
 | 
						|
            }
 | 
						|
 | 
						|
            const handleUsbCamState = () => {
 | 
						|
                Promise.all([rpc("usb.ptz_get"), rpc("usb.insta360_get")]).then(([data1, data2]) => {
 | 
						|
                    if(Object.keys(data1).length > 0)
 | 
						|
                        Object.assign(state.ptz,data1);
 | 
						|
                    if(Object.keys(data2).length > 0)
 | 
						|
                        Object.assign(state.options,data2);
 | 
						|
                    setTimeout(handleUsbCamState,500);
 | 
						|
                });
 | 
						|
            }
 | 
						|
 | 
						|
            const updatePtz = () => {
 | 
						|
                state.ptz.p += state.stepP*3600;
 | 
						|
                state.ptz.t += state.stepT*3600;
 | 
						|
                rpc("usb.ptz_set", [state.ptz.p,state.ptz.t,state.ptz.p]);
 | 
						|
            }
 | 
						|
 | 
						|
            const ptzMoveStart = () => {
 | 
						|
                if(state.timerId === 0)
 | 
						|
                    state.timerId=setInterval(updatePtz,100);
 | 
						|
            }
 | 
						|
 | 
						|
            const ptzMoveStop = () => {
 | 
						|
                if(state.timerId !== 0) {
 | 
						|
                    clearInterval(state.timerId);
 | 
						|
                    state.timerId = 0;
 | 
						|
                }
 | 
						|
                state.stepP = 0;
 | 
						|
                state.stepT = 0;
 | 
						|
            }
 | 
						|
 | 
						|
            const handlePtzMove = type => {
 | 
						|
                if(type === "up") {
 | 
						|
                    ptzMoveStart();
 | 
						|
                    state.stepT = 1;
 | 
						|
                }
 | 
						|
                if(type === "right") {
 | 
						|
                    ptzMoveStart();
 | 
						|
                    state.stepP = 1;
 | 
						|
                }
 | 
						|
                if(type === "down") {
 | 
						|
                    ptzMoveStart();
 | 
						|
                    state.stepT = -1;
 | 
						|
                }
 | 
						|
                if(type === "left") {
 | 
						|
                    ptzMoveStart();
 | 
						|
                    state.stepP = -1;
 | 
						|
                }
 | 
						|
                if(type === "home") {
 | 
						|
                    ptzMoveStop();
 | 
						|
                    state.ptz.p = 0;
 | 
						|
                    state.ptz.t = 0;
 | 
						|
                    rpc("usb.ptz_set",[state.ptz.p,state.ptz.t,state.ptz.p]);
 | 
						|
                }
 | 
						|
                if(type === "move-stop")
 | 
						|
                    ptzMoveStop();
 | 
						|
            }
 | 
						|
 | 
						|
            const handleZoomChange = zoomVal => {
 | 
						|
                state.ptz.z = zoomVal;
 | 
						|
                rpc("usb.ptz_set",[state.ptz.p,state.ptz.t,state.ptz.p]);
 | 
						|
            }
 | 
						|
 | 
						|
            const handleCallPreset = presetVal => {
 | 
						|
                rpc("usb.preset_call", [presetVal]);
 | 
						|
            }
 | 
						|
 | 
						|
            const handleSetPreset = presetVal => {
 | 
						|
                rpc("usb.preset_set", [presetVal, state.ptz.p,state.ptz.t,state.ptz.p]);
 | 
						|
            }
 | 
						|
 | 
						|
            const onUsbCamOptionChange = () => {
 | 
						|
                rpc("usb.insta360_set", [state.options]);
 | 
						|
            }
 | 
						|
 | 
						|
            onMounted(handleUsbCamState);
 | 
						|
            
 | 
						|
            return {...state, handlePtzMove,handleZoomChange,handleCallPreset,handleSetPreset,onUsbCamOptionChange}
 | 
						|
        }
 | 
						|
    });
 | 
						|
    app.use(ignoreCustomElementPlugin);
 | 
						|
    app.use(filterKeywordPlugin);
 | 
						|
    app.mount('#app');
 | 
						|
</script>
 | 
						|
</body>
 | 
						|
</html>
 |