فهرست منبع

fix: Merge branch 'dev' of http://face3d.4dage.com:7005/4dkankan/4dkankan_bim into dev

bill 2 سال پیش
والد
کامیت
581ebc443b

+ 3 - 2
public/smart-sviewer.html

@@ -6,9 +6,10 @@
         <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0" />
         <link rel="stylesheet" href="<%= VUE_APP_STATIC_DIR %>/lib/iconfont/iconfont.css" />
         <link rel="stylesheet" href="//at.alicdn.com/t/c/font_3693743_qnz6eozqyvk.css" />
-        <script src="<%= VUE_APP_STATIC_DIR %>/lib/mobile-detect.js"></script>
+        <script src="<%= VUE_APP_STATIC_DIR %>/ext/mobile-detect.js"></script>
+        <script src="<%= VUE_APP_STATIC_DIR %>/ext/base64.min.js"></script>
         <script src="<%= VUE_APP_STATIC_DIR %>/lib/three.js/build/three.min.js"></script>
-        <script src="<%= VUE_APP_STATIC_DIR %>/lib/base64.min.js"></script>
+        
     </head>
     <body>
         <noscript>

+ 3 - 3
public/smart-viewer.html

@@ -4,11 +4,11 @@
         <title></title>
         <meta charset="utf-8" />
         <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0" />
-        <link rel="stylesheet" href="<%= VUE_APP_STATIC_DIR %>/lib/iconfont/iconfont.css" />
+        <link rel="stylesheet" href="<%= VUE_APP_STATIC_DIR %>/ext/iconfont/iconfont.css" />
         <link rel="stylesheet" href="//at.alicdn.com/t/c/font_3693743_qnz6eozqyvk.css" />
-        <script src="<%= VUE_APP_STATIC_DIR %>/lib/mobile-detect.js"></script>
+        <script src="<%= VUE_APP_STATIC_DIR %>/ext/mobile-detect.js"></script>
+        <script src="<%= VUE_APP_STATIC_DIR %>/ext/base64.min.js"></script>
         <script src="<%= VUE_APP_STATIC_DIR %>/lib/three.js/build/three.min.js"></script>
-        <script src="<%= VUE_APP_STATIC_DIR %>/lib/base64.min.js"></script>
     </head>
     <body>
         <noscript>

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 11 - 0
public/static/ext/animate/animate.min.css


تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 1 - 0
public/static/ext/base64.min.js


+ 539 - 0
public/static/ext/iconfont/demo.css

@@ -0,0 +1,539 @@
+/* Logo 字体 */
+@font-face {
+  font-family: "iconfont logo";
+  src: url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834');
+  src: url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834#iefix') format('embedded-opentype'),
+    url('https://at.alicdn.com/t/font_985780_km7mi63cihi.woff?t=1545807318834') format('woff'),
+    url('https://at.alicdn.com/t/font_985780_km7mi63cihi.ttf?t=1545807318834') format('truetype'),
+    url('https://at.alicdn.com/t/font_985780_km7mi63cihi.svg?t=1545807318834#iconfont') format('svg');
+}
+
+.logo {
+  font-family: "iconfont logo";
+  font-size: 160px;
+  font-style: normal;
+  -webkit-font-smoothing: antialiased;
+  -moz-osx-font-smoothing: grayscale;
+}
+
+/* tabs */
+.nav-tabs {
+  position: relative;
+}
+
+.nav-tabs .nav-more {
+  position: absolute;
+  right: 0;
+  bottom: 0;
+  height: 42px;
+  line-height: 42px;
+  color: #666;
+}
+
+#tabs {
+  border-bottom: 1px solid #eee;
+}
+
+#tabs li {
+  cursor: pointer;
+  width: 100px;
+  height: 40px;
+  line-height: 40px;
+  text-align: center;
+  font-size: 16px;
+  border-bottom: 2px solid transparent;
+  position: relative;
+  z-index: 1;
+  margin-bottom: -1px;
+  color: #666;
+}
+
+
+#tabs .active {
+  border-bottom-color: #f00;
+  color: #222;
+}
+
+.tab-container .content {
+  display: none;
+}
+
+/* 页面布局 */
+.main {
+  padding: 30px 100px;
+  width: 960px;
+  margin: 0 auto;
+}
+
+.main .logo {
+  color: #333;
+  text-align: left;
+  margin-bottom: 30px;
+  line-height: 1;
+  height: 110px;
+  margin-top: -50px;
+  overflow: hidden;
+  *zoom: 1;
+}
+
+.main .logo a {
+  font-size: 160px;
+  color: #333;
+}
+
+.helps {
+  margin-top: 40px;
+}
+
+.helps pre {
+  padding: 20px;
+  margin: 10px 0;
+  border: solid 1px #e7e1cd;
+  background-color: #fffdef;
+  overflow: auto;
+}
+
+.icon_lists {
+  width: 100% !important;
+  overflow: hidden;
+  *zoom: 1;
+}
+
+.icon_lists li {
+  width: 100px;
+  margin-bottom: 10px;
+  margin-right: 20px;
+  text-align: center;
+  list-style: none !important;
+  cursor: default;
+}
+
+.icon_lists li .code-name {
+  line-height: 1.2;
+}
+
+.icon_lists .icon {
+  display: block;
+  height: 100px;
+  line-height: 100px;
+  font-size: 42px;
+  margin: 10px auto;
+  color: #333;
+  -webkit-transition: font-size 0.25s linear, width 0.25s linear;
+  -moz-transition: font-size 0.25s linear, width 0.25s linear;
+  transition: font-size 0.25s linear, width 0.25s linear;
+}
+
+.icon_lists .icon:hover {
+  font-size: 100px;
+}
+
+.icon_lists .svg-icon {
+  /* 通过设置 font-size 来改变图标大小 */
+  width: 1em;
+  /* 图标和文字相邻时,垂直对齐 */
+  vertical-align: -0.15em;
+  /* 通过设置 color 来改变 SVG 的颜色/fill */
+  fill: currentColor;
+  /* path 和 stroke 溢出 viewBox 部分在 IE 下会显示
+      normalize.css 中也包含这行 */
+  overflow: hidden;
+}
+
+.icon_lists li .name,
+.icon_lists li .code-name {
+  color: #666;
+}
+
+/* markdown 样式 */
+.markdown {
+  color: #666;
+  font-size: 14px;
+  line-height: 1.8;
+}
+
+.highlight {
+  line-height: 1.5;
+}
+
+.markdown img {
+  vertical-align: middle;
+  max-width: 100%;
+}
+
+.markdown h1 {
+  color: #404040;
+  font-weight: 500;
+  line-height: 40px;
+  margin-bottom: 24px;
+}
+
+.markdown h2,
+.markdown h3,
+.markdown h4,
+.markdown h5,
+.markdown h6 {
+  color: #404040;
+  margin: 1.6em 0 0.6em 0;
+  font-weight: 500;
+  clear: both;
+}
+
+.markdown h1 {
+  font-size: 28px;
+}
+
+.markdown h2 {
+  font-size: 22px;
+}
+
+.markdown h3 {
+  font-size: 16px;
+}
+
+.markdown h4 {
+  font-size: 14px;
+}
+
+.markdown h5 {
+  font-size: 12px;
+}
+
+.markdown h6 {
+  font-size: 12px;
+}
+
+.markdown hr {
+  height: 1px;
+  border: 0;
+  background: #e9e9e9;
+  margin: 16px 0;
+  clear: both;
+}
+
+.markdown p {
+  margin: 1em 0;
+}
+
+.markdown>p,
+.markdown>blockquote,
+.markdown>.highlight,
+.markdown>ol,
+.markdown>ul {
+  width: 80%;
+}
+
+.markdown ul>li {
+  list-style: circle;
+}
+
+.markdown>ul li,
+.markdown blockquote ul>li {
+  margin-left: 20px;
+  padding-left: 4px;
+}
+
+.markdown>ul li p,
+.markdown>ol li p {
+  margin: 0.6em 0;
+}
+
+.markdown ol>li {
+  list-style: decimal;
+}
+
+.markdown>ol li,
+.markdown blockquote ol>li {
+  margin-left: 20px;
+  padding-left: 4px;
+}
+
+.markdown code {
+  margin: 0 3px;
+  padding: 0 5px;
+  background: #eee;
+  border-radius: 3px;
+}
+
+.markdown strong,
+.markdown b {
+  font-weight: 600;
+}
+
+.markdown>table {
+  border-collapse: collapse;
+  border-spacing: 0px;
+  empty-cells: show;
+  border: 1px solid #e9e9e9;
+  width: 95%;
+  margin-bottom: 24px;
+}
+
+.markdown>table th {
+  white-space: nowrap;
+  color: #333;
+  font-weight: 600;
+}
+
+.markdown>table th,
+.markdown>table td {
+  border: 1px solid #e9e9e9;
+  padding: 8px 16px;
+  text-align: left;
+}
+
+.markdown>table th {
+  background: #F7F7F7;
+}
+
+.markdown blockquote {
+  font-size: 90%;
+  color: #999;
+  border-left: 4px solid #e9e9e9;
+  padding-left: 0.8em;
+  margin: 1em 0;
+}
+
+.markdown blockquote p {
+  margin: 0;
+}
+
+.markdown .anchor {
+  opacity: 0;
+  transition: opacity 0.3s ease;
+  margin-left: 8px;
+}
+
+.markdown .waiting {
+  color: #ccc;
+}
+
+.markdown h1:hover .anchor,
+.markdown h2:hover .anchor,
+.markdown h3:hover .anchor,
+.markdown h4:hover .anchor,
+.markdown h5:hover .anchor,
+.markdown h6:hover .anchor {
+  opacity: 1;
+  display: inline-block;
+}
+
+.markdown>br,
+.markdown>p>br {
+  clear: both;
+}
+
+
+.hljs {
+  display: block;
+  background: white;
+  padding: 0.5em;
+  color: #333333;
+  overflow-x: auto;
+}
+
+.hljs-comment,
+.hljs-meta {
+  color: #969896;
+}
+
+.hljs-string,
+.hljs-variable,
+.hljs-template-variable,
+.hljs-strong,
+.hljs-emphasis,
+.hljs-quote {
+  color: #df5000;
+}
+
+.hljs-keyword,
+.hljs-selector-tag,
+.hljs-type {
+  color: #a71d5d;
+}
+
+.hljs-literal,
+.hljs-symbol,
+.hljs-bullet,
+.hljs-attribute {
+  color: #0086b3;
+}
+
+.hljs-section,
+.hljs-name {
+  color: #63a35c;
+}
+
+.hljs-tag {
+  color: #333333;
+}
+
+.hljs-title,
+.hljs-attr,
+.hljs-selector-id,
+.hljs-selector-class,
+.hljs-selector-attr,
+.hljs-selector-pseudo {
+  color: #795da3;
+}
+
+.hljs-addition {
+  color: #55a532;
+  background-color: #eaffea;
+}
+
+.hljs-deletion {
+  color: #bd2c00;
+  background-color: #ffecec;
+}
+
+.hljs-link {
+  text-decoration: underline;
+}
+
+/* 代码高亮 */
+/* PrismJS 1.15.0
+https://prismjs.com/download.html#themes=prism&languages=markup+css+clike+javascript */
+/**
+ * prism.js default theme for JavaScript, CSS and HTML
+ * Based on dabblet (http://dabblet.com)
+ * @author Lea Verou
+ */
+code[class*="language-"],
+pre[class*="language-"] {
+  color: black;
+  background: none;
+  text-shadow: 0 1px white;
+  font-family: Consolas, Monaco, 'Andale Mono', 'Ubuntu Mono', monospace;
+  text-align: left;
+  white-space: pre;
+  word-spacing: normal;
+  word-break: normal;
+  word-wrap: normal;
+  line-height: 1.5;
+
+  -moz-tab-size: 4;
+  -o-tab-size: 4;
+  tab-size: 4;
+
+  -webkit-hyphens: none;
+  -moz-hyphens: none;
+  -ms-hyphens: none;
+  hyphens: none;
+}
+
+pre[class*="language-"]::-moz-selection,
+pre[class*="language-"] ::-moz-selection,
+code[class*="language-"]::-moz-selection,
+code[class*="language-"] ::-moz-selection {
+  text-shadow: none;
+  background: #b3d4fc;
+}
+
+pre[class*="language-"]::selection,
+pre[class*="language-"] ::selection,
+code[class*="language-"]::selection,
+code[class*="language-"] ::selection {
+  text-shadow: none;
+  background: #b3d4fc;
+}
+
+@media print {
+
+  code[class*="language-"],
+  pre[class*="language-"] {
+    text-shadow: none;
+  }
+}
+
+/* Code blocks */
+pre[class*="language-"] {
+  padding: 1em;
+  margin: .5em 0;
+  overflow: auto;
+}
+
+:not(pre)>code[class*="language-"],
+pre[class*="language-"] {
+  background: #f5f2f0;
+}
+
+/* Inline code */
+:not(pre)>code[class*="language-"] {
+  padding: .1em;
+  border-radius: .3em;
+  white-space: normal;
+}
+
+.token.comment,
+.token.prolog,
+.token.doctype,
+.token.cdata {
+  color: slategray;
+}
+
+.token.punctuation {
+  color: #999;
+}
+
+.namespace {
+  opacity: .7;
+}
+
+.token.property,
+.token.tag,
+.token.boolean,
+.token.number,
+.token.constant,
+.token.symbol,
+.token.deleted {
+  color: #905;
+}
+
+.token.selector,
+.token.attr-name,
+.token.string,
+.token.char,
+.token.builtin,
+.token.inserted {
+  color: #690;
+}
+
+.token.operator,
+.token.entity,
+.token.url,
+.language-css .token.string,
+.style .token.string {
+  color: #9a6e3a;
+  background: hsla(0, 0%, 100%, .5);
+}
+
+.token.atrule,
+.token.attr-value,
+.token.keyword {
+  color: #07a;
+}
+
+.token.function,
+.token.class-name {
+  color: #DD4A68;
+}
+
+.token.regex,
+.token.important,
+.token.variable {
+  color: #e90;
+}
+
+.token.important,
+.token.bold {
+  font-weight: bold;
+}
+
+.token.italic {
+  font-style: italic;
+}
+
+.token.entity {
+  cursor: help;
+}

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 3385 - 0
public/static/ext/iconfont/demo_index.html


