本文已参与「新人创作礼」活动,一起开启掘金创作之路。
在ThinkCMF框架中,我们在点击一个列表中的一条进入详细,做了【审核】【驳回】类似的状态更新,然后列表没有变化。 ThinkCMF的后台页面构造是一个父层页面,生成多个动态iframe。其实每个iframe页面都是兄弟关系。每个iframe在生成时都有自己唯一的id.
这里做四个步骤来解决此问题。
1.在列表页我们做一个 refresh按钮,点击这里能完成当前页面刷新。
操作如下:
我们去核心配置也增加一个这样的自刷按钮配置
/**
* 刷新当前页按钮 这个是我们自己做的
* @param string $text
* @return string
*/
protected function getRefreshButton($text = '<span id="refresh">refresh</span>')
{
$url = $this->url($this->currentPage() );
return $this->getPageLinkWrapper($url, $text);
}
/**
* 上一页按钮
* @param string $text
* @return string
*/
方法做好后,我们渲染时也要调整,还是这个文件:
/**
* 渲染分页html
* @return mixed
*/
public function render()
{
if ($this->hasPages()) {
$request = request();
if ($this->simple || $request->isMobile()) {
return sprintf(
'%s %s %s',
$this->getSimplePreviousButton(),
$this->getSimpleNextButton(),
$this->getRefreshButton() //移动端 渲染!!!
);
} else {
return sprintf(
'%s %s %s %s',
$this->getPreviousButton(),
$this->getLinks(),
$this->getNextButton(),
$this->getRefreshButton()//非移动端 渲染!!!
);
}
}else{
return sprintf(
'%s',
$this->getRefreshButton() //不满分页 渲染!!! 这里配置 默认:不满一页 翻页信息都不展示了,我们自刷新按钮 也要给它盘出来!!!
);
}
}
2.列表页把,当前页的动态id 在打开新页面时,给它当做一个参数传传过去
放置一个getFromId()方法,让它帮助我们获取当前页面id (这个id)
<include file="public@header"/>
<script>
//获取当前iframe的id 传入下一页
function getFromId() {
var frameId = window.frameElement && window.frameElement.id || '';
return frameId;
}
</script>
</head>
在列表页放置我们的参数 为了阅读方便: 这里我把javascript:parent.openIframeLayer的三个参数单独拿出来看一下:
javascript:parent.openIframeLayer( '{:url('kaohe/workinfo',['work_id'=>id])}', 第一个参数:url '{$vo.pname}-家庭协议明细', 第二个参数:title {'fromId':getFromId()} 第三个参数:options )"
<td>
<a href="javascript:parent.openIframeLayer('{:url(\'kaohe/workinfo\',[\'work_id\'=>$vo.id])}','{$vo.pname}-家庭协议明细',{'fromId':getFromId()})">
<button type="button" class="btn btn-success">查看</button>
</a>
</td>
3.列表把参数传进来,然后我们调整一下admin.js 把接进来的参数封装一下
找到这个方法function openIframeLayer(url, title, options)
function openIframeLayer(url, title, options) {
var params = {
type: 2,
title: title,
shadeClose: true,
// skin: 'layui-layer-nobg',
anim: -1,
shade: [0.001, '#000000'],
shadeClose: true,
area: ['95%', '90%'],
move: false,
content: url,
yes: function (index, layero) {
//do something
layer.close(index); //如果设定了yes回调,需进行手工关闭
}
};
params = options ? $.extend(params, options) : params;
//下面封装我们传进来的参数
//因为很多情况我们第二步列表 不会传输options的参数 所有做以下判断
if(typeof(options) == "object" && options.hasOwnProperty("fromId")){
params.content +="?fromId="+options.fromId;//在layer在执行渲染打开页面是 页面地址是params的content 参数,所有我们把参数封装到它的后最为一个get参数带过去
}
console.log(params)
Wind.css('layer');
Wind.use("layer", function () {
layer.open(params);
});
}
第四步,在我们的详细页面处理
<script>
//详细页面我们防止一个getUrlParam(name)方法,把第二步、第三步放置进来的iframe接出来
function getUrlParam(name) {
var reg = new RegExp("(^|&)" + name + "=([^&]*)(&|$)"); //构造一个含有目标参数的正则表达式对象
var r = window.location.search.substr(1).match(reg); //匹配目标参数
if (r != null) return unescape(r[2]);
return null; //返回参数值
}
</script>
在能触发数据更新的位置,调用我们的刷新“实际是兄弟的伪父层页面”
如:异步的更新数据成功后等,具体以自己的逻辑为准:
<script>
//去除第二三步拿过来的“实际是兄弟的伪父层页面”的iframe的动态id.
var fromId = getUrlParam("fromId")
//通过id获取到“实际是兄弟的伪父层页面”的iframe的对象
var parentIframe = window.parent.document.getElementById(fromId);
//通过对象获取到第一步我们放置好的刷新当前页的url地址(之所以这么取地址,这样的好处及时你的当前地址是个综合查询页面列表,只要你的查询逻辑没毛病,你拿到的地址也是带有条件的!!!)
var url = parentIframe.contentWindow.document.getElementsByClassName("pagination")[0].lastElementChild.firstChild.href;
// “实际是兄弟的伪父层页面”的iframe的刷新
parentIframe.src=url
</script>
亲测可用!