分析的程序来源:
https://my.oschina.net/u/1012086/blog/751455
作者: 黄秀杰
OsChina地址: http://git.oschina.net/dotton/news/tree/master
其实该代码的作者的博文里面已经写的很清楚了. 我只是站在一个分析者的角度学习一下.
有些小问题我已经反馈给了作者. 坐等作者更新吧.
"pages":[
"pages/index/index",
"pages/detail/detail"
]
从pages数组看出, 程序只有两个页面.
从页面上看, 新闻列表头部是一个swiper, 底下就是之前讲过的列表渲染. 我们从index.wxml开始解读.
<swiper indicator-dots="true"
autoplay="true" interval="5000" duration="1000">
<block wx:for="{{topNews}}">
<swiper-item>
<image src="{{item.thumbnail_pic_s02}}" mode="aspectFill" class="slide-image" width="375" height="250"/>
swiper-item>
block>
swiper>
这个是swiper的用法. 微信已经帮你集成好了轮播图组件. 文档-swiper
有几个比较常用的属性indicator-dots(是否显示指示点),autoplay(是否自动播放),interval(事件间隔),bindchange(滑动change事件).
swiper有个特别要注意的地方就是中只可放置组件,其他节点会被自动删除。
代码中使用了block wx:for的列表渲染结构. 文档-列表渲染
利用数据绑定topNews数组, 每个swiper-item中显示一张图片.
虽然image设置了aspectFill属性,但是在实际调试看起来并没有铺满.
底下就是列表项了. 经过之前文章的讲解, 这个很容易看懂.
<view class="container news-list">
<block wx:for="{{techNews}}">
<view class="news-item" data-title="{{item.title}}" data-url="{{item.url}}" bindtap="bindViewTap">
<image src="{{item.thumbnail_pic_s}}" mode="aspectFill" class="list-image"/>
<view class="news-text">
<text class="news-title">{{item.title}}text>
<view class="news-stamp">
<text>{{item.author_name}}text>
<text>{{item.date}}text>
view>
view>
view>
block>
view>
这样的布局逻辑结构很清晰. 一个包裹所有item的view, 利用列表渲染生成多个item,每个item都包括左侧的一张图片还有标题和时间戳等.
不过我有一点比较好奇的是, 当显示的项目超过屏幕高度时, 显示出来的效果是可以滚动, 这里并没有添加srcoll-view. 这一点和Android好像不同.
这里面有两个属性data-title, data-url和事件处理有关,在讲解代码的时候再说.文档-事件
data: {
topNews:[], //顶部新闻
techNews:[] //列表新闻
},
onLoad: function () {
var that = this
// 访问聚合数据的网络接口-头条新闻
wx.request({
url: 'http://v.juhe.cn/toutiao/index',
data: {
type: 'topNews' ,
key: '482e213ca7520ff1a8ccbb262c90320a'
},
header: {
'Content-Type': 'application/json'
},
success: function(res) {
if (res.data.error_code == 0) {
that.setData({
topNews:res.data.result.data
})
} else {
console.log('获取失败');
}
}
})
// 访问聚合数据的网络接口-科技新闻
wx.request({
url: 'http://v.juhe.cn/toutiao/index',
data: {
type: 'keji' ,
key: '482e213ca7520ff1a8ccbb262c90320a'
},
header: {
'Content-Type': 'application/json'
},
success: function(res) {
if (res.data.error_code == 0) {
that.setData({
techNews:res.data.result.data
})
} else {
console.log('获取失败');
}
}
})
},
利用wx.request()发起请求. 这个看API就能懂. 文档-发起请求.
注意的是这里var that=this
, 在success()中调用则是
that.setData({
techNews:res.data.result.data
})
一般而言,在Javascript中,this指向函数执行时
的当前对象。所以不能使用this.setData(). 这一点和Android中this类似(在Activity的匿名内部类中使用this, 这个this表示匿名内部类的对象).
前面从wxml中看到每个item的view都bind了tap事件.
//事件处理函数
bindViewTap: function(event) {
wx.navigateTo({
url: '../detail/detail?title='+event.currentTarget.dataset.title+'&url='+event.currentTarget.dataset.url
})
},
bind事件绑定不会阻止冒泡事件向上冒泡. 事件对象event有两个重要的属性target和currentTarget. target表示触发事件的源组件, currentTarget表示事件绑定的当前组件. 文档-事件
currentTarget对象有一个dataset的属性. dataset属性允许在组件中自定义数据,这些数据将会通过事件传递给AppService。以data-开头,多个单词由连字符-链接.
我们之前看到的在item的view中写的属性data-title, data-url就是事件对象event中包含的dataset.
<view class="news-item" data-title="{{item.title}}" data-url="{{item.url}}" bindtap="bindViewTap">
也就是说当item的view触发tap事件时, 设置在view的data-title, data-url将封装到最终的事件对象event中. 这样我们在js中就可以获得这些值了. event.currentTarget.dataset.title
和 event.currentTarget.dataset.url
.
wx.navigateTo({
url: '../detail/detail?title='+event.currentTarget.dataset.title+'&url='+event.currentTarget.dataset.url
})
这里利用导航的API进行页面间的跳转wx.navigateTo(). 文档-导航
从url的组成形式来看, 完全是http的那一套. 多个参数之间利用&链接.
这个页面其实是个半成品. 作者的原意是要显示一个网页的. 但是没有找到类似Android平台的webview控件, 所以基本上没有功能.
Page({
data: {
title:'',
url:''
},
onLoad: function (options) {
this.setData({
title:options.title,
url:options.url
})
}
})
这里还是只讲一下如何获得从其他页面传过来的值的问题.
page的生命周期方法onLoad有个参数options. 我们可以直接从options中获得页面路由携带的参数.
目前作者的代码也就更新到这里. 暂时就讲解到这里.
the end.