Framework7学习笔记(二):组件
为F7应用添加导航栏和工具栏之前,需要决定使用何种导航/工具栏布局。F7支持三种导航/工具栏布局。
这是最少使用的一种布局,使用该布局时,导航/工具栏随着页面滚动,它们仅仅是页面的一部分,每个页面拥有自己的导航/工具栏:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
<!-- 这是一个页面 --> <div data-page="index" class="page"> <div class="page-content"> <!-- 顶部导航栏开始 --> <div class="navbar"> <div class="navbar-inner"> <div class="center">Awesome App</div> </div> </div> <!-- 导航栏结束--> <p>页面主体内容</p> <!-- 底部工具栏开始 --> <div class="toolbar"> <div class="toolbar-inner">Hello</div> </div> <!-- 底部工具栏结束--> </div> </div> |
与静态布局类似,每个页面拥有自己的导航/工具栏,但是导航/工具栏不随页面滚动,它们分别固定在顶部/底部,始终可见。启用固定布局很简单,只需要在页面元素上添加样式类:
1 |
<div data-page="index" class="page navbar-fixed toolbar-fixed"> |
这是最常使用的一种方式,一个视图中的所有页面共享导航/工具栏。该布局支持动态导航栏(Dynamic Navbar):
1 2 3 4 5 6 7 8 9 10 11 12 13 |
<div class="view view-main"> <!-- 视图唯一的导航栏 --> <div class="navbar"><div class="navbar-inner"></div></div> <!-- 导航栏结束--> <!-- 页面容器(pages)元素需要额外的"navbar-through"、"toolbar-through"样式类,分别表示启用贯穿导航栏、工具栏 --> <div class="pages navbar-through toolbar-through"> <!-- 页面 --> <div data-page="index" class="page"><div class="page-content"></div></div> </div> <!-- 视图唯一的工具栏 --> <div class="toolbar"></div> <!--工具栏结束--> </div> |
F7支持在一个视图内混合使用多种布局方式。例如你可以使用贯穿的导航栏 + 固定的工具栏:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
<div class="view view-main"> <!-- 视图唯一的贯穿导航栏 --> <div class="navbar"><div class="navbar-inner"><div class="center"></div></div></div> <!-- 为所有页面声明:使用贯穿导航栏、固定工具栏 --> <div class="pages navbar-through toolbar-fixed"> <!-- 一个页面定义 --> <div data-page="index" class="page"> <div class="page-content"></div> <!-- 固定工具栏,因此每个页面都需要定义自己的 --> <div class="toolbar"><div class="toolbar-inner">Hello</div></div> </div> </div> </div> |
你也可以不使用导航栏和(或)工具栏,只要不声明它们、同时不在page/pages/view元素上添加冲突的样式类:navbar-fixed、navbar-through、toolbar-fixed、 toolbar-through即可。
所谓导航栏,是位于屏幕顶部的,包含页面标题、导航元素的一个区域。导航栏分为三个部分(左、中、右),这三个部分都可以包含任意HTML,但是F7建议这样使用导航栏:
- 左侧部分:用于放置返回链接,可以是图标或者文本
- 中间部分:显示页面标题
- 右侧部分:类似于左侧,放置按钮或链接
导航栏内部的结构很简单且自描述:
1 2 3 4 5 6 7 8 9 |
<div class="navbar"> <div class="navbar-inner"> <div class="left">Left</div> <!-- 注意,center具有最低的宽度优先级,当空间不够时,center的内容自动被省略,确保左右正常显示 --> <!-- 如果center中存放文本,无法显示的内容使用省略号代替,如果放置了自定义元素,则需要小心处理 --> <div class="center">Center</div> <div class="right">Right</div> </div> </div> |
可以在导航栏中添加多种链接:
链接类型 | 说明与示例 | ||
文本链接 |
|
||
多个链接 |
|
||
图标+文本链接 |
|
||
图标链接 |
|
对于已初始化的视图,我们可以用JavaScript API操控其导航栏:
方法 | 说明 | ||
app.hideNavbar(navbar) | 隐藏或显示指定的导航栏。navbar为代表目标导航栏的HTMLElement或者CSS选择器(字符串) | ||
app.showNavbar(navbar) | |||
view.hideNavbar() | 隐藏或显示视图view的导航栏。示例:
|
||
view.showNavbar() | |||
view.sizeNavbars(viewContainer) | 仅iOS主题。重新计算导航栏的位置。示例: app.sizeNavbars('.view-main') |
使用贯穿布局时,F7允许对某些Ajax页面自动隐藏/显示导航栏:
1 2 3 4 5 6 |
<!-- 为此页面声明一个空白导航栏 --> <div class="navbar"><div class="navbar-inner"></div></div> <!-- 同时为页面添加"no-navbar"样式类 --> <div data-page="about" class="page no-navbar"> <div class="page-content"></div> </div> |
注意动态导航栏仅适用于iOS主题 + 贯穿布局。所谓动态导航栏,在页面切换时,其内容具有滑动和淡入淡出效果。
动态导航栏的内部布局和普通导航栏没太大区别,只是你可以为导航栏的左中右三个部分添加额外的样式类。默认的,F7为这三个部分添加淡入淡出效果,如果要启用滑动效果,你可以添加样式类:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<!-- 每个页面可以指定自己的动态导航栏,默认具有淡入淡出切换效果 --> <!-- 动态导航栏声明在页面外部(从其它html加载为页面、或者创建动态页面时) --> <div class="navbar"> <div class="navbar-inner"> <div class="left"> <a href="#" class="link">Left</a> </div> <!-- 为中间部分添加滑动效果,注意整个应用的风格应当统一 --> <div class="center sliding">Home</div> <div class="right"> <a href="#" class="link">Right</a> </div> </div> </div> <div class="page" data-page="about">页面内容</div> |
设置应用初始化参数 animateNavBackIcon: true 可以为后退按钮添加更多的动画效果,从而更像iOS 7的风格。
F7为动态导航栏添加了几种事件,这些事件的源(Target) 都是 <div class="navbar-inner"> :
事件 | 说明 |
navbarBeforeInit | 插入一个新的导航栏到DOM时,触发该事件 |
navbarInit | 初始化一个导航栏后,触发该事件 |
navbarReinit | 当缓存的导航栏变得再次可见时,触发该事件 |
navbarBeforeRemove | 当导航栏即将从DOM中移除时,触发该事件 |
下面的代码演示了该事件的使用:
1 2 3 4 5 6 7 |
$$(document).on('navbarInit', function (e) { var navbar = e.detail.navbar; // 可以访问导航栏对象的以下属性: // navbarContainer 链接到导航栏容器元素 // navbarInnerContainer 链接到导航栏内部容器元素 var page = e.detail.page }); |
当你需要在导航栏添加额外的元素时,可以使用子导航栏。当导航栏隐藏时,子导航栏仍然保持可见。
在线演示:http://framework7.taobao.org/docs-demos/subnavbar.html
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<div class="navbar-inner"> <div class="left"></div> <div class="center"></div> <div class="right"></div> <!-- 子导航栏 --> <div class="subnavbar"> <!-- 子导航栏内容,这里存放了三个按钮 --> <div class="buttons-row"> <a href="#tab1" class="button active">Tab 1</a> <a href="#tab2" class="button">Tab 2</a> <a href="#tab3" class="button">Tab 3</a> </div> </div> </div> |
工具栏是屏幕上的一个固定区域,可以包含导航元素。不像导航栏,工具栏不包含任何部分,内部可以直接是若干链接。
1 2 3 4 5 6 7 |
<div class="toolbar"> <div class="toolbar-inner"> <a href="#" class="link">Link 1</a> <a href="#" class="link">Link 2</a> <a href="#" class="link">Link 3</a> </div> </div> |
默认的,工具栏内的元素均匀的分布在工具栏中。
以下方法可用于操控已初始化视图中的工具栏:
方法 | 说明 |
app.hideToolbar(toolbar) | 隐藏或者显示指定的工具栏。 toolbar:目标工具栏对应的HTMLElement或者String(CSS选择器) |
app.showToolbar(toolbar) | |
view.hideToolbar() | 隐藏或者显示当前视图的工具栏 |
view.showToolbar() |
如果某个Ajax页面不需要显示工具栏,可以在页面上添加样式类:
1 2 |
<!-- no-toolbar表示为该页面隐藏工具栏 --> <div data-page="about" class="page no-toolbar"> |
仅用于Material主题,对于iOS主题工具栏默认就在底部。
Material主题常常把工具栏/页签栏置于屏幕上面,导航栏下面。如果要改变此行为,可以为工具栏添加额外的样式类:
1 2 3 4 |
<!-- toolbar-bottom导致Material主题的工具栏放置于屏幕底部 --> <div class="toolbar toolbar-bottom"> <div class="toolbar-inner"></div> </div> |
页签栏只是工具栏的特例,它包含图标(或者图标+文本),而不仅仅是文本。
与工具栏类似,只是多一个样式类声明:
1 2 3 4 5 6 7 8 9 10 11 |
<!-- 比工具栏多一个tabbar的样式类 --> <div class="toolbar tabbar"> <div class="toolbar-inner"> <a href="#tab1" class="tab-link active"> <i class="icon demo-icon-1"></i> </a> <a href="#tab2" class="tab-link"> <i class="icon demo-icon-2"></i> </a> </div> </div> |
默认的,页签栏内的元素(链接)均匀的分布在页签栏中。但是要注意以下两点:
- 在iPhone中,每个元素的大小一致,为屏幕宽度/元素个数
- 在iPad中,所有元素的被居中显示,元素最小宽度105px
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<div class="toolbar tabbar"> <div class="toolbar-inner"> <a href="#tab2" class="tab-link"> <i class="icon demo-icon-2"> <!-- 只需要图标元素内放置一个span元素,并添加badge样式,即可增加角标 --> <span class="badge bg-red">5</span><!-- 红色背景角标,数字5 --> </i> </a> <a href="#tab4" class="tab-link"> <i class="icon demo-icon-4"> <span class="badge bg-green">15</span><!-- 绿色背景角标,数字15 --> </i> </a> </div> </div> |
类似的,为图标添加一个兄弟元素,可以显示文本标签:
1 2 3 4 5 |
<a href="#tab1" class="tab-link active"> <i class="icon demo-icon-1"></i> <!-- 文本标签,默认位于图标下方 --> <span class="tabbar-label">Label 1</span> </a> |
当页签栏中的元素非常多,屏幕宽度不足以显示时,应该使用可滚动页签栏,当手指划过页签栏时,会自动滚动以显示不可见元素:
1 2 |
<!-- 只需要添加tabbar-scrollable样式类即可 --> <div class="toolbar tabbar tabbar-scrollable"></div> |
方法 | 说明 |
app.hideToolbar(toolbar) | 这两个方法同样适用于页签栏 |
app.showToolbar(toolbar) |
如果某个Ajax页面不需要显示页签栏,可以在页面上添加样式类:
1 2 |
<!-- no-tabbar表示为该页面隐藏页签栏 --> <div data-page="about" class="page no-tabbar"> |
F7支持当页面向下滚动时,自动隐藏导航/工具栏。
要全局性的启用该功能,可以配置以下应用初始化参数:
- hideNavbarOnPageScroll:滚动时隐藏导航栏
- hideToolbarOnPageScroll:滚动时隐藏工具栏
- hideTabbarOnPageScroll:滚动时隐藏页签栏
- showBarsOnPageScrollEnd :滚动到页面底部时显示所有栏
要针对某些特定页面启用该功能,可以在 <div class="page-content"> 元素上添加以下样式类:
- hide-bars-on-scroll
- hide-navbar-on-scroll
- hide-toolbar-on-scroll
- hide-tabbar-on-scroll
在全局启用时,可以使用下面的样式类,针对特定页面禁用此功能:
- keep-bars-on-scroll
- keep-navbar-on-scroll
- keep-toolbar-on-scroll
- keep-tabbar-on-scroll
搜索栏可以对列表视图(List View)执行搜索,或者作为自定义搜索实现的视觉元素。
在线演示:http://framework7.taobao.org/docs-demos/searchbar.html
搜索栏应该放置在 .page 和 .page-content 元素之间:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
<!-- 页面 --> <div class="page"> <!-- 搜索栏 --> <form class="searchbar"><!-- 搜索栏容器元素,推荐使用form --> <div class="searchbar-input"> <input type="search" placeholder="Search"><!-- 搜索栏 --> <a href="#" class="searchbar-clear"></a><!-- 可选元素,用于清空输入值的按钮,可选 --> </div> <a href="#" class="searchbar-cancel">Cancel</a><!-- 取消搜索,隐藏搜索栏,清空结果过滤,可选 --> </form> <!-- 搜索栏overlay,深色的、覆盖在页面内容上面的一层内容,可选 --> <div class="searchbar-overlay"></div> <!-- 页面内容部分 --> <div class="page-content"> <!-- searchbar-not-found:如果找不到匹配的元素,显示此div --> <div class="content-block searchbar-not-found">Nothing found</div> <!-- list-block-search:被搜索的列表块 --> <!-- searchbar-found:如果找到匹配的元素,显示此div --> <div class="list-block list-block-search searchbar-found"></div> </div> </div> |
除了搜索栏布局,我们还需要调用API初始化它:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
/** * 初始化一个搜索栏 * @param searchbarContainer 搜索栏容器元素,HTMLElement或者CSS选择器 * @param parameters 搜索栏初始化参数 * @return 已初始化的搜索栏实例 */ app.searchbar(searchbarContainer, parameters); //示例: var mySearchbar = app.searchbar( '.searchbar', { searchList : '.list-block-search', searchIn : '.item-title' } ); |
你也可以通过HTML初始化搜索栏:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
<div class="page"> <!-- 为搜索栏添加searchbar-ini属性,则F7自动初始化之 --> <!-- data-*属性提供初始化参数,连字符小写风格 --> <form class="searchbar searchbar-init" data-search-list=".list-block-search" data-search-in=".item-title" data-found=".searchbar-found" data-not-found=".searchbar-not-found"> <div class="searchbar-input"> <input type="search" placeholder="Search"> <a href="#" class="searchbar-clear"></a> </div> <a href="#" class="searchbar-cancel">Cancel</a> </form> <div class="searchbar-overlay"></div> <div class="page-content"> <div class="content-block searchbar-not-found"></div> <div class="list-block list-block-search searchbar-found"></div> </div> </div> |
通过下面的方式可以获得DOM关联的搜索栏实例:
1 2 |
var searchbar = $$('.searchbar')[0].f7Searchbar; //通过该属性访问 searchbar.search('Hello world'); |
参数 | 类型和默认值 | 说明 |
searchList | string / HTMLElement | 被搜索的列表块(list block),HTMLElement或者CSS选择器 |
searchIn | string = '.item-title' | CSS选择器,指定列表视图元素的字段,搜索在该字段上进行,通常我们通过元素的标题搜索(.item-title) |
found | string / HTMLElement | 搜索结果可用时显示的元素的CSS选择器或者DOM,如果不指定,默认使用页面内的.searchbar-found元素 |
notFound | string / HTMLElement | 类似上面,搜索结果不可用时显示的元素,默认使用页面内的.searchbar-not-found元素 |
overlay | string / HTMLElement | 搜索栏overlay元素,默认使用页面内的.searchbar-overlay元素 |
ignore | string = '.searchbar-ignore' | CSS选择器,哪些元素被搜索栏忽略,总是显示在搜索结果中 |
customSearch | boolean = false | 如果设置为true,则搜索栏不去搜索searchList指定的列表块。你可以定制自己的搜索逻辑,并手工处理数据展示 |
hideDividers | boolean = true | 如果列表分隔器没有匹配的条目,则隐藏分隔器 |
hideGroups | boolean = true | 如果组内没有匹配的条目,则隐藏组标题 |
onSearch | function (s) | 搜索时(输入值改变)触发此回调 |
onEnable | function (s) | 当搜索栏被启用时,触发此回调 |
onDisable | function (s) | 当搜索栏被禁用(例如点击取消按钮、或者触碰searchbar-overlay元素)时,触发此回调 |
onClear | function (s) | 当用户点击了搜索栏的clear元素时触发此回调 |
方法/属性/事件 | 说明 |
params | 搜索栏的所有初始化参数 |
query | 当前搜索条件,即输入框的内容 |
searchList | 搜索列表块对应的DOM元素 |
container | 搜索栏容器DOM元素 |
input | 搜索输入框DOM元素 |
active | boolean,当前搜索框是否处于激活状态 |
search(query) | 依据入参条件执行搜索 |
enable() | 启用搜索栏 |
disable() | 禁用搜索栏 |
clear() | 清空查询条件并更新搜素结果 |
destroy() | 销毁该搜索栏实例 |
⚡search | 这些事件的target都是搜索栏关联的
<div class="list-block"> 元素。分别在以下时机触发:
|
⚡clearSearch | |
⚡enableSearch | |
⚡disableSearch |
状态栏是指设备屏幕顶端的一个窄条,包含信标、电量、时间等信息。F7框架中和状态栏相关的主题是状态栏overlay。
iOS7+系统允许你创建全屏应用程序,但是状态栏可能覆盖应用程序的内容。F7能够处理该问题,当应用程序处于全屏状态时,F7会自动检测到并添加 with-statusbar-overlay 样式类到 <html> 元素上,当应用程序退出全屏时,则去掉该样式类。
该样式类自动在应用程序顶端添加20像素的补白,从而防止状态栏覆盖掉用程序内容。
你可以控制全屏应用状态栏的背景色:
1 2 3 4 5 6 7 8 9 |
<style> /*修改状态栏背景色*/ .statusbar-overlay { background: pink; } </style> <body> <div class="statusbar-overlay"></div> </div> |
.statusbar-overlay 这个div总是固定在屏幕顶部,默认隐藏。当应用程序进入全屏状态、且 <html> 元素上具有 with-statusbar-overlay 样式时自动显示。
注意:
- Home界面中的Web应用,其状态栏总是白色,无法改变
- Apache Cordova 应用的状态栏默认总是黑色,F7无法修改。你可以使用Cordova插件 cordova-plugin-statusbar 来定制状态栏颜色
侧边栏是从左侧或者右侧滑动进入屏幕,并且覆盖在页面主体内容上方的组件。
1 2 3 4 5 6 7 8 |
<body> <!-- 需要增加此元素,以便侧面板能够覆盖在应用主体内容上方(z-index) --> <div class="panel-overlay"></div> <!-- 左侧面板,打开时特效:移动应用主体内容 --> <div class="panel panel-left panel-reveal"></div> <!-- 右侧面板,打开时特效:覆盖应用主体内容 --> <div class="panel panel-right panel-cover"></div> </body> |
1 2 3 4 5 6 7 8 9 10 11 |
<body> <div class="panel-overlay"></div> <div class="panel panel-left panel-reveal"> <div class="content-block"> <!-- close-panel类用于关闭面板 --> <p><a href="#" class="close-panel">关闭当前面板</a></p> <!-- open-panel类用于打开面板,data-panel用于指定操作目标 --> <p><a href="#" data-panel="right" class="open-panel">打开右侧面板</a></p> </div> </div> </body> |
1 2 3 4 5 6 7 8 9 |
/** * 打开面板 * @param position 打开哪一侧面板,"left" 或 "right" */ app.openPanel(position); /** * 关闭当前打开的面板 */ app.closePanel(); |
事件 | 说明 |
⚡open | 这些事件的target都是
<div class="panel"> 元素。分别在以下时机触发:
|
⚡opened | |
⚡close | |
⚡closed |
F7支持通过滑动手势打开面板,但是只有左侧或者右侧面板中的一个可以启用该手势:
1 2 3 |
var app = new Framework7( { swipePanel : 'left' //让左侧面板支持滑动手势 } ); |
其它与面板相关的应用初始化参数包括:swipePanelCloseOpposite、 swipePanelOnlyClose、swipePanelActiveArea、swipePanelNoFollow、swipePanelThreshold。
当面板处于打开状态时,F7会给 <body> 元素添加额外的样式类: with-panel-[position]-[effect] :
- position区分左右面板,取值left或right
- effect表示面板打开效果,取值reveal或cover
下面的代码测试当前是否以覆盖方式打开了左侧面板:
1 2 3 |
if ($$('body').hasClass('with-panel-left-cover')) { console.log('左侧面板处于打开状态') } |
内容块主要用于为文本内容添加额外的格式或边距:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
<div class="page-content"> <p>页面中普通的,位于内容块之外的文本</p> <!-- 内容块 --> <div class="content-block"> <p>内容块中的文本颜色改变,且和四周有额外的边距</p> </div> <!-- 内容块 + inner容器 --> <div class="content-block"> <div class="content-block-inner">内容块背景颜色改变</div> </div> <div class="content-block-title">为内容块添加标题</div> <div class="content-block"><p></p></div> <!-- 带有内凹效果的内容块,在iOS主题中表现为圆角边框、额外的边距--> <div class="content-block inset"> <div class="content-block-inner"><p></p></div> </div> <!-- 仅在面板电脑中有内凹效果的内容块 --> <div class="content-block tablet-inset"> <div class="content-block-inner"><p></p></div> </div> </div> |
使用 F7的布局网格,我们可以灵活的在页面中定位自己的组件。
1 2 3 4 5 6 7 8 9 10 11 12 |
<!-- 布局表格以行包装列的形式出现 --> <div class="row"><!-- 包含两列的一行 --> <!-- 每个单元格被添加样式类col-*,*表示占据的宽度百分比 --> <div class="col-50">50%</div> <div class="col-50">50%</div> </div> <!-- 默认的,单元格之间有15像素的空隙,添加no-gutter则无空隙 --> <div class="row no-gutter"><!-- 包含三列的一行 --> <div class="col-33">33%</div> <div class="col-33">33%</div> <div class="col-33">33%</div> </div> |
用于指定网格的单元格的宽度的样式类包括:
- col-* :其中*为5/10/15...90/95.100,数字代表占据的相对宽度。设置样式类为col-auto的单元格,平均分配剩余的宽度
- tablet-* :与上面类似,用于平板类型(窗口宽度大于768像素时)
默认情况下,F7没有给单元格添加任何样式,可以参考如下的CSS语法统一添加:
1 2 3 4 5 6 7 8 9 10 |
div[class*="col-"] { background: #fff; text-align: center; color: #000; border: 1px solid #ddd; padding: 5px; } .row { margin-bottom: 15px; } |
这一大类的F7组件都在z-index方向覆盖在应用主体内容之上,它们都属于临时视图(Temporary Views)的一部分。
模态是一系列包含了简短内容的小面板,类似于居中于屏幕的弹出窗口。模态通常用于向用户提问,或者给用户发出通知。
F7预定义了一些常用的模态组件,例如警告框、确认框等。这些模态组件的标题、按钮文本的默认值可以通过modalTitle、modalPreloaderTitle 、modalButtonOk、modalButtonCancel 等应用初始化参数修改。
组件 | 说明 | ||
信息框(Alert) | 类似于window.alert(),可以具有标题、文本、点击后的回调。函数签名:
|
||
确认框(Confirm) | 与信息框类似,但是具有确定、取消两个按钮,点击后可以执行不同的回调。函数签名:
|
||
提示框(Prompt) | 与确认框类似,但是还让用户输入一些文本。函数签名:
|
||
登录和密码框 | 可以进行用户身份验证的模态窗口。函数签名:
|
||
预加载器(Preloader) | 用于提示用户:由于某些后台操作(例如XHR)正在执行,应用需要阻塞用户操作。 iOS主题下的默认UI效果是:旋转菊花 + 文本。 F7提供了两个函数来操控预加载器:
|
||
指示器(Indicator) | 和预加载类似,但是UI只有一个旋转菊花图标,没有文本。F7提供两个函数来操控指示器:
|
上表中所有预定义模态组件,实际上都属于“快捷方式”,它们最终都是调用下面的函数实现功能的:
1 2 3 4 5 6 |
/** * 新建一个模态组件 * @param parameters 初始化参数 * @return 动态创建的代表了模态组件的HTMLElement */ app.modal(parameters); |
定制的模块组件的内容可以相当丰富,下面是两个例子:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
var modal = app.modal( { title : '照片墙', text : '你觉得我的照片怎么样', //文本后的内容被替换为Swiper Slider组件 afterText : '<div class="swiper-container" style="width: auto; margin:5px -15px -15px">' + '<div class="swiper-pagination"></div>' + '<div class="swiper-wrapper">' + '<div class="swiper-slide"><img src="..." height="150" style="display:block"></div>' + '<div class="swiper-slide"><img src="..." height="150" style="display:block"></div>' + '</div>' + '</div>', buttons : [ { text : '一般般' }, { text : '太好了', bold : true, onClick : function() { app.alert( '谢谢!' ); } } ] } ); app.swiper( $$( modal ).find( '.swiper-container' ), { pagination : '.swiper-pagination' } ); /** * 该模态组件显示两个页签 */ app.modal( { //标题被设置为切换页签的按钮 title : '<div class="buttons-row">' + '<a href="#tab1" class="button active tab-link">页签一</a>' + '<a href="#tab2" class="button tab-link">页签二</a>' + '</div>', //文本被设置为两个页签 text : '<div class="tabs">' + '<div class="tab active" id="tab1">页签一的内容</div>' + '<div class="tab" id="tab2">页签二的内容</div>' + '</div>', buttons : [ { text : '确定', bold : true } ] } ); |
参数 | 类型与默认值 | 说明 | ||
title | string | 可选的模态组件标题,可以是HTML片段 | ||
text | string | 可选的模态组件文本,可以是HTML片段 | ||
afterText | string | 可选的,在text之后展示的额外文本,可以是HTML片段 | ||
buttons | Button[] | 模态按钮的数组,每个元素均是如下格式的对象:
|
||
verticalButtons | boolean = false | 是否纵向排列模态按钮 | ||
onClick | function(modelEl, index) |
用户点击 任何模态按钮后执行的函数:
|
1 2 3 4 5 |
/** * 关闭一个模态窗口 * @param modal 代表模态组件的CSS选择器或者HTMLElement */ app.closeModal(modal); |
方法/事件 | 说明 |
⚡open |
这些事件的target均为 <div class="modal"> 元素,分别在以下时机触发:
|
⚡opened | |
⚡close | |
⚡closed |
通过传递应用初始化参数 modalTemplate ,可以为模态组件定制HTML模板, 该参数必须是Template7模板,下面是一个例子:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
<div class="modal {{#unless buttons}}modal-no-buttons{{/unless}}"><!-- 如果定义了按钮 --> <div class="modal-inner"> <!-- 如果定义了标题 --> {{#if title}} <div class="modal-title">{{title}}</div> {{/if}} <!-- 如果定义了文本 --> {{#if text}} <div class="modal-text">{{text}}</div> {{/if}} <!-- 如果定义了文本后内容 --> {{#if afterText}} {{afterText}} {{/if}} </div> {{#if buttons}} <div class="modal-buttons"> <!-- 遍历所有按钮 --> {{#each buttons}} <span class="modal-button {{#if bold}}modal-button-bold{{/if}}">{{text}}</span> {{/each}} </div> {{/if}} </div> |
这类弹窗覆盖F7应用的主体内容上面,默认从屏幕底部滑动进入。在手机上具有全屏效果,在平板上默认630像素宽高。
1 2 3 4 |
<body> <!-- 额外的样式类tablet-fullscreen让Popup在平板上也全屏 --> <div class="popup tablet-fullscreen"></div> </body> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<body> <div class="page-content"> <div class="content-block"> <!-- 样式类open-popup用于打开Popup弹窗(可用于任何HTML元素,不仅仅是a),data-popup指定Popup的CSS选择器 --> <p><a href="#" data-popup=".popup-about" class="open-popup">Open About Popup </a></p> </div> </div> <!-- 额外的样式类popup-about相当于该弹窗的标识符 --> <div class="popup popup-about"> <div class="content-block"> <!-- 样式类close-popup用于关闭当前打开的弹窗 --> <p><a href="#" class="close-popup">Close popup</a></p> </div> </div> </body> |
1 2 3 4 5 6 7 8 9 10 11 12 |
/** * 打开Popup弹窗 * @param popup HTMLElement或者String(CSS选择器) */ app.popup(popup); /** * 关闭Popup弹窗 * @param popup * HTMLElement或者String(CSS选择器) * 如果省略该参数,则关闭任何打开的Popup或其它模态组件 */ app.closeModal(popup); |
方法/事件 | 说明 |
⚡open |
这些事件的target均为 <div class="popup"> 元素,分别在以下时机触发:
|
⚡opened | |
⚡close | |
⚡closed |
F7提供了一个动态创建、打开Popup弹窗的函数:
1 2 3 4 5 6 |
/** * 动态打开一个Popup弹窗 * @param popupHTML Popup的HTML内容 * @param removeOnClose 默认true,是否在关闭时移除Popup的DOM */ app.popup(popupHTML, removeOnClose); |
下面是一个例子:
1 2 3 4 5 6 7 8 9 10 |
$$('.create-popup').on('click', function () { var popupHTML = '<div class="popup">'+ '<div class="content-block">'+ '<p>Popup created dynamically.</p>'+ '<p><a href="#" class="close-popup">关闭</a></p>'+ '</div>'+ '</div>'; app.popup(popupHTML); }); |
Popover类似于ExtJS的Tips,是一个展示临时信息的较小的弹出窗口。当用户触碰空白处时,Popover自动关闭。Popover默认宽度是320px。
在小屏幕上,不建议使用Popover,最好使用操作列表(Action Sheet)代替。
1 2 3 4 5 6 7 8 9 10 |
<body> <div class="popover"> <!-- Popover的小箭头 --> <div class="popover-angle"></div> <!-- Popover的内容 --> <div class="popover-inner"> <!-- 这里面可以包含任何HTML内容 --> </div> </div> </body> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<body> <div class="page-content"> <div class="content-block"> <!-- open-popover用于打开Popover弹窗 --> <p><a href="#" data-popover=".popover-about" class="open-popover">打开</a></p> </div> </div> <div class="popover popover-about"> <div class="popover-angle"></div> <div class="popover-inner"> <!-- close-popover用于关闭目前打开的Popover弹窗 --> <div class="content-block"><a href="#" class="close-popover">关闭</a></div> </div> </div> </body> |
通过HTML打开的Popover,其显示位置会自动计算(在打开Popover的元素的周围),以确保正确显示。
1 2 3 4 5 6 7 8 9 10 11 12 13 |
/** * 打开一个Popover弹窗 * @param popover 目标弹窗的HTMLElement或者CSS选择器 * @param target 针对的元素,弹窗会在此元素的周围定位 */ app.popover(popover, target); /** * 关闭一个Popover弹窗 * @param popover * 目标弹窗的HTMLElement或者CSS选择器 * 如果忽略此参数,则任何打开的Popover都被关闭 */ app.closeModal(popover); |
和Popover类似,Popover也可以动态创建和展示:
1 2 3 4 5 6 7 8 9 10 11 |
/** * 动态创建并打开一个Popover弹窗 * * @param popover * Popover的HTML内容 * @param target * 针对的元素,弹窗会在此元素的周围定位 * @param removeOnClose * 默认true,是否在关闭时移除Popover的DOM */ app.popover( popoverHTML, target, removeOnClose ); |
与Popup类似,事件的Target是 <div class="popover"> 元素。
操作列表通常表现为从屏幕底部滑动进入的、包含若干纵向排列按钮的弹窗。操作列表可以把按钮分成若干组。可以通过操作列表,让用户确认潜在危险的操作。
不建议在大屏幕(平板)上使用操作列表,最好用Popover代替。
操作列表属于动态组件,只能通过JavaScript创建和打开:
1 2 3 4 5 6 7 8 9 10 11 12 |
/** * 创建并打开由若干按钮组构成的操作列表 * @param groups 相当于button[][],按钮组的数组,每个按钮组则是button的数组 * @return 动态创建的、代表操作列表的HTMLElement */ app.actions( groups ); /** * 创建并打开由若干按钮构成的操作列表(单个组) * @param buttons 按钮的数组 * @return 动态创建的、代表操作列表的HTMLElement */ app.actions( buttons ); |
上述groups、buttons的最内层元素是按钮的配置对象:
参数 | 类型和默认值 | 说明 |
text | string | 按钮的文本,可以是HTML |
bold | boolean = false | 可选,设置按钮文本为粗体 |
color | string | 可选,按钮的文字颜色,可以是10种内置颜色的英文名称 |
bg | string | 可选,按钮的北京颜色 ,可以是10种内置颜色的英文名称 |
label | boolean = true | 如果设置为true,则当前项作为按钮组的标题,而不是按钮 |
disabled | boolean = false | 设置为true则按钮被标记为禁用 |
onClick | function() | 点击按钮后,执行的回调 |
由于屏幕大小的原因,F7不建议:在手机上使用Popover;或者在平板上使用Action Sheet。为了让单份代码能够同时适用手机和平板,F7提供了操作列表到Popover的转换机制:
1 2 3 4 5 6 7 8 |
/** * 这两个函数,在手机上创建的是操作列表,而在平板上创建的则是Popover * @target HTMLElement或者CSS选择器,当作为Popover时,在哪个元素周围弹出 * @groups 操作列表/Popover包含的按钮组的数组 * @buttons 操作列表/Popover包含的按钮的数组 */ app.actions(target, groups); app.actions(target, buttons); |
默认的,操作列表在以下情况下自动关闭:
- 当其中某个按钮被点击时
- 当触碰操作列表外部的屏幕空间时(可通过应用初始化参数modalActionsCloseByOutside定制)
如果要手工关闭操作列表,可以调用: app.closeModal(actionSheet) ,该方法前面的章节已有说明。
与Popup、Popover类似,操作列表具有4个相关事件,这些事件的Target均为 <div class="actions-modal"> 元素。
通过传递应用初始化参数 modalActionsTemplate ,可以为操作列表定制HTML模板, 该参数必须是Template7模板,下面的模板展现了操作列表的默认布局:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<div class="actions-modal"> <!-- this表示单个组 --> {{#each this}} <div class="actions-modal-group"> <!-- this表示单个按钮 --> {{#each this}} {{#if label}} <span class="actions-modal-label">{{text}}</span><!-- 作为标题 --> {{else}} <div class="actions-modal-button {{#if color}}color-{{color}}{{/if}} {{#if bold}}actions-modal-button-bold{{/if}}">{{text}}</div> {{/if}} {{/each}} </div> {{/each}} </div> |
如果你使用操作列表到Popover的转换,则还可以传递应用初始化参数 modalActionsToPopoverTemplate ,从而定制目标Popover的HTML模板,下面是默认的模板:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<div class="popover actions-popover"> <div class="popover-inner"> <!-- 每个按钮组转换为一个列表块 --> {{#each this}} <div class="list-block"> <ul> <!-- 每个按钮转换为一个列表条目 --> {{#each this}} {{#if label}} <li class="actions-popover-label {{#if color}}color-{{color}}{{/if}} {{#if bold}}actions-popover-bold{{/if}}">{{text}}</li> {{else}} <li><a href="#" class="item-link list-button {{#if color}}color-{{color}}{{/if}} {{#if bg}}bg-{{bg}}{{/if}} {{#if bold}}actions-popover-bold{{/if}} {{#if disabled}}disabled{{/if}}">{{text}}</a></li> {{/if}} {{/each}} </ul> </div> {{/each}} </div> </div> |
大部分应用程序都有登录功能, 因此F7内置了登录屏幕组件。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
<body> <!-- 登录屏幕应当是body的直接子元素 --> <div class="login-screen"> <!-- 所有子元素都是可选的 --> <!-- 默认的视图-页面布局 --> <div class="view"> <div class="page"> <!-- 页面内容包含额外的login-screen-content类 --> <div class="page-content login-screen-content"> <div class="login-screen-title">登录屏幕标题</div> <!-- 登录表单 --> <form> <div class="list-block"> <ul> <li class="item-content"> <div class="item-inner"> <div class="item-title label">用户名</div> <div class="item-input"> <input type="text" name="username" placeholder="用户名"> </div> </div> </li> <li class="item-content"> <div class="item-inner"> <div class="item-title label">密码</div> <div class="item-input"> <input type="password" name="password" placeholder="密码"> </div> </div> </li> </ul> </div> <div class="list-block"> <ul> <li> <a href="#" class="item-link list-button">登录</a> </li> </ul> <div class="list-block-labe">与登录相关的提示信息</div> </div> </form> </div> </div> </div> </div> </body> |
HTML方式:
1 2 |
<a href="#" class="open-login-screen">打开登录屏幕</a> <a href="#" class="close-login-screen">关闭登录屏幕</a> |
JavaScript方式:
1 2 3 4 5 6 7 8 9 |
/** * 打开登录屏幕 */ app.loginScreen(); /** * 关闭登录屏幕 * @param loginScreen 登录屏幕的TMLElement或者CSS选择器 */ app.closeModal(loginScreen); |
与Popup、Popover、ActionSheet类似,登录屏幕具有4个相关事件,这些事件的Target均为 <div class="login-screen"> 元素。
某些应用要求先登录后使用,我们可以为登录屏幕添加 modal-in 类,这样F7应用加载后,立即显示登录屏幕:
1 2 3 |
<body> <div class="login-screen modal-in"></div> </body> |
这是一种特殊的Overlay组件,可以用于实现定制的选取器。其内容不受限制,UI默认表现为从屏幕底部滑入的弹窗,右上侧有一个关闭按钮,类似于手机虚拟键盘。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
<body> <!-- 模态选取器容器元素 --> <div class="picker-modal"> <!-- 可选的工具栏 --> <div class="toolbar"> <div class="toolbar-inner"> <div class="left"></div> <div class="right"> <a href="#" class="link close-picker">完成</a> </div> </div> </div> <!-- 选取器内部元素 --> <div class="picker-modal-inner"> <!-- 选取器内容,任意自定义HTML --> <div class="content-block"> </div> </div> </div> </body> |
HTML方式:
1 2 3 |
<a href="#" data-picker=".picker-1" class="link open-picker">打开选取器</a> <a href="#" data-picker=".picker-1" class="close-picker">关闭选取器</a> <div class="picker-modal picker-1">选取器实例</div> |
JavaScript方式:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
/** * 打开选取器 * * @param picker * 选取器的HTMLElement或者CSS选择器 */ app.pickerModal( picker ); /** * 关闭选取器 * * @param picker * 选取器的HTMLElement或者CSS选择器 * 如果不指定则关闭任何打开的模态窗口 */ app.closeModal( picker ); |
1 2 3 4 5 6 |
/** * 动态创建并打开选取器 * @param pickerHTML 选取器的HTML * @param removeOnClose 是否在关闭选取器时将其从DOM中移除 */ app.pickerModal(pickerHTML, removeOnClose); |
与Popup、Popover、ActionSheet、登录屏幕类似,模态选取器具有4个相关事件,这些事件的Target均为 <div class="picker-modal"> 元素。
F7自带了基于SVG和CSS动画的的预加载提示器,可以随意的放大缩小,其UI效果是旋转菊花。预加载指示器具有两个版本,分别用于浅色、深色背景。
以模态方式使用预加载指示器,可以通过上一章提到的“预加载器”、“指示器”。
1 2 3 4 5 |
<!-- 默认预加载器 --> <span class="preloader"></span> <!-- 白色版本的预加载器,用于深色背景 --> <span class="preloader preloader-white"></span> <!-- 指定大小 --> |
除了预加载指示器以外,F7还提供另外一种用于提示“正在处理”活动的组件——进度条。进度条分为确定的(Determinate,显示实际进度)、无限的(Infinite)两种。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<!-- 确定的进度条,20%完成进度 --> <div class="progressbar" data-progress="20"> <span></span> </div> <!-- 也可以用span元素 --> <span class="progressbar" data-progress="50"> <span></span> </span> <!-- 无限的进度条 --> <div class="progressbar-infinite"></div> <span class="progressbar-infinite"></span> <!-- 多彩效果 --> <div class="progressbar-infinite color-multi"></div> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
/** * 设置确定进度条的进度 * @param container 进度条的容器的HTMLElement或者CSS选择器,默认body * @param progress 目标进度,0-100 * @param speed 到达目标进度的动画耗时,单位ms * @return 返回进度条容器元素 */ app.setProgressbar(container, progress, speed); /** * 隐藏进度条 * @param container 进度条的容器的HTMLElement或者CSS选择器,默认body */ app.hideProgressbar(container); /** * 创建或显示(如果已经创建)进度条 * @param container 进度条的容器的HTMLElement或者CSS选择器,默认body * @param progress 目标进度,0-100 * @param color 进度条颜色名称 * @return 返回进度条容器元素 */ app.showProgressbar(container, progress, color); //外加两个快捷方法 //在指定容器内打开(显示)某种颜色的无限进度条 app.showProgressbar(container, color); //在body内打开(显示)color颜色的进度条,当前进度progress app.showProgressbar(progress, color); |
列表视图是多用途、强大的UI组件,在iOS应用中经常可以看到。列表视图在一个可滚动的区域内显示多行数据,可选的,它讲数据分为若干组/段。我们可以用列表视图来:
- 在层次型数据结构(树形)内进行导航
- 展现列表中的数据、选项
- 显示详细信息
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
<!-- 列表块(List block):列表块元素是列表视图的包装(wrapper)元素 --> <!-- 注意不要把list-block放在content-block内 --> <div class="list-block"> <!-- ul内是列表视图的全部元素 --> <ul> <!-- li代表列表视图的元素(条目),其内容相当复杂而灵活 --> <li> <!-- item-content为必需,作为item-media、item-inner的包装器--> <div class="item-content"> <!-- item-media为可选,用于图标、图片等媒体元素 --> <div class="item-media"> <i class="icon my-icon"></i> </div> <!-- item-inner为必需,作为item-title、item-after的包装器 --> <div class="item-inner"> <!-- 必需,单行的元素标题 --> <div class="item-title">列表元素的标题</div> <!-- 可选,标题后内容,可以是标记(badge)、开关、按钮等任意HTML,默认右侧对齐 --> <div class="item-after">列表元素的标签</div> </div> </div> </li> </ul> <!-- 可以在列表块的结尾处,添加一个列表块标签 --> <div class="list-block-label">列表块标签</div> </div> |
如果li元素内没有其它内容,你可以把item-content类标注到li元素上,少写一个div:
1 2 3 4 5 6 7 8 |
<li class="item-content"> <div class="item-media"> <i class="icon my-icon"></i> </div> <div class="item-inner"> <div class="item-title"></div> </div> </li> |
很多时候需要在点击列表条目后,链接到其它页面,这时需要为 <div class="item-content"> 添加额外的包装元素:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
<li> <!-- 额外的包装元素 --> <a href="#" class="item-link"> <!-- 导致列表右侧出现额外的箭头(链接)标记 --> <div class="item-content"> <div class="item-media"></div> <div class="item-inner"></div> </div> </a> </li> <li> <!-- 如果li下没有其它元素,则可以把a、div合并 --> <a href="#" class="item-link item-content"> <div class="item-media">...</div> <div class="item-inner">...</div> </a> </li> |
可以插入类似下面的li元素,将列表分为两个部分:
1 |
<li class="item-divider">Divider title here</li> |
可以将不同的列表元素进行分组:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
<div class="list-block"> <!-- 第一个分组 --> <div class="list-group"> <ul> <!-- 分组的标题 --> <li class="list-group-title"></li> <li class="item-content"></li> </ul> </div> <!-- 第二个分组--> <div class="list-group"> <ul> <li class="list-group-title"></li> <li class="item-content"> </li> </ul> </div> </div> |
列表块可以是Inset(非全宽度、圆角矩形边框)的:
1 2 3 4 5 6 7 |
<div class="list-block inset"> <ul></ul> </div> <!-- 仅在平板电脑上启用Inset效果 --> <div class="list-block tablet-inset"> <ul></ul> </div> |
该组件是分组列表的特例,用于显示联系人的列表,其布局如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
<!-- page-content元素必须有额外的contacts-content类 --> <div class="page-content contacts-content"> <!-- list-block元素必须有额外的contacts-block类 --> <div class="list-block contacts-block"> <div class="list-group"> <ul> <li class="list-group-title">汪</li> <li> <div class="item-content"> <div class="item-inner"> <div class="item-title">汪震</div> </div> </div> </li> <li> <div class="item-content"> <div class="item-inner"> <div class="item-title">汪静好</div> </div> </div> </li> </ul> </div> <div class="list-group"> <ul> <li class="list-group-title">李</li> <li> <div class="item-content"> <div class="item-inner"> <div class="item-title">李晓蒙</div> </div> </div> </li> </ul> </div> </div> </div> |
该组件是列表视图的扩展,用于显示更复杂的数据,其布局如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
<!-- 媒体列表有额外的media-list元素 --> <div class="list-block media-list"> <ul> <li> <!-- 必需的item-content,和列表视图一样,作为item-media、item-inner的包装器 --> <div class="item-content"> <!-- 可选的item-media --> <div class="item-media"> <img src="path/to/img.jpg"> </div> <div class="item-inner"><!-- 必须 --> <div class="item-title-row"><!-- 类似与列表视图 --> <div class="item-title">元素标题</div> <div class="item-after">元素标签</div> </div> <!--子标题,单行文本 --> <div class="item-subtitle">子标题</div> <!--占两行的额外文本 --> <div class="item-text">额外文本内容</div> </div> </div> </li> </ul> </div> |
该组件是列表视图的扩展,支持滑动手势(例如滑动以删除, swipe-to-delete),滑动后可以显示针对列表元素的隐藏按钮。 可滑动列表的布局如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
<div class="list-block"> <ul> <!-- li元素上需要额外的swipeout类 --> <li class="swipeout"> <!-- swipeout-content、swipeout-actions-left/right必须是直接子元素 --> <!-- 元素内容元素外部通常包裹swipeout-content元素 --> <div class="swipeout-content"> <!-- 如果只有item-content这一个子元素,那么它可以和父元素合并 --> <div class="item-content"> <div class="item-media"></div> <div class="item-inner"></div> </div> </div> <!-- 左侧操作集,手指向右滑动时的显示 --> <div class="swipeout-actions-left"> <!-- 这里可以是按钮、链接--> <a href="#">操作1</a> <a href="#">操作2</a> </div> <!-- 右侧操作集,手指向左滑动时的显示 --> <div class="swipeout-actions-right"> <a href="#">操作3</a> <!-- swipeout-close,点击后关闭(隐藏)操作集 --> <a class="swipeout-close" href="#">操作4</a> </div> </li> </ul> </div> |
F7对滑动删除这一经常使用的特性内置了支持,你只需要在操作集中增加 <a class="swipeout-delete"> 按钮即可。
1 2 3 4 5 6 7 |
<!-- 添加data-confirm,则在删除前会提示用户确认 --> <!-- 设置data-close-on-cancel为true,当用户点击确认框的取消按钮时,自动关闭当前列表元素的操作集 --> <a href="#" class="swipeout-delete" data-confirm="真的要删除吗" data-confirm-title="请确认" data-close-on-cancel="true" >删除</a> |
F7支持当滑动距离过长时,自动执行:
- 向左长滑时,自动执行右侧操作集的最后一个按钮上的动作
- 向右长滑时,自动执行左侧操作集的第一个按钮上的动作
启用长滑时,F7通过脚本触发相应按钮的click事件。在长滑执行期间,目标按钮会添加额外的 swipeout-overswipe-active 样式类。
启用长滑的示例代码如下:
1 2 3 4 5 6 7 8 9 10 |
<div class="swipeout-actions-left"> <!-- 左侧的第一个按钮,可以添加swipeout-overswipe以启用长滑 --> <a href="#" class="swipeout-overswipe bg-green reply">回复</a> <a href="#" class="bg-blue forward">转发</a> </div> <div class="swipeout-actions-right"> <a href="#" class="mark bg-orange">标记</a> <!-- 右侧的最后一个按钮,可以添加swipeout-overswipe以启用长滑 --> <a href="#" class="swipeout-delete swipeout-overswipe">删除</a> </div> |
方法/属性/事件 | 说明 | ||
app.swipeoutOpen() |
|
||
app.swipeoutClose() |
|
||
app.swipeoutDelete() |
|
||
app.swipeoutOpenedEl | 该属性指向当前处于打开状态的列表条目的HTMLElement | ||
⚡swipeout |
这些事件的Target都是 <li class="swipeout"> 元素
|
||
⚡open | |||
⚡opened | |||
⚡close | |||
⚡closed | |||
⚡delete | |||
⚡deleted |
该组件是列表视图的扩展,支持调整条目的顺序,其布局如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
<!-- 列表块元素上需要额外的sortable样式类 --> <div class="list-block sortable"> <ul> <li> <div class="item-content"> <div class="item-media"></div> <div class="item-inner"></div> </div> <!-- 一个可拖拽的小图标,用来调整条目的顺序,默认隐藏 --> <div class="sortable-handler"></div> </li> </ul> </div> |
通过HTML:
1 2 3 4 |
<!-- data-sortable指定目标可排序列表的CSS选择器 --> <a href="#" data-sortable=".sortable" class="open-sortable">启用排序</a> <a href="#" data-sortable=".sortable" class="close-sortable">禁用排序</a> <a href="#" data-sortable=".sortable" class="toggle-sortable">切换启禁用状态</a> |
通过JavaScript:
1 2 3 4 5 6 7 8 |
/** * @param sortableContainer * 可排序列表(<div class="list-block sortable">)的HTMLElement或者CSS选择器 * 如果不指定,F7尝试寻找第一个可排序列表 */ app.sortableOpen( sortableContainer ); // 启用 app.sortableClose( sortableContainer ); // 禁用 app.sortableToggle( sortableContainer ); // 切换 |
事件 | 说明 |
⚡open | 这两个事件的Target均为 <div class="list-block sortable"> 元素。分别在启用、禁用可排序功能时触发 |
⚡close | |
⚡sort | 该事件的Target为 <li> ,当用户释放拖拽小图标时触发 |
使用虚列表,我们可以在不影响性能的前提下展现具有大量元素的列表。虚列表和搜索栏、无限滚动、下拉刷新、滑动删除等F7组件完全兼容 。
1 2 3 4 |
<!-- 额外的virtual-list样式类 --> <div class="list-block virtual-list"> <!-- 内部保持空白 --> </div> |
需要调用JavaScript API来初始化虚列表的内容:
1 2 3 4 5 6 7 |
/** * 初始化一个虚列表 * @param listBlockContainer 列表块(list-block)的HTMLElement或者CSS选择器 * @param parameters 虚列表初始化参数 * @return 已初始化的初始化实例 */ app.virtualList( listBlockContainer, parameters ); |
注意列表块元素在此时必须已经存在于DOM中,如果当前不是首页,你应当在pageInit事件内初始化虚列表。
参数 | 类型和默认值 | 说明 |
items | array | 列表条目的数组。不使用模板时,其元素是HTML片段;使用模板时,其元素一般是纯数据(JSON对象) |
rowsBefore | number | 在当前屏幕滚动位置之前(即屏幕底部)渲染的条目的数量,默认是单屏可容纳行数的2倍 |
rowsAfter | number | 在当前屏幕滚动位置之后渲染的条目的数量,默认是单屏可容纳行数的1倍 |
cols | number = 1 | 每行显示的条目数量,当使用动态高度(height参数为函数)的虚列表时,此选项不兼容 |
height | number = 44 / function(item) |
每个条目的高度,如果指定函数,则高度为函数的返回值 注意,该参数并不会设置条目的高度样式 |
template | string / function | Template7字符串模板或者Template已编译模板(函数形式),用来渲染单个条目。该目标必须包含条目的完整布局,包括li元素 |
renderItem | function(index, item) | 该函数可以代替template来渲染每个条目 |
dynamicHeightBufferSize | number = 1 | 用于动态高度列表,控制缓冲大小(buffer size) |
cache | boolean = true | 是否启用已渲染条目的DOM缓存。如果列表条目中包含用户交互元素(按钮、表单元素等)或者列表条目可能被修改,可以启用 |
updatableScroll | boolean | 在滚动时,设备是否更新、处理滚动事件。默认对于所有iOS 8-为fasle |
showFilteredItemsOnly | boolean = false | 是否仅显示 filter() 过滤后的元素 |
searchByItem | function(query, index, item) | 搜索栏使用的搜索判断函数,入参包括查询条件、待判断条目及其索引。如果条目匹配搜索,则该函数应当返回true |
searchAll | function(query, items) | 搜索栏使用的搜索函数,你必须遍历items,并返回匹配的item数组 |
onItemBeforeInsert | function(list, item) | 回调,条目被插入到虚拟文档片段(virtual document fragment)中时调用 文档片段相当于包含了本次待渲染的列表条目的临时DOM,下同 |
onBeforeClear | function(list, fragment) | 回调,当前DOM列表将被移除前调用 |
onItemsBeforeInsert | function(list, fragment) | 回调,当前DOM列表将被移除后,新的文档片段被插入前调研与 |
onItemsAfterInsert | function(list, fragment) | 回调,新的文档片段被插入后调用 |
方法/属性 | 说明 |
items | 虚列表包含的条目 |
filteredItems | 过滤后的条目 |
domCache | 条目的DOM缓存 |
params | 所有初始化参数 |
listBlock | list-block的Dom7元素实例 |
pageContent | page-content的Dom7元素实例 |
currentFromIndex | 当前正在渲染的第一个条目的索引 |
currentToIndex | 当前正在渲染的最后一个条目的索引 |
reachEnd | 如果当前已经渲染了最后一个条目,则为true |
filterItems(indexes) | 仅显示indexes数组中包含的条目 |
resetFilter() | 禁用过滤器,显示全部条目 |
appendItem(item) | 添加条目到虚列表的尾部 |
appendItems(items) | |
prependItem(item) | 添加条目到虚列表的头部 |
prependItems(items) | |
replaceItem(index, items) | 从指定索引开始替换条目 |
replaceAllItems(items) | 替换全部条目 |
moveItem(oldIdx, newIdx) | 将虚拟条目从oldIndex移动到newIdx |
insertItemBefore(index, item) | 在指定索引前面插入元素 |
deleteItem(index) | 删除指定索引上的元素 |
deleteItems(indexes) | |
deleteAllItems() | 删除全部元素 |
clearCache() | 清空DOM缓存 |
destroy() | 销毁虚列表的实例,解除所有事件注册 |
update() | 更新虚列表,重新计算列表的size、重新渲染虚列表 |
scrollToItem(index) | 滚动虚拟列表到指定的索引 |
注意,上述添加、删除、改变列表元素的方法,其操作结果会立即反应到视图上。
通用的手风琴布局如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<!-- 手风琴条目列表 --> <div class="accordion-list"> <!-- 手风琴条目 --> <div class="accordion-item"> <!-- 触碰后展开/折叠条目内容,必需 --> <div class="accordion-item-toggle"></div> <!-- 默认隐藏的条目内容,必需 --> <div class="accordion-item-content"></div> </div> <!-- 处于展开状态的手风琴条目,只能有一个 --> <div class="accordion-item accordion-item-expanded"> <div class="accordion-item-toggle"></div> <div class="accordion-item-content"></div> </div> </div> |
手风琴布局实质上是多个联动的可折叠条目的集合 ,可收折叠的手风琴条目可以脱离 accordion-list 单独使用:
1 2 3 4 |
<div class="accordion-item"> <div class="accordion-item-toggle"></div> <div class="accordion-item-content"></div> </div> |
可以把手风琴布局和列表视图结合起来使用:
1 2 3 4 5 6 7 8 9 10 11 12 |
<div class="list-block accordion-list"> <ul> <li class="accordion-item"><!-- 使用li代替通用手风琴布局中的div --> <a href="" class="item-link item-content"><!-- 使用item-link代替accordion-item-toggle --> <div class="item-inner"> <div class="item-title">条目标题</div> </div> </a> <div class="accordion-item-content">条目内容</div> </li> </ul> </div> |
可以通过如下方式修改手风琴条目展开、折叠时的样式:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
<div class="content-block accordion-list custom-accordion"> <div class="accordion-item"> <div class="accordion-item-toggle"> <!-- 折叠时的图标,显示一个+号 --> <i class="icon icon-plus">+</i> <!-- 展开时的图标,显示一个-号 --> <i class="icon icon-minus">-</i> <span>条目标题</span> </div> <div class="accordion-item-content"> <p>条目内容</p> </div> </div> </div> <style> /* 设置折叠、展开图标的边框为圆形 */ .custom-accordion .icon-plus, .custom-accordion .icon-minus { display: inline-block; width: 22px; height: 22px; border: 1px solid #000; border-radius: 100%; line-height: 20px; text-align: center; } </style> |
1 2 3 4 5 6 7 |
/** * @param item * 手风琴条目(accordion-item)的HTMLElement或CSS选择器 */ app.accordionOpen( item ); // 展开手风琴条目 app.accordionClose( item ); // 折叠手风琴条目 app.accordionToggle( item );// 切换手风琴条目的展开/折叠状态 |
以下4个事件的Target均为 <div class="accordion-item"> 。触发时机分别为:
- open 条目打开动画开始时
- opened 条目打开动画结束时
- close 条目关闭动画开始时
- closed 条目关闭动画结束时
类似于列表视图,卡片也是包含和组织相关信息的常用方式。单张卡片常常包含一些相关的图片、文字、连接信息,作为更详细信息的入口,本站的首页就是卡片布局典型的例子。F7完整的支持卡片布局。
1 2 3 4 5 6 7 8 9 10 11 12 |
<!-- 卡片容器 --> <div class="card"> <!-- 卡片头部,常常显示卡片标题,可选 --> <div class="card-header">Header</div> <!-- 卡片主体部分,必需 --> <div class="card-content"> <!-- 可选的内部包装元素,添加额外的补白 --> <div class="card-content-inner">Card content</div> </div> <!-- 卡片脚注,包含一些附加信息,链接/动作按钮等,可选 --> <div class="card-footer">Footer</div> </div> |
注意,卡片头、脚使用flexbox布局(display:flex),在垂直方向默认居中对齐。如果你需要顶部/底部对齐,可以:
1 2 |
<div class="card-header" valgin="top"> <div class="card-footer" valgin="bottom"> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<!-- 需要为列表块添加额外的样式类cards-list --> <div class="list-block cards-list"> <ul> <li class="card"><!-- 条目元素需要添加card类 --> <div class="card-header">Card Header</div> <div class="card-content"> <div class="card-content-inner">Card content</div> </div> <div class="card-footer">Card footer</div> </li> <li class="card"> <div class="card-header">Card Header</div> <div class="card-content"> <div class="card-content-inner">Card content</div> </div> <div class="card-footer">Card footer</div> </li> </ul> </div> |
该组件只适用于Material主题。
Chips在一个很小的内联块中显示复杂的信息,其中可以包含照片、小标题、文本。在视觉效果上,Chip表现为圆角小矩形:
1 2 3 4 5 6 7 8 9 10 11 |
<!-- 容器元素 --> <div class="chip"> <!-- 媒体元素,指定一个图片/头像等,可选 --> <div class="chip-media"> <img src="avator/alex.png"> </div> <!-- 文本标签 --> <div class="chip-label">Alex Wong</div> <!-- 删除按钮,可选 --> <a href="#" class="chip-delete"></a> </div> |
F7框架包含了大量开箱即用的按钮组件,只需要把合适的样式类添加到链接/按钮/提交input元素上即可。
F7中的按钮默认均为 display:block ,且占据父容器100%宽度。
普通按钮,默认具有蓝色边框和蓝色文字样式:
1 2 |
<p><a href="#" class="button">Button</a></p> <p><a href="#" class="button">Button</a></p> |
激活态按钮,默认具有蓝色背景和白色文字样式:
1 |
<a href="#" class="button active">Active Button</a> |
圆角按钮,具有更加圆润的边框:
1 |
<p><a href="#" class="button button-round">Round Button</a></p> |
大按钮,比普通按钮更高:
1 |
<a href="#" class="button button-big">Big Button </a> |
按钮行,其中每个按钮具有相同的宽度,没有边距:
1 2 3 4 5 |
<p class="buttons-row"> <a href="#" class="button">Button 1</a> <a href="#" class="button">Button 2</a> <a href="#" class="button">Button 3</a> </p> |
填充按钮,看上去和激活态按钮类似,但是点击/触碰时有额外的样式效果:
1 |
<a href="#" class="button button-fill">Fill Button </a> |
彩色按钮:
1 2 3 4 5 6 7 8 |
<!-- 彩色按钮,在按钮行上指定主题 --> <p class="buttons-row theme-pink"> <a href="#" class="button active">Button 1</a> <a href="#" class="button">Button 2</a> <a href="#" class="button">Button 3</a> </p> <!-- 彩色按钮,指定单个按钮的颜色类 --> <a href="#" class="button button-fill color-green">Green</a> |
由按钮组成的列表视图:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<div class="content-block-title">Inset list block buttons</div> <div class="list-block inset"> <ul> <li> <a href="#" class="item-link list-button">List Button 1</a> </li> <li> <a href="#" class="item-link list-button">List Button 2</a> </li> <li> <a href="#" class="item-link list-button">List Button 3</a> </li> </ul> </div> |
使用网格布局对按钮进行排版,这样可以让按钮之间有边距:
1 2 3 4 5 6 7 8 |
<div class="row"> <div class="col-50"> <a href="#" class="button button-big button-red">Cancel</a> </div> <div class="col-50"> <a href="#" class="button button-big button-green">Submit</a> </div> </div> |
普通按钮,与iOS主题类似,但是没有边框:
1 |
<p><a href="#" class="button">Button</a></p> |
按钮行,与iOS主题类似,但是没有边框:
1 2 3 4 |
<p class="buttons-row"> <a href="#" class="button">Button</a> <a href="#" class="button">Button</a> </p> |
浮雕效果按钮(Raised Buttons) ,具有阴影效果:
1 |
<a href="#" class="button button-raised">Button</a> |
填充按钮,默认具有蓝色背景和白色文字:
1 |
<a href="#" class="button button-fill button-raised">Button</a> |
为Material波纹效果(从触碰点向周围扩散的动画)指定颜色:
1 |
<a href="#" class="button color-green ripple-pink">Button</a> |
大按钮、列表块按钮、彩色按钮与iOS主题类似。
浮动动作按钮(FAB)仅适用于Material主题,在视觉效果上,它表现为浮动的(不随页面滚动,通常位于屏幕右下角)、圆形的的按钮 。触碰后,FAB可能会:
- 变形:转换为一个Popover
- 快速拨号:弹出一组相关的按钮
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
<!-- 当前页面 --> <div class="page navbar-fixed"> <!-- 导航栏--> <div class="navbar"> <div class="navbar-inner"> <div class="center"></div> </div> </div> <!-- 浮动动作按钮 --> <a href="#" class="floating-button color-pink"> <i class="icon icon-plus"></i><!-- 按钮图标 --> </a> <!-- 可滚动的页面内容 --> <div class="page-content"> <div class="content-block"></div> </div> </div> |
如果你需要在触碰FAB后显示一个Popover,可以:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
<div class="page navbar-fixed"> <!-- open-popover 用于打开一个Popover --> <!-- floating-button-to-popover 在打开Popover时显示变形动画 --> <!-- data-popover指定目标Popover的CSS选择器 --> <a href="#" data-popover=".demo-popver" class="floating-button floating-button-to-popover open-popover color-purple"> <i class="icon icon-plus"></i> </a> </div> <!-- Popover --> <div class="popover demo-popover"> <div class="popover-inner"> <div class="list-block"> <ul> <li> <a href="#" class="item-content item-link"> <div class="item-inner"> <div class="item-title">Link</div> </div> </a> </li> </ul> </div> </div> </div> |
可以在触碰FAB后,向上动画弹出一组按钮。再次触碰FAB,则按相反的动画隐藏这些按钮。你应当保证按钮组元素的数量在3-6之间:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
<div class="page navbar-fixed"> <div class="navbar"> <div class="navbar-inner"> <div class="center"></div> </div> </div> <!-- 快速拨号包装元素 --> <div class="speed-dial"> <a href="#" class="floating-button"> <!-- 第一个按钮:快速拨号按钮组处于关闭状态时显示 --> <i class="icon icon-plus"></i> <!-- 第二个按钮:快速拨号按钮组处于打开状态时显示 --> <i class="icon icon-close"></i> </a> <!-- 快速拨号按钮组 --> <div class="speed-dial-buttons"> <!-- 第一个按钮(最下面) --> <a href="#"> <i class="icon demo-icon-email"></i> </a> <!-- 第二个按钮 --> <a href="#"> <i class="icon demo-icon-calendar"></i> </a> <!-- 第三个按钮 --> <a href="#"> <i class="icon demo-icon-upload"></i> </a> </div> </div> <div class="page-content"></div> </div> |
F7支持大量的表单元素类型,表单元素通常在列表视图中组织。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<!-- 表单中的元素(字段)往往放置到一个列表视图中 --> <form id="formx" class="list-block"> <!-- 有时也使用div元素 --> <ul> <li> <div class="item-content"> <!-- 图标为可选元素 --> <div class="item-media">字段图标</div> <div class="item-inner"> <!-- 标签为可选元素 --> <div class="item-title label">字段标签</div> <!-- 表单元素的包装元素 --> <div class="item-input"> <!-- 各类型字段的HTML标记存放在这里 --> </div> </div> </div> </li> </ul> </form> |
可以放在 <div class="item-input"> 内部的表单元素如下表:
元素类型 | 说明 | ||||
各种文本元素 | 支持text、password、email、url、tel、date、number、datetime-local等类型:
|
||||
选择菜单 |
|
||||
多行文本 |
注意,作为列表条目时,需要额外的对齐属性:
|
||||
可缩放多行文本 | 文本框的大小会随着其内容自动缩放:
|
||||
开关 | 需要额外的包装元素:
|
||||
滑块 | 可以选择一个范围的值,需要额外的包装元素:
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 |
<form id="formx" class="list-block"> <ul> <!-- 文本输入 --> <li> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-name"></i> </div> <div class="item-inner"> <div class="item-title label">Name</div> <!-- 普通文本框 --> <div class="item-input"> <input type="text" placeholder="Your name"> </div> </div> </div> </li> <li> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-email"></i> </div> <div class="item-inner"> <div class="item-title label">E-mail</div> <div class="item-input"> <!-- 电子邮件 --> <input type="email" placeholder="E-mail"> </div> </div> </div> </li> <!-- 下拉选择菜单 --> <li> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-gender"></i> </div> <div class="item-inner"> <div class="item-title label">Gender</div> <div class="item-input"> <select> <option>Male</option> <option>Female</option> </select> </div> </div> </div> </li> <!-- 日期控件 --> <li> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-calendar"></i> </div> <div class="item-inner"> <div class="item-title label">Birth date</div> <div class="item-input"> <input type="date" placeholder="Birth day" value="2014-04-30"> </div> </div> </div> </li> <!-- 开关 --> <li> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-toggle"></i> </div> <div class="item-inner"> <div class="item-title label">Switch</div> <div class="item-input"> <label class="label-switch"> <input type="checkbox"> <div class="checkbox"></div> </label> </div> </div> </div> </li> <!-- 滑块 --> <li> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-settings"></i> </div> <div class="item-inner"> <div class="item-title label">Slider</div> <div class="item-input"> <div class="range-slider"> <input type="range" min="0" max="100" value="50" step="0.1"> </div> </div> </div> </div> </li> <!-- 多行文本 --> <li class="align-top"> <div class="item-content"> <div class="item-media"> <i class="icon icon-form-comment"></i> </div> <div class="item-inner"> <div class="item-title label">Textarea</div> <div class="item-input"> <textarea></textarea> </div> </div> </div> </li> </ul> </form> |
这是一个列表视图的扩展,可用于创建复选框/单选框的分组。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
<div class="list-block"> <ul> <!-- 第一个复选框 --> <li> <!-- 列表条目的内容必须是label元素,且添加样式类label-checkbox --> <label class="label-checkbox item-content"> <!-- input必须是第一个元素 --> <input type="checkbox" name="my-checkbox" value="Books" checked="checked"><!-- 默认选中 --> <!-- 图标 --> <div class="item-media"> <i class="icon icon-form-checkbox"></i> </div> <!-- 文本 --> <div class="item-inner"> <div class="item-title">Books</div> </div> </label> </li> <!-- 第二个复选框 --> <li> <label class="label-checkbox item-content"> <input type="checkbox" name="my-checkbox" value="Movies"> <div class="item-media"> <i class="icon icon-form-checkbox"></i> </div> <div class="item-inner"> <div class="item-title">Movies</div> </div> </label> </li> </ul> </div> |
Material主题支持额外的图标,iOS主题则不支持图标:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
<div class="list-block"> <ul> <!-- 第一个单选框 --> <li> <!-- 列表条目的内容必须是label元素,且添加样式类label-radio --> <label class="label-radio item-content"> <!-- input必须是第一个元素 --> <input type="radio" name="my-radio" value="Books" checked="checked"><!-- 默认选中 --> <!-- 图标,仅Material主题支持 --> <div class="item-media"> <i class="icon icon-form-radio"></i> </div> <div class="item-inner"> <div class="item-title">Books</div> </div> </label> </li> <!-- 第二个单选框 --> <li> <label class="label-radio item-content"> <input type="radio" name="my-radio" value="Movies"> <div class="item-inner"> <div class="item-title">Movies</div> </div> </label> </li> </ul> </div> |
复选框组、单选框组可以和媒体列表视图一起工作,展现更丰富的内容。下面是一个示例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
<div class="content-block-title">你最喜爱的歌曲是?</div> <div class="list-block media-list"> <ul> <li> <label class="label-radio item-content"> <input type="radio" name="my-radio" checked> <div class="item-media"> <img src="..." width="80"> </div> <div class="item-inner"> <div class="item-title-row"> <div class="item-title">黄色潜水艇</div> <div class="item-after">$15</div> </div> <div class="item-subtitle">披头士</div> <div class="item-text">披头士乐队60年代的一首著名歌曲</div> </div> </label> </li> </ul> </div> |
使用智能选择,并结合复选框组/单选框组,你可以轻易的把常规的下拉菜单(select) 转换为动态页面。在Native的iOS应用中,经常可以看到类似的UI特性。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
<form class="list-block"> <ul> <!-- 第一个智能选择组件 --> <li> <!-- 需要额外的 "smart-select" 样式类 --> <a href="#" class="item-link smart-select"> <select name="fruits"> <option value="apple" selected>苹果</option> <option value="pineapple">橘子</option> </select> <!-- 在列表视图中显示的内容 --> <div class="item-content"> <div class="item-inner"> <!-- 文本 --> <div class="item-title">水果</div> <!-- 哪个菜单选项处于选中状态 --> <div class="item-after">苹果</div> </div> </div> </a> </li> <!-- 第二个智能选择组件 --> </ul> </form> |
注意智能选择只能在已初始化的视图中使用。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<div class="list-block"> <ul> <!-- 带搜索栏的智能选择条目 data-searchbar 为此智能选择启用搜索栏 data-searchbar-placeholder 搜索框的占位符文本 data-searchbar-cancel 取消按钮的文本 --> <li> <a href="#" class="item-link smart-select" data-searchbar="true" data-searchbar-placeholder="Search fruits"> </a> </li> </ul> </div> |
默认的,智能选择子页面的标题与父页面一致,返回按钮的文本默认则由应用初始化参数 smartSelectBackText 指定。这些文本都可以定制:
1 2 3 4 5 6 7 8 9 10 11 |
<div class="list-block"> <ul> <!-- data-page-title 子页面标题 data-back-text 子页面返回按钮文本 --> <li> <a href="#" class="item-link smart-select" data-page-title="美味的水果" data-back-text="返回"></a> </li> </ul> </div> |
F7支持以Popup的方式打开智能选择组件,设置应用初始化参数 smartSelectOpenIn:'popup' 则默认所有智能选择均以Popup的方式打开。下面演示如何指定单个智能选择以Popup方式打开:
1 2 3 4 5 6 7 8 |
<div class="list-block"> <ul> <li> <!-- data-open-in设置为popup,则以弹窗方式打开智能选择 --> <a href="#" class="item-link smart-select" data-open-in="popup"> </a> </li> </ul> </div> |
F7还支持在选取器模态窗口,而不是页面中打开智能选择组件,设置应用初始化参数 smartSelectOpenIn:'picker' 则默认所有智能选择均以Picker的方式打开。下面演示如何指定单个智能选择以Picker方式打开:
1 2 3 4 5 6 7 8 9 10 11 |
<div class="list-block"> <ul> <li> <!-- data-open-in设置为picker,则以选取器方式打开智能选择 data-picker-height 指定选取器的高度 --> <a href="#" class="item-link smart-select" data-open-in="picker" data-picker-height="200px"></a> </li> </ul> </div> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<a href="#" class="item-link smart-select"> <!-- 在select元素上添加data-option-image、data-option-icon,为所有选项指定默认图标 --> <select name="fruits" data-option-image=""> <!-- data-option-image 指定图标 --> <option value="apple" selected data-option-image="">苹果</option> <option value="pineapple" data-option-image="">菠萝</option> <!-- data-option-color 指定文本颜色 --> <option value="pear" data-option-color="orange" data-option-image>梨</option> </select> <div class="item-content"> <div class="item-inner"> <div class="item-title">水果</div> </div> </div> </a> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 |
<div class="list-block"> <ul> <li> <a href="#" class="item-link smart-select"> <!-- multiple :表示支持多选 --> <!-- maxlength:指定最多选中的选项个数 --> <select name="car" multiple maxlength="3"> <!-- 使用optgroup,可以将选项分组,组名由label指定 --> <optgroup label="日产"> <option value="honda" selected>本田</option> <option value="lexus">雷克萨斯</option> <option value="mazda">马自达</option> <option value="nissan">尼桑</option> <option value="toyota">丰田</option> </optgroup> <optgroup label="德产"> <option value="audi">奥迪</option> <option value="bmw">宝马</option> <option value="mercedes">奔驰</option> <option value="volvo">沃尔沃</option> </optgroup> </select> <div class="item-content"> <div class="item-inner"> <div class="item-title">汽车品牌</div> </div> </div> </a> </li> </ul> </div> |
1 2 3 4 5 6 7 8 9 10 11 |
<div class="list-block"> <ul> <li> <!-- 设置data-back-on-select="true" 则智能选择可以自动关闭 --> <a href="#" class="item-link smart-select" data-back-on-select="true"> <select></select> <div class="item-content"></div> </a> </li> </ul> </div> |
如果选项特别多(例如1000个),则可以使用虚列表:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<div class="list-block"> <ul> <li> <!-- data-virtual-list="true" 使用虚列表 data-virtual-list-height="55"设置虚列表单条目的高度为55px --> <a href="#" class="item-link smart-select" data-virtual-list="true" data-virtual-list-height="55"> <select name="numbers"> <option value="1">1</option> <option value="2">2</option> ... <option value="100000">100000</option> </select> <div class="item-content"></div> </a> </li> </ul> </div> |
可以为智能选择页面、Popup设置主题:
1 2 3 4 5 6 7 8 9 10 11 12 |
<div class="list-block"> <ul> <li> <!-- data-navbar-theme="red" 设置导航栏为红色主题 --> <!-- data-form-theme="green" 设置表单为绿色主题 --> <a href="#" class="item-link smart-select" data-navbar-theme="red" data-form-theme="green"> <select name="car"></select> <div class="item-content"></div> </a> </li> </ul> </div> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<div class="list-block"> <ul> <li> <a href="#" class="item-link smart-select"> <select name="fruits"> <option value="apple">Apple</option><!-- 被选中 --> <option value="pineapple">Pineapple</option> </select> <div class="item-content"> <div class="item-inner"> <div class="item-title">Fruit</div> <!-- 在item-after元素上设置smart-select-value,则其文本对应的选项自动选中 --> <div class="item-after smart-select-value">Apple</div> </div> </div> </a> </li> </ul> </div> |
方法 | 说明 | ||
app.smartSelectOpen() |
|
||
app.smartSelectAddOption() |
|
F7支持为任何元素添加“禁用”样式:
- disabled样式类:可以为任何元素添加禁用样式
- disabled属性:可以为表单元素添加禁用样式
被禁用的元素具有较低的不透明度,而且不接受任何touch/click事件。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<div class="list-block"> <ul> <!-- 此列表条目被禁用 --> <li class="item-content disabled"> <div class="item-inner"> <div class="item-title"></div> </div> </li> <!-- 此条目的表单元素被禁用 --> <li class="item-content"> <div class="item-inner"> <div class="item-input"> <!-- 禁用的元素 --> <input type="text" name="name" disabled> </div> </div> </li> </ul> </div> |
F7提供了一些便利的方法,用来收集表单数据为JSON,或者读取JSON并设置表单元素的值。
方法 | 说明 | ||
app.formToJSON() |
注意:
|
||
app.formFromJSON() |
|
F7支持自动存储/加载表单数据,即使是Ajax页面也支持。要启用本地存储,只需要:
- 为表单添加额外的样式类:store-data
- 为表单设置id属性
- 为所有表单字段设置name属性,不设置的字段将被忽略
JavaScript API不需要直接调用。下面是一个样例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
<!-- 设置表单的id,添加store-data样式类 --> <form id="my-form" class="list-block store-data"> <ul> <li> <div class="item-content"> <div class="item-inner"> <div class="item-title label">姓名</div> <div class="item-input"> <!-- 确保表单元素具有name属性 --> <input type="text" name="name" placeholder="请输入你的姓名"> </div> </div> </div> </li> <li> </ul> </form> |
- 在监听到 pageInit 事件后,F7会调用 formFromJSON 函数,从HTML5的本地存储(Local Storage)中加载数据
- 在监听到表单元素的 change 事件后,F7会调用 formToJSON() 函数,存储最新的表单元素值到本地存储中
任何一个表单都具有自己的本地存储键,键命名规则为 localStorage.f7form-[formID] ,其中formID就是表单的id属性。本地存储的值是串行化后的JSON对象。
F7提供了一些API,可以用来管理表单的本地存储:
方法/事件 | 说明 |
app.formGetData(formId) | 获得特定表单的本地存储,返回JSON对象 |
app.formDeleteData(formId) | 删除特地表单的本地存储 |
formStoreData(formId, formJSON) | 以formJSON替换特定表单的本地存储 |
⚡formFromJSON | formFromJSON()方法被调用后触发 |
⚡formToJSON | formToJSON()方法被调用后触发 |
F7支持基于Ajax的自动表单提交,自动提交有两种方式
- 当用户点击submit按钮时,或者表单的submit事件被手工触发时
- 当用户修改表单字段值时,或者表单/表单元素的change事件被手工触发时
1 2 3 4 5 6 7 |
<!-- 添加ajax-submit样式类,则表单支持submit事件时自动提交 action 存放接受请求的地址 method 使用的HTTP方法 enctype HTML的内容类型(Content type) --> <form action="/save" method="GET" class="ajax-submit" enctype="application/x-www-form-urlencoded"></form> |
与上面类似:
1 |
<form action="/save" method="GET" class="ajax-submit-onchange"></form> |
事件 | 说明 | ||
⚡submitted |
这些事件的Target均为 <form class="ajax-submit"> 元素。分别在:
触发。示例:
|
||
⚡beforeSubmit | |||
⚡submitError |
使用页签,可以方便的在不同内容直接切换。
1 2 3 4 5 6 7 |
<!-- 页签包装元素 --> <div class="tabs"> <!-- 页签,必须具有tab类,唯一的id,激活的(可见)页签添加active类 --> <div class="tab active" id="tab1">页签一的内容</div> <div class="tab" id="tab2">页签二的内容</div> <div class="tab" id="tab3">页签三的内容</div> </div> |
1 2 3 4 5 6 |
<!-- 为链接添加tab-link类,则它可以用来打开页签 --> <!-- href指定页签的id --> <!-- active指定此链接的样式为激活的 --> <a href="#tab1" class="tab-link active">页签一</a> <a href="#tab2" class="tab-link">页签二</a> <a href="#tab3" class="tab-link">页签三</a> |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
<div class="page-content"> <div class="content-block"> <!-- 按钮组,用于控制页签 --> <div class="buttons-row"> <a href="#tab1" class="tab-link active button">Tab1</a> <a href="#tab2" class="tab-link button">Tab2</a> <a href="#tab3" class="tab-link button">Tab3</a> </div> </div> <!-- 页签--> <div class="tabs"> <div id="tab1" class="tab active"> <div class="content-block"></div> </div> <div id="tab2" class="tab"> <div class="content-block"></div> </div> <div id="tab3" class="tab"> <div class="content-block"></div> </div> </div> </div> |
有时需要在点击链接时,打开(属于不同页签的)多个标签页,这时可以使用data-tab属性而不是href:
1 2 3 4 5 6 7 8 9 10 11 |