• 【vue】下拉、上拉刷新


    第一部分:下拉刷新

    我这里就把主要的下拉刷新的写一下,上拉是一样的道理,就不写了

    1. <div class="talk_top" ref="listWrapper" id="listWrapper">
    2. <div class="loadingpic" v-loading="loading">div>
    3. <div v-for="message in messages" :key="message.id" class="message">
    4. <div class="minetext" v-html="message.text">div>
    5. div>
    6. div>

    在他的基础上修改了一下,他的上面有点小问题https://www.cnblogs.com/zmcxsf/p/10443189.html

    第二部分:滚动条到底部

    1、调用接口数据,然后调用re()方法,如果不调用re方法,页面没反应

    2、在 mounted中获取滚动区域的document,然后让调用方法,让盒子滚动到底部,这样页面一打开,滚动条就在底部了

    3、监听滚动事件,判断用户滚动状态

    1. <template>
    2. <div class="chat">
    3. <div class="center">
    4. <div v-if="pasId === 0">
    5. <div class="talk_history" id="chat">
    6. <div class="talk_top" ref="listWrapper" id="listWrapper">
    7. <div class="loadingpic" v-loading="loading">div>
    8. <div v-for="message in messages" :key="message.id" class="message">
    9. 。。。。内容
    10. div>
    11. div>
    12. div>
    13. <div class="talk_huifu">
    14. <div style="border-bottom:1px solid #f8f8f8;display:flex">
    15. <el-upload
    16. ref="upload"
    17. class="upload-demo"
    18. action="https://jsonplaceholder.typicode.com/posts/"
    19. :show-file-list="false"
    20. :file-list="fileList"
    21. accept=".pdf"
    22. :on-change="talkchange"
    23. :http-request="http"
    24. >
    25. <img
    26. style="margin:0 15px 0 10px"
    27. src="../../assets/img/wenjianjia.png"
    28. title="发送文件"
    29. />
    30. el-upload>
    31. div>
    32. <div align="right">
    33. <el-input
    34. type="textarea"
    35. v-model="talk"
    36. :maxlength="4000"
    37. :rows="3"
    38. resize="none"
    39. placeholder="有什么我可以帮您?"
    40. >el-input>
    41. <el-button size="medium" :disabled="disabled" @click="sub(0)"
    42. >发送
    43. >
    44. div>
    45. div>
    46. div>
    47. div>
    48. template>
    49. <script>
    50. let source = null;
    51. var AIurl = "http://192.168.4.172:8081/userApp/ai/sse";
    52. var resultUrl = "http://192.168.4.172:8081/userApp/ai/aiHelp";
    53. import { EventSourcePolyfill } from "event-source-polyfill";
    54. export default {
    55. layout: "AI2",
    56. name: "",
    57. data() {
    58. return {
    59. disabled: false, //ai回答结束,按钮取消禁用
    60. showdown: false, //数据到底啦
    61. chatContent: null,
    62. isScrolling: true,
    63. loading: false, // 加载中
    64. page: 1,
    65. total: 0, //总条数
    66. talk: "", //发送的聊天信息
    67. len: true, //发送信息的次数
    68. fileList: [], //发送文件
    69. topic: {}, //新建对话的信息
    70. word: {}, //文件的信息
    71. messages: [], //聊天历史
    72. page: {
    73. pageNum: 0,
    74. pageSize: 10
    75. },
    76. total: 0,
    77. pasId: 0, //上一页的id
    78. };
    79. },
    80. mounted() {
    81. this.getAiLogsByTopicId(); // 初始化数据
    82. this.re();
    83. setTimeout(() => {
    84. this.chatContent = document.getElementsByClassName("talk_top")[0];
    85. this.scrollToBottom();
    86. // 监听滚动事件,判断用户滚动状态
    87. this.chatContent.addEventListener("scroll", this.handleScroll);
    88. }, 1000);
    89. },
    90. watch: {
    91. disabled: {
    92. handler(newval, oldval) {
    93. this.disabled = newval;
    94. },
    95. deep: true,
    96. immediate: true
    97. }
    98. },
    99. methods: {
    100. // 定义将滚动条定位在底部的方法
    101. scrollToBottom() {
    102. var that = this;
    103. this.$nextTick(() => {
    104. if (that.isScrolling) {
    105. that.chatContent.scrollTop =
    106. that.chatContent.scrollHeight - that.chatContent.offsetHeight;
    107. // console.log(that.chatContent.scrollTop);
    108. }
    109. });
    110. },
    111. handleScroll() {
    112. const scrollContainer = this.chatContent;
    113. const scrollTop = scrollContainer.scrollTop;
    114. const scrollHeight = scrollContainer.scrollHeight;
    115. const offsetHeight = scrollContainer.offsetHeight;
    116. if (scrollTop + offsetHeight < scrollHeight) {
    117. // 用户开始滚动并在最底部之上,取消保持在最底部的效果
    118. this.isScrolling = true;
    119. } else {
    120. // 用户停止滚动并滚动到最底部,开启保持到最底部的效果
    121. this.isScrolling = false;
    122. }
    123. },
    124. // 发送对话---------------------------------------------------
    125. // 加载数据对话
    126. getAiLogsByTopicId() {
    127. this.$axios
    128. .get("/userApp/ai/getAiLogsByTopicId", {
    129. params: {
    130. TopicId: this.topic.topicId,
    131. pageNum: 1,
    132. pageSize: this.page.pageSize
    133. }
    134. })
    135. .then(res => {
    136. if (res.code === 200) {
    137. this.messages = res.rows.reverse();
    138. // console.log(res.rows);
    139. this.total = Number(res.total);
    140. }
    141. });
    142. },
    143. getlist() {
    144. if (this.total >= this.messages.length) {
    145. this.page.pageNum++;
    146. this.loading = true;
    147. this.$axios
    148. .get("/userApp/ai/getAiLogsByTopicId", {
    149. params: {
    150. TopicId: this.topic.topicId,
    151. pageNum: this.page.pageNum,
    152. pageSize: this.page.pageSize
    153. }
    154. })
    155. .then(res => {
    156. if (res.code === 200) {
    157. if (this.page.pageNum >= Number(res.allPage)) {
    158. this.$message.success("数据到底啦");
    159. this.loading = false;
    160. return;
    161. } else {
    162. this.messages = [...res.rows.reverse(), ...this.messages];
    163. this.total = Number(res.total);
    164. // console.log(this.messages);
    165. this.loading = false;
    166. }
    167. }
    168. })
    169. .catch(error => {
    170. this.$message.error(error.msg);
    171. this.loading = false;
    172. });
    173. } else {
    174. this.$message.success("数据到底啦");
    175. // this.showdown = true;
    176. this.loading = false;
    177. }
    178. },
    179. // 下拉、上拉刷新
    180. re() {
    181. var flag = false;
    182. var PstartX;
    183. var PstartY;
    184. var PMoveX;
    185. var PMoveY;
    186. var PendX;
    187. var PendY;
    188. let that = this;
    189. document.onmousedown = function(ev) {
    190. flag = true;
    191. PstartX = ev.pageX;
    192. PstartY = ev.pageY;
    193. // console.log("start:" + PstartX, PstartY);
    194. document.onmousemove = function(ev) {
    195. PMoveX = ev.pageX;
    196. PMoveY = ev.pageY;
    197. if (flag) {
    198. // console.log("move:" + PMoveX, PMoveY);
    199. var resutl = getpostion(PMoveY, PstartY);
    200. switch (resutl) {
    201. case 0:
    202. // console.log("无操作");
    203. break;
    204. case 1:
    205. // console.log("向上");
    206. break;
    207. case 2:
    208. // console.log("向下");
    209. if (PMoveY - PstartY > 0) {
    210. if (PMoveY - PstartY >= 50) {
    211. document.getElementById("listWrapper").style.marginTop =
    212. PMoveY - PstartY + "px";
    213. }
    214. that.loading = true;
    215. // document.getElementById("loadingpic").style.display = "block";
    216. }
    217. break;
    218. }
    219. }
    220. };
    221. document.onmouseup = function(ev) {
    222. flag = false;
    223. PendX = ev.pageX;
    224. PendY = ev.pageY;
    225. // console.log("end:" + PendX, PendY);
    226. var resutl = getpostion(PMoveY, PstartY);
    227. switch (resutl) {
    228. case 0:
    229. // console.log("无操作");
    230. break;
    231. case 1:
    232. // console.log("向上");
    233. break;
    234. case 2:
    235. // console.log("向下");
    236. // location.reload();
    237. setTimeout(() => {
    238. that.getlist(); //调用接口
    239. //回弹到初始位置
    240. document.getElementById("listWrapper").style.marginTop = "0px";
    241. }, 500);
    242. break;
    243. }
    244. };
    245. // 判断是上拉还是下拉
    246. function getpostion(PMoveY, PstartY) {
    247. if (PMoveY - PstartY == 0) {
    248. return 0; //无操作
    249. }
    250. if (PMoveY - PstartY < 0) {
    251. return 1; //向上
    252. }
    253. if (PMoveY - PstartY > 0) {
    254. return 2; //向下
    255. }
    256. }
    257. };
    258. },
    259. sub(type) {
    260. let that = this;
    261. // 判断次数,在发送
    262. if (type === 1) {
    263. this.messages.push({
    264. aiId: "", //编号
    265. userId: "", //用户id
    266. userAsk: "", //用户询问
    267. aiReply: "", //ai回复
    268. askTime: "", //询问时间
    269. isPdf: true, //是否是pdf
    270. fileName: this.word.fileName, //文件名称
    271. fileSize: this.word.fileSize, //文件大小
    272. aiTopicId: this.topic.topicId //话题编号
    273. });
    274. this.$message.success("请稍等,正在响应中");
    275. this.load(this.messages[this.messages.length - 1], 1, that.chatContent);//调用接口
    276. setTimeout(() => {
    277. that.chatContent.scrollTop = that.chatContent.scrollHeight + 150;
    278. }, 500);
    279. this.word = {};
    280. } else {
    281. if (this.talk === "") {
    282. this.$message.error("请填写内容");
    283. } else {
    284. this.messages.push({
    285. aiId: "", //编号
    286. userId: "", //用户id
    287. userAsk: this.talk, //用户询问
    288. aiReply: "", //ai回复
    289. askTime: "", //询问时间
    290. isPdf: false, //是否是pdf
    291. fileName: null, //文件名称
    292. fileSize: null, //文件大小
    293. aiTopicId: this.topic.topicId //话题编号
    294. });
    295. this.$message.success("请稍等,正在响应中");
    296. this.load(
    297. this.messages[this.messages.length - 1],
    298. 0,
    299. that.chatContent
    300. );
    301. setTimeout(() => {
    302. that.chatContent.scrollTop = that.chatContent.scrollHeight + 150;
    303. }, 500);
    304. }
    305. this.talk = "";
    306. }
    307. },
    308. // 获取ai结果
    309. load(item, type, chatContent) {
    310. this.disabled = true;
    311. if (type === 1) {
    312. source = new EventSourcePolyfill(
    313. Url +
    314. "userApp/ai/sse?question=" +
    315. this.word.fileDownloadPath +
    316. "&fileName=" +
    317. this.word.fileName +
    318. "&fileSize=" +
    319. this.word.fileSize +
    320. "&isPdf=true&aiTopicId=" +
    321. this.topic.topicId,
    322. {
    323. headers: {
    324. token: this.$cookies.get("userToken")
    325. }
    326. }
    327. );
    328. } else {
    329. source = new EventSourcePolyfill(
    330. Url +
    331. "userApp/ai/sse?question=" +
    332. this.talk +
    333. "&isPdf=false&aiTopicId=" +
    334. this.topic.topicId,
    335. {
    336. headers: {
    337. token: this.$cookies.get("userToken")
    338. }
    339. }
    340. );
    341. }
    342. // open:订阅成功(和后端连接成功)
    343. source.addEventListener("open", function(e) {});
    344. source.onmessage = e => {
    345. // console.log(JSON.parse(e.data));
    346. if (JSON.parse(e.data).end) {
    347. // 结束了
    348. item.aiId = JSON.parse(e.data).end;
    349. this.disabled = false;
    350. return;
    351. } else if (JSON.parse(e.data).error) {
    352. this.$message.error(JSON.parse(e.data).error);
    353. this.disabled = false;
    354. return;
    355. } else {
    356. item.aiReply += JSON.parse(e.data).content.replace(/\\n/g, "\n");
    357. if (this.isScrolling) {
    358. chatContent.scrollTop = chatContent.scrollHeight;
    359. }
    360. }
    361. };
    362. source.onerror = event => {
    363. if (event.error !== undefined) {
    364. this.$message.error("出错了,请联系客服人员");
    365. }
    366. this.disabled = false;
    367. event.target.close();
    368. };
    369. },
    370. // 上传文件
    371. talkchange(file, fileList) {
    372. this.$refs.upload.uploadFiles = [];
    373. this.fileList = [];
    374. this.fileList = fileList;
    375. },
    376. async http(file, fileList) {
    377. var formData = new FormData();
    378. formData.append("files", file.file);
    379. this.$axios.post("/dev/file/uploadFile", formData).then(res => {
    380. if (res.code === 200) {
    381. this.word = {
    382. fileName: res.data[0].fileName,
    383. fileSize: res.data[0].fileSize,
    384. fileDownloadPath: res.data[0].fileDownloadPath
    385. };
    386. // this.$message.success("上传成功");
    387. this.sub(1);
    388. }
    389. });
    390. },
    391. }
    392. };
    393. script>

  • 相关阅读:
    从零点五开始的深度学习笔记——VAE(Variational AutoEncoder) (三)VAE的简单实现
    Avalonia开发(二)项目结构解析
    OJ---Z 字形变换
    ASP.NET大型外卖订餐系统源码 (PC版+手机版+商户版)
    火爆全网的“亿级流量高并发系统设计v1.0”,七大专题+47W字
    Makefile教程
    工业电子中的深力科分享一款PWM控制器 KA3525A
    面试题-React(八):React如何实现插槽?
    如何在 Unbuntu 下安装配置 Apache Zookeeper
    AI歌手是否会取代流行歌手成为主流?
  • 原文地址:https://blog.csdn.net/Qxn530/article/details/132761311