最近看到sakura主题的关于页面,发现可以采用伪聊天方式组织内容,比较有意思,看了一下主要利用的是botui这个基于vue的东西,并不复杂,于是也就整了一个,安排在about页面。

botui

这个botui上面是这样说的:

A JavaScript framework to create conversational UIs.

看了一下,文档在https://docs.botui.org/,全是英文的,但能用到的内容也就不多,而且还可以按照大佬搞好的照葫芦画瓢。

安装

文档中的安装方式给出了好几个,上面有通过cdn的途径,既然有给出cdn那就cdn了。

一共需要四个文件


// required for basic layout
https://unpkg.com/botui/build/botui.min.css

// default theme - you can create your own theme
https://unpkg.com/botui/build/botui-theme-default.css

// Vue - BotUI requires Vue to be present in page
https://cdn.jsdelivr.net/vue/latest/vue.min.js

// BotUI - main file
https://unpkg.com/botui/build/botui.min.js

但测试的时候官方给出的这几个cdn在本地网络环境下面不太稳定,于是就换了几个,而对于botui.min.js这个文件,后面用的时候遇到了一个小bug,按照github上面的issue指导,需要注释掉三行,那就没法用cdn了,况且botui.js内容也不多,直接去github上面把源文件复制粘贴就好了,就安排到nginx下面的静态目录了。

<link href="https://cdn.bootcdn.net/ajax/libs/botui/0.3.9/botui.min.css" rel="stylesheet">
  <link href="https://cdn.bootcdn.net/ajax/libs/botui/0.3.9/botui-theme-default.css" rel="stylesheet">
  <script src="https://cdn.jsdelivr.net/vue/latest/vue.min.js"></script>
  <script src="https://www.dogcraft.top/js/botui.js"></script>

在网页上面部署

在安排到关于界面之前,先搞了一个静态页面试一下。

按照文档要求,在需要安排botui的地方要添加一个div


<div id="my-botui-app">
  <bot-ui></botui>
</div>

然后在JavaScript里面进行初始化:


 var botui = new BotUI("my-botui-app");

这会得到一个botui的对象,然后调用这个对象的方法就可以了。


botui.message.add({
  delay: 800, //延迟时间
  content: "Hi, there" //内容
});

如果是连续对话需要再后面添加then


botui.message.add({
  delay: 800,
  content: "Hi, there👋"
}).then(function () {
  botui.message.add({
    delay: 1100,
    content: "这里是 dogcraft"
  }).then(function () {
    botui.message.add({
      delay: 1100,
      content: "一个可爱的蓝孩子~"
    })
})
})

多个对话就需要这样一层层嵌套下去

禁止套娃

原来尝试过不这样一层层的套娃,在外面定义函数替换掉then()里面的套娃部分,但这样延迟时间会出问题,下一句会比上一句提前出来,设置的延时没起效,最后有改回到这种套娃式的结构。

如果要设置按钮与分支需要这样安排:


function () {
      botui.action.button({
        delay: 1600,
        action: [{
          text: "然后呢? ",
          value: "sure"
        }, {
          text: "少废话!",
          value: "skip"
        }]
      }).then(function (a) {
        "sure" == a.value && sure();
        "skip" == a.value && end()
      })
    }

最后这个分支还是跳出了套娃链条,由于需要用户点击,所以就没有延时问题了。

可以在内容里面添加图片或html,加的时候要在type里面注明,否则还是会出现奇奇怪怪的错误。

botui.message.add(
                {
                  type: 'html',
                  loading: true,
                  delay: 1400,
                  content: '<img style="width:100%" src="https://steamsignature.com/profile/schinese//76561198343712334.png" > '
                }
              )

还可以利用类似于markdown格式添加图片或链接


 botui.message.add({
      delay: 600,
      content: "![...](https://upyun.dogcraft.top/img/20200531211632.jpg)"
    })

设置完了之后可以把相关的JavaScript整合到一个js文件里面,这样在html看起来也好看,移植起来也比较方便。

部署到typecho独立页面

由于不会php,也不会改主题,没法把相关的css以及vue整合到head标签里,只能利用markdown编辑器里面的三个叹号包裹起来的方式直接安排到正文里面

!!!
<link href="https://cdn.bootcdn.net/ajax/libs/botui/0.3.9/botui.min.css" rel="stylesheet">
  <link href="https://cdn.bootcdn.net/ajax/libs/botui/0.3.9/botui-theme-default.css" rel="stylesheet">
  <script src="https://cdn.jsdelivr.net/vue/latest/vue.min.js"></script>
  <script src="https://www.dogcraft.top/js/botui.js"></script>

  <div   >
    <div id="my-botui-app" class="botui">
      <h4 class="text-center">与 dogcraft 对话中……</h4>
      <bot-ui></bot-ui>
    </div>
  </div>

  <script src="https://www.dogcraft.top/js/lt.js"></script>

!!!

刚开始安排上去的时候遇到了一个bug,每次出现新的对话之后,滚动条会自动滚动,滚动到最下方,什么也看不到。

最后在github的issue找到这个

按照说明注释掉botui.js里面的三行就可以了

现在想来能不能通过一个ifame来解决这个问题?

抽空可以试一下

pjax问题

在开启了pjax之后,基本上任何与JavaScript有关的东西都会或多或少碰上这个东西。

在通过pjax跳转到关于页面之后,botui并不总是可以正常启动,于是把所用的botui的对话部分的代码做到一个函数里面。但并不能直接写到pjax重载函数里面,首先并不是所有页面都有这个聊天框,另一个就是如果正常页面启动了,pjax再来一次不仅会报错,而且还会卡住。所以要有两个判断,首先看一看页面里面有没有botui与botui有没有正常启动,如果没有启动,再通过pjax重载函数安排一下。

最后的结果就是这样子:


if (document.getElementById("my-botui-app")) {
    if ($("div").hasClass("botui-container")==false) {
        botuiinit();
    }
}            })

现在想来<ifame> 或许也可以解决这个重载问题,抽空的时候要试一下。


下午试了一下,利用<ifame>可以解决pjax的问题,不用添加pjax重载函数,但滚动的问题解决不了。但采用<ifame>会出现div高度不能自适应变化的问题,需要另外用别的方法来安排,过于复杂,于是改回了原来的样子。现在把<ifame>方式放到这里,说明可行性。