去哪儿首页下拉加载优化

 

刚入职去哪儿时做的一个下拉加载交互,最近有些时间所以就将设计和Demo制作过程进行整理分享。

背景:

  1. 首页APP下拉只有slogan的曝光尚未有下拉请求刷新的功能;
  2. 整个首页在品牌调性传达上较弱,没有差异化的品牌设计。

设计目的:融入品牌形象进行趣味化的表达,增强APP首页的品牌调性

一、故事场景构建:

因为咱们一开始敲定品牌形象是一只具象的骆驼,所以这也决定了整个动画也只能具象化的场景故事,而且要让故事有趣有逻辑最好是下拉过程动画和加载中动画有故事串联,小骆驼角色最好有一些贱萌的属性取悦年轻用户…等等这些在设计初我就对场景和角色进行了一些不成形的设想。

基于设想通过一系列脑暴后,做实了其中一版方案决定落地:

  1. 初始态:小骆驼在沉睡;
  2. 下拉中:沉睡中的小骆驼的鼻涕泡变大;
  3. 加载中,小骆驼被唤醒,破涕泪奔…

二、角色动画设计

最难的创意部分通过后,剩下的就是AE落地实现啦。这个阶段得注意两个部分:1.下拉加载前后动画衔接上不要有跳帧 2.加载中的动画需要设计成可循环。AE动画渲染时我们截断成前后两段动画输出:下拉中的动画是和下拉交互联动的、我们输出序列帧;加载中的动画我们导出个循环的gif就好。

因为不是工具类教程这里不作过多赘述,唯一要注意的是输出视频的帧速率需要控制在24~30fps内才能保证动画的流畅性。

 

三、交互原型试做

从单单一个动画概念到落地其实还有一段距离:页面布局、下拉的距离、释放的位置、动画流畅性等等一大堆细节需要你在交互文档里标注。尴尬的是这些参数在没有原型校验的情况下了也只能给个大概数,剩下的只能是坐在程序员旁边一点点调试。

与其把风险留在开发阶段不如自己先写一个原型进行一番验证,其实下拉加载交互也不是很复杂,打开Framer剖析下如何按程序的思路一步步分解落地。

 

第一步:页面搭建:这里页面元素包括动画视窗、动画帧容器(这里我用的雪碧图)、加载文案、Scroll组件;其中动画帧容器是剪切进动画视窗里的。


#创建一个scroll组件
scroll = new ScrollComponent
    width: Screen.width,
    height: Screen.height-128*n
    y: 128*n
    z: 3

scroll.content.draggable.horizontal = false


#初始化头部结构
topGdt = new Layer
    width: Screen.width
    height: 360*n
    image: "images/gradiantbg.png"
    background:null
    z: 2
    opacity: 0


navbar = new Layer
    width: Screen.width
    height: 128*n
    image: "images/navbar.png"
    opacity: 1
    z: 1

view = new Layer
    width: loadWidth
    height: loadHeight
    x: Align.center
    y: 120*n
    backgroundColor: null
    clip: true
    z: 2

loadcontent = new Layer
    parent: view
    x: 0
    width: loadWidth*frameStep
    height: loadHeight
    image: "images/startsprite.png"

loadtxt = new TextLayer
    z: 2
    text: "下拉加载"
    fontSize: 24*n
    x: Align.center
    y: view.y+view.height-24*n
    opacity: 0
    

代码块里也模拟了搜索导航的结构。其中loadcontent是动画帧容器;view是动画视窗;

第二步:下拉联动:我们要监听下拉的距离并将这个返回值转换成动画序列帧的步数,传给控制动画播放的函数;代码如下:

#申明一个切换图片帧的函数,形参s为帧的步数
pullAnimate = (s) ->
    loadcontent.states =
        on:
            x:-frameWidth*n*s       
    loadcontent.animate "on",time:0

pullAnimate函数就是用来控制播放第几帧。

#页面移动后触发执行一个scrolltoY函数
frameRate = 1.6
scroll.on Events.Move, ->
    scrolltoY(scroll.scrollY)
scrolltoY = (y) ->
  s = -Math.round(y/frameRate)
  pullAnimate(s)

frameRate其实是为了以后支持拓展和微调,记录的拖动一个单位像素播放多少帧的转化系数;默认1.6的意思是,拖动一个像素播放1.6帧。

s是页面滑动到当前值y时,当前动画的步数。注意往上滑动y是正值、往下是负数。

第三步:阈值判断:阈值应该是动画播放到最后一帧的临界点,如果动画的总步长为frameStep的话,那么留在视窗内的最后一帧就是frameStep-1;判断如下:

1)判断如果页面往上滑动则动画则校准到第0帧;

2)判断如果刚好在临界值的时候播放音效;

3)判断如果页面往下滑动超过总步长的话停留在最后一帧,同时动画帧容器里替换文字和gif循环动画;

scrolltoY = (y) ->
  s = -Math.round(y/frameRate)
  if s < 0
    s = 0

  if s == frameStep-1
    sound.play()

  if s > frameStep-1
    loadtxt.text = "加载中..."
    loadcontent.image = "images/sprite.gif"
   #view.image = "images/loadloop.gif"
    s = frameStep-1
  else
    loadcontent.image = "images/startsprite.png"

  pullAnimate(s)

至此一个下拉加载效果就完成了,为了方便下次继续复用,我们把常修改的变量提出来进行置换,以后替换帧图片后直接修改步长和联动系数等就能快速可视化得到一个新的下拉加载效果。

n = Screen.width/750
sound = new Audio("sounds/pop03.wav")
frameStep = 38
frameWidth = 260
frameRate = 1.6
loadWidth = 260*n
loadHeight = 180*n
imageStart = "images/startsprite.png"
imageLoop = "images/sprite.gif"

总结

有一种说法是测试驱动产品设计,作为一名设计师也是这样,有时我们在萌生一个交互创意时,很难脑补出在开发落地时会产生多少边界场景,所以有条件不妨动手实践一次,实践的过程就是一次补差补漏的过程,要知道完善的交互文档能为开发哥哥节省很多不必要麻烦,而你们之间的信任关系也建立于此。

刷牙君

View posts by 刷牙君
处女座设计师一枚,涉及的专业领域视觉,交互,前端。

Leave a Reply

Your email address will not be published. Required fields are marked *