声明:FineUIMvc(基础版)是免费软件,本系列文章适用于基础版。

这篇文章我们将改造 FineUIMvc 默认的通知对话框,使得同时显示多个也不会重叠。并提前出一个公共的JS文件,供大家使用。

FineUIMvc 的通知对话框

FineUIMvc默认的通知对话框通过 F.notify 来显示,可以在页面上的 9 个位置显示,分别对应于属性:

  1. PosotionX = Left,  PositionY = Top
  2. PosotionX = Left,  PositionY = Center
  3. PosotionX = Left,  PositionY = Bottom
  4. PosotionX = Center,  PositionY = Top
  5. PosotionX = Center,  PositionY = Center
  6. PosotionX = Center,  PositionY = Bottom
  7. PosotionX = Right,  PositionY = Top
  8. PosotionX = Right,  PositionY = Center
  9. PosotionX = Right,  PositionY = Bottom

我们有专门的示例页面来演示相应的效果:

http://fineui.com/demo_mvc/#/demo_mvc/Message/Notify

美中不足的时,如果同时有多个通知对话框时,就会出现重叠,如下所示:

自定义通知对话框分组

为了解决这个问题,我们需要对 F.notify 进行一个简单的封装,得到的效果如下图所示:

调用这个封装好的函数非常简单,来看下这个页面的实现代码:

@(F.Button()
.Text("弹出通知对话框(多次点击)")
.ID("btnOperation1")
.Listener("click", "onOperation1Click")
)
<script src="~/res/js/notify_group.js"></script>
<script type="text/javascript"> var _orderNumber = 0; function onOperation1Click(event) {
// 创建一个消息对话框实例
var displayTime = 2000 + Math.random() * 10000; var allMessageIcons = ['information', 'warning', 'question', 'error', 'success'];
showNotifyGroup({
message: '这是第 <strong>' + _orderNumber + '</strong> 条提示信息,显示' + Math.floor(displayTime / 1000) + '秒',
messageIcon: allMessageIcons[_orderNumber % allMessageIcons.length],
header: false,
displayMilliseconds: displayTime
}); _orderNumber++;
} </script>

这里面实际执行的函数就是 showNotifyGroup,需要传入的参数如下:

1. message:显示的消息正文

2. messgeIcon:消息正文前面的图标

3. displayMilliseconds:显示的毫秒数(然后会自动消失)

其实,我们可以传入 F.notify 的任何参数,因为 showNotifyGroup 内部也是对 F.notify 的调用,只不过做了一定的扩展。

下面就来看下 showNotifyGroup 函数的具体实现:

// 通知对话框分组
(function () { // _notifySpace: 消息框之间的间距
// _notifies: 存放当前正在显示的对话框列表
var _orderNumber = 1, _notifySpace = 5, _notifies = []; // 对话框关闭处理函数
function onNotifyHide() {
var notify = this;
var notifyHeight = notify.el.outerHeight(true) + _notifySpace;
var notifyIndex = $.inArray(notify, _notifies);
_notifies.splice(notifyIndex, 1); var count = _notifies.length;
if (count) {
for (var i = notifyIndex; i < count; i++) {
var item = _notifies[i];
item.top -= notifyHeight;
item.el.animate({
'top': item.top
});
} // 按照 notify.top 重新排序
_notifies.sort(function (a, b) {
return a.top - b.top;
});
}
} // 获取对话框元素的top属性
function calcNotifyTop() {
var top = _notifySpace;
if (_notifies.length) {
var lastNotify = _notifies[_notifies.length - 1];
top += lastNotify.top + lastNotify.el.outerHeight(true);
}
return top;
} // 公开方法
window.showNotifyGroup = function (options) {
// 创建一个消息对话框实例
$.extend(options, {
top: calcNotifyTop(),
positionX: 'right',
listeners: {
hide: onNotifyHide
}
}); _notifies.push(F.notify(options));
} })();

首先看下公开的 showNotifyGroup 方法的实现,需要传入 F.notify 的有三个参数:

1. top:消息框左上角的垂直坐标,由于最新的在最后面显示,所以每次都要计算这个位置

2. posotionX:固定为 right,也就是在页面右侧显示

3. hide:消息框隐藏时的处理函数,里面主要是 3 个处理:

------3.1:从消息框队列中删除需要隐藏的消息框

------3.2:改变正在显示的所有消息框的 top 属性

------3.3:按照 top 由小到大的顺序排序

自定义通知对话框分组(最新的显示在最上方)

上面实现的效果是最新的显示在最下方,代码还比较简洁。而如果要求最新的显示在最上方,则面临对动画效果的控制:

1. 显示新消息框时,需要将现有的所有消息框下移,并且等到大家都完成下移动作后,再显示新消息框

