<template>
<div class="pl-tabs-panel" :title="title" :style="tabStyle">
<div class="pl-loading pl-loading-fixed" v-show="url && !loaded" ref="dom-loader">
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
</div>
<iframe v-if="hasUrl" @load="handleIframeLoad" :name="'iframe' + name" ref="iframe"></iframe>
<slot v-if="!hasUrl"></slot>
</div>
</template>
<script>
import { getUrlValue, setUrlValue, getUrlSearch } from "@main/utils";
import { getToken } from '@main/utils/auth'
export default {
name: 'PTabpanel',
props: {
close: [String, Number, Boolean],
itemData: Object,
title: {
type: String,
default: ""
},
name: {
type: [String, Number],
default: ""
},
url: {
type: [String],
default: ""
},
index: [String, Number]
},
data() {
return {
scrollTop: 0,
loaded: false,
loadTimer: null
}
},
computed: {
tabStyle() {
return {
position: "absolute",
width: "100%",
top: this.active ? 0 : "-200%",
left: 0,
opacity: this.active ? 1 : 0,
visibility: this.active ? "visible" : "hidden",
};
},
active() {
return this.$parent.currentName === this.name;
},
//hasUrl改为计算属性,动态监听url变化
hasUrl() {
return !(this.url == null || this.url === '');
}
},
watch: {
active(val) {
let ifm = this.$refs["iframe"];
if (val) {
this.setIframeSrc();
if (ifm && ifm.contentDocument) {
this.$nextTick(() => {
//保持原有的滚动位置
ifm.contentDocument.documentElement.scrollTop = this.scrollTop;
});
}
} else {
if (ifm && ifm.contentDocument) {
//保持原有的滚动位置
this.scrollTop = ifm.contentDocument.documentElement.scrollTop;
}
}
}
},
updated() {
this.$parent.$emit('tab-nav-update');
},
mounted() {
if (this.active) {
this.setIframeSrc();
}
},
beforeDestroy() {
this.clearLoadTimer();
},
methods: {
clearLoadTimer() {
if (this.loadTimer) {
clearTimeout(this.loadTimer);
this.loadTimer = null;
}
},
// 启动加载超时兜底
startLoadTimer() {
this.clearLoadTimer();
this.loadTimer = setTimeout(() => {
this.loaded = true;
}, 12000);
},
setIframeSrc() {
let ifm = this.$refs['iframe'];
if (!this.hasUrl || this.loaded == true) {
if (ifm && ifm.contentDocument) {
ifm.contentWindow.document.body.scrollTop = this.scrollTop;
}
return;
}
if (ifm && this.url.indexOf("about:blank") < 0) {
this.loaded = false;
this.startLoadTimer(); // 开始兜底计时
ifm.setAttribute('src', this.url);
} else {
this.loaded = true;
}
},
reload() {
let ifm = this.$refs['iframe'];
this.loaded = false;
this.startLoadTimer(); // 刷新页面同样开启兜底
let urlToken = getUrlValue(ifm.contentWindow.location.href, "access_token");
let nowToken = getToken();
if (false && !window._global && urlToken && nowToken && (urlToken != nowToken)) {//正式环境
ifm.contentWindow.location = setUrlValue(decodeURIComponent(ifm.contentWindow.location.href), "access_token", nowToken);
}
ifm.contentWindow.location.reload();
},
handleIframeLoad(evt) {
// 正常触发load,清除超时定时器
this.clearLoadTimer();
let ifm = this.$refs['iframe'];
// 尝试获取页面标题,增加try-catch防止跨域报错
try {
if (this.title == "" && ifm.contentWindow.document.title != "") {
this.$emit("update:title", ifm.contentWindow.document.title);
}
} catch (e) {
// 跨域无法读取标题,静默捕获异常
}
// 简化判断,移除危险的contentWindow.body读取(跨域会报错阻断代码)
if (ifm.src && ifm.src !== "about:blank") {
this.loaded = true;
} else {
this.loaded = true;
}
// 绑定beforeunload增加异常捕获
try {
if (ifm.contentDocument) {
ifm.contentWindow.addEventListener('beforeunload', () => {
//this.loaded=false;//右击刷新 时进行加载状态
});
}
} catch (e) {
}
this.loaded && this.$emit('onIframeLoad', this, evt);
},
}
}
</script>