├── .babelrc ├── .gitignore ├── README.md ├── build └── index.js ├── dist ├── vue-krpano.common.js └── vue-krpano.esm.js ├── package.json └── src ├── core.js ├── features ├── freezeVertical.js └── lazyLoad.js ├── index.js └── krpanoProps.js /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | [ 4 | "es2015", 5 | { 6 | "modules": false 7 | } 8 | ], 9 | "stage-3" 10 | ], 11 | "plugins": [ 12 | "external-helpers" 13 | ], 14 | "compact": "true" 15 | } -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | 6 | # Runtime data 7 | pids 8 | *.pid 9 | *.seed 10 | 11 | # Directory for instrumented libs generated by jscoverage/JSCover 12 | lib-cov 13 | 14 | # Coverage directory used by tools like istanbul 15 | coverage 16 | 17 | # nyc test coverage 18 | .nyc_output 19 | 20 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) 21 | .grunt 22 | 23 | # node-waf configuration 24 | .lock-wscript 25 | 26 | # Compiled binary addons (http://nodejs.org/api/addons.html) 27 | build/Release 28 | 29 | # Dependency directories 30 | node_modules 31 | jspm_packages 32 | 33 | # Optional npm cache directory 34 | .npm 35 | 36 | # Optional REPL history 37 | .node_repl_history 38 | 39 | .idea -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ![Somewhats](http://is2.mzstatic.com/image/thumb/Purple127/v4/36/ec/67/36ec677d-1556-8811-9b02-3b3931657f01/source/175x175bb.jpg) 2 | 3 | # vue-krpano 4 | 5 | A Vue component for [krpano](http://www.krpano.com) player. 6 | 7 | ## Demo 8 | 9 | [https://www.somewhats.cn/pois/10045](https://www.somewhats.cn/pois/10045) 10 | 11 | [https://itunes.apple.com/cn/app/%E5%A3%B9%E4%BA%8C/id1190188895?l=en&mt=8](https://itunes.apple.com/cn/app/%E5%A3%B9%E4%BA%8C/id1190188895?l=en&mt=8) 12 | 13 | ## Installation 14 | 15 | ``` 16 | npm install vue-krpano --save 17 | ``` 18 | 19 | ## Dependency 20 | 21 | * [vuejs@2.0](http://vuejs.org) 22 | * A Krpano player globally referenced by ` 108 | 111 | ``` 112 | 113 | In krpano scripts, you can access the callback object via [krpano](https://krpano.com/docu/actions/#jscall 114 | ) instance. 115 | 116 | ```xml 117 | 118 | 119 | jscall(calc('krpano.hooks.sceneChanged("' + scene[get(xml.scene)].name + '")')); 120 | 121 | ``` 122 | 123 | ## About 124 | 125 | For any question, please feel free to write email to chshapple@gmail.com 126 | 127 | -------------------------------------------------------------------------------- /build/index.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 03/03/2017. 3 | */ 4 | "use strict"; 5 | 6 | const fs = require("fs"); 7 | const path = require("path"); 8 | const rollup = require("rollup"); 9 | const babel = require("rollup-plugin-babel"); 10 | 11 | const resolve = _path => path.resolve(__dirname, "../", _path); 12 | 13 | if (!fs.existsSync(resolve("dist"))) { 14 | fs.mkdirSync(resolve("dist")); 15 | } 16 | 17 | build([ 18 | { 19 | dest: resolve('dist/vue-krpano.common.js'), 20 | format: 'cjs' 21 | }, 22 | { 23 | dest: resolve('dist/vue-krpano.esm.js'), 24 | format: 'es' 25 | } 26 | ].map(genConfig)); 27 | 28 | function build(builds) { 29 | let built = 0; 30 | const total = builds.length; 31 | const next = () => { 32 | buildEntry(builds[built]).then(() => { 33 | built++; 34 | if (built < total) { 35 | next() 36 | } 37 | }).catch() 38 | }; 39 | 40 | next() 41 | } 42 | 43 | function genConfig(opts) { 44 | return { 45 | entry: resolve('src/index.js'), 46 | dest: opts.dest, 47 | format: opts.format, 48 | moduleName: 'VueKrpano', 49 | plugins: [ 50 | babel({}) 51 | ] 52 | }; 53 | } 54 | 55 | function buildEntry(config) { 56 | return rollup.rollup(config).then(bundle => { 57 | console.log(config.dest); 58 | return bundle.write(config); 59 | }); 60 | } -------------------------------------------------------------------------------- /dist/vue-krpano.common.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | /** 4 | * Created by chenshu on 02/03/2017. 5 | */var krpanoProps = {bgcolor:{type:String},wmode:{type:String,default:"opaque"},vars:{type:Object},initvars:{type:Object},basepath:{type:String},mwheel:{type:Boolean,default:false},focus:{type:Boolean,default:true},consolelog:{type:Boolean,default:false},mobilescale:{type:Number,default:0.5},fakedevice:{type:String},passQueryParameters:{type:Boolean,default:false},webglsettings:{type:Object}}; 6 | 7 | var _extends = Object.assign || function (target) { 8 | for (var i = 1; i < arguments.length; i++) { 9 | var source = arguments[i]; 10 | 11 | for (var key in source) { 12 | if (Object.prototype.hasOwnProperty.call(source, key)) { 13 | target[key] = source[key]; 14 | } 15 | } 16 | } 17 | 18 | return target; 19 | }; 20 | 21 | /** 22 | * Created by chenshu on 02/03/2017. 23 | */var config={props:_extends({xml:{type:String,required:true},scene:{type:String},hooks:{type:Object},debug:{type:Boolean,default:false}},krpanoProps),data:function data(){return{createLock:false,krpanoObjId:"krpano_"+Math.floor(Math.random()*(100000-100+1)+100)};},methods:{createPano:function createPano(){var _window=window,embedpano=_window.embedpano,removepano=_window.removepano;if(!(embedpano&&removepano)){throw new Error("krpano player is required");}if(!this.createLock&&!this.krpanoObj){this.createLock=true;var vm=this;this.$el.id=this.krpanoObjId+"_container";embedpano({id:this.krpanoObjId,target:this.$el.id,xml:this.xml,bgcolor:this.bgcolor,wmode:this.wmode,vars:this.vars,initvars:this.initvars,basepath:this.basepath,mwheel:this.mwheel,focus:this.focus,consolelog:this.consolelog,mobilescale:this.mobilescale,fakedevice:this.fakedevice,passQueryParameters:this.passQueryParameters,webglsettings:this.webglsettings,onready:function onready(krpanoObj){vm.krpanoObj=krpanoObj;vm.krpanoObj.hooks=vm.hooks;vm.log("pano created");vm.$emit("panoCreated",vm.krpanoObj);vm.createLock=false;},onerror:function onerror(msg){vm.$emit("panoError",msg);vm.createLock=false;}});}},removePano:function removePano(){var _window2=window,removepano=_window2.removepano;if(this.krpanoObj){removepano(this.krpanoObj.id);this.log("pano removed");delete this.krpanoObj;}},loadScene:function loadScene(){var scene=this.scene;if(this.krpanoObj){if(scene){var str="if(scene["+scene+"]===null,\n loadscene(get(scene[0].name),null,MERGE,BLEND(0.5)),\n loadscene("+scene+",null,MERGE,BLEND(0.5)))";this.krpanoObj.call(str);this.log("scene changed: "+scene);this.$emit("sceneChanged",scene);}else{this.krpanoObj.call("loadscene(get(scene[0].name),null,MERGE,BLEND(0.5))");}}},log:function log(content){if(this.debug){if(this.krpanoObj){content="["+this.krpanoObj.id+"] "+content;}console.debug(content);}}},watch:{xml:function xml(newXml){if(this.krpanoObj&&newXml){this.krpanoObj.call("loadpano("+newXml+",null,IGNOREKEEP)");this.$emit("xmlChanged",newXml);this.log("xml changed: "+newXml);}},scene:function scene(){this.loadScene();}},created:function created(){this.$on(["panoCreated","xmlChanged"],this.loadScene);},beforeDestroy:function beforeDestroy(){this.removePano();}}; 24 | 25 | /** 26 | * Created by chenshu on 02/03/2017. 27 | */var config$1={props:{lazyLoad:{type:Boolean,default:true}},mounted:function mounted(){if(this.lazyLoad){this.createLock=true;this.scrollListener();window.addEventListener("scroll",this.scrollListener);}else{this.createPano();}},methods:{scrollListener:function scrollListener(){var rect=this.$el.getBoundingClientRect();if(-rect.top>rect.height||rect.top>window.innerHeight){//屏幕之外 28 | if(this.krpanoObj){this.krpanoObj.call("if(autorotate.enabled,autorotate.pause())");this.log("out of screen: autorotate paused");}}else{//屏幕之内 29 | if(!this.krpanoObj){this.createLock=false;//lazy load 30 | this.createPano();}else{this.krpanoObj.call("if(autorotate.enabled,autorotate.resume())");this.log("in screen: autorotate resumed");}}}}}; 31 | 32 | /** 33 | * Created by chenshu on 03/03/2017. 34 | */var config$2={props:{freezeVertical:{type:Boolean,default:false}},data:function data(){return{eventDelegate:undefined};},methods:{},watch:{freezeVertical:function freezeVertical(val){if(this.eventDelegate){if(val){this.eventDelegate.style.display="block";var hlookat=this.krpanoObj.get("view.hlookat");this.krpanoObj.call("lookat("+hlookat+",0)");}else{this.eventDelegate.style.display="none";}}}},created:function created(){var _this=this;if(TouchEvent){this.$on("panoCreated",function(krpano){var origin=krpano.firstChild;var eventDelegate=document.createElement("DIV");eventDelegate.className="event-delegate";Object.assign(eventDelegate.style,{display:_this.freezeVertical?"block":"none",width:"100%",height:"100%",position:"absolute","user-select":"none","z-index":1});krpano.appendChild(eventDelegate);_this.eventDelegate=eventDelegate;var originTouch=void 0;eventDelegate.addEventListener("touchstart",function(e){originTouch=e;Object.defineProperty(e,"cancelable",{value:true});var event=new TouchEvent("touchstart",e);return origin.dispatchEvent(event);});eventDelegate.addEventListener("touchend",function(e){Object.defineProperty(e,"cancelable",{value:true});var event=new TouchEvent("touchend",e);return origin.dispatchEvent(event);});eventDelegate.addEventListener("touchmove",function(e){var currentTouch=e.changedTouches[0];var deltaX=originTouch.clientX-currentTouch.clientX;var hlookat=krpano.get("view.hlookat")+deltaX;var vlookat=krpano.get("view.vlookat");krpano.call("lookat("+hlookat+","+vlookat+")");originTouch=currentTouch;return true;});eventDelegate.addEventListener("mousedown",function(e){Object.defineProperty(e,"cancelable",{value:true});return origin.dispatchEvent(new MouseEvent("mousedown",e));});eventDelegate.addEventListener("mousewheel",function(e){Object.defineProperty(e,"cancelable",{value:true});return origin.dispatchEvent(new MouseEvent("mousewheel",e));});});}}}; 35 | 36 | /** 37 | * Created by chenshu on 02/03/2017. 38 | */var component={name:"Krpano",mixins:[config,config$1,config$2],template:"
",mounted:function mounted(){this.createPano();}};component.install=function(Vue){Vue.component(component.name,component);}; 39 | 40 | module.exports = component; 41 | -------------------------------------------------------------------------------- /dist/vue-krpano.esm.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 02/03/2017. 3 | */var krpanoProps = {bgcolor:{type:String},wmode:{type:String,default:"opaque"},vars:{type:Object},initvars:{type:Object},basepath:{type:String},mwheel:{type:Boolean,default:false},focus:{type:Boolean,default:true},consolelog:{type:Boolean,default:false},mobilescale:{type:Number,default:0.5},fakedevice:{type:String},passQueryParameters:{type:Boolean,default:false},webglsettings:{type:Object}}; 4 | 5 | var _extends = Object.assign || function (target) { 6 | for (var i = 1; i < arguments.length; i++) { 7 | var source = arguments[i]; 8 | 9 | for (var key in source) { 10 | if (Object.prototype.hasOwnProperty.call(source, key)) { 11 | target[key] = source[key]; 12 | } 13 | } 14 | } 15 | 16 | return target; 17 | }; 18 | 19 | /** 20 | * Created by chenshu on 02/03/2017. 21 | */var config={props:_extends({xml:{type:String,required:true},scene:{type:String},hooks:{type:Object},debug:{type:Boolean,default:false}},krpanoProps),data:function data(){return{createLock:false,krpanoObjId:"krpano_"+Math.floor(Math.random()*(100000-100+1)+100)};},methods:{createPano:function createPano(){var _window=window,embedpano=_window.embedpano,removepano=_window.removepano;if(!(embedpano&&removepano)){throw new Error("krpano player is required");}if(!this.createLock&&!this.krpanoObj){this.createLock=true;var vm=this;this.$el.id=this.krpanoObjId+"_container";embedpano({id:this.krpanoObjId,target:this.$el.id,xml:this.xml,bgcolor:this.bgcolor,wmode:this.wmode,vars:this.vars,initvars:this.initvars,basepath:this.basepath,mwheel:this.mwheel,focus:this.focus,consolelog:this.consolelog,mobilescale:this.mobilescale,fakedevice:this.fakedevice,passQueryParameters:this.passQueryParameters,webglsettings:this.webglsettings,onready:function onready(krpanoObj){vm.krpanoObj=krpanoObj;vm.krpanoObj.hooks=vm.hooks;vm.log("pano created");vm.$emit("panoCreated",vm.krpanoObj);vm.createLock=false;},onerror:function onerror(msg){vm.$emit("panoError",msg);vm.createLock=false;}});}},removePano:function removePano(){var _window2=window,removepano=_window2.removepano;if(this.krpanoObj){removepano(this.krpanoObj.id);this.log("pano removed");delete this.krpanoObj;}},loadScene:function loadScene(){var scene=this.scene;if(this.krpanoObj){if(scene){var str="if(scene["+scene+"]===null,\n loadscene(get(scene[0].name),null,MERGE,BLEND(0.5)),\n loadscene("+scene+",null,MERGE,BLEND(0.5)))";this.krpanoObj.call(str);this.log("scene changed: "+scene);this.$emit("sceneChanged",scene);}else{this.krpanoObj.call("loadscene(get(scene[0].name),null,MERGE,BLEND(0.5))");}}},log:function log(content){if(this.debug){if(this.krpanoObj){content="["+this.krpanoObj.id+"] "+content;}console.debug(content);}}},watch:{xml:function xml(newXml){if(this.krpanoObj&&newXml){this.krpanoObj.call("loadpano("+newXml+",null,IGNOREKEEP)");this.$emit("xmlChanged",newXml);this.log("xml changed: "+newXml);}},scene:function scene(){this.loadScene();}},created:function created(){this.$on(["panoCreated","xmlChanged"],this.loadScene);},beforeDestroy:function beforeDestroy(){this.removePano();}}; 22 | 23 | /** 24 | * Created by chenshu on 02/03/2017. 25 | */var config$1={props:{lazyLoad:{type:Boolean,default:true}},mounted:function mounted(){if(this.lazyLoad){this.createLock=true;this.scrollListener();window.addEventListener("scroll",this.scrollListener);}else{this.createPano();}},methods:{scrollListener:function scrollListener(){var rect=this.$el.getBoundingClientRect();if(-rect.top>rect.height||rect.top>window.innerHeight){//屏幕之外 26 | if(this.krpanoObj){this.krpanoObj.call("if(autorotate.enabled,autorotate.pause())");this.log("out of screen: autorotate paused");}}else{//屏幕之内 27 | if(!this.krpanoObj){this.createLock=false;//lazy load 28 | this.createPano();}else{this.krpanoObj.call("if(autorotate.enabled,autorotate.resume())");this.log("in screen: autorotate resumed");}}}}}; 29 | 30 | /** 31 | * Created by chenshu on 03/03/2017. 32 | */var config$2={props:{freezeVertical:{type:Boolean,default:false}},data:function data(){return{eventDelegate:undefined};},methods:{},watch:{freezeVertical:function freezeVertical(val){if(this.eventDelegate){if(val){this.eventDelegate.style.display="block";var hlookat=this.krpanoObj.get("view.hlookat");this.krpanoObj.call("lookat("+hlookat+",0)");}else{this.eventDelegate.style.display="none";}}}},created:function created(){var _this=this;if(TouchEvent){this.$on("panoCreated",function(krpano){var origin=krpano.firstChild;var eventDelegate=document.createElement("DIV");eventDelegate.className="event-delegate";Object.assign(eventDelegate.style,{display:_this.freezeVertical?"block":"none",width:"100%",height:"100%",position:"absolute","user-select":"none","z-index":1});krpano.appendChild(eventDelegate);_this.eventDelegate=eventDelegate;var originTouch=void 0;eventDelegate.addEventListener("touchstart",function(e){originTouch=e;Object.defineProperty(e,"cancelable",{value:true});var event=new TouchEvent("touchstart",e);return origin.dispatchEvent(event);});eventDelegate.addEventListener("touchend",function(e){Object.defineProperty(e,"cancelable",{value:true});var event=new TouchEvent("touchend",e);return origin.dispatchEvent(event);});eventDelegate.addEventListener("touchmove",function(e){var currentTouch=e.changedTouches[0];var deltaX=originTouch.clientX-currentTouch.clientX;var hlookat=krpano.get("view.hlookat")+deltaX;var vlookat=krpano.get("view.vlookat");krpano.call("lookat("+hlookat+","+vlookat+")");originTouch=currentTouch;return true;});eventDelegate.addEventListener("mousedown",function(e){Object.defineProperty(e,"cancelable",{value:true});return origin.dispatchEvent(new MouseEvent("mousedown",e));});eventDelegate.addEventListener("mousewheel",function(e){Object.defineProperty(e,"cancelable",{value:true});return origin.dispatchEvent(new MouseEvent("mousewheel",e));});});}}}; 33 | 34 | /** 35 | * Created by chenshu on 02/03/2017. 36 | */var component={name:"Krpano",mixins:[config,config$1,config$2],template:"
",mounted:function mounted(){this.createPano();}};component.install=function(Vue){Vue.component(component.name,component);}; 37 | 38 | export default component; 39 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vue-krpano", 3 | "version": "1.5.3", 4 | "description": "", 5 | "main": "dist/vue-krpano.common.js", 6 | "scripts": { 7 | "build": "node build/index.js" 8 | }, 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/chshapple/vue-krpano.git" 12 | }, 13 | "author": "chshapple", 14 | "license": "ISC", 15 | "bugs": { 16 | "url": "https://github.com/chshapple/vue-krpano/issues" 17 | }, 18 | "homepage": "https://github.com/chshapple/vue-krpano#readme", 19 | "devDependencies": { 20 | "babel-cli": "^6.22.2", 21 | "babel-plugin-external-helpers": "^6.22.0", 22 | "babel-preset-es2015": "^6.22.0", 23 | "babel-preset-stage-3": "^6.22.0", 24 | "rollup": "^0.41.4", 25 | "rollup-plugin-babel": "^2.7.1" 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /src/core.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 02/03/2017. 3 | */ 4 | "use strict"; 5 | 6 | import krpanoProps from "./krpanoProps"; 7 | 8 | let config = { 9 | props: { 10 | xml: { 11 | type: String, required: true 12 | }, 13 | scene: { 14 | type: String 15 | }, 16 | hooks: { 17 | type: Object 18 | }, 19 | debug: { 20 | type: Boolean, default: false 21 | }, 22 | ...krpanoProps 23 | }, 24 | data() { 25 | return { 26 | createLock: false, 27 | krpanoObjId: "krpano_" + Math.floor(Math.random() * (100000 - 100 + 1) + 100) 28 | }; 29 | }, 30 | methods: { 31 | createPano() { 32 | const {embedpano, removepano} = window; 33 | 34 | if (!(embedpano && removepano)) { 35 | throw new Error("krpano player is required"); 36 | } 37 | 38 | if (!this.createLock && !this.krpanoObj) { 39 | this.createLock = true; 40 | const vm = this; 41 | this.$el.id = this.krpanoObjId + "_container"; 42 | 43 | embedpano({ 44 | id: this.krpanoObjId, 45 | target: this.$el.id, 46 | xml: this.xml, 47 | bgcolor: this.bgcolor, 48 | wmode: this.wmode, 49 | vars: this.vars, 50 | initvars: this.initvars, 51 | basepath: this.basepath, 52 | mwheel: this.mwheel, 53 | focus: this.focus, 54 | consolelog: this.consolelog, 55 | mobilescale: this.mobilescale, 56 | fakedevice: this.fakedevice, 57 | passQueryParameters: this.passQueryParameters, 58 | webglsettings: this.webglsettings, 59 | onready(krpanoObj) { 60 | vm.krpanoObj = krpanoObj; 61 | vm.krpanoObj.hooks = vm.hooks; 62 | vm.log("pano created"); 63 | vm.$emit("panoCreated", vm.krpanoObj); 64 | vm.createLock = false; 65 | }, 66 | onerror(msg) { 67 | vm.$emit("panoError", msg); 68 | vm.createLock = false; 69 | } 70 | }); 71 | } 72 | }, 73 | removePano() { 74 | const {removepano} = window; 75 | 76 | if (this.krpanoObj) { 77 | removepano(this.krpanoObj.id); 78 | this.log("pano removed"); 79 | delete this.krpanoObj; 80 | } 81 | }, 82 | loadScene() { 83 | let scene = this.scene; 84 | if (this.krpanoObj) { 85 | if (scene) { 86 | let str = `if(scene[${scene}]===null, 87 | loadscene(get(scene[0].name),null,MERGE,BLEND(0.5)), 88 | loadscene(${scene},null,MERGE,BLEND(0.5)))`; 89 | this.krpanoObj.call(str); 90 | this.log("scene changed: " + scene); 91 | this.$emit("sceneChanged", scene); 92 | 93 | } else { 94 | this.krpanoObj.call("loadscene(get(scene[0].name),null,MERGE,BLEND(0.5))"); 95 | } 96 | } 97 | }, 98 | log(content) { 99 | if (this.debug) { 100 | if (this.krpanoObj) { 101 | content = "[" + this.krpanoObj.id + "] " + content; 102 | } 103 | console.debug(content); 104 | } 105 | } 106 | }, 107 | watch: { 108 | xml(newXml) { 109 | if (this.krpanoObj && newXml) { 110 | this.krpanoObj.call(`loadpano(${newXml},null,IGNOREKEEP)`); 111 | this.$emit("xmlChanged", newXml); 112 | this.log("xml changed: " + newXml); 113 | } 114 | }, 115 | scene: function () { 116 | this.loadScene(); 117 | } 118 | }, 119 | created() { 120 | this.$on(["panoCreated", "xmlChanged"], this.loadScene); 121 | }, 122 | beforeDestroy() { 123 | this.removePano(); 124 | } 125 | }; 126 | 127 | export default config; -------------------------------------------------------------------------------- /src/features/freezeVertical.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 03/03/2017. 3 | */ 4 | "use strict"; 5 | 6 | let config = { 7 | props: { 8 | freezeVertical: { 9 | type: Boolean, 10 | default: false 11 | } 12 | }, 13 | data(){ 14 | return { 15 | eventDelegate: undefined 16 | } 17 | }, 18 | methods: {}, 19 | watch: { 20 | freezeVertical(val){ 21 | if (this.eventDelegate) { 22 | if (val) { 23 | this.eventDelegate.style.display = "block"; 24 | let hlookat = this.krpanoObj.get("view.hlookat"); 25 | this.krpanoObj.call(`lookat(${hlookat},0)`); 26 | } else { 27 | this.eventDelegate.style.display = "none"; 28 | } 29 | } 30 | } 31 | }, 32 | created(){ 33 | 34 | if (TouchEvent) { 35 | 36 | this.$on("panoCreated", krpano => { 37 | 38 | let origin = krpano.firstChild; 39 | 40 | let eventDelegate = document.createElement("DIV"); 41 | eventDelegate.className = "event-delegate"; 42 | Object.assign(eventDelegate.style, { 43 | display: this.freezeVertical ? "block" : "none", 44 | width: "100%", 45 | height: "100%", 46 | position: "absolute", 47 | "user-select": "none", 48 | "z-index": 1 49 | }); 50 | krpano.appendChild(eventDelegate); 51 | this.eventDelegate = eventDelegate; 52 | 53 | let originTouch; 54 | 55 | eventDelegate.addEventListener("touchstart", function (e) { 56 | originTouch = e; 57 | Object.defineProperty(e, "cancelable", {value: true}); 58 | let event = new TouchEvent("touchstart", e); 59 | return origin.dispatchEvent(event); 60 | }); 61 | 62 | eventDelegate.addEventListener("touchend", function (e) { 63 | Object.defineProperty(e, "cancelable", {value: true}); 64 | let event = new TouchEvent("touchend", e); 65 | return origin.dispatchEvent(event); 66 | }); 67 | 68 | eventDelegate.addEventListener("touchmove", function (e) { 69 | 70 | let currentTouch = e.changedTouches[0]; 71 | let deltaX = originTouch.clientX - currentTouch.clientX; 72 | let hlookat = krpano.get("view.hlookat") + deltaX; 73 | let vlookat = krpano.get("view.vlookat"); 74 | krpano.call(`lookat(${hlookat},${vlookat})`); 75 | 76 | originTouch = currentTouch; 77 | 78 | return true; 79 | }); 80 | 81 | eventDelegate.addEventListener("mousedown", function (e) { 82 | Object.defineProperty(e, "cancelable", {value: true}); 83 | return origin.dispatchEvent(new MouseEvent("mousedown", e)); 84 | }); 85 | 86 | eventDelegate.addEventListener("mousewheel", function (e) { 87 | Object.defineProperty(e, "cancelable", {value: true}); 88 | return origin.dispatchEvent(new MouseEvent("mousewheel", e)); 89 | }); 90 | }); 91 | } 92 | 93 | } 94 | }; 95 | 96 | export default config; -------------------------------------------------------------------------------- /src/features/lazyLoad.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 02/03/2017. 3 | */ 4 | "use strict"; 5 | 6 | let config = { 7 | props: { 8 | lazyLoad: { 9 | type: Boolean, 10 | default: true 11 | } 12 | }, 13 | mounted(){ 14 | if (this.lazyLoad) { 15 | this.createLock = true; 16 | this.scrollListener(); 17 | window.addEventListener("scroll", this.scrollListener); 18 | } else { 19 | this.createPano(); 20 | } 21 | }, 22 | methods: { 23 | scrollListener(){ 24 | 25 | let rect = this.$el.getBoundingClientRect(); 26 | 27 | if (-rect.top > rect.height || rect.top > window.innerHeight) { 28 | //屏幕之外 29 | if (this.krpanoObj) { 30 | this.krpanoObj.call("if(autorotate.enabled,autorotate.pause())"); 31 | this.log("out of screen: autorotate paused"); 32 | } 33 | 34 | } else { 35 | //屏幕之内 36 | if (!this.krpanoObj) { 37 | this.createLock = false; 38 | //lazy load 39 | this.createPano(); 40 | } 41 | else { 42 | this.krpanoObj.call("if(autorotate.enabled,autorotate.resume())"); 43 | this.log("in screen: autorotate resumed"); 44 | } 45 | } 46 | } 47 | } 48 | }; 49 | 50 | export default config; -------------------------------------------------------------------------------- /src/index.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 02/03/2017. 3 | */ 4 | "use strict"; 5 | 6 | import core from "./core"; 7 | import lazyLoad from "./features/lazyLoad"; 8 | import freezeVertical from "./features/freezeVertical"; 9 | 10 | let component = { 11 | 12 | name: "Krpano", 13 | 14 | mixins: [core, lazyLoad, freezeVertical], 15 | 16 | template: "
", 17 | 18 | mounted(){ 19 | this.createPano(); 20 | } 21 | }; 22 | 23 | component.install = function (Vue) { 24 | Vue.component(component.name, component); 25 | }; 26 | 27 | export default component; -------------------------------------------------------------------------------- /src/krpanoProps.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Created by chenshu on 02/03/2017. 3 | */ 4 | 5 | "use strict"; 6 | 7 | export default { 8 | bgcolor: { 9 | type: String 10 | }, 11 | wmode: { 12 | type: String, default: "opaque" 13 | }, 14 | vars: { 15 | type: Object 16 | }, 17 | initvars: { 18 | type: Object 19 | }, 20 | basepath: { 21 | type: String 22 | }, 23 | mwheel: { 24 | type: Boolean, default: false 25 | }, 26 | focus: { 27 | type: Boolean, default: true 28 | }, 29 | consolelog: { 30 | type: Boolean, default: false 31 | }, 32 | mobilescale: { 33 | type: Number, default: 0.5 34 | }, 35 | fakedevice: { 36 | type: String 37 | }, 38 | passQueryParameters: { 39 | type: Boolean, default: false 40 | }, 41 | webglsettings: { 42 | type: Object 43 | } 44 | } --------------------------------------------------------------------------------