+ 571 - 0
public/static/ext/iconfont/iconfont.css

@@ -0,0 +1,571 @@
+@font-face {
+  font-family: "iconfont"; /* Project id 2596172 */
+  src: url('iconfont.woff2?t=1659061669448') format('woff2'),
+       url('iconfont.woff?t=1659061669448') format('woff'),
+       url('iconfont.ttf?t=1659061669448') format('truetype');
+}
+
+.iconfont {
+  font-family: "iconfont" !important;
+  font-size: 16px;
+  font-style: normal;
+  -webkit-font-smoothing: antialiased;
+  -moz-osx-font-smoothing: grayscale;
+}
+
+.icon-show_share:before {
+  content: "\e690";
+}
+
+.icon-show_more_ruler:before {
+  content: "\e67b";
+}
+
+.icon-transparency:before {
+  content: "\e6d7";
+}
+
+.icon-mosaic_e:before {
+  content: "\e6d2";
+}
+
+.icon-eraser:before {
+  content: "\e6d3";
+}
+
+.icon-video2:before {
+  content: "\e6d4";
+}
+
+.icon-down:before {
+  content: "\e6d5";
+}
+
+.icon-qingkong-copy-copy:before {
+  content: "\e68f";
+}
+
+.icon-_qq:before {
+  content: "\e64b";
+}
+
+.icon-_friend:before {
+  content: "\e64c";
+}
+
+.icon-link1:before {
+  content: "\e6ff";
+}
+
+.icon-icon_share_facebook:before {
+  content: "\e745";
+}
+
+.icon-icon_share_whatsapp:before {
+  content: "\e746";
+}
+
+.icon-_wechat:before {
+  content: "\e64a";
+}
+
+.icon-watermark:before {
+  content: "\e6cb";
+}
+
+.icon-camera_h:before {
+  content: "\e6c7";
+}
+
+.icon-a-1V1:before {
+  content: "\e6c8";
+}
+
+.icon-hengbiaoEN:before {
+  content: "\e6b9";
+}
+
+.icon-hot_spot:before {
+  content: "\e6b8";
+}
+
+.icon-foot:before {
+  content: "\e6ba";
+}
+
+.icon-music-t:before {
+  content: "\e6b7";
+}
+
+.icon-yes:before {
+  content: "\e6b5";
+}
+
+.icon-no:before {
+  content: "\e6b6";
+}
+
+.icon-floor_rename:before {
+  content: "\e75b";
+}
+
+.icon-play_stop:before {
+  content: "\e6b4";
+}
+
+.icon-scene_auto:before {
+  content: "\e721";
+}
+
+.icon-compass:before {
+  content: "\e6b3";
+}
+
+.icon-h-d:before {
+  content: "\e6b2";
+}
+
+.icon-scene_screen:before {
+  content: "\e717";
+}
+
+.icon-scene_full:before {
+  content: "\e712";
+}
+
+.icon-scene_window:before {
+  content: "\e713";
+}
+
+.icon-_back:before {
+  content: "\e609";
+}
+
+.icon-show_back:before {
+  content: "\e678";
+}
+
+.icon-show_more_share:before {
+  content: "\e680";
+}
+
+.icon-show_more_finish:before {
+  content: "\e67a";
+}
+
+.icon-show_more_music:before {
+  content: "\e67c";
+}
+
+.icon-show_map_collect:before {
+  content: "\e679";
+}
+
+.icon-data-j:before {
+  content: "\e6b1";
+}
+
+.icon-cancel:before {
+  content: "\e688";
+}
+
+.icon-affirm:before {
+  content: "\e689";
+}
+
+.icon-checkbox_p:before {
+  content: "\e6b0";
+}
+
+.icon-left:before {
+  content: "\e6ae";
+}
+
+.icon-right:before {
+  content: "\e6af";
+}
+
+.icon-_loading_:before {
+  content: "\e627";
+}
+
+.icon-show_function_collect:before {
+  content: "\e687";
+}
+
+.icon-show_more:before {
+  content: "\e67e";
+}
+
+.icon-d-r:before {
+  content: "\e68d";
+}
+
+.icon-up-a:before {
+  content: "\e68e";
+}
+
+.icon-fanzhuan:before {
+  content: "\e6fa";
+}
+
+.icon-cad-neiqiang:before {
+  content: "\e698";
+}
+
+.icon-cad-waiqiang:before {
+  content: "\e69a";
+}
+
+.icon-cad-shuangkaimen:before {
+  content: "\e69b";
+}
+
+.icon-cad-zimumen:before {
+  content: "\e69c";
+}
+
+.icon-cad-men:before {
+  content: "\e69d";
+}
+
+.icon-cad-yimen:before {
+  content: "\e69e";
+}
+
+.icon-cad-zhediemen:before {
+  content: "\e69f";
+}
+
+.icon-cad-luodichuang:before {
+  content: "\e6a0";
+}
+
+.icon-cad-chuang:before {
+  content: "\e6a1";
+}
+
+.icon-cad-piaochuang:before {
+  content: "\e6a2";
+}
+
+.icon-cad-uxingchuang:before {
+  content: "\e6a4";
+}
+
+.icon-cad-lxingchuang:before {
+  content: "\e6a5";
+}
+
+.icon-cad-lpiaochuang:before {
+  content: "\e6a6";
+}
+
+.icon-cad-upiaochuang:before {
+  content: "\e6a7";
+}
+
+.icon-cad-liang:before {
+  content: "\e6a8";
+}
+
+.icon-cad-yandao:before {
+  content: "\e6a9";
+}
+
+.icon-cad-zhuzi:before {
+  content: "\e6aa";
+}
+
+.icon-cad-dianti:before {
+  content: "\e6ab";
+}
+
+.icon-cad-loudao:before {
+  content: "\e6ac";
+}
+
+.icon-cad-dange:before {
+  content: "\e6ad";
+}
+
+.icon-cad-yakou:before {
+  content: "\e699";
+}
+
+.icon-more:before {
+  content: "\e600";
+}
+
+.icon-mosaic1:before {
+  content: "\e697";
+}
+
+.icon-hengbiaoCN:before {
+  content: "\e6a3";
+}
+
+.icon-nor:before {
+  content: "\e696";
+}
+
+.icon-checkbox1:before {
+  content: "\e65d";
+}
+
+.icon-rotate:before {
+  content: "\e695";
+}
+
+.icon-adapt:before {
+  content: "\e692";
+}
+
+.icon-recover:before {
+  content: "\e693";
+}
+
+.icon-repeal:before {
+  content: "\e694";
+}
+
+.icon-reset:before {
+  content: "\e65a";
+}
+
+.icon-course1:before {
+  content: "\e68c";
+}
+
+.icon-publish:before {
+  content: "\e68a";
+}
+
+.icon-save:before {
+  content: "\e68b";
+}
+
+.icon-checkbox:before {
+  content: "\e649";
+}
+
+.icon-mosaic:before {
+  content: "\e646";
+}
+
+.icon-media:before {
+  content: "\e647";
+}
+
+.icon-pic:before {
+  content: "\e648";
+}
+
+.icon-eye_f:before {
+  content: "\e644";
+}
+
+.icon-eye_c:before {
+  content: "\e645";
+}
+
+.icon-size-o:before {
+  content: "\e640";
+}
+
+.icon-size-f:before {
+  content: "\e641";
+}
+
+.icon-magnify:before {
+  content: "\e642";
+}
+
+.icon-reduce:before {
+  content: "\e643";
+}
+
+.icon-video1:before {
+  content: "\e63b";
+}
+
+.icon-uploading_s:before {
+  content: "\e63c";
+}
+
+.icon-path:before {
+  content: "\e63d";
+}
+
+.icon-record:before {
+  content: "\e63e";
+}
+
+.icon-clear:before {
+  content: "\e63f";
+}
+
+.icon-pause:before {
+  content: "\e636";
+}
+
+.icon-preview:before {
+  content: "\e63a";
+}
+
+.icon-full:before {
+  content: "\e638";
+}
+
+.icon-add:before {
+  content: "\e631";
+}
+
+.icon-del:before {
+  content: "\e632";
+}
+
+.icon-close:before {
+  content: "\e633";
+}
+
+.icon-web:before {
+  content: "\e635";
+}
+
+.icon-music:before {
+  content: "\e637";
+}
+
+.icon-uploading1:before {
+  content: "\e639";
+}
+
+.icon-state_e:before {
+  content: "\e624";
+}
+
+.icon-state_f:before {
+  content: "\e625";
+}
+
+.icon-state_s:before {
+  content: "\e626";
+}
+
+.icon-vip_uploading:before {
+  content: "\e623";
+}
+
+.icon-eye-n:before {
+  content: "\e621";
+}
+
+.icon-eye-s:before {
+  content: "\e622";
+}
+
+.icon-course:before {
+  content: "\e620";
+}
+
+.icon-edit:before {
+  content: "\e61f";
+}
+
+.icon-help:before {
+  content: "\e615";
+}
+
+.icon-rule:before {
+  content: "\e617";
+}
+
+.icon-link:before {
+  content: "\e618";
+}
+
+.icon-uploading:before {
+  content: "\e619";
+}
+
+.icon-vr:before {
+  content: "\e61a";
+}
+
+.icon-complete:before {
+  content: "\e61b";
+}
+
+.icon-download:before {
+  content: "\e61c";
+}
+
+.icon-pull-down:before {
+  content: "\e61d";
+}
+
+.icon-pull-up:before {
+  content: "\e61e";
+}
+
+.icon-updown:before {
+  content: "\e613";
+}
+
+.icon-scene:before {
+  content: "\e614";
+}
+
+.icon-message:before {
+  content: "\e60c";
+}
+
+.icon-basic:before {
+  content: "\e60d";
+}
+
+.icon-hotspot:before {
+  content: "\e60e";
+}
+
+.icon-guide:before {
+  content: "\e60f";
+}
+
+.icon-wander:before {
+  content: "\e610";
+}
+
+.icon-house:before {
+  content: "\e611";
+}
+
+.icon-video:before {
+  content: "\e612";
+}
+
+.icon-show_3d_normal:before {
+  content: "\e677";
+}
+
+.icon-show_plane_normal:before {
+  content: "\e67d";
+}
+
+.icon-show_roaming_selected:before {
+  content: "\e682";
+}
+
+.icon-show_plane_selected:before {
+  content: "\e684";
+}
+
+.icon-show_3d_selected:before {
+  content: "\e685";
+}
+
+.icon-show_roaming_normal:before {
+  content: "\e686";
+}
+

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 1 - 0
public/static/ext/iconfont/iconfont.js


+ 982 - 0
public/static/ext/iconfont/iconfont.json

