极简实现列表查看页面

最近在和各种文档文案展现斗智斗勇,在解决帮助列表静态化的同时,尝试了一下以前构思过的极简列表实现,发现居然还不错。css

本文可能涉及的内容--html

  • 模板渲染
  • 比较冷门的CSS用法
  • 一些小声哔哔

场景简介

假如咱们有下面这组数据,须要将它们变成一个常规的Q&A页面,而且但愿它是个独立的、小型的静态页。(若是有可能的话,尽可能赋予它通用化、模板化的能力)vue

试试别想vue和react?

虽然说vue和react给了咱们不少惊喜,可是并非全部的项目都适合使用它们,好比此次咱们须要实现的 -- 静态化的文档列表查看页面,固然这并非说vue、react不能静态化,而是有点杀鸡用牛刀的意味了。react

如何实现?

好了,咱直接进入主题。虽然不打算用视图框架了,可是咱们仍是能够借助一下里面的思路,其实咱们想要作的页面本质就是对一堆已知数据解析以及渲染。基于此咱们大概能构思这样的一个实现流程,获取数据 -- 填充模板 -- 生成可用静态页css3

① 数据源

数据的源头变幻无穷,这里以我实践的状况来介绍。json

咱们会有许许多多条简短的问答条目存储在monogoDB中,根据某个tag,能够在库里取出一条或者多条数据,例如:数组

[{"_id":"111","title":"问题一","body":{"text":"答案一"}},{"_id":"222","title":"问题二","body":{"text":"答案二"}},{"_id":"333","title":"问题三","body":{"text":"答案三"}},{"_id":"444","title":"问题四","body":{"text":"答案四"}},{"_id":"555","title":"问题五","body":{"text":"答案五"}}]
复制代码

取出来很简单,可是咱们要怎么塞进咱们的页面中呢?(经过接口呀!)其实也不难,甚至只须要replace就能将数据放进去。假设咱们的模板中有一段JS是这样的:浏览器

// ......
let FAQ_LIST = {{FAQ_LIST}};
// ......
复制代码

咱们只须要将模板中的{{FAQ_LIST}}替换成咱们的数据就好啦,那么,只要将上述取出的数据直接替换掉{{FAQ_LIST}}这里的占位字符串就行了吗?咱们这么作了以后会发现,咱们只塞了段字符串进去!app

那应该咋办,既然替换进去成了字符串,那咱们在替换以前就把它变成字符串不就行了?而后在后续的调用中,把它解析成数组就完美了。因而就有了下面这个流程:框架

//...
const cursor = await col.find({ tag: 'xxx' }) //获取数据
const list = await cursor.toArray() //将数据转为数组
let template = fs.readFileSync(path.join(__dirname, '../templates.html'), 'utf-8') //获取模板
const tp = template.replace(/{{FAQ_LIST}}/, JSON.stringify(list)) //替换占位符
//...
复制代码

没错,在填充模板以前,咱们就将取得的数组变成了字符串,而后在模板实际调用时再将其JSON.parse()

② 页面布局

<div class="wrapper">
    <div id="help-list"></div>
    <div class="help-content">
        <div id="help-content-container"></div>
        <div class="help-button">
            <div id="button-ok" class="button-item" onclick='handleButtonClick("ok");'>已解决</div>
            <div id="button-no" class="button-item" onclick='handleButtonClick("no");'>未解决</div>
        </div>
    </div>
</div>
复制代码

咱们整个列表查看页的布局大体如上,你们会发现,这是否是少了点内容?是的,咱们条目内容并无出如今html中,它们将会在后续的JS处理被插入到相应的节点中。

看到这里,也许你们会疑惑,这不是把全部的内容(问题标题&问题正文)混到一块儿了吗,怎么才能实现点击查看详情的效果呢?这就要借助咱们神奇的CSS选择器了,具体请看下面对页面样式的介绍。

③ 页面样式

整个列表页面比较简单,一些总体的布局就不在赘述,你们能够点击后面的demo页面自行查看。如今想重点介绍一下点击列表项实现原页面查看详情的实现:

你们能够再去看看上面的页面节点图,会发现列表项的href是对应的详情的id,若是是锚点功能的话还能够理解,可是怎么作到相似页面切换的查看详情呢?看到这里是否是以为很像咱们写单页应用时用过的路由?

虽然不是同一个东西,可是咱们能够把这看做一个极简易的单页路由。咱们点击任意一个列表项,url都会带上#xxx字样,这就能够与css3的target选择器配合:

#help-list:target {
    display: block
}

#help-list:target~.help-content {
    display: none
}

#help-content-container>.ww-section {
    display: none
}

#help-content-container>.ww-section:target {
    display: block
}
复制代码

当url中带有#help-list锚点时,详情父节点help-content将会被隐藏,在未选中列表项时,详情模块的父节点help-content-container也是隐藏的状态,当咱们点击某项列表项时,咱们的url会带上相应的锚点,带有相应id的ww-section节点将会显示,因为锚点再也不是#help-list,咱们的列表也会一并隐藏。

也许上面的文字描述比较抽象,你们能够看看上面的GIF,关注url的变化。在刚进入页面的时候,若是判断到url没有带hash,我会重定向到带有#help-list的url,这样就能让列表显示出来。

点击列表中的某一项时,url同时也发生了变化,而且浏览器记录也增长了一条(能够模拟页面返回的效果)。

总结

前面啰嗦了不少,但通篇想表达的意思很少 -- 一些页面仍是能够用简单且高效的方案实现的,没必要都拿着全家桶往上套。

在笔者的实际应用场景中,是须要在外部触发事件后,将库中相应的数据取出,而且塞进已编辑好的模板,最终直接上传到CDN,而后输出对应连接给使用方。

固然这是千万种方案中的一种,咱们彻底能够写个接口来获取数据并在页面中动态渲染......这里就当作是笔者的一次尝新实践~

测试页面附送 -- 猛击此处!!

相关文章
相关标签/搜索