2. 显示新消息框时,有可能正在进行下移动画效果,并且上一个消息框还没显示(正在等动画完成),此时需要立即终止所有动画,并显示上一个消息框,之后再处理新的消息框

3. 某个消息框隐藏时,也有可能正在进行下移动画,此时也要做相同的处理

所以,虽然封装的代码逻辑复杂了,不过调用方法依然没变,效果也是很赞的:

这个示例的调用代码很简单,和上例相比,只多了一个 true 的参数:

<script src="~/res/js/notify_group.js"></script>
<script type="text/javascript"> var _orderNumber = 0; function onOperation1Click(event) {
// 创建一个消息对话框实例
var displayTime = 2000 + Math.random() * 10000; var allMessageIcons = ['information', 'warning', 'question', 'error', 'success'];
showNotifyGroup({
message: '这是第 <strong>' + _orderNumber + '</strong> 条提示信息,显示' + Math.floor(displayTime / 1000) + '秒',
messageIcon: allMessageIcons[_orderNumber % allMessageIcons.length],
header: false,
displayMilliseconds: displayTime
}, true); _orderNumber++;
} </script>

现在来看下完整的 notify_group.js 的代码:

// 通知对话框分组
(function () { // _notifySpace: 消息框之间的间距
// _notifies: 存放当前正在显示的对话框列表
var _orderNumber = 1, _notifySpace = 5, _notifies = []; // 对话框关闭处理函数
function onNotifyHide() {
// 先清空之前尚未完成的动画
clearNotifiesAnimation(); var notify = this;
var notifyHeight = notify.el.outerHeight(true) + _notifySpace;
var notifyIndex = $.inArray(notify, _notifies);
_notifies.splice(notifyIndex, 1); var count = _notifies.length;
if (count) {
for (var i = notifyIndex; i < count; i++) {
var item = _notifies[i];
item.top -= notifyHeight;
item.el.animate({
'top': item.top
});
} // 按照 notify.top 重新排序
_notifies.sort(function (a, b) {
return a.top - b.top;
});
}
} // 所有对话框下移
function moveNotifiesDown(newNotify, fn) {
// 先清空之前尚未完成的动画
clearNotifiesAnimation(); var count = _notifies.length, finished = 0;
if (!count) {
fn.apply(window);
return;
} var notifyHeight = newNotify.el.outerHeight(true) + _notifySpace;
for (var i = 0; i < count; i++) {
var item = _notifies[i];
item.top += notifyHeight;
item.el.animate({
'top': item.top
}, function () {
// 动画完成后执行的函数
finished++; if (finished >= count) {
fn.apply(window);
}
});
}
} // 停止动画,并回调
function clearNotifiesAnimation() {
var count = _notifies.length;
if (count) {
for (var i = 0; i < count; i++) {
var item = _notifies[i];
var itemEl = item.el;
if (itemEl.is(":animated")) {
itemEl.stop(false, true);
}
}
}
} // 获取对话框元素的top属性
function calcNotifyTop() {
var top = _notifySpace;
if (_notifies.length) {
var lastNotify = _notifies[_notifies.length - 1];
top += lastNotify.top + lastNotify.el.outerHeight(true);
}
return top;
} // 公开方法
window.showNotifyGroup = function (options, newestOnTop) {
// 创建一个消息对话框实例
$.extend(options, {
positionX: 'right',
listeners: {
hide: onNotifyHide
}
}); if (newestOnTop) {
// 最新的显示在最上方,需要先隐藏,等 moveNotifiesDown 之后再显示
options.hidden = true;
options.top = _notifySpace;
} else {
options.top = calcNotifyTop();
} var notify = F.notify(options); if (newestOnTop) {
moveNotifiesDown(notify, function () {
notify.show();
});
_notifies.splice(0, 0, notify);
} else {
_notifies.push(notify);
}
} })();

如果你也想要这样的效果,很简单,把 notify_group.js 丢到你的项目中,直接调用 showNotifyGroup 函数即可!

小结

虽然本篇讲的是 FineUIMvc ,其实是对内部 JavaScript 代码的一个简单扩展和封装,由此可见 FineUIMvc 前端库的灵活性。我们可以直接把 notify_group.js 丢到项目中,调用 showNotifyGroup 函数即可实现上述效果。你也可以自行扩展来在页面的不同地方显示通知对话框,实现更复杂的动画效果。

《FineUIMvc随笔》目录:http://www.cnblogs.com/sanshi/p/6473592.html