@@ -0,0 +1,982 @@
+{
+  "id": "2596172",
+  "name": "四维看看编辑器V4",
+  "font_family": "iconfont",
+  "css_prefix_text": "icon-",
+  "description": "四维看看编辑器设计优化",
+  "glyphs": [
+    {
+      "icon_id": "20600368",
+      "name": "show_share",
+      "font_class": "show_share",
+      "unicode": "e690",
+      "unicode_decimal": 59024
+    },
+    {
+      "icon_id": "19543928",
+      "name": "show_more_ruler",
+      "font_class": "show_more_ruler",
+      "unicode": "e67b",
+      "unicode_decimal": 59003
+    },
+    {
+      "icon_id": "30499411",
+      "name": "transparency",
+      "font_class": "transparency",
+      "unicode": "e6d7",
+      "unicode_decimal": 59095
+    },
+    {
+      "icon_id": "30490892",
+      "name": "mosaic_e",
+      "font_class": "mosaic_e",
+      "unicode": "e6d2",
+      "unicode_decimal": 59090
+    },
+    {
+      "icon_id": "30490893",
+      "name": "eraser",
+      "font_class": "eraser",
+      "unicode": "e6d3",
+      "unicode_decimal": 59091
+    },
+    {
+      "icon_id": "30490894",
+      "name": "video",
+      "font_class": "video2",
+      "unicode": "e6d4",
+      "unicode_decimal": 59092
+    },
+    {
+      "icon_id": "30490946",
+      "name": "down",
+      "font_class": "down",
+      "unicode": "e6d5",
+      "unicode_decimal": 59093
+    },
+    {
+      "icon_id": "3141534",
+      "name": "清空",
+      "font_class": "qingkong-copy-copy",
+      "unicode": "e68f",
+      "unicode_decimal": 59023
+    },
+    {
+      "icon_id": "7878582",
+      "name": "QQ",
+      "font_class": "_qq",
+      "unicode": "e64b",
+      "unicode_decimal": 58955
+    },
+    {
+      "icon_id": "7878584",
+      "name": "朋友",
+      "font_class": "_friend",
+      "unicode": "e64c",
+      "unicode_decimal": 58956
+    },
+    {
+      "icon_id": "14887802",
+      "name": "link",
+      "font_class": "link1",
+      "unicode": "e6ff",
+      "unicode_decimal": 59135
+    },
+    {
+      "icon_id": "26296900",
+      "name": "icon_share_facebook",
+      "font_class": "icon_share_facebook",
+      "unicode": "e745",
+      "unicode_decimal": 59205
+    },
+    {
+      "icon_id": "26296901",
+      "name": "icon_share_whatsapp",
+      "font_class": "icon_share_whatsapp",
+      "unicode": "e746",
+      "unicode_decimal": 59206
+    },
+    {
+      "icon_id": "7878583",
+      "name": "微信",
+      "font_class": "_wechat",
+      "unicode": "e64a",
+      "unicode_decimal": 58954
+    },
+    {
+      "icon_id": "30230568",
+      "name": "watermark",
+      "font_class": "watermark",
+      "unicode": "e6cb",
+      "unicode_decimal": 59083
+    },
+    {
+      "icon_id": "30230353",
+      "name": "camera_h",
+      "font_class": "camera_h",
+      "unicode": "e6c7",
+      "unicode_decimal": 59079
+    },
+    {
+      "icon_id": "30230374",
+      "name": "1V1",
+      "font_class": "a-1V1",
+      "unicode": "e6c8",
+      "unicode_decimal": 59080
+    },
+    {
+      "icon_id": "12324810",
+      "name": "横标EN",
+      "font_class": "hengbiaoEN",
+      "unicode": "e6b9",
+      "unicode_decimal": 59065
+    },
+    {
+      "icon_id": "22788718",
+      "name": "hot_spot",
+      "font_class": "hot_spot",
+      "unicode": "e6b8",
+      "unicode_decimal": 59064
+    },
+    {
+      "icon_id": "29982018",
+      "name": "foot",
+      "font_class": "foot",
+      "unicode": "e6ba",
+      "unicode_decimal": 59066
+    },
+    {
+      "icon_id": "29365471",
+      "name": "music-t",
+      "font_class": "music-t",
+      "unicode": "e6b7",
+      "unicode_decimal": 59063
+    },
+    {
+      "icon_id": "29346730",
+      "name": "yes",
+      "font_class": "yes",
+      "unicode": "e6b5",
+      "unicode_decimal": 59061
+    },
+    {
+      "icon_id": "29346731",
+      "name": "no",
+      "font_class": "no",
+      "unicode": "e6b6",
+      "unicode_decimal": 59062
+    },
+    {
+      "icon_id": "20764383",
+      "name": "floor_rename",
+      "font_class": "floor_rename",
+      "unicode": "e75b",
+      "unicode_decimal": 59227
+    },
+    {
+      "icon_id": "29255507",
+      "name": "play_stop",
+      "font_class": "play_stop",
+      "unicode": "e6b4",
+      "unicode_decimal": 59060
+    },
+    {
+      "icon_id": "16303117",
+      "name": "scene_auto",
+      "font_class": "scene_auto",
+      "unicode": "e721",
+      "unicode_decimal": 59169
+    },
+    {
+      "icon_id": "28895680",
+      "name": "compass",
+      "font_class": "compass",
+      "unicode": "e6b3",
+      "unicode_decimal": 59059
+    },
+    {
+      "icon_id": "28351771",
+      "name": "h-d",
+      "font_class": "h-d",
+      "unicode": "e6b2",
+      "unicode_decimal": 59058
+    },
+    {
+      "icon_id": "16270567",
+      "name": "scene_screen",
+      "font_class": "scene_screen",
+      "unicode": "e717",
+      "unicode_decimal": 59159
+    },
+    {
+      "icon_id": "15936377",
+      "name": "scene_full",
+      "font_class": "scene_full",
+      "unicode": "e712",
+      "unicode_decimal": 59154
+    },
+    {
+      "icon_id": "15936378",
+      "name": "scene_window",
+      "font_class": "scene_window",
+      "unicode": "e713",
+      "unicode_decimal": 59155
+    },
+    {
+      "icon_id": "7857935",
+      "name": "返回",
+      "font_class": "_back",
+      "unicode": "e609",
+      "unicode_decimal": 58889
+    },
+    {
+      "icon_id": "20066553",
+      "name": "show_back",
+      "font_class": "show_back",
+      "unicode": "e678",
+      "unicode_decimal": 59000
+    },
+    {
+      "icon_id": "20066555",
+      "name": "show_more_share",
+      "font_class": "show_more_share",
+      "unicode": "e680",
+      "unicode_decimal": 59008
+    },
+    {
+      "icon_id": "19543927",
+      "name": "show_more_finish",
+      "font_class": "show_more_finish",
+      "unicode": "e67a",
+      "unicode_decimal": 59002
+    },
+    {
+      "icon_id": "19543929",
+      "name": "show_more_music",
+      "font_class": "show_more_music",
+      "unicode": "e67c",
+      "unicode_decimal": 59004
+    },
+    {
+      "icon_id": "19543926",
+      "name": "show_map_collect",
+      "font_class": "show_map_collect",
+      "unicode": "e679",
+      "unicode_decimal": 59001
+    },
+    {
+      "icon_id": "27985200",
+      "name": "data-j",
+      "font_class": "data-j",
+      "unicode": "e6b1",
+      "unicode_decimal": 59057
+    },
+    {
+      "icon_id": "26690641",
+      "name": "cancel",
+      "font_class": "cancel",
+      "unicode": "e688",
+      "unicode_decimal": 59016
+    },
+    {
+      "icon_id": "26690677",
+      "name": "affirm",
+      "font_class": "affirm",
+      "unicode": "e689",
+      "unicode_decimal": 59017
+    },
+    {
+      "icon_id": "27896904",
+      "name": "checkbox_p",
+      "font_class": "checkbox_p",
+      "unicode": "e6b0",
+      "unicode_decimal": 59056
+    },
+    {
+      "icon_id": "27765016",
+      "name": "left",
+      "font_class": "left",
+      "unicode": "e6ae",
+      "unicode_decimal": 59054
+    },
+    {
+      "icon_id": "27765017",
+      "name": "right",
+      "font_class": "right",
+      "unicode": "e6af",
+      "unicode_decimal": 59055
+    },
+    {
+      "icon_id": "7858065",
+      "name": "loading",
+      "font_class": "_loading_",
+      "unicode": "e627",
+      "unicode_decimal": 58919
+    },
+    {
+      "icon_id": "20066572",
+      "name": "show_function_collect",
+      "font_class": "show_function_collect",
+      "unicode": "e687",
+      "unicode_decimal": 59015
+    },
+    {
+      "icon_id": "19543931",
+      "name": "show_more",
+      "font_class": "show_more",
+      "unicode": "e67e",
+      "unicode_decimal": 59006
+    },
+    {
+      "icon_id": "26914809",
+      "name": "d-r",
+      "font_class": "d-r",
+      "unicode": "e68d",
+      "unicode_decimal": 59021
+    },
+    {
+      "icon_id": "26914810",
+      "name": "up-a",
+      "font_class": "up-a",
+      "unicode": "e68e",
+      "unicode_decimal": 59022
+    },
+    {
+      "icon_id": "14510564",
+      "name": "edit_mirror",
+      "font_class": "fanzhuan",
+      "unicode": "e6fa",
+      "unicode_decimal": 59130
+    },
+    {
+      "icon_id": "27294582",
+      "name": "neiqiang",
+      "font_class": "cad-neiqiang",
+      "unicode": "e698",
+      "unicode_decimal": 59032
+    },
+    {
+      "icon_id": "27294583",
+      "name": "waiqiang",
+      "font_class": "cad-waiqiang",
+      "unicode": "e69a",
+      "unicode_decimal": 59034
+    },
+    {
+      "icon_id": "27294616",
+      "name": "shuangkaimen",
+      "font_class": "cad-shuangkaimen",
+      "unicode": "e69b",
+      "unicode_decimal": 59035
+    },
+    {
+      "icon_id": "27294617",
+      "name": "zimumen",
+      "font_class": "cad-zimumen",
+      "unicode": "e69c",
+      "unicode_decimal": 59036
+    },
+    {
+      "icon_id": "27294618",
+      "name": "men",
+      "font_class": "cad-men",
+      "unicode": "e69d",
+      "unicode_decimal": 59037
+    },
+    {
+      "icon_id": "27294620",
+      "name": "yimen",
+      "font_class": "cad-yimen",
+      "unicode": "e69e",
+      "unicode_decimal": 59038
+    },
+    {
+      "icon_id": "27294621",
+      "name": "zhediemen",
+      "font_class": "cad-zhediemen",
+      "unicode": "e69f",
+      "unicode_decimal": 59039
+    },
+    {
+      "icon_id": "27294699",
+      "name": "luodichuang",
+      "font_class": "cad-luodichuang",
+      "unicode": "e6a0",
+      "unicode_decimal": 59040
+    },
+    {
+      "icon_id": "27294700",
+      "name": "chuang",
+      "font_class": "cad-chuang",
+      "unicode": "e6a1",
+      "unicode_decimal": 59041
+    },
+    {
+      "icon_id": "27294701",
+      "name": "piaochuang",
+      "font_class": "cad-piaochuang",
+      "unicode": "e6a2",
+      "unicode_decimal": 59042
+    },
+    {
+      "icon_id": "27294702",
+      "name": "uxingchuang",
+      "font_class": "cad-uxingchuang",
+      "unicode": "e6a4",
+      "unicode_decimal": 59044
+    },
+    {
+      "icon_id": "27294703",
+      "name": "lxingchuang",
+      "font_class": "cad-lxingchuang",
+      "unicode": "e6a5",
+      "unicode_decimal": 59045
+    },
+    {
+      "icon_id": "27294704",
+      "name": "lpiaochuang",
+      "font_class": "cad-lpiaochuang",
+      "unicode": "e6a6",
+      "unicode_decimal": 59046
+    },
+    {
+      "icon_id": "27294705",
+      "name": "upiaochuang",
+      "font_class": "cad-upiaochuang",
+      "unicode": "e6a7",
+      "unicode_decimal": 59047
+    },
+    {
+      "icon_id": "27294743",
+      "name": "liang",
+      "font_class": "cad-liang",
+      "unicode": "e6a8",
+      "unicode_decimal": 59048
+    },
+    {
+      "icon_id": "27294744",
+      "name": "yandao",
+      "font_class": "cad-yandao",
+      "unicode": "e6a9",
+      "unicode_decimal": 59049
+    },
+    {
+      "icon_id": "27294745",
+      "name": "zhuzi",
+      "font_class": "cad-zhuzi",
+      "unicode": "e6aa",
+      "unicode_decimal": 59050
+    },
+    {
+      "icon_id": "27294746",
+      "name": "dianti",
+      "font_class": "cad-dianti",
+      "unicode": "e6ab",
+      "unicode_decimal": 59051
+    },
+    {
+      "icon_id": "27294747",
+      "name": "loudao",
+      "font_class": "cad-loudao",
+      "unicode": "e6ac",
+      "unicode_decimal": 59052
+    },
+    {
+      "icon_id": "27297593",
+      "name": "dange",
+      "font_class": "cad-dange",
+      "unicode": "e6ad",
+      "unicode_decimal": 59053
+    },
+    {
+      "icon_id": "27294584",
+      "name": "yakou",
+      "font_class": "cad-yakou",
+      "unicode": "e699",
+      "unicode_decimal": 59033
+    },
+    {
+      "icon_id": "11304931",
+      "name": "more read",
+      "font_class": "more",
+      "unicode": "e600",
+      "unicode_decimal": 58880
+    },
+    {
+      "icon_id": "27264933",
+      "name": "mosaic",
+      "font_class": "mosaic1",
+      "unicode": "e697",
+      "unicode_decimal": 59031
+    },
+    {
+      "icon_id": "12324809",
+      "name": "横标CN",
+      "font_class": "hengbiaoCN",
+      "unicode": "e6a3",
+      "unicode_decimal": 59043
+    },
+    {
+      "icon_id": "27200779",
+      "name": "nor",
+      "font_class": "nor",
+      "unicode": "e696",
+      "unicode_decimal": 59030
+    },
+    {
+      "icon_id": "25671886",
+      "name": "checkbox",
+      "font_class": "checkbox1",
+      "unicode": "e65d",
+      "unicode_decimal": 58973
+    },
+    {
+      "icon_id": "27198807",
+      "name": "rotate",
+      "font_class": "rotate",
+      "unicode": "e695",
+      "unicode_decimal": 59029
+    },
+    {
+      "icon_id": "27198774",
+      "name": "adapt",
+      "font_class": "adapt",
+      "unicode": "e692",
+      "unicode_decimal": 59026
+    },
+    {
+      "icon_id": "27198776",
+      "name": "recover",
+      "font_class": "recover",
+      "unicode": "e693",
+      "unicode_decimal": 59027
+    },
+    {
+      "icon_id": "27198777",
+      "name": "repeal",
+      "font_class": "repeal",
+      "unicode": "e694",
+      "unicode_decimal": 59028
+    },
+    {
+      "icon_id": "25654903",
+      "name": "reset",
+      "font_class": "reset",
+      "unicode": "e65a",
+      "unicode_decimal": 58970
+    },
+    {
+      "icon_id": "26971297",
+      "name": "course",
+      "font_class": "course1",
+      "unicode": "e68c",
+      "unicode_decimal": 59020
+    },
+    {
+      "icon_id": "26950708",
+      "name": "publish",
+      "font_class": "publish",
+      "unicode": "e68a",
+      "unicode_decimal": 59018
+    },
+    {
+      "icon_id": "26950711",
+      "name": "save",
+      "font_class": "save",
+      "unicode": "e68b",
+      "unicode_decimal": 59019
+    },
+    {
+      "icon_id": "23842269",
+      "name": "sel",
+      "font_class": "checkbox",
+      "unicode": "e649",
+      "unicode_decimal": 58953
+    },
+    {
+      "icon_id": "23786361",
+      "name": "mosaic",
+      "font_class": "mosaic",
+      "unicode": "e646",
+      "unicode_decimal": 58950
+    },
+    {
+      "icon_id": "23786362",
+      "name": "media",
+      "font_class": "media",
+      "unicode": "e647",
+      "unicode_decimal": 58951
+    },
+    {
+      "icon_id": "23786363",
+      "name": "pic",
+      "font_class": "pic",
+      "unicode": "e648",
+      "unicode_decimal": 58952
+    },
+    {
+      "icon_id": "23783948",
+      "name": "eye_f",
+      "font_class": "eye_f",
+      "unicode": "e644",
+      "unicode_decimal": 58948
+    },
+    {
+      "icon_id": "23783949",
+      "name": "eye_c",
+      "font_class": "eye_c",
+      "unicode": "e645",
+      "unicode_decimal": 58949
+    },
+    {
+      "icon_id": "23783512",
+      "name": "size-o",
+      "font_class": "size-o",
+      "unicode": "e640",
+      "unicode_decimal": 58944
+    },
+    {
+      "icon_id": "23783513",
+      "name": "size-f",
+      "font_class": "size-f",
+      "unicode": "e641",
+      "unicode_decimal": 58945
+    },
+    {
+      "icon_id": "23783514",
+      "name": "magnify",
+      "font_class": "magnify",
+      "unicode": "e642",
+      "unicode_decimal": 58946
+    },
+    {
+      "icon_id": "23783515",
+      "name": "reduce",
+      "font_class": "reduce",
+      "unicode": "e643",
+      "unicode_decimal": 58947
+    },
+    {
+      "icon_id": "23781429",
+      "name": "video",
+      "font_class": "video1",
+      "unicode": "e63b",
+      "unicode_decimal": 58939
+    },
+    {
+      "icon_id": "23781430",
+      "name": "uploading_s",
+      "font_class": "uploading_s",
+      "unicode": "e63c",
+      "unicode_decimal": 58940
+    },
+    {
+      "icon_id": "23781431",
+      "name": "path",
+      "font_class": "path",
+      "unicode": "e63d",
+      "unicode_decimal": 58941
+    },
+    {
+      "icon_id": "23781432",
+      "name": "record",
+      "font_class": "record",
+      "unicode": "e63e",
+      "unicode_decimal": 58942
+    },
+    {
+      "icon_id": "23781433",
+      "name": "clear",
+      "font_class": "clear",
+      "unicode": "e63f",
+      "unicode_decimal": 58943
+    },
+    {
+      "icon_id": "23773343",
+      "name": "pause",
+      "font_class": "pause",
+      "unicode": "e636",
+      "unicode_decimal": 58934
+    },
+    {
+      "icon_id": "23773344",
+      "name": "preview",
+      "font_class": "preview",
+      "unicode": "e63a",
+      "unicode_decimal": 58938
+    },
+    {
+      "icon_id": "23773141",
+      "name": "full",
+      "font_class": "full",
+      "unicode": "e638",
+      "unicode_decimal": 58936
+    },
+    {
+      "icon_id": "23773068",
+      "name": "add",
+      "font_class": "add",
+      "unicode": "e631",
+      "unicode_decimal": 58929
+    },
+    {
+      "icon_id": "23773069",
+      "name": "del",
+      "font_class": "del",
+      "unicode": "e632",
+      "unicode_decimal": 58930
+    },
+    {
+      "icon_id": "23773070",
+      "name": "close",
+      "font_class": "close",
+      "unicode": "e633",
+      "unicode_decimal": 58931
+    },
+    {
+      "icon_id": "23773072",
+      "name": "web",
+      "font_class": "web",
+      "unicode": "e635",
+      "unicode_decimal": 58933
+    },
+    {
+      "icon_id": "23773074",
+      "name": "music",
+      "font_class": "music",
+      "unicode": "e637",
+      "unicode_decimal": 58935
+    },
+    {
+      "icon_id": "23773076",
+      "name": "uploading",
+      "font_class": "uploading1",
+      "unicode": "e639",
+      "unicode_decimal": 58937
+    },
+    {
+      "icon_id": "22132762",
+      "name": "state_e",
+      "font_class": "state_e",
+      "unicode": "e624",
+      "unicode_decimal": 58916
+    },
+    {
+      "icon_id": "22132763",
+      "name": "state_f",
+      "font_class": "state_f",
+      "unicode": "e625",
+      "unicode_decimal": 58917
+    },
+    {
+      "icon_id": "22132764",
+      "name": "state_s",
+      "font_class": "state_s",
+      "unicode": "e626",
+      "unicode_decimal": 58918
+    },
+    {
+      "icon_id": "22130256",
+      "name": "vip_uploading",
+      "font_class": "vip_uploading",
+      "unicode": "e623",
+      "unicode_decimal": 58915
+    },
+    {
+      "icon_id": "22099675",
+      "name": "eye-n",
+      "font_class": "eye-n",
+      "unicode": "e621",
+      "unicode_decimal": 58913
+    },
+    {
+      "icon_id": "22099676",
+      "name": "eye-s",
+      "font_class": "eye-s",
+      "unicode": "e622",
+      "unicode_decimal": 58914
+    },
+    {
+      "icon_id": "22099634",
+      "name": "course",
+      "font_class": "course",
+      "unicode": "e620",
+      "unicode_decimal": 58912
+    },
+    {
+      "icon_id": "22099525",
+      "name": "edit",
+      "font_class": "edit",
+      "unicode": "e61f",
+      "unicode_decimal": 58911
+    },
+    {
+      "icon_id": "22099475",
+      "name": "help",
+      "font_class": "help",
+      "unicode": "e615",
+      "unicode_decimal": 58901
+    },
+    {
+      "icon_id": "22099478",
+      "name": "rule",
+      "font_class": "rule",
+      "unicode": "e617",
+      "unicode_decimal": 58903
+    },
+    {
+      "icon_id": "22099479",
+      "name": "link",
+      "font_class": "link",
+      "unicode": "e618",
+      "unicode_decimal": 58904
+    },
+    {
+      "icon_id": "22099480",
+      "name": "uploading",
+      "font_class": "uploading",
+      "unicode": "e619",
+      "unicode_decimal": 58905
+    },
+    {
+      "icon_id": "22099481",
+      "name": "vr",
+      "font_class": "vr",
+      "unicode": "e61a",
+      "unicode_decimal": 58906
+    },
+    {
+      "icon_id": "22099484",
+      "name": "complete",
+      "font_class": "complete",
+      "unicode": "e61b",
+      "unicode_decimal": 58907
+    },
+    {
+      "icon_id": "22099499",
+      "name": "download",
+      "font_class": "download",
+      "unicode": "e61c",
+      "unicode_decimal": 58908
+    },
+    {
+      "icon_id": "22099518",
+      "name": "pull-down",
+      "font_class": "pull-down",
+      "unicode": "e61d",
+      "unicode_decimal": 58909
+    },
+    {
+      "icon_id": "22099519",
+      "name": "pull-up",
+      "font_class": "pull-up",
+      "unicode": "e61e",
+      "unicode_decimal": 58910
+    },
+    {
+      "icon_id": "22099070",
+      "name": "updown",
+      "font_class": "updown",
+      "unicode": "e613",
+      "unicode_decimal": 58899
+    },
+    {
+      "icon_id": "22099071",
+      "name": "scene",
+      "font_class": "scene",
+      "unicode": "e614",
+      "unicode_decimal": 58900
+    },
+    {
+      "icon_id": "22099025",
+      "name": "message",
+      "font_class": "message",
+      "unicode": "e60c",
+      "unicode_decimal": 58892
+    },
+    {
+      "icon_id": "22099028",
+      "name": "basic",
+      "font_class": "basic",
+      "unicode": "e60d",
+      "unicode_decimal": 58893
+    },
+    {
+      "icon_id": "22099032",
+      "name": "hotspot",
+      "font_class": "hotspot",
+      "unicode": "e60e",
+      "unicode_decimal": 58894
+    },
+    {
+      "icon_id": "22099035",
+      "name": "guide",
+      "font_class": "guide",
+      "unicode": "e60f",
+      "unicode_decimal": 58895
+    },
+    {
+      "icon_id": "22099060",
+      "name": "wander",
+      "font_class": "wander",
+      "unicode": "e610",
+      "unicode_decimal": 58896
+    },
+    {
+      "icon_id": "22099068",
+      "name": "house",
+      "font_class": "house",
+      "unicode": "e611",
+      "unicode_decimal": 58897
+    },
+    {
+      "icon_id": "22099069",
+      "name": "video",
+      "font_class": "video",
+      "unicode": "e612",
+      "unicode_decimal": 58898
+    },
+    {
+      "icon_id": "20066551",
+      "name": "show_3d_normal",
+      "font_class": "show_3d_normal",
+      "unicode": "e677",
+      "unicode_decimal": 58999
+    },
+    {
+      "icon_id": "20066554",
+      "name": "show_plane_normal",
+      "font_class": "show_plane_normal",
+      "unicode": "e67d",
+      "unicode_decimal": 59005
+    },
+    {
+      "icon_id": "20066556",
+      "name": "show_roaming_selected",
+      "font_class": "show_roaming_selected",
+      "unicode": "e682",
+      "unicode_decimal": 59010
+    },
+    {
+      "icon_id": "20066557",
+      "name": "show_plane_selected",
+      "font_class": "show_plane_selected",
+      "unicode": "e684",
+      "unicode_decimal": 59012
+    },
+    {
+      "icon_id": "20066558",
+      "name": "show_3d_selected",
+      "font_class": "show_3d_selected",
+      "unicode": "e685",
+      "unicode_decimal": 59013
+    },
+    {
+      "icon_id": "20066559",
+      "name": "show_roaming_normal",
+      "font_class": "show_roaming_normal",
+      "unicode": "e686",
+      "unicode_decimal": 59014
+    }
+  ]
+}

BIN
public/static/ext/iconfont/iconfont.ttf


BIN
public/static/ext/iconfont/iconfont.woff


BIN
public/static/ext/iconfont/iconfont.woff2


+ 16 - 0
public/static/ext/mobile-detect.js

@@ -0,0 +1,16 @@
+(function(win) {
+    var orgLink = win.location.href
+    var newLink = ''
+    if (/iPhone|iPad|Android/i.test(win.navigator.userAgent)) {
+        if (orgLink.indexOf('smart-viewer.html') !== -1) {
+            newLink = orgLink.replace('smart-viewer.html', 'smart-sviewer.html')
+        }
+    } else {
+        if (orgLink.indexOf('smart-sviewer.html') !== -1) {
+            newLink = orgLink.replace('smart-sviewer.html', 'smart-viewer.html')
+        }
+    }
+    if (newLink) {
+        win.location.href = newLink
+    }
+}(window))

+ 16 - 13
public/static/lib/potree/potree.js

@@ -798,10 +798,13 @@
         intersectWhenHover:true,
 
         notAdditiveBlending:false, //点云是否使用普通的blend, 否则会曝光过渡
-        precision:2  // 两位小数
+        precision:2,  // 两位小数
+        
+        testV4url:true, //v4的全景图等路径不一样 scene_view_data
     };
-     
-     
+      
+
+    //https://4dkk.4dage.com/images/imagesSS-V4-aaeaQxWA/tiles/4k/0_skybox2.jpg?x-oss-process=image/resize,h_512&time=20221024105628
 
     //JSON.parse(localStorage.getItem('setting'))
 