自行扩展 FineUIMvc 通知对话框(多个并排显示不重叠,支持最新的显示在最上方)的更多相关文章

  1. FineUIMvc随笔(7)扩展通知对话框(显示多个不重叠)

    声明:FineUIMvc(基础版)是免费软件,本系列文章适用于基础版. 这篇文章我们将改造 FineUIMvc 默认的通知对话框,使得同时显示多个也不会重叠.并提前出一个公共的JS文件,供大家使用. ...

  2. (转)css中通常会用到浮动与清除,也是一个必须掌握的知识点,概念性的东西不多说,下面举几个例子,来说明它的用法:1.文字环绕效果 2.多个div并排显示 3.清除浮动(默认显示)

    一.文字环绕效果: html代码如下: 1 <body> 2 3 <style type="text/css"> 4 #big img {float: le ...

  3. iOS UITableView行高自行扩展

    myTableView.estimatedRowHeight = ; myTableView.rowHeight = UITableViewAutomaticDimension; 不需要实现 - (C ...

  4. Java基础之扩展GUI——使用对话框创建文本元素(Sketcher 4 creating text elements)

    控制台程序. 为了与Sketcher中的其他元素类型保持一致,需要为Elements菜单添加Text菜单项和工具栏按钮.还需要定义用来表示文本元素的类Element.Text. 1.修改Sketche ...

  5. 【纯代码】Swift - 自定义底部弹窗基类(可根据需要自行扩展内容)

    //弹窗视图 class PopView : UIView { var selectButtonCallBack:((_ title:String)-> Void)? var contenVie ...

  6. jquery本地上传预览扩展(隐藏上传控件单击图片上传支持ie!!)

    我用到的原材料地址:http://www.cnblogs.com/leejersey/p/3660202.html 修改后: /// <reference path="../../Js ...

  7. HslCommunication库的二次协议扩展,适配第三方通讯协议开发,基础框架支持长短连接模式

    本文将使用一个gitHub开源的项目来扩展实现二次协议的开发,该项目已经搭建好了基础层架构,并实现了三菱,西门子,欧姆龙,MODBUS-TCP的通讯示例,也可以参照这些示例开发其他的通讯协议,并Pul ...

  8. 通知:逆天异常库 V1.0版本支持下载了~~

    百度网盘:http://pan.baidu.com/s/1bongheJ GitHub:https://github.com/dunitian/LoTDotNet

  9. JDK6 新特性

    JDK6新特性目录导航: Desktop类和SystemTray类 JAXB2实现对象与XML之间的映射 StAX Compiler API 轻量级 Http Server API 插入式注解处理AP ...

随机推荐

  1. Github创建分支

    一.clone Repository clone Github 上的Repository,如下: git clone git@github.com:FBing/design-patterns.git ...

  2. VUE2.0实现购物车和地址选配功能学习第六节

    第六节 地址列表过滤和展开所有的地址 html:<li v-for="(item,index) in filterAddress">js: new Vue({ el:' ...

  3. 对JavaScript中变量类型的重新理解

    <JavaScript启示录>这本书中提出:JavaScript中,对象为“王”(JavaScript里的几乎所有东西都是对象或者用起来像对象). 飞燕草对JavaScript最深刻的理解 ...

  4. Apache Struts2存在S2-045

    麻蛋的,批了老半天都找不到,还得谷歌 不扯蛋了,直接主题: Struts2 2.3.32 版本 下载地址:https://dist.apache.org/repos/dist/release/stru ...

  5. Jackson学习(一)

    Jackson的一些配置.使用方式以及效率方面的简单介绍. 1.jackson的maven依赖 <!-- jackson依赖 --> <dependency> <grou ...

  6. h5标签基础 meta标签

    <meta>标签位于<head>标签里面,具体作用有如下: 1.设置网页编码 eg: <meta charset="utf-8"/>  ,//u ...

  7. String类的indexOf方法的用法和举例

    2017年3月3号博主第一次去郑州互联网公司面试,背景是这样的我先前去了农大龙子湖校园招聘投简历,然后第二天去面试了那经历可以说是很失败的一次面试,当然这跟自己的水平有关了接下来重点讲一下面试的题目: ...

  8. Javascript把数据从一个页面的层传递到另一个页面层里面

    背景:昨天头脑发热投了某一家国企的计算机类岗位(说是有前端岗位),通过找同学内推,虽然也笔试了一大堆题目(行测题,计算机网络,http协议,英译汉,古诗文默写,自己把品质排序并且进行200字以上的阐述 ...

  9. Strtus2 S2-045漏洞

    S2-045漏洞已经爆发几天了,但还很多网址都存在此漏洞,很多金融类网站也收到了保护费通知...唉,收保护费少,报警无效!只能酌情处理了!做黑产的,还是少做为秒,常在河边站哪有不湿鞋,劝各位早日金盆洗 ...

  10. Visual Studio 2017 ASP.NET Core开发

    Visual Studio 2017 ASP.NET Core开发,Visual Studio 2017 已经内置ASP.NET Core 开发工具. 在选择.NET Core 功能安装以后就可以进行 ...