@@ -66198,16 +66201,15 @@ void main() {
     			let nodes = {};
     			nodes[node.name] = node;
     			let pco = node.pcoGeometry;
-
+                let maxLevel_ = 0;
     			for (let i = 0; i < decoded.length; i++) {
     				let name = decoded[i].name;
     				let decodedNumPoints = decoded[i].numPoints;
     				let index = parseInt(name.charAt(name.length - 1));
     				let parentName = name.substring(0, name.length - 1);
     				let parentNode = nodes[parentName];
-    				let level = name.length - 1;
-                    pco.dispatchEvent({type:'updateNodeMaxLevel',level});//add
-                    
+    				let level = name.length - 1; 
+                    maxLevel_ = Math.max(maxLevel_,level);//add
     				let boundingBox = Utils.createChildAABB(parentNode.boundingBox, index);
 
     				let currentNode = new PointCloudOctreeGeometryNode(name, pco, boundingBox);
@@ -66218,7 +66220,7 @@ void main() {
     				parentNode.addChild(currentNode);
     				nodes[name] = currentNode;
     			}
-
+                pco.dispatchEvent({type:'updateNodeMaxLevel',level:maxLevel_});//add
     			let duration = performance.now() - tStart;
     			if(duration > 5){
     				/* let msg = `duration: ${duration}ms, numNodes: ${decoded.length}`;
@@ -89869,8 +89871,8 @@ void main() {
 
         
 
-        getTiles(d, sceneNum){
-            if(Potree.settings.isLocal2 && !this.local2SrcFailed){//新的地址  scene_view_data/场景码/images/tiles
+        getTiles(d, sceneNum, useV4url){
+            if(Potree.settings.isLocal2 && !this.local2SrcFailed || useV4url){//新的地址  scene_view_data/场景码/images/tiles
                 return `${Potree.settings.urls.prefix3}/scene_view_data/${sceneNum}/images/${d}`    
             }
             
@@ -89954,7 +89956,8 @@ void main() {
                 panoSize = o.panoSize,
                 tileSize = o.tileSize,
                 tileIndex = o.tileIndex,
-                sceneCode = o.pano.pointcloud.sceneCode;
+                sceneCode = o.pano.pointcloud.sceneCode,
+                useV4url = Potree.settings.testV4url; /* && o.pano.pointcloud.useV4url */     //v4的全景图等路径不一样  
             var metadata = {sceneScheme:10};  
             
             
@@ -89971,7 +89974,7 @@ void main() {
                 //1 === config.tiling.customCompression && (u = "_" + config.tiling["q" + e[panoSize]]);
                 //1 === o.tiling.customCompression && (u = "_" + o.tiling["q" + e[n]]);
                 d = "tiles/" + id + "/" + e[panoSize] + u + "_face" + h + "_" + t.tileX + "_" + t.tileY + ".jpg"; 
-                d =  this.getTiles(d, sceneCode);
+                d =  this.getTiles(d, sceneCode, useV4url);
                 g = "?";  
               
             }else {//阿里云oss的规则   if (metadata.sceneScheme == 10) 
@@ -90000,7 +90003,7 @@ void main() {
                     } 
                 }
                 
-                d = this.getTiles(d, sceneCode);
+                d = this.getTiles(d, sceneCode, useV4url);
                 g = "&"; 
             } 
             

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 1 - 1
public/static/lib/potree/potree.js.map


+ 40 - 25
src/pages/SViewer.vue

@@ -28,11 +28,11 @@ import { http } from '@/utils/request'
 import Toast from '@/components/dialog/Toast'
 import browser from '@/utils/browser'
 import Calendar from '@/components/calendar/mobile.vue'
-import sync, { loadSourceScene, loadTargetScene } from '@/utils/sync'
+import sync, { loadSourceScene, loadTargetScene , setPanoWithBim} from '@/utils/sync'
 
 // 点位信息
 let lastFakeApp = null
-
+let panoData
 const showBimTips = ref(false)
 
 const showTips = ref(null)
@@ -57,9 +57,7 @@ const scenes = computed(() => {
     })
 })
 const sourceURL = computed(() => {
-    if (bimChecked.value) {
-        return `smart-bim.html?m=${project.value.bimData.bimOssFilePath}`
-    }
+     
     /*if (source.value.type < 2) {
         let pose = ''
         // 获取当前点位旋转值
@@ -74,13 +72,14 @@ const sourceURL = computed(() => {
     } else {
         // 深时场景
         return `smart-kankan.html?m=${source.value.num}`//`smart-laser.html?m=${source.value.num}&dev`
-    }*/
+    }*/ 
     
-    if (sourceFrame.value && sourceFrame.value.contentWindow){ 
-        lastFakeApp = sync.views.createTempApp(sourceFrame.value.contentWindow, true);
+    if(sourceFrame.value && (bimChecked.value || sourceFrame.value.contentWindow.app || sourceFrame.value.contentWindow.loaded)){
+        sync.views.addViewInfo(sourceFrame.value.contentWindow)
     }
-
-    if(source.value.type < 2) {
+    if(bimChecked.value){
+        return `smart-bim.html?m=${project.value.bimData.bimOssFilePath}`
+    }else if(source.value.type < 2) {
         return `smart-kankan.html?m=${source.value.num}`
     } else {
         return `smart-laser.html?m=${source.value.num}&dev`
@@ -90,26 +89,37 @@ const sourceURL = computed(() => {
 const onLoadSource = () => { 
     let win = sourceFrame.value.contentWindow 
         window.app = win
-    if (source.value.type < 2) {
+        
+    let loaded = ()=>{
+        if (lastFakeApp) {
+            if(bimChecked.value || lastFakeApp.sceneType == 'bim'){//->bim
+                sync.views.bindFakeWithBim(lastFakeApp, win, panoData) 
+            }else{
+                sync.views.bindWithSameFakeType(lastFakeApp,win) 
+            }
+            
+              
+        } 
+        lastFakeApp = sync.views.createTempApp(sourceFrame.value.contentWindow);  
+    } 
+
+ 
+     
+    if(bimChecked.value){//bim
+        win.sceneType = 'bim'
+        win.loaded.then(sdk => { 
+            loaded() 
+        }) 
+    }else if (source.value.type < 2) { 
         win.sceneType = 'kankan'
         let sdk = win.app 
         sdk.Scene.on('loaded', () => {
-            if (lastFakeApp) {
-                if(sdk){
-                    sync.views.bindWithSameFakeType(lastFakeApp,win)  
-                }
-            }
-        }) 
+            loaded() 
+        })  
     }else{ 
-        debugger
         win.sceneType = 'laser' 
-        win.loaded.then(sdk => {
-            debugger
-            if (lastFakeApp) {
-                 
-                    sync.views.bindWithSameFakeType(lastFakeApp,win)  
-                 
-            }
+        win.loaded.then(sdk => { 
+            loaded() 
         }) 
     }
      
@@ -225,6 +235,11 @@ onMounted(() => {
                 if (project.value.sceneList.length) {
                     source.value = project.value.sceneList[0]
                 }
+                if(response.data.panos){
+                    response.data.panos = JSON.parse(response.data.panos)
+                    panoData = response.data.panos  //convert with bim
+                }
+                
             } else {
                 showTips.value = response.message
             }

+ 23 - 8
src/pages/Viewer.vue

@@ -2,9 +2,9 @@
     <AppHeader v-show="!fscChecked" :project="project" :show-adjust="showAdjust" @update="onPointsUpdate" />
     <article>
         <main>
-            <div class="split" v-if="source">
-                <iframe ref="sourceFrame" :src="sourceURL" frameborder="0" @load="onLoadSource"></iframe>
-                <div class="tools" v-show="!showAdjust && !fscChecked && (dbsChecked || (!target && !bimChecked))">
+            <div class="split">
+                <iframe ref="sourceFrame" v-if="sourceURL" :src="sourceURL" frameborder="0" @load="onLoadSource"></iframe>
+                <div class="tools" v-if="source" v-show="!showAdjust && !fscChecked && (dbsChecked || (!target && !bimChecked))">
                     <div class="item-date">
                         <calendar name="source" :count="scenes.length" :value="sourceDate" :highlighted="sourceDays" @selected="onSelected" @pick="onPickDate" @prev="onPrevDate" @next="onNextDate"></calendar>
                     </div>
@@ -70,7 +70,7 @@ import browser from '@/utils/browser'
 import Toast from '@/components/dialog/Toast'
 import AppHeader from '@/components/header'
 import Calendar from '@/components/calendar'
-import sync, { loadSourceScene, loadTargetScene, setPanoWithBim, flyToP1P2} from '@/utils/sync'
+import sync, { beforeChangeURL, loadSourceScene, loadTargetScene, setPanoWithBim, flyToP1P2} from '@/utils/sync'
 
 // 是否BIM模式
 const showBim = ref(browser.urlHasValue('bim'))
@@ -108,9 +108,16 @@ const scenes = computed(() => {
     })
 })
 const sourceURL = computed(() => {
+
+    beforeChangeURL('source' ) 
+
     if (bimChecked.value && !dbsChecked.value) {
         return `smart-bim.html?m=${project.value.bimData.bimOssFilePath}`
     }
+       
+    if(!source.value){
+        return
+    }
 
     if (source.value.type < 2) {
         // 看看、看见场景
@@ -424,6 +431,7 @@ onMounted(() => {
         .then(response => {
             if (response.success) {
                 if (response.data) {
+                    document.title = response.data.projectName
                     if (response.data.panos) {
                         try {
                             response.data.panos = JSON.parse(response.data.panos)
@@ -437,7 +445,10 @@ onMounted(() => {
  
                     }
                     project.value = response.data
-                    if (project.value.sceneList.length) {
+                    if (showBim.value) {
+                        onBimChecked()
+                    }
+                    else if (project.value.sceneList.length) {
                         if (num) {
                             source.value = project.value.sceneList.find(c => c.num == num)
                         }
@@ -447,8 +458,6 @@ onMounted(() => {
                         if (showAdjust.value || showSplit.value) {
                             onBimChecked()
                             nextTick(() => onDbsChecked())
-                        } else if (showBim.value) {
-                            onBimChecked()
                         }
                     }
                 }
@@ -678,10 +687,16 @@ main {
 .vuejs3-datepicker__calendar header .next:not(.disabled):hover {
     background: rgba(0, 0, 0, 0.3);
 }
+.vuejs3-datepicker__calendar .cell{
+    font-size:16px !important;
+    border-radius:4px;
+}
 .highlighted {
-    background: #4ebde1 !important;
+    color:#076EDE !important;
+    background: transparent !important;
 }
 .selected {
+    color:#fff !important;
     background: #0076f6 !important;
 }
 </style>

+ 374 - 301
src/utils/ConvertViews.js

@@ -14,16 +14,6 @@ export default class ConvertViews extends THREE.EventDispatcher{
     }
 
      
-    clear(o={}){
-        this.loaded = false;
-        this.sourceApp = null;
-        if(!o.dontClearTarget){
-            this.targetApp = null
-        }
-        
-        this.dispatchEvent({type:'clearBind-sameType'})
-        window.Log('clear done')
-    }
     /* 
         laser暂时做成这样: 全景模式时不跟踪pos,跟踪pano变化。点云模式时也跟踪pano变化,但移动时完全跟踪位置变化 ,所以会有左边marker在脚下,右边marker不在脚下的情况。
         
@@ -44,21 +34,31 @@ export default class ConvertViews extends THREE.EventDispatcher{
                 quaternion: player.quaternion.clone(),
                 fov: player.zoomFov,
             }
+        }else{
+            let bimViewer = app.viewer
+            let info = bimViewer.getCameraStatus();
+            return {
+                position: info.position,
+                target: info.target,
+                fov: info.fov,
+            }
         }     
     }
     
     
     createTempApp(app, addsubInfo){//for mobile 
+          
         let fakeApp = {
             isFake : true, //标志是虚拟的app。每个真实的app都要带一个这个。在移动端如果大的销毁了还有小的
-            sceneType : app.sceneType, 
-            panos : app.sceneType == 'laser' ? getPanos(app.viewer.images360.panos) : getPanos(app.app.core.get('Player').model.panos.list) 
-            
+            sceneType : app.sceneType 
         }
-        
-        function getPanos(panos){ // only data
-            return panos.map(e=>{return {id:e.id, position:e.position, quaternion:e.quaternion}})
+        if(app.sceneType != 'bim'){
+            function getPanos(panos){ // only data
+                return panos.map(e=>{return {id:e.id, position:e.position, quaternion:e.quaternion}})
+            }   
+            fakeApp.panos = app.sceneType == 'laser' ? getPanos(app.viewer.images360.panos) : getPanos(app.app.core.get('Player').model.panos.list) 
         }
+         
         app.fakeApp = fakeApp
         
         if(addsubInfo){
@@ -74,7 +74,7 @@ export default class ConvertViews extends THREE.EventDispatcher{
             let images360 = app.viewer.images360
             viewInfo = {
                 displayMode : app.Potree.settings.displayMode,
-                currentPano : images360.currentPano.id,
+                currentPano :  images360.currentPano && images360.currentPano.id,
                 isAtPano : images360.isAtPano(),
                 quaternionChanged : true,
                 
@@ -87,11 +87,15 @@ export default class ConvertViews extends THREE.EventDispatcher{
                 lat : player.cameraControls.activeControl.lat,
                 zoomLevel : player.zoomLevel,
             }
+        }else{
+            viewInfo = {}
         }
         
-        viewInfo.position = cameraData.position
-        viewInfo.quaternion = cameraData.quaternion
-        viewInfo.fov = cameraData.fov
+        
+        for(let i in cameraData){
+            viewInfo[i] = cameraData[i]
+        }
+         
         
         app.fakeApp.viewInfo = viewInfo
         
@@ -102,13 +106,15 @@ export default class ConvertViews extends THREE.EventDispatcher{
         return app.sceneType == 'laser' ? app.viewer.images360.getPano(id) : app.app.core.get('Player').panos.index[id]
     } */
     
-    syncView(master, customer ){//补充一下 moveCamera的函数 
+    syncView(master, customer, convertInfo ){//同类型 相当于moveCamera的函数 
         let fakeApp = master.fakeApp;
+        convertInfo = convertInfo || this.convertInfo
         if(fakeApp.sceneType == 'laser'){
-            if(fakeApp.viewInfo.isAtPano || fakeApp.viewInfo.displayMode == 'showPanos'){ //转换朝向 
+            customer.Potree.settings.displayMode = fakeApp.viewInfo.displayMode
+            if(fakeApp.viewInfo.isAtPano || fakeApp.viewInfo.displayMode == 'showPanos'){ //不改变漫游点,仅转换朝向 
                 if( fakeApp.viewInfo.quaternionChanged){
              
-                    let diffQua = customer == this.targetApp ? this.diffQuaternion : this.diffQuaternionInvert
+                    let diffQua = customer == this.targetApp ? convertInfo.diffQua : convertInfo.diffQuaInvert
                     let quaternion = fakeApp.viewInfo.quaternion.clone().premultiply(diffQua)
                     let rotation = new THREE.Euler().setFromQuaternion(quaternion)  
                     customer.viewer.mainViewport.view.rotation = rotation
@@ -121,11 +127,11 @@ export default class ConvertViews extends THREE.EventDispatcher{
                     }
                 }
             }else{//转换朝向和位置 
-                this.receive(fakeApp.viewInfo, customer ) 
+                this.syncPosRot(fakeApp.viewInfo, customer ) 
             } 
         }else if(fakeApp.sceneType == 'kankan'){
             let player = customer.app.core.get('Player')
-            let diffLon = THREE.Math.radToDeg(customer == this.sourceApp ? -this.diffLon : this.diffLon)
+            let diffLon = THREE.Math.radToDeg(customer == this.sourceApp ? -convertInfo.diffLon : convertInfo.diffLon)
             player.cameraControls.controls.panorama.lon = fakeApp.viewInfo.lon + diffLon
             player.cameraControls.controls.panorama.lat = fakeApp.viewInfo.lat
             
@@ -141,24 +147,45 @@ export default class ConvertViews extends THREE.EventDispatcher{
     
     
     bindWithSameFakeType(sourceFakeApp, targetApp){//for mobile 实际只有一个场景,未分屏,和上一个场景相比
-        this.sourceApp = {sceneType: targetApp.sceneType,  fakeApp:sourceFakeApp} 
-        this.targetApp = targetApp
+        let sourceApp = {sceneType: sourceFakeApp.sceneType,  fakeApp:sourceFakeApp} 
+ 
         this.createTempApp(targetApp, true)
-        this.computeAveDiffLon(sourceFakeApp, targetApp.fakeApp)
-        this.sourceApp.sceneName = 'sourceApp'
-        this.targetApp.sceneName = 'targetApp'
         
+        let convertInfo = this.computeAveDiffLon(sourceFakeApp, targetApp.fakeApp)
         
-        if(this.sourceApp.sceneType == 'laser'){
-            this.computeShift() //因为有点云模式自由移动所以需要计算
-            
-        }
+        sourceApp.sceneName = 'sourceApp'
+        targetApp.sceneName = 'targetApp'
+         
         
-        this.syncView(this.sourceApp, this.targetApp)
+        if(sourceApp.sceneType == 'laser'){
+            let data = this.computeShift({sourceApp,targetApp}) //因为有点云模式自由移动所以需要计算
+            convertInfo.convertMatrix = data.convertMatrix
+            convertInfo.convertMatrixInvert = data.convertMatrixInvert
+        }
+        this.flyToPano(targetApp, sourceFakeApp.viewInfo.currentPano,{duration:0})
+        this.syncView(sourceApp, targetApp, convertInfo)
         
+        if(sourceApp.sceneType == 'laser'){
+            targetApp.viewer.mainViewport.view.applyToCamera(targetApp.viewer.mainViewport.camera)//使获得的cameraInfo正确
+        }else if(sourceApp.sceneType == 'kankan'){ 
+            targetApp.app.core.get('Player').cameraControls.activeControl.locked = false  //怎么刚加载时lock了
+            targetApp.app.core.get('Player').update()//cameraControls.activeControl.update() //使获得的cameraInfo正确
+        }        
     }
     
-    
+    flyToPano(app, panoId, o={}){
+        if(app.sceneType == 'laser'){
+            app.viewer.images360.flyToPano(Object.assign({},{ 
+                pano: app.viewer.images360.getPano(panoId)
+            },o)) 
+        }else{
+            let player = app.app.core.get('Player')
+            player.flyToPano(Object.assign({},{ 
+                pano: player.model.panos.index[panoId]
+            },o))
+             
+        }  
+    }
     
     bindWithSameType(sourceApp,targetApp, isSwitchScene){ 
         
@@ -168,13 +195,17 @@ export default class ConvertViews extends THREE.EventDispatcher{
         this.createTempApp(sourceApp)
         this.createTempApp(targetApp)
         
-        this.computeAveDiffLon(sourceApp.fakeApp, targetApp.fakeApp)
+        this.convertInfo = this.computeAveDiffLon(sourceApp.fakeApp, targetApp.fakeApp)
          
         sourceApp.sceneName = 'sourceApp'
         targetApp.sceneName = 'targetApp'
         
-        if(sourceApp.sceneType == 'laser'){
-            this.computeShift() //因为有点云模式自由移动所以需要计算
+        if(sourceApp.sceneType == 'laser'){ 
+            {
+                let data = this.computeShift({sourceApp,targetApp}) //因为有点云模式自由移动所以需要计算
+                this.convertInfo.convertMatrix = data.convertMatrix
+                this.convertInfo.convertMatrixInvert = data.convertMatrixInvert
+            }
             //只监听左边
             let displayMode = (e)=>{
                 targetApp.Potree.settings.displayMode = e.mode
@@ -199,38 +230,14 @@ export default class ConvertViews extends THREE.EventDispatcher{
                     customer.viewer.images360.flyToPano({pano} )
                 }
                 master.viewer.images360.addEventListener('flyToPano',flyToPano)
-             
-                
-                
+              
                 var cameraMove = (e)=>{ 
                     if(master != this.masterApp || !customer.viewer )return
                     
                     this.addViewInfo(master)
                     
                     master.fakeApp.viewInfo.quaternionChanged = e.changeInfo && e.changeInfo.quaternionChanged
-                    this.syncView(master, customer)
-                    
-                    /* //console.log('cameraMove')
-                    if(master.viewer.images360.isAtPano() || master.Potree.settings.displayMode == 'showPanos'){ //转换朝向 
-                        if(e.changeInfo && e.changeInfo.quaternionChanged){
-                            let data = this.getCameraData(master)
-                            let diffQua = master == this.sourceApp ? this.diffQuaternion : this.diffQuaternionInvert
-                            let quaternion = data.quaternion.premultiply(diffQua)
-                            let rotation = new THREE.Euler().setFromQuaternion(quaternion)  
-                            customer.viewer.mainViewport.view.rotation = rotation
-                            //console.log('cameraMove',customer == this.targetApp) 
-                        }
-                        if(master.Potree.settings.displayMode == 'showPanos' ){
-                            if(customer.viewer.mainViewport.camera.fov != master.viewer.mainViewport.camera.fov){
-                                customer.viewer.mainViewport.camera.fov = master.viewer.mainViewport.camera.fov
-                                customer.viewer.mainViewport.camera.updateProjectionMatrix()
-                            }
-                        }
-                    }else{//转换朝向和位置
-                        let data = this.getCameraData(master)
-                        this.receive(data, customer ) 
-                    }  */
-                                            
+                    this.syncView(master, customer) 
                 } 
                 master.viewer.addEventListener('camera_changed',cameraMove)
                 
@@ -258,29 +265,16 @@ export default class ConvertViews extends THREE.EventDispatcher{
                 
                 
                 var cameraMove = (e)=>{//暂时只有漫游模式
-                    if(!e.hasChanged.cameraChanged)return
+                    if(!e.hasChanged.cameraChanged || !customer.app || !customer.app.core)return
                     
                     this.addViewInfo(master)
-                    this.syncView(master, customer)
-                    
-                    /* let diffLon = master == this.sourceApp ? this.diffLon : -this.diffLon
-                    player2.cameraControls.controls.panorama.lon = player1.cameraControls.controls.panorama.lon + diffLon
-                    player2.cameraControls.controls.panorama.lat = player1.cameraControls.controls.panorama.lat
-                    
-                    if(player2.zoomLevel != player1.zoomLevel){
-                        player2.zoomTo(player1.zoomLevel)
-                    } */
-                    
+                    this.syncView(master, customer) 
                 }
                 player1.on("update",cameraMove)
-                
-                
+                 
             }
             
-           
-        
-        
-        
+            
             
             let changeMaster = ()=>{
                 this.masterApp = master  //主控方。只有主控方能控制被控方。鼠标操作过mousedown mousewheel等才能认定为主控方
@@ -325,8 +319,7 @@ export default class ConvertViews extends THREE.EventDispatcher{
                 this.addViewInfo(master)
                 this.syncView(master, customer)
                     
-                
-                
+                 
                 if(master.sceneType == 'laser'){
                     customer.Potree.settings.displayMode = master.Potree.settings.displayMode
                     let pano = master.viewer.images360.nextPano || master.viewer.images360.currentPano
@@ -349,15 +342,147 @@ export default class ConvertViews extends THREE.EventDispatcher{
     
     
     
+    bimGetPanoData(sourceApp, targetApp, panoData){
+        if(panoData){
+            let sourcePano,targetPano 
+            let pano1 = [{position:new THREE.Vector3().copy(panoData.p1.position)},{position:new THREE.Vector3().copy(panoData.p2.position)}]
+            
+            let getPano2 = (app)=>{
+                return [app.fakeApp.panos.find(e=>e.id == panoData.p1.id), app.fakeApp.panos.find(e=>e.id == panoData.p2.id)] 
+            }
+            
+            if(targetApp.sceneType == 'bim'){ 
+                targetPano = pano1 
+                sourcePano = getPano2(sourceApp)
+            }else{ 
+                targetPano = getPano2(targetApp) 
+                sourcePano = pano1
+            }
+            return {sourcePano, targetPano} 
+        }else return {}
+    }
+    
+    
+    getTranPosData(data, convertInfo, ifRevert ){
+        let position = new THREE.Vector3, target = new THREE.Vector3
+        
+        if(data.position){
+            position = new THREE.Vector3().copy(data.position)
+        } 
+        if(!data.target){
+            if(data.quaternion){ 
+                let dir = new THREE.Vector3(0, 0, -1).applyQuaternion(data.quaternion)
+                target.copy(position).add(dir) 
+            }
+        }else{ 
+            target.copy(data.target) 
+        } 
+        
+        if(ifRevert){
+            position.applyMatrix4(convertInfo.convertMatrixInvert)
+            target.applyMatrix4(convertInfo.convertMatrixInvert)
+            if(convertInfo.convertAxis){
+                position = math.convertVector[convertInfo.convertAxis](position)
+                target = math.convertVector[convertInfo.convertAxis](target)
+            }
+        }else{
+            if(convertInfo.convertAxis){
+                position = math.convertVector[convertInfo.convertAxis](position)
+                target = math.convertVector[convertInfo.convertAxis](target)
+            }
+
+            position.applyMatrix4(convertInfo.convertMatrix)
+            target.applyMatrix4(convertInfo.convertMatrix)
+        }
+        return {position, target}
+    }
+    
+    bindFakeWithBim(sourceFakeApp, targetApp, panoData ){// bim和其他类型互转
+        if(!panoData)return
+    
+    
+        let sourceApp = {sceneType: sourceFakeApp.sceneType,  fakeApp:sourceFakeApp} 
+    
+        this.createTempApp(targetApp)
+        let {sourcePano, targetPano} = this.bimGetPanoData(sourceApp, targetApp, panoData) 
+        
+        let convertAxis = sourceApp.sceneType == 'kankan' ? 'YupToZup' : targetApp.sceneType == 'kankan' ? 'ZupToYup' : null
+             
+        let convertInfo = this.computeShift({sourcePano, targetPano, convertAxis})  
+       
+        console.log('convertInfo', convertInfo, sourcePano, targetPano)
+         
+         
+        let selectBestPose = ()=>{
+            
+            let data = this.getTranPosData(sourceFakeApp.viewInfo, convertInfo ) 
+  
+            let panos = targetApp.fakeApp.panos;
+            
+            let panos2 = panos.sort((a,b)=>{ 
+                return data.position.distanceToSquared(a.position) - data.position.distanceToSquared(b.position)
+            })
+            let dir = new THREE.Vector3().subVectors( data.target, data.position )
+            console.log('dir', dir)
+            let prop = { duration:0,}
+            if(targetApp.sceneType == 'laser'){ 
+                targetApp.viewer.mainViewport.view.direction = dir  
+            }else{
+                let player = targetApp.app.core.get('Player') 
+                console.log('nearest:', panos2[0].id)
+                prop.aimDuration = 0                   
+                prop.lookAtPoint = new THREE.Vector3().addVectors(panos2[0].position, dir)
+
+            } 
+            this.flyToPano(targetApp, panos2[0].id, prop)     
+            
+            
+        } 
+        
+        if(targetApp.sceneType == 'bim'){
+            bimViewer = targetApp.viewer
+            bimViewer.getViewer().setTransitionAnimationState(false)
+            targetApp.CLOUD.GlobalData.WalkRotationSpeed = -0.2 //反向一下
+        }
+        
+        //this.syncView(sourceApp, targetApp)
+        if(targetApp.sceneType == 'bim' /* || this.ifCanChangePos(targetApp) */){
+            
+            this.syncPosRot(sourceFakeApp.viewInfo, targetApp, convertInfo) 
+            
+        }else if(targetApp.sceneType == 'laser' ){
+            setTimeout(()=>{//一开始虽然是点云模式,但过后又变成showPano所以是没加载好
+                if(this.ifCanChangePos(targetApp) ){
+                    this.syncPosRot(sourceFakeApp.viewInfo, targetApp, convertInfo) 
+                }else{
+                    selectBestPose()
+                }
+                
+            },1000)
+        
+        
+        }else{//bim -> 固定点位
+            selectBestPose()
+             
+        }
+        
+    }
+    
+    
      
-    bindWithBim(sourceApp, targetApp,   sourcePano, targetPano  ) {
+     
+    bindWithBim(sourceApp, targetApp, panoData ) {
         //if (!this.player1.model.panos.list.length || !this.player2.model.panos.list.length) return
         
         if(this.loaded || !targetApp ) return 
         let needBindEvent = !this.targetApp // 若targetApp存在表明targetApp的dom未换掉,事件还存在
+        this.createTempApp(sourceApp)
+        this.createTempApp(targetApp)
+        let {sourcePano, targetPano} = this.bimGetPanoData(sourceApp, targetApp, panoData)
+          
         this.sourceApp = sourceApp
         this.targetApp = targetApp
-        let data = this.getCameraData(sourceApp)
+        
         let modelSize = new THREE.Vector3
         bimViewer = this.bimViewer = targetApp.viewer 
         let modelBound = bimViewer.getViewer().modelManager.boundingBox
@@ -366,21 +491,22 @@ export default class ConvertViews extends THREE.EventDispatcher{
         bimViewer.setFlySpeedRate(THREE.MathUtils.clamp(  modelSize.length() / 10, 1, 6)) //会被限制
         //bimViewer.getViewer().setWalkSpeedRate(2)
         
-        let camera = bimViewer.getViewer().camera
-        if(camera.fov != data.fov){
-            camera.fov = data.fov
-            camera.updateProjectionMatrix()
-        }
-       
+        
+        
+        this.sourceDom = sourceApp.sceneType == 'laser' ? this.sourceApp.viewer.inputHandler.domElement : this.sourceApp.app.core.get('Player').domElement
        
         if(targetPano){
             bimViewer.getViewer().setTransitionAnimationState(false) //setCameraStatus瞬间变化相机 ,or setCameraAnimation?
             
             
-            this.needConvertAxis = sourceApp.sceneType == 'kankan' && targetApp.sceneType == 'bim'// Y朝上需要转换
+            var convertAxis = sourceApp.sceneType == 'kankan' && targetApp.sceneType == 'bim' && 'YupToZup'// Y朝上需要转换
             
             this.lastCamStatus = bimViewer.getCameraStatus()
-            this.computeShift(sourcePano, targetPano)
+            
+            this.convertInfo = this.computeShift({sourcePano, targetPano, convertAxis})
+            
+            
+            
             bimViewer.addEventListener('Rendered', (e)=>{//反向改变左侧相机
                  
                 let info = bimViewer.getCameraStatus() 
@@ -389,53 +515,82 @@ export default class ConvertViews extends THREE.EventDispatcher{
                     || !math.closeTo(this.lastCamStatus.fov, info.fov)
                 
                 if(poseChanged){ 
-                    if(this.leftCanChangePos()){
+                    if(this.ifCanChangePos(this.sourceApp)){
                         this.send(info)
                         this.lastCamStatus = info 
                     }  
                 } 
                 
             })  
-            if(sourceApp.sceneType == 'laser'){
-                this.sourceDom = this.sourceApp.viewer.inputHandler.domElement  
-                sourceApp.viewer.addEventListener('camera_changed', e => {
-                    targetApp && this.receive(this.getCameraData(sourceApp))
-                })
-                //master.viewer.images360.isAtPano() || master.Potree.settings.displayMode == 'showPanos'
-                /* if(this.lastBimStatus){
-                    this.lastBimStatus
-                    let pano 
-                    if(this.lastBimStatus.panoId != void 0) pano = this.sourceApp.viewer.images360.panos[this.lastBimStatus.panoId]
-                    this.sourceApp.viewer.dispatchEvent({type:'camera_changed',changeInfo:{quaternionChanged:true},viewport:this.sourceApp.viewer.mainViewport }) //朝向位置同步
-                    
-                    pano && customer.viewer.images360.flyToPano({pano, duration: 0 }) 
-                } */
-                
+            
+            if(needBindEvent){
+                this.bindCamEvent()  
+            }else{//替换的左侧的,需要使左侧和右侧同步, 其实是左侧要和上一个左侧先同步,再让右侧和左侧同步
+                 
+                this.bindWithSameFakeType(this.lastFakeApp, sourceApp)
+                 
+            }
+            
+            {
                 
-            }else if(sourceApp.sceneType == 'kankan'){
-                let player = this.sourceApp.app.core.get('Player')
-                this.sourceDom = player.domElement 
-                var cameraMove = (e)=>{//暂时只有漫游模式
-                    if(!e.hasChanged.cameraChanged2)return
-                    this.receive(this.getCameraData(sourceApp)) 
-                }
-                player.on("update",cameraMove)
+                let cameraMove
+                if(sourceApp.sceneType == 'laser'){ 
+                    cameraMove = e => {
+                        targetApp && this.syncPosRot(this.getCameraData(sourceApp))
+                    }   
+                    sourceApp.viewer.addEventListener('camera_changed', cameraMove)
+                }else if(sourceApp.sceneType == 'kankan'){
+                    var player = this.sourceApp.app.core.get('Player')
+                    //this.sourceDom = player.domElement 
+                    cameraMove = (e)=>{//暂时只有漫游模式
+                        if(!e.hasChanged.cameraChanged2)return
+                        //console.log('cameraMove', this.getCameraData(sourceApp)) 
+                        this.syncPosRot(this.getCameraData(sourceApp)) 
+                    }
+                    player.on("update",cameraMove) 
+                } 
+                 
+                let dispose = ()=>{ 
+                    if(sourceApp.sceneType == 'laser'){
+                        //if(!sourceApp.viewer || !sourceApp.viewer.images360)return
+                        sourceApp.viewer.removeEventListener('camera_changed', cameraMove)
+                    }else{
+                        //if(!sourceApp.app || !sourceApp.app.core)return
+                        player.off("update",cameraMove) 
+                    } 
+                    this.removeEventListener('clearBind-sameType',dispose)
+                } 
+                this.addEventListener('clearBind-sameType',dispose) 
             }
             
             /* bimViewer.addEventListener(targetApp.Glodon.Bimface.Viewer.Viewer3DEvent.ViewAdded,
                 ()=>{
                     this.loaded = true
                     if(this.firstData){
-                        this.receive(this.firstData)
+                        this.syncPosRot(this.firstData)
                     }
                 }
             ) */
             
-            needBindEvent && this.bindCamEvent() 
+            
+            
+            let data = this.getCameraData(sourceApp)  
+            this.syncPosRot(data)
             this.loaded = true
-            this.receive(data)
         }else{
-             
+            //分屏 不同步
+            
+            let data = this.getCameraData(sourceApp)
+            let camera = bimViewer.getViewer().camera
+            if(camera.fov != data.fov){
+                camera.fov = data.fov
+                camera.updateProjectionMatrix()
+            }
+            
+            
+            
+            //补充control
+            
             bimViewer.getViewer().animator.setDuration(60)//滚轮缩放时长,原先:1000
           
             let baseSpeed = THREE.MathUtils.clamp( modelSize.length() / 10, 1, 10)
@@ -446,21 +601,47 @@ export default class ConvertViews extends THREE.EventDispatcher{
                 let info = bimViewer.getCameraStatus()  
                 let dis = modelBound.distanceToPoint(info.position)
                 let speed = baseSpeed + dis / 8
-                console.log('speed', speed)
+                //console.log('speed', speed)
                
                 this.bimFlyTo({forwardDis: e.wheelDelta > 0 ? speed : -speed})
-            })
+            }) 
             
-        }
-         
-        
-        
-        
-          
+            //右键pan
+            let dragging , pointerDelta = new THREE.Vector2, pointerStart = new THREE.Vector2
+            dom.addEventListener('mousedown', e => {  
+                if(e.button == 2){//右键
+                    dragging = true
+                    pointerStart.set(e.clientX, e.clientY)
+                }
+            }) 
+            dom.addEventListener('mousemove', e => {   
+                if(!dragging)return
+                let pointerEnd = new THREE.Vector2(e.clientX, e.clientY) 
+                pointerDelta.subVectors(pointerEnd, pointerStart)
+                //pointerDelta.multiplyScalar(0.07)
+                pointerStart.copy(pointerEnd)
+                
+                bimViewer.getViewer().cameraControl.pan(pointerDelta.x,pointerDelta.y)
+            }) 
+            targetApp.addEventListener('mouseup', e => {   
+                dragging = false
+            }) 
+            this.sourceDom.addEventListener('mouseup', e => {   
+                dragging = false 
+            }) 
+            this.addEventListener('globalMouseUp', e => {   
+                dragging = false
+            }) 
+            
+            targetApp.CLOUD.GlobalData.WalkRotationSpeed = -0.2 //反向一下
+             
+            //bimViewer.viewer.getViewer().editorManager.userInputEditor.enable = true//这句近似将control切换成orbit
+            
+        }    
     }
     
-    leftCanChangePos(){
-        return this.sourceApp.sceneType == 'laser' && this.sourceApp.Potree.settings.displayMode != 'showPanos'
+    ifCanChangePos(app){
+        return app.sceneType == 'laser' && app.Potree.settings.displayMode != 'showPanos'   //app.fakeApp.viewInfo.displayMode != 'showPanos'
     }
     
     
@@ -561,16 +742,17 @@ export default class ConvertViews extends THREE.EventDispatcher{
         app.viewer.mainViewport.view.lookAt(data.target)
     }
     
-    receive(data, customer){
-        
+    
+    
+    syncPosRot(data, customer, convertInfo ){//同步 自由位置和朝向(不被漫游点束缚时)
+        /* 
         if(!this.loaded){
             return this.firstData = data
-        }
-        /* if(this.isMaster){
-            return //正在操作当前,不接收 
         } */
-        
-        let position = new THREE.Vector3, target = new THREE.Vector3
+        convertInfo = convertInfo || this.convertInfo
+        let {position,target} = this.getTranPosData(data, convertInfo ) 
+
+        /* let position = new THREE.Vector3, target = new THREE.Vector3
        
         if(data.position){
             position = new THREE.Vector3().copy(data.position)
@@ -580,30 +762,20 @@ export default class ConvertViews extends THREE.EventDispatcher{
         
         if(!data.target){
             if(data.quaternion){ 
-                /* if(this.needConvertAxis){
-                    data.quaternion = math.convertQuaternion.YupToZup(data.quaternion)
-                } */
                 let dir = new THREE.Vector3(0, 0, -1).applyQuaternion(data.quaternion)
-                //dir.applyQuaternion(this.diffQuaternion)/////!
-                 
-                
                 target.copy(position).add(dir) 
             }
-        }else{
-            if(this.needConvertAxis){
-                target = math.convertVector.YupToZup(target)
-            }else{
-                target.copy(data.target)
-            } 
+        }else{ 
+            target.copy(data.target) 
         }
         
-        if(this.needConvertAxis){
-            position = math.convertVector.YupToZup(position)
-            target = math.convertVector.YupToZup(target)
+        if(convertInfo.convertAxis){
+            position = math.convertVector[convertInfo.convertAxis](position)
+            target = math.convertVector[convertInfo.convertAxis](target)
         }
 
-        position.applyMatrix4(this.convertMatrix)
-        target.applyMatrix4(this.convertMatrix)
+        position.applyMatrix4(convertInfo.convertMatrix)
+        target.applyMatrix4(convertInfo.convertMatrix) */
 
         if(customer && customer.sceneType == 'laser'){
             this.laserSyncView(customer, {position,target})
@@ -625,41 +797,25 @@ export default class ConvertViews extends THREE.EventDispatcher{
                 camera.updateProjectionMatrix()
             }
 
-            //fov, near,  far
-            /*   aspect: 0.7879440258342304
-                coordinateSystem: "world"
-                far: 11485.989363357028
-                fov: 45
-                name: "persp"
-                near: 1.1852000000072447
-                position: {x: -1130.0432094639486, y: -6058.569138159733, z: 2265.9284566100446}
-                target: {x: 310.3968263091223, y: -66.0595010237127, z: 1477.7045866099475}
-                up: {x: 0, y: 1.534753124827774e-13, z: 1}
-                version: 1
-                zoom: 0 */
-
         }
 
     }
 
 
     send(info){ 
-        let camera = this.bimViewer.getViewer().camera
-        
-        let data = { 
-            position : new THREE.Vector3().copy(info.position).applyMatrix4(this.convertMatrixInvert),
+        //let camera = bimViewer.getViewer().camera
+        let data = this.getTranPosData(info, this.convertInfo, true ) 
+        /* let data = { 
+            position : new THREE.Vector3().copy(info.position).applyMatrix4(this.convertInfo.convertMatrixInvert),
             //quaternion : camera.quaternion.clone().applyMatrix4(this.convertMatrix),
-            target : new THREE.Vector3().copy(info.target).applyMatrix4(this.convertMatrixInvert),
+            target : new THREE.Vector3().copy(info.target).applyMatrix4(this.convertInfo.convertMatrixInvert),
         }  
         
-        if(this.needConvertAxis){
-            data.position = math.convertVector.ZupToYup(data.position)
-            data.target = math.convertVector.ZupToYup(data.target)
-        }
-        /* this.dispatchEvent({
-            type: 'sendCameraData',
-            data
-        }) */
+        if(this.convertInfo.convertAxis){
+            data.position = math.convertVector[this.convertInfo.convertAxis](data.position)
+            data.target = math.convertVector[this.convertInfo.convertAxis](data.target)
+        } */
+         
         this.laserSyncView(this.sourceApp, data) //左侧只有laser点云模式才能接收到
     } 
 
@@ -676,25 +832,7 @@ export default class ConvertViews extends THREE.EventDispatcher{
         let panoPos2 = targetFakeApp.panos.map(e=>{
             return e.position
         })    
-            
-        /* if(this.sourceApp.sceneType == 'laser'){
-            panoPos1 = this.sourceApp.viewer.images360.panos.map(e=>{
-                return e.position
-            })
-            panoPos2 = this.targetApp.viewer.images360.panos.map(e=>{
-                return e.position
-            }) 
              
-        }else{
-            panoPos1 = this.sourceApp.app.core.get('Player').model.panos.list.map(e=>{
-                return e.position
-            })
-            panoPos2 = this.targetApp.app.core.get('Player').model.panos.list.map(e=>{
-                return e.position
-            })  
-        } */
-        
-        
         length = panoPos1.length
 
         //挑选连续的两个点为向量来计算,如有123个漫游点,则选取12 23 31作为向量
@@ -717,33 +855,35 @@ export default class ConvertViews extends THREE.EventDispatcher{
         diffLonAve /= length
         console.log('diffLonAve', diffLonAve)
         
-        this.diffLon = diffLonAve
-        this.diffQuaternion = new THREE.Quaternion().setFromAxisAngle(new THREE.Vector3(0, 1, 0), this.diffLon)
-        this.diffQuaternionInvert = this.diffQuaternion.clone().invert()
-        
+        let diffQua = new THREE.Quaternion().setFromAxisAngle(new THREE.Vector3(0, 1, 0), diffLonAve) 
         
+        return {
+            diffLon : diffLonAve,
+            diffQua  ,
+            diffQuaInvert : diffQua.clone().invert() 
+        } 
         
     }
 
-    computeShift(sourcePano, targetPano) { //获取两个场景的旋转和位移偏差值
+    computeShift(o={}/* sourcePano, targetPano */) { //获取两个场景的旋转和位移偏差值
         //需要点的个数>1, 且两个场景点一一对应,位置接近且顺序一致
         
         let panoPos1, panoPos2
          
-        if(this.sourceApp.sceneType == this.targetApp.sceneType){
+        if(o.sourceApp && o.targetApp && o.sourceApp.sceneType == o.targetApp.sceneType){
             var angle = this.diffLon; //直接使用 更精准
-            panoPos1 = this.sourceApp.fakeApp.panos.map(e=>{
+            panoPos1 = o.sourceApp.fakeApp.panos.map(e=>{
                 return e.position
             })
-            panoPos2 = this.targetApp.fakeApp.panos.map(e=>{
+            panoPos2 = o.targetApp.fakeApp.panos.map(e=>{
                 return e.position
             }) 
         }else{
-            panoPos1 = sourcePano.map(e=>e.position) //pick两个点来计算
-            panoPos2 = targetPano.map(e=>e.position)
-        
-            if(this.needConvertAxis){
-                panoPos1 = panoPos1.map(e=>math.convertVector.YupToZup(e))
+            panoPos1 = o.sourcePano.map(e=>e.position) //pick两个点来计算
+            panoPos2 = o.targetPano.map(e=>e.position)
+             
+            if(o.convertAxis){
+                panoPos1 = panoPos1.map(e=>math.convertVector[o.convertAxis](e))
             }
             var vec1 = new THREE.Vector3().subVectors(panoPos1[0], panoPos1[1]) //旧的向量
             var vec2 = new THREE.Vector3().subVectors(panoPos2[0], panoPos2[1])//新的向量
@@ -761,11 +901,8 @@ export default class ConvertViews extends THREE.EventDispatcher{
         matrix.premultiply(moveBackMatrix)//再移动到realPosition的点0处
 
 
-
-        this.convertMatrix = matrix
-        this.convertMatrixInvert = matrix.clone().invert()
-        
-        
+        return { convertMatrix:  matrix, convertMatrixInvert:matrix.clone().invert(), convertAxis:o.convertAxis}
+          
 
     }
 
@@ -786,90 +923,26 @@ export default class ConvertViews extends THREE.EventDispatcher{
     }
 
 
-
-
-
-    /* applyDiff(app) {
-        //sourcePlayer -> targetPlayer
-        if (!this.player1 || !this.player2 || this.targetApp.config.num == this.sourceApp.config.num) return //场景码相同的话返回
-        if (this.player1.mode != this.player2.mode) return
-
-        let player1, player2, quaternion //player1为要改变的, player2是参照
-        if (app == this.sourceApp) {
-            player1 = this.player1
-            player2 = this.player2
-            quaternion = this.diffQuaternion
-        } else {
-            player1 = this.player2
-            player2 = this.player1
-            quaternion = this.diffQuaternionInvert
-        }
-
-        let control1 = player1.cameraControls.activeControl
-        let control2 = player2.cameraControls.activeControl
-        //if(!control1 || !control2)return
-
-        player1.quaternion.copy(player2.quaternion).premultiply(quaternion)
-
-        if (player1.mode == 'panorama') {
-            //平移
-            let dir = new THREE.Vector3().subVectors(control2.target, player2.position)
-            dir.applyQuaternion(quaternion)
-            let target1 = new THREE.Vector3().addVectors(player1.position, dir)
-            control1.lookAt(target1)
-            control1.target.copy(target1)
-        } else if (control2) {
-            //修改target,保证target在panos之间的相对位置一样
-            //console.log('target', control2.target.clone())
-            //console.log('position', control2.target.clone())
-            let vec = new THREE.Vector3().subVectors(control2.target, player2.model.panos.list[0].position)
-            vec.applyQuaternion(quaternion)
-            control1.target.addVectors(player1.model.panos.list[0].position, vec)
-            player1.target.copy(control1.target)
-            //修改position,保证方向一样
-            let dir = new THREE.Vector3().subVectors(control2.camera.position , control2.target)
-            dir.applyQuaternion(quaternion)
-            player1.position = new THREE.Vector3().addVectors(control1.target, dir)
-
-            control1.camera.position.copy(player1.position)
-        }
-        control1.camera.quaternion.copy(player1.quaternion)
-    } */
-
-    /* applyDiff(app, data) {
-        //sourcePlayer -> targetPlayer
-
-        let quaternion
-        if (data.quaternion) {
-            quaternion = new THREE.Quaternion().copy(data.quaternion)
-            data.quaternion = quaternion
-        } else if (data.info && data.info.quaternion) {
-            //飞出
-            quaternion = new THREE.Quaternion(data.info.quaternion._x, data.info.quaternion._y, data.info.quaternion._z, data.info.quaternion._w)
-            data.info.quaternion = quaternion
-            //let radius = data.info.position.distanceTo(data.info.target)
-        }
-        if (!quaternion) return
-
-        if (app == this.sourceApp) {
-            quaternion.premultiply(this.diffQuaternionInvert)
-        } else {
-            quaternion.premultiply(this.diffQuaternion)
-        }
-
-        if (data.info && data.info.quaternion) {
-            //飞出
-            let dir = new THREE.Vector3().subVectors(data.info.position, data.info.target)
-            dir.applyQuaternion(app == this.sourceApp ? this.diffQuaternionInvert : this.diffQuaternion)
-            data.info.position = new THREE.Vector3().addVectors(data.info.target, dir)
+    clear(o={}){
+        this.loaded = false;
+        
+        
+        
+        if(o.dontClearTarget){
+            if(this.sourceApp){
+                this.lastFakeApp = this.sourceApp.fakeApp //记住当前左屏
+                this.addViewInfo(this.sourceApp)
+            }
+        }else{ 
+            this.targetApp = null
+            this.lastFakeApp = null
         }
-
-         
-
-        //先不管飞出后的位置平移
-
-        //位置参照第一个漫游点。保持相机相对第一个漫游点的位移和
-    } */
+        
+        this.sourceApp = null;
+        this.dispatchEvent({type:'clearBind-sameType'})
+        window.Log('clear done')
+    }
+ 
 }
 
 

+ 46 - 40
src/utils/sync.js

@@ -8,7 +8,7 @@ let sourceApp = null,
   
 const isEdit = browser.urlHasValue('adjust')
 
-let panoData = {p1:{id:0},p2:{id:1}}//默认
+let panoData //= {p1:{id:0},p2:{id:1}}//默认
 let targetPano /* = isEdit ? null : [//targetPano
                         {position: new THREE.Vector3( -5.313605730801787,  -4.889868407960505,  1.237447893355817),},
                         {position: new THREE.Vector3( -5.337403524084278,  -2.5012228235167737, 1.2808838933558175),} 
@@ -16,8 +16,7 @@ let targetPano /* = isEdit ? null : [//targetPano
 export function setPanoWithBim(data){
     if(!isEdit){
         panoData = data 
-        targetPano = [{position:new THREE.Vector3().copy(data.p1.position)},{position:new THREE.Vector3().copy(data.p2.position)}]
-    }  
+     }  
 }
 
 export function flyToP1P2(data){
@@ -34,36 +33,26 @@ export function flyToP1P2(data){
     }
 }
 
-
+/* const getSourcePanos = (sourceApp)=>{
+    let sourcePanos
+    if(sourceApp.sceneType == 'laser'){  
+        sourcePanos = [sourceApp.viewer.images360.panos[panoData.p1.id], sourceApp.viewer.images360.panos[panoData.p2.id]], //sourceApp.viewer.images360.panos.slice(0, 2),
+          
+        sourceApp.Potree.settings.rotAroundPoint = false
+        
+    }else if(sourceApp.sceneType == 'kankan'){ 
+        sourcePanos = [sourceApp.app.core.get('Player').model.panos.index[panoData.p1.id], sourceApp.app.core.get('Player').model.panos.index[panoData.p2.id]],//sourceApp.app.core.get('Player').model.panos.list.slice(0, 2), 
+        
+    }
+    return sourcePanos
+} */
  
 const initConvertView = (isSwitchScene) => {  
 
     if (sourceApp && targetApp) {
-        if(targetApp.sceneType == 'bim'){
-              
-            if(sourceApp.sceneType == 'laser'){ 
-                views.bindWithBim(
-                    sourceApp,
-                    targetApp, 
-                    [sourceApp.viewer.images360.panos[panoData.p1.id], sourceApp.viewer.images360.panos[panoData.p2.id]], //sourceApp.viewer.images360.panos.slice(0, 2),
-                    
-                    targetPano
-                     
-                )
-                sourceApp.Potree.settings.rotAroundPoint = false
-                
-            }else if(sourceApp.sceneType == 'kankan'){
-                
-                views.bindWithBim(
-                    sourceApp,
-                    targetApp,
-                    [sourceApp.app.core.get('Player').model.panos.index[panoData.p1.id], sourceApp.app.core.get('Player').model.panos.index[panoData.p2.id]],//sourceApp.app.core.get('Player').model.panos.list.slice(0, 2), 
-                    targetPano,
-                     
-                )
-                
-                
-            }
+        if(targetApp.sceneType == 'bim'){  
+            views.bindWithBim( sourceApp, targetApp, panoData/* getSourcePanos(sourceApp),  targetPano */) 
+            
         }else if(sourceApp.sceneType == targetApp.sceneType){
             
             views.bindWithSameType(sourceApp,targetApp, isSwitchScene)
@@ -72,16 +61,36 @@ const initConvertView = (isSwitchScene) => {
             
     }
 }
+
+export function singleConvert(lastFakeApp, targetApp ){//单屏转换
+
+    if(targetApp.sceneType == 'bim'){
+         
+        views.fakeWithBim(lastFakeApp, targetApp, getSourcePanos(sourceApp), targetPano)
+    } 
+    
+}
+
+let isSwitchScene
+
+ 
+export function beforeChangeURL(which  ){
+    //if (views.loaded ) {
+        isSwitchScene = true
+        views.clear({ dontClearTarget: targetApp && targetApp.sceneType == 'bim' })
+    //} 
+}
+
 /**
  * 左屏加载
  * @param {String} type kankan|laser
  */
 export function loadSourceScene(sourceFrame,type) {
-    let isSwitchScene 
-    if (views.loaded ) {
+     
+    /* if (views.loaded ) {
         isSwitchScene = true
         views.clear({ dontClearTarget: targetApp.sceneType == 'bim' })
-    }
+    } */
     
     Log('loadSourceScene, ' + type)
     sourceApp = window.app1 = null 
@@ -151,13 +160,7 @@ export function loadTargetScene(targetFrame, type, mode) {
             loaded()
         }) 
         
-    }        
-    
-    
-    
-    
-    
-     
+    }     
 
 }
 
@@ -197,8 +200,10 @@ function laserLoaded(app){
 
 window.addEventListener('mouseup',(e)=>{
     //iframe的window的mouseup 在拖拽出窗口外居然不执行,只好用全局的通知它们
-    targetApp && targetApp.sceneType == 'laser' && targetApp.viewer && targetApp.viewer.inputHandler.onMouseUp(e) 
     sourceApp && sourceApp.sceneType == 'laser' && sourceApp.viewer && sourceApp.viewer.inputHandler.onMouseUp(e)  
+    targetApp && targetApp.sceneType == 'laser' && targetApp.viewer && targetApp.viewer.inputHandler.onMouseUp(e) 
+    views.dispatchEvent({type:'globalMouseUp'})
+
 })
 
   
@@ -210,6 +215,7 @@ export default {
     get targetInst() {
         return targetApp
     },
+    
 }
 
 /*