This commit is contained in:
zoujiandong
2025-03-07 17:11:01 +08:00
commit 5850bdee94
66 changed files with 10952 additions and 0 deletions
+118
View File
@@ -0,0 +1,118 @@
<template>
<div class="home" @click="goHome">
{{ source?'点击返回新医视':'点击返回首页' }}
<!-- <div
v-if="source==3"
class="appbtn"
style="
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
width: 100%;
height: 100%;
z-index: 9999;
opacity: 0;
"
>
<wx-open-launch-weapp
:key="freshkey"
style="
width:94px;
height: 30px;
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
"
id="launch-btn-miniApp"
appid="wx6e3ba63efef32cc4"
:env-version="envVersion"
path="pages/media_home/index"
>
<div v-is="'script'" type="text/wxtag-template">
<button class="btn" style="width:100%;height:30px;position:absolute;left:0;right:0;top:0;bottom:0;">打开小程序</button>
</div>
</wx-open-launch-weapp>
</div> -->
<!-- <img src="../assets/home.png" @click="goHome" /> -->
<!-- <img src="../assets/home.png" v-else @click="goHome"/> -->
</div>
</template>
<script setup>
import { onMounted, nextTick } from "vue";
import { useRouter, useRoute } from 'vue-router';
import openTag from "../utils/openTag";
import wx from 'jweixin-1.6.0'
const router = useRouter();
const route = useRoute();
let origin=route.query.source?route.query.source:'';
const source=ref(origin);
const freshkey = ref(0);
const goHome = () => {
if(source.value==3){
// try {
// wx.miniProgram.navigateBack();
// } catch (error) {
// wx.miniProgram.switchTab({
// url: '/pages/media_home/index'
// })
// }
wx.miniProgram.switchTab({
url: '/pages/media_home/index',
success(res) {
consoe.log('跳转成功');
},
fail(res) {
consoe.log('跳转失败');
}
});
}else{
router.push({
path: "/home",
});
}
};
onMounted(() => {
openTag();
// nextTick(() => {
// var btn = document.getElementById("launch-btn-miniApp");
// if (btn) {
// btn.addEventListener("launch", function (e) {
// showToast("success");
// freshkey.value++;
// });
// btn.addEventListener("error", function (e) {
// showToast("fail", e.detail);
// });
// }
// });
});
</script>
<style lang='scss' scoped>
.home {
position: fixed;
right: 0;
z-index: 10;
width:27px;
padding:8px 0;
line-height: 17px;
top:50%;
font-size: 14px;
color:#fff;
display: flex;
text-align: center;
align-items: center;
justify-content: center;
border-radius: 5px;
background:#0caf98;
flex-direction: column;
transform: translateY(-50%);
}
</style>
+111
View File
@@ -0,0 +1,111 @@
<template>
<van-overlay :show="show" z-index="9999">
<div class="wrapper">
<div class="box">
<div class="title">温馨提示</div>
<div class="content">{{ message }}</div>
<div class="foot">
<div class="cancle" @click="cancelDialog" v-show="showCancel" >否</div>
<div class="ok" @click="closeDialog">{{confirmText}}</div>
</div>
</div>
</div>
</van-overlay>
</template>
<script setup>
import { ref} from 'vue'
const show = ref(false);
const props=defineProps({
message: {
type: String,
default:''
},
showCancel: {
type: Boolean,
default: true,
},
confirmText: {
type: String,
default:'是'
}
});
const emit = defineEmits(['handledConfirm']);
const closeDialog = () => {
show.value = false;
emit('handledConfirm');
};
const cancelDialog = () => {
show.value = false;
emit('handledCancel');
};
const openDialog = () => {
show.value = true;
};
defineExpose({
openDialog
});
</script>
<style lang='scss' scoped>
.wrapper {
display: flex;
align-items: center;
justify-content: center;
height: 100%;
.box {
width: 80%;
box-sizing: border-box;
margin: 0 auto;
padding: 24px;
border-radius: 12px;
background: #fff;
.title {
font-weight: 550;
text-align: center;
font-size: 18px;
color: rgba(0, 0, 0, 0.85);
}
.content {
margin-top: 13px;
text-align: center;
font-size: 14px;
color: rgba(0, 0, 0, 0.65);
line-height: 22px;
}
.foot {
margin-top: 24px;
display: flex;
justify-content: center;
margin-top: 20px;
.cancle {
width: 128px;
height: 44px;
margin-right: 12px;
display: flex;
justify-content: center;
align-items: center;
background: #FFFFFF;
border-radius: 25px;
font-size: 16px;
color: rgba(0, 0, 0, 0.85);
border: 1px solid rgba(0, 0, 0, 0.15);
}
.ok {
width: 128px;
height: 44px;
display: flex;
justify-content: center;
align-items: center;
font-size: 16px;
color: #fff;
background: #43C9C3;
border-radius: 25px;
border: 1px solid 43C9C3;
}
}
}
}
</style>
+166
View File
@@ -0,0 +1,166 @@
<template>
<van-pull-refresh v-model="pull_loading" @refresh="onRefresh" success-text="刷新成功">
<van-list v-model:loading="loading" :finished="finished" finished-text="" style="min-height: 350px;" ref="clist"
@load="onLoad" class="msglist">
<div class="bar"></div>
<div class="cell" v-for="(item, index) in list" :key="item.case_id" @click="goDetail(item.case_id, item.is_join)">
<div class="namebox">
<img src="../assets/newicon.png" alt="" v-if="item.is_new == 1">
<img src="../assets/fuli.png" alt="" v-if="item.is_welfare == 1">
<div class="name">{{ item.case_name }}</div>
</div>
<div class="btnbox">
<div class="writer">{{ item.case_author }}</div>
<div class="btn" :class="{ finsihed: item.is_join == 1 }">{{ item.is_join == 1 ? '已参与' : '立即参与' }}</div>
</div>
</div>
<div class="nodata" v-show="list.length == 0">
<div class="empty">
<div class="emptydesc">
"暂无相关数据~"
</div>
</div>
</div>
</van-list>
</van-pull-refresh>
</template>
<script setup>
import { ref } from 'vue';
import api from '../api/user.js';
import { useRouter, useRoute } from 'vue-router';
const router = useRouter();
const route = useRoute();
const pull_loading = ref(false);
const page = ref(0);
const project_id = ref(route.query.project_id);
const list = ref([]);
const loading = ref(false);
const finished = ref(false);
const props = defineProps({
is_take_part: {
type: Number,
default: 0
},
});
const getList = async () => {
let { code, data } = await api.getCaseList({
page: page.value,
project_id: project_id.value,
page_size: 10,
is_take_part: props.is_take_part
})
loading.value = false;
if (code == 200) {
pull_loading.value = false;
list.value = list.value.concat(data.data);
if (data.data.length <10) {
finished.value = true;
}
}
}
const onRefresh = () => {
finished.value = false;
loading.value = true;
list.value = [];
page.value = 1;
getList()
}
const goDetail = (id, join) => {
if (join == 1) {
router.push({
path: '/result',
query: {
case_id: id,
project_id: project_id.value
}
})
} else {
router.push({
path: '/caseIntro',
query: {
case_id: id
}
})
}
}
const onLoad = () => {
if(!finished.value) {
page.value++;
getList();
}
};
</script>
<style lang='scss' scoped>
.bar {
width: 100%;
height: 10px;
background: #F5F5F5;
}
.cell {
margin: 0 15px;
border-bottom: 1px solid #E6E6E6;
.btnbox {
margin-top: 18px;
margin-bottom: 8px;
display: flex;
align-items: center;
justify-content: space-between;
.writer {
font-size: 15px;
color: #666666;
}
.btn {
display: flex;
align-items: center;
height: 27px;
background: #43C9C3;
border-radius: 14px;
padding: 0 6px;
font-size: 12px;
color: #FFFFFF;
}
.finsihed {
background: #B5B5B5;
}
}
.namebox {
margin-top: 15px;
vertical-align: baseline;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 2;
overflow: hidden;
text-overflow: ellipsis;
.name {
font-weight: 500;
font-size: 16px;
color: #000000;
display: inline;
}
img {
display: inline-block;
position: relative;
top: 4px;
line-height: 24px;
height: 20px;
}
}
}
</style>
+256
View File
@@ -0,0 +1,256 @@
<template>
<div class="cellbox" v-for="(item, index) in childList" :key="item.comment_id">
<commentunit :item="item" :parentIndex="parentIndex" :index="index" :childList="childList" :parent_id="item.comment_id" :root_id="root_id" :case_id="case_id" :project_id="project_id" @freshLike="freshLike" @freshList="freshList" :replyName="replyName"></commentunit>
<expandunit v-if="parentIndex<0 && item.case_comment && item.case_comment.length>0" :parent_id="item.comment_id" :case_id="case_id" :project_id="project_id" :total_amount="item.total_amount" @freshSecComment="freshSecComment" :index="index" :listLength="item.case_comment.length"></expandunit>
</div>
</template>
<script setup>
import { ref } from "vue";
const expand = ref(true);
const props = defineProps({
item:{
type:Object,
default:()=>{}
},
parentIndex:{
type:Number,
default:-1
},
index:{
type:Number,
default:0
},
root_id:{
type:String,
default:''
},
childList:{
type:Array,
default:()=>[]
},
parent_id:{
type:String,
default:''
},
root_id:{
type:String,
default:''
},
replyName:{
type:String,
default:''
},
case_id:{
type:String,
default:''
},
project_id:{
type:String,
default:''
}
})
const emit = defineEmits(['freshLike','handleFreshList','freshSecComment']);
const freshLike = (data) => {
emit('freshLike',data);
};
const freshList = () => {
emit('handleFreshList',true);
};
const freshSecComment = (data) => {
emit('freshSecComment',data);
}
// const list=ref(props.childList);
// const handleShowMore = () => {
// list.value=expand.value?props.childList:props.childList.slice(0,3);
// }
// watch(() =>props.childList, () => {
// if(props.childList.length>=1 && props.parentIndex<0 ) {
// expand.value=false;
// handleShowMore()
// }
// },{
// immediate:true
// });
</script>
<style lang='scss' scoped>
.cellbox {
padding-top: 15px;
}
.active {
border-bottom: 1px solid #E5E5E5;
}
.comemntcell {
display: flex;
.descbox {
margin-left: 12px;
flex: 1;
// border-bottom: 1px solid #E5E5E5;
.depart {
margin-top: 10px;
font-weight: 400;
font-size: 12px;
color: #333333;
}
.hospital {
margin-top: 4px;
font-weight: 400;
font-size: 12px;
color: #333333;
}
.date {
margin-top: 4px;
font-weight: 400;
font-size: 12px;
color: #333333;
}
.comemntcell {
border-bottom: 1px solid #E5E5E5;
.descbox {
border: none;
padding-bottom: 15px;
}
}
.comment {
margin-top: 4px;
display: flex;
.text {
font-size: 12px;
color: #333333;
line-height: 17px;
flex: 1;
}
.reply {
margin-left: 30px;
width: 40px;
height: 20px;
background: #43C9C3;
border-radius: 4px;
display: flex;
justify-content: center;
align-items: center;
font-size: 12px;
color: #FFFFFF;
}
}
.tag {
margin-top: 2px;
font-size: 12px;
color: #FFFFFF;
height: 15px;
background: #43C9C3;
border-radius: 10px;
display: flex;
padding: 0 4px;
width: 52px;
justify-content: center;
align-items: center;
span {
transform: scale(0.9);
}
}
.namebox {
display: flex;
align-items: center;
justify-content: space-between;
.name {
font-size: 17px;
color: #333333;
}
.zanbox {
display: flex;
font-size: 15px;
color: #333333;
align-items: center;
margin-right: 40px;
img {
width: 20px;
height: 20px;
}
}
}
}
}
.talkbox {
margin: 12px 30px 0px 0;
}
.textbox {
border-radius: 5px;
border: .5px solid #43C9C3;
:deep() .van-cell {
background: none;
}
:deep() .van-field__word-limit {
color: #999999;
}
}
.toolbox {
margin-top: 12px;
display: flex;
justify-content: space-between;
.cancel {
height: 38px;
background: #FFFFFF;
border: 1px solid #EBEBEB;
border-radius: 4px;
font-size: 14px;
display: flex;
justify-content: center;
align-items: center;
color: #737478;
flex: 1;
}
.ok {
margin-left: 12px;
flex: 1;
border-radius: 4px;
height: 38px;
display: flex;
justify-content: center;
align-items: center;
background: #43C9C3;
border: 1px solid #43C9C3;
font-size: 14px;
color: #fff;
}
}
</style>
+417
View File
@@ -0,0 +1,417 @@
<template>
<div class="comemntcell">
<van-image
round
width="49"
height="49"
:src="avatar"
/>
<div class="descbox">
<div class="namebox">
<div class="name">{{ formatName(item.user_name) }}</div>
<div
class="zanbox"
@click="toggleLike(item.comment_id, item.is_like, index)"
>
<img src="../assets/nozan.png" alt="" v-if="!item.is_like" />
<img src="../assets/zan.png" alt="" v-else />
<div class="num" v-if="item.like_num > 0">{{ formatNumber(item.like_num) }}</div>
</div>
</div>
<div class="depart">{{ item.department_name }}</div>
<div class="hospital">{{ item.hospital_name }}</div>
<div class="date">{{ formateDate(item.created_at) }}</div>
<div class="tag" v-if="item.is_high_quality == 1">
<span>优质解答</span>
</div>
<div class="comment">
<div class="text">
{{ item.content }}
</div>
<div class="reply" @click="openConmment(item.level, item.user_name)">
{{ item.level == 1 ? "回复" : "评论" }}
</div>
</div>
<!-- <reply ref="replyRef" :parentIndex="parentIndex" :parent_id='item.comment_id' :root_id="''" :case_id="case_id" :project_id="project_id"></reply> -->
<div class="talkbox" v-show="showReply">
<div class="textbox">
<van-field
:autosize="{ minHeight: 120 }"
v-model="content"
rows="2"
autosize
type="textarea"
maxlength="200"
placeholder="请输入评论内容"
show-word-limit
/>
</div>
<div class="toolbox">
<div class="cancel" @click="showReply = false">取消</div>
<button class="ok" @click="handleAdd" :disabled="isLock">提交</button>
</div>
</div>
<div class="sondiv">
<comment-list
v-if="item.case_comment && item.case_comment.length > 0"
:childList="item.case_comment"
:parentIndex="index"
@freshLike="freshLike"
:root_id="parent_id"
:replyName="item.user_name"
:case_id="case_id"
:project_id="project_id"
@freshSecComment="freshSecComment"
@handleFreshList="handleFreshList"
></comment-list>
</div>
</div>
</div>
</template>
<script setup>
import { showToast } from "vant";
import { ref } from "vue";
import api from "../api/user.js";
import dayjs from "dayjs";
import avatar from "../assets/doctor_avatar.png";
const replyRef = ref(null);
const showReply = ref(false);
const content = ref("");
const level = ref(2);
const writer = ref("");
const isLock = ref(false);
const props = defineProps({
item: {
type: Object,
default: () => {},
},
parent_id: {
type: String,
default: "",
},
root_id: {
type: String,
default: "",
},
replyName: {
type: String,
default: "",
},
index: {
type: Number,
default: 0,
},
childList: {
type: Array,
default: () => [],
},
project_id: {
type: String,
default: "",
},
case_id: {
type: String,
default: "",
},
parentIndex: {
type: Number,
default: -1,
},
});
const emit = defineEmits([
"freshLike",
"freshList",
"freshSecComment",
"handleFreshList",
]);
const formateDate = (val) => {
return dayjs(val).format("YYYY-MM-DD HH:mm");
};
/**
* 显示回复框的处理函数
*
* 该函数用于设置 showReply 的值为 true,从而显示回复框。
*/
const handleReply = () => {
replyRef.value[0].openReply();
};
const handleLike = async (id, index) => {
const { code } = await api.like(id);
if (code == 200) {
showToast("点赞成功");
emit("freshLike", {
parentIndex: props.parentIndex,
index: index,
likeNum: 1,
});
}
};
const freshLike = (data) => {
emit("freshLike", data);
};
const freshSecComment = (data) => {
emit("freshSecComment", data);
};
const handleCancleLike = async (id, index) => {
const { code } = await api.cancleLike(id);
if (code == 200) {
showToast("取消点赞成功");
emit("freshLike", {
parentIndex: props.parentIndex,
index: index,
likeNum: -1,
});
}
};
const toggleLike = (id, flag, index) => {
console.log(id, flag, props.parentIndex, index);
if (flag) {
handleCancleLike(id, index);
} else {
handleLike(id, index);
}
};
const formatNumber = (value) => {
if (value > 9999) {
return (value / 10000).toFixed(1) + "w";
} else {
return value;
}
};
const formatName=(val)=>{
if(!val) return '医生'
return val.slice(0,1)+'医生'
}
const openConmment = (flag, name) => {
showReply.value = true;
if (flag == 2 || flag == 3) {
content.value = "@" + formatName(name) + ":";
writer.value = "@" + formatName(name) + ":";
level.value = 3;
} else {
content.value = "";
writer.value = "";
level.value = 2;
}
};
const handleAdd = async () => {
if (content.value == "" || content.value == writer.value) {
showToast("请输入内容");
return false;
}
showReply.value = false;
isLock.value = true;
const { code, data } = await api.addComment({
case_id: props.case_id,
project_id: props.project_id,
content: content.value,
level: level.value,
root_id: level.value == 2 ? props.parent_id : props.root_id,
parent_id: props.parent_id,
});
isLock.value = false;
if (code == 200) {
emit("freshList");
content.value = "";
}
};
const handleFreshList = () => {
emit("freshList");
};
</script>
<style lang='scss' scoped>
.sondiv {
margin-top: 15px;
:deep() .cellbox {
padding-top: 15px;
}
}
.cellbox {
padding-top: 15px;
}
.active {
border-bottom: 1px solid #e5e5e5;
}
.comemntcell {
display: flex;
.descbox {
margin-left: 12px;
flex: 1;
// border-bottom: 1px solid #E5E5E5;
.depart {
margin-top: 10px;
font-weight: 400;
font-size: 14px;
color: #333333;
}
.hospital {
margin-top: 5px;
font-weight: 400;
font-size: 14px;
color: #333333;
}
.date {
margin-top: 5px;
font-weight: 400;
font-size: 14px;
color: #333333;
}
.comemntcell {
border-bottom: 1px solid #e5e5e5;
.descbox {
border: none;
padding-bottom: 15px;
}
}
.comment {
margin-top: 5px;
display: flex;
.text {
font-size: 14px;
color: #333333;
line-height: 17px;
flex: 1;
white-space: pre-wrap;
word-wrap: break-word;
word-break: break-all;
}
.reply {
margin-left: 30px;
width: 50px;
height: 25px;
background: #43c9c3;
border-radius: 4px;
display: flex;
justify-content: center;
align-items: center;
font-size: 14px;
color: #ffffff;
}
}
.tag {
margin-top: 2px;
font-size: 12px;
color: #ffffff;
height: 15px;
background: #43c9c3;
border-radius: 10px;
display: flex;
padding: 0 4px;
width: 52px;
justify-content: center;
align-items: center;
span {
transform: scale(0.9);
}
}
.namebox {
display: flex;
align-items: center;
justify-content: space-between;
.name {
font-size: 16px;
color: #333333;
}
.zanbox {
display: flex;
font-size: 15px;
justify-content: flex-end;
color: #333333;
align-items: center;
margin-right: 40px;
img {
width: 20px;
height: 20px;
}
}
}
}
}
.expand {
width: 240px;
height: 19px;
margin: 12px auto 12px;
background: #43c9c3;
border-radius: 4px;
display: flex;
justify-content: center;
align-items: center;
font-size: 10px;
color: #ffffff;
}
.talkbox {
margin: 12px 30px 0px 0;
}
.textbox {
border-radius: 5px;
border: 0.5px solid #43c9c3;
:deep() .van-cell {
background: none;
}
:deep() .van-field__word-limit {
color: #999999;
}
}
.toolbox {
margin-top: 12px;
display: flex;
justify-content: space-between;
.cancel {
height: 38px;
background: #ffffff;
border: 1px solid #ebebeb;
border-radius: 4px;
font-size: 14px;
display: flex;
justify-content: center;
align-items: center;
color: #737478;
flex: 1;
}
.ok {
margin-left: 12px;
flex: 1;
border-radius: 4px;
height: 38px;
display: flex;
justify-content: center;
align-items: center;
background: #43c9c3;
border: 1px solid #43c9c3;
font-size: 14px;
color: #fff;
}
}
</style>
+82
View File
@@ -0,0 +1,82 @@
<template>
<div class="expand" @click="showMore" v-if="restNum>0">
展示剩余({{restNum}})条回复
</div>
</template>
<script setup>
import { ref } from 'vue';
import api from '../api/user.js';
const page=ref(1);
const props = defineProps({
parent_id:{
type:String,
default:'',
},
index:{
type:Number,
default:0
},
case_id:{
type:String,
default:''
},
project_id:{
type:String,
default:''
},
listLength:{
type:Number,
default:0
},
total_amount:{
type:Number,
default:0
}
})
const restNum=ref(props.total_amount);
const emit = defineEmits(['freshSecComment']);
const showMore=()=>{
page.value++;
getList(props.parent_id)
}
const getList = async (root_id='') => {
const { code, data } = await api.getCommentList({
case_id:props.case_id,
project_id:props.project_id,
page:page.value,
page_size:5,
root_id:root_id
})
if (code == 200) {
if(data.data.length>0){
emit('freshSecComment',{
commentIndex:props.index,
commentData:data.data
});
nextTick(()=>{
restNum.value=data.total-props.listLength;
})
}
//console.log(data);
}
}
</script>
<style lang='scss' scoped>
.expand {
width: 240px;
height: 19px;
margin: 12px auto 12px;
background: #43C9C3;
border-radius: 4px;
display: flex;
justify-content: center;
align-items: center;
font-size: 10px;
color: #FFFFFF;
}
</style>
+28
View File
@@ -0,0 +1,28 @@
import { createApp } from "vue"
// 导入写好的Loading.vue文件
import Loading from "./loading.vue"
export default {
loading: null,
// 每当这个插件被添加到应用程序中时,如果它是一个对象,就会调用 install 方法。如果它是一个 function,则函数本身将被调用。在这两种情况下——它都会收到两个参数:由 Vue 的 createApp 生成的 app 对象和用户传入的选项。
install(app) {
if (this.loading) {
// 防止多次载入
app.config.globalProperties.$loading = this.loading
return
}
// 创建Loading实例,用于挂载
let instance = createApp(Loading)
// 创建div元素装载Loading对象
let div = document.createElement("div")
div.setAttribute("id","maskbox")
let body = document.body
// 导入body中
body.appendChild(div);
this.loading = instance.mount(div)
// 挂载vue身上
app.config.globalProperties.$loading = this.loading;
}
}
+194
View File
@@ -0,0 +1,194 @@
<template>
<div class="maskbox" v-if="loading">
<div class="mask"></div>
<div class="sk-fading-circle">
<div class="sk-circle1 sk-circle"></div>
<div class="sk-circle2 sk-circle"></div>
<div class="sk-circle3 sk-circle"></div>
<div class="sk-circle4 sk-circle"></div>
<div class="sk-circle5 sk-circle"></div>
<div class="sk-circle6 sk-circle"></div>
<div class="sk-circle7 sk-circle"></div>
<div class="sk-circle8 sk-circle"></div>
<div class="sk-circle9 sk-circle"></div>
<div class="sk-circle10 sk-circle"></div>
<div class="sk-circle11 sk-circle"></div>
<div class="sk-circle12 sk-circle"></div>
</div>
</div>
</template>
<script setup>
import { ref } from 'vue'
const loading = ref(false)
const show = () => {
loading.value = true
}
const hide = () => {
loading.value = false
}
defineExpose({
show,
hide
})
</script>
<style lang="scss">
.maskbox{
top:0;
bottom:0;
width:100%;
height:100%;
z-index:9990;
position: fixed;
display: flex;
justify-content: center;
align-items: center;
.mask{
top:0;
bottom:0;
position: absolute;
width:100%;
height:100%;
opacity: 0.4;
background-color: #000;
}
}
.sk-fading-circle {
margin: 100px auto;
width: 40px;
height: 40px;
position: relative;
}
.sk-fading-circle .sk-circle {
width: 100%;
height: 100%;
position: absolute;
left: 0;
top: 0;
}
.sk-fading-circle .sk-circle:before {
content: '';
display: block;
margin: 0 auto;
width: 15%;
height: 15%;
background-color: #fff;
border-radius: 100%;
-webkit-animation: sk-circleFadeDelay 1.2s infinite ease-in-out both;
animation: sk-circleFadeDelay 1.2s infinite ease-in-out both;
}
.sk-fading-circle .sk-circle2 {
-webkit-transform: rotate(30deg);
-ms-transform: rotate(30deg);
transform: rotate(30deg);
}
.sk-fading-circle .sk-circle3 {
-webkit-transform: rotate(60deg);
-ms-transform: rotate(60deg);
transform: rotate(60deg);
}
.sk-fading-circle .sk-circle4 {
-webkit-transform: rotate(90deg);
-ms-transform: rotate(90deg);
transform: rotate(90deg);
}
.sk-fading-circle .sk-circle5 {
-webkit-transform: rotate(120deg);
-ms-transform: rotate(120deg);
transform: rotate(120deg);
}
.sk-fading-circle .sk-circle6 {
-webkit-transform: rotate(150deg);
-ms-transform: rotate(150deg);
transform: rotate(150deg);
}
.sk-fading-circle .sk-circle7 {
-webkit-transform: rotate(180deg);
-ms-transform: rotate(180deg);
transform: rotate(180deg);
}
.sk-fading-circle .sk-circle8 {
-webkit-transform: rotate(210deg);
-ms-transform: rotate(210deg);
transform: rotate(210deg);
}
.sk-fading-circle .sk-circle9 {
-webkit-transform: rotate(240deg);
-ms-transform: rotate(240deg);
transform: rotate(240deg);
}
.sk-fading-circle .sk-circle10 {
-webkit-transform: rotate(270deg);
-ms-transform: rotate(270deg);
transform: rotate(270deg);
}
.sk-fading-circle .sk-circle11 {
-webkit-transform: rotate(300deg);
-ms-transform: rotate(300deg);
transform: rotate(300deg);
}
.sk-fading-circle .sk-circle12 {
-webkit-transform: rotate(330deg);
-ms-transform: rotate(330deg);
transform: rotate(330deg);
}
.sk-fading-circle .sk-circle2:before {
-webkit-animation-delay: -1.1s;
animation-delay: -1.1s;
}
.sk-fading-circle .sk-circle3:before {
-webkit-animation-delay: -1s;
animation-delay: -1s;
}
.sk-fading-circle .sk-circle4:before {
-webkit-animation-delay: -0.9s;
animation-delay: -0.9s;
}
.sk-fading-circle .sk-circle5:before {
-webkit-animation-delay: -0.8s;
animation-delay: -0.8s;
}
.sk-fading-circle .sk-circle6:before {
-webkit-animation-delay: -0.7s;
animation-delay: -0.7s;
}
.sk-fading-circle .sk-circle7:before {
-webkit-animation-delay: -0.6s;
animation-delay: -0.6s;
}
.sk-fading-circle .sk-circle8:before {
-webkit-animation-delay: -0.5s;
animation-delay: -0.5s;
}
.sk-fading-circle .sk-circle9:before {
-webkit-animation-delay: -0.4s;
animation-delay: -0.4s;
}
.sk-fading-circle .sk-circle10:before {
-webkit-animation-delay: -0.3s;
animation-delay: -0.3s;
}
.sk-fading-circle .sk-circle11:before {
-webkit-animation-delay: -0.2s;
animation-delay: -0.2s;
}
.sk-fading-circle .sk-circle12:before {
-webkit-animation-delay: -0.1s;
animation-delay: -0.1s;
}
@-webkit-keyframes sk-circleFadeDelay {
0%, 39%, 100% { opacity: 0; }
40% { opacity: 1; }
}
@keyframes sk-circleFadeDelay {
0%, 39%, 100% { opacity: 0; }
40% { opacity: 1; }
}
</style>
+207
View File
@@ -0,0 +1,207 @@
<template>
<div class="qbox">
<div class="title">{{question.question_name}}({{question.question_type==1?'单选':question.question_type==2?'多选':question.question_type==3?'问答':'判断' }})</div>
<div class="tips" v-if="question.question_type==2">注:本题可选择多个选项!</div>
<div class="tips" v-else-if="question.question_type==1">注:本题最多可选择1个选项!</div>
<div class="options" v-if="question.question_type==2">
<van-checkbox-group v-model="manychecked" @change="changeCheck" :disabled="disabled">
<div class="cell" v-for="(item,index) in question.case_item_question_option" :key="item.option_id">
<van-checkbox :name="zimu[index]">
{{ item.option_value }}
<template #icon="props">
<img class="img-icon" :src="props.checked ? activeIcon : inactiveIcon" />
</template>
</van-checkbox>
</div>
<!-- <div class="cell">
<van-checkbox name="b">
复选框 b
<template #icon="props">
<img class="img-icon" :src="props.checked ? activeIcon : inactiveIcon" />
</template>
</van-checkbox>
</div> -->
</van-checkbox-group>
</div>
<div class="options" v-else-if="question.question_type==1" >
<van-radio-group v-model="singlechecked" @change="changeRadio" :disabled="disabled">
<div class="cell" v-for="(item,index) in question.case_item_question_option" :key="item.option_id">
<van-radio :name="zimu[index]">
{{ item.option_value }}
<template #icon="props">
<img class="img-icon" :src="props.checked ? activeIcon : inactiveIcon" />
</template>
</van-radio>
</div>
</van-radio-group>
</div>
<div class="options_con" v-else-if="question.question_type == 3">
<van-field @update:model-value="changeContent" :autosize="{ minHeight: 120 }" v-model="content" rows="2" autosize type="textarea"
placeholder="请输入内容" show-word-limit />
</div>
<div class="options" v-else-if="question.question_type == 4">
<van-radio-group v-model="singlechecked" @change="changeRadio" :disabled="disabled">
<div class="cell" v-for="(item,index) in question.case_item_question_option" :key="item.option_id">
<van-radio :name="zimu[index]">
{{ item.option_value }}
<template #icon="props">
<img class="img-icon" :src="props.checked ? activeIcon : inactiveIcon" />
</template>
</van-radio>
</div>
</van-radio-group>
</div>
</div>
</template>
<script setup>
import { ref } from "vue";
import activeIcon from "@/assets/select.png";
import inactiveIcon from "@/assets/noselect.png";
const emit = defineEmits(['checkAnswer']);
const manychecked = ref([]);
const singlechecked = ref('');
const content = ref('')
const zimu=['A','B','C','D','E','F','G','H','I','J'];
const props=defineProps({
question: {
type: Object,
default: () => ({}),
},
disabled:{
type:Boolean,
default:false
},
pageIndex:{
type:Number,
default:0
},
questionIndex:{
type:Number,
default:0
},
});
const changeRadio = (val) => {
let optionObj=props.question.case_item_question_option.find((item,index)=>zimu[index]==val);
emit('checkAnswer',{
pageIndex:props.pageIndex,
answer:val,
questionId:props.question.question_id,
error_tips:props.question.error_tips,
is_right_next:props.question.is_right_next,
option_id:optionObj?optionObj.option_id:'',
questionIndex:props.questionIndex,
question_type:props.question.question_type,
question_name:props.question.question_name,
question_answer:props.question.question_answer
})
};
const changeContent = (val) => {
emit('checkAnswer',{
pageIndex:props.pageIndex,
answer:val,
error_tips:props.question.error_tips,
questionId:props.question.question_id,
is_right_next:props.question.is_right_next,
questionIndex:props.questionIndex,
question_type:props.question.question_type,
question_name:props.question.question_name,
question_answer:props.question.question_answer
})
};
const changeCheck = (val) => {
let sortAnswer=val.sort();
let option_id='';
for(let i=0;i<sortAnswer.length;i++){
let optionObj=props.question.case_item_question_option.find((item,index)=>zimu[index]==sortAnswer[i]);
if(option_id){
if(optionObj.option_id){
option_id+=','+optionObj.option_id;
}
}else{
if(optionObj.option_id){
option_id=optionObj.option_id;
}
}
}
//let optionObj=props.question.case_item_question_option.find((item,index)=>zimu[index]==val);
emit('checkAnswer',{
pageIndex:props.pageIndex,
answer:sortAnswer,
option_id:option_id,
is_right_next:props.question.is_right_next,
error_tips:props.question.error_tips,
questionId:props.question.question_id,
questionIndex:props.questionIndex,
question_type:props.question.question_type,
question_name:props.question.question_name,
question_answer:props.question.question_answer
})
};
</script>
<style lang='scss' scoped>
.options_con {
border-radius: 5px;
border: .5px solid #B8B8B8;
margin-top: 15px;
box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.08);
border-radius: 10px;
padding: 15px 0px;
padding-bottom: 8px;
:deep() .van-cell {
background: none;
}
:deep() .van-field__word-limit {
color: #999999;
}
}
.qbox {
margin-bottom: 15px;
.title {
font-weight: bold;
font-size: 16px;
color: #333333;
}
.tips {
margin-top: 8px;
font-weight: 500;
font-size: 12px;
color: #999999;
}
.cell {
border-radius: 10px;
border: 1px solid #B8B8B8;
padding: 12px;
background: #fff;
margin-bottom: 12px;
}
.active{
border: 1px solid #43C9C3;
}
.cell:last-child {
margin-bottom: 0;
}
.options {
margin-top: 15px;
box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.08);
border-radius: 10px;
padding: 15px 12px;
}
.img-icon{
width: 19px;
height: 19px;
}
}
</style>
+163
View File
@@ -0,0 +1,163 @@
<template>
<div class="qbox" v-if="question.question_type != 3">
<div class="title">
{{ question.question_name }}({{ question.question_type == 1 ? '单选' : question.question_type == 2 ? '多选' :question.question_type == 3 ? '问答' : '判断'}})</div>
<div class="tips" v-if="question.question_type == 2">注:本题可选择多个选项!</div>
<div class="tips" v-else-if="question.question_type == 1">注:本题最多可选择1个选项!</div>
<div class="options" v-if="question.question_type == 1 || question.question_type == 2 || question.question_type == 4">
<div class="cell" v-for="(item, index) in question.case_item_question_option" :key="item.option_id" v-if="question.case_item_question_option">
<div class="title">{{ item.option_value }}</div>
<div class="progressbox">
<div class="progress">
<div class="inner" :style="{ width: 220 / 100 * item.proportion + 'px' }"></div>
</div>
<div class="numbox">
<div class="num">{{ item.select_num }}票</div>
<div class="precent">{{ item.proportion }}%</div>
</div>
</div>
</div>
</div>
<div class="options_con" v-if="question.question_type == 3">
<van-field readonly :autosize="{ minHeight: 120 }" v-model="question.question_answer" rows="2" autosize type="textarea"
placeholder="请输入内容" show-word-limit />
</div>
</div>
</template>
<script setup>
import { ref } from "vue";
const emit = defineEmits(['checkAnswer']);
const zimu = ['A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J']
const props = defineProps({
question: {
type: Object,
default: () => ({}),
},
disabled: {
type: Boolean,
default: false
},
pageIndex: {
type: Number,
default: 0
},
questionIndex: {
type: Number,
default: 0
},
});
</script>
<style lang='scss' scoped>
.options_con {
border-radius: 5px;
border: .5px solid #efefef;
margin-top: 15px;
box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.08);
border-radius: 10px;
padding: 15px 0px;
padding-bottom: 8px;
:deep() .van-cell {
background: none;
}
:deep() .van-field__word-limit {
color: #999999;
}
}
.qbox {
margin-bottom: 15px;
.title {
font-weight: bold;
font-size: 16px;
color: #333333;
}
.tips {
margin-top: 8px;
font-weight: 500;
font-size: 12px;
color: #999999;
}
.cell {
border-bottom: 1px solid #efefef;
background: #fff;
margin-bottom: 12px;
.title {
margin: 0 10px;
font-weight: 500;
font-size: 14px;
color: #1F1F1F;
}
.numbox {
display: flex;
font-size: 12px;
color: #999999;
.precent {
margin-left: 5px;
}
}
.progressbox {
justify-content: space-between;
align-items: center;
margin: 8px 10px 15px;
margin-bottom: 15px;
display: flex;
border-radius: 5px;
.progress {
margin-right: 10px;
width: 220px;
overflow: hidden;
height: 5px;
background: #EFF3FF;
border-radius: 5px;
}
.inner {
width: 80%;
height: 5px;
border-radius: 5px;
background: #43C9C3;
}
}
}
.active {
border: 1px solid #43C9C3;
}
.cell:last-child {
margin-bottom: 0;
border: none;
}
.options {
margin-top: 15px;
box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.08);
border-radius: 10px;
padding: 15px 0px;
padding-bottom: 8px;
}
.img-icon {
width: 19px;
height: 19px;
}
}
</style>
+103
View File
@@ -0,0 +1,103 @@
<template>
<div class="talkbox " v-show="showReply">
<div class="textbox">
<van-field :autosize="{ minHeight: 120 }" v-model="content" rows="2" autosize type="textarea"
maxlength="200" placeholder="请输入评论内容" show-word-limit />
</div>
<div class="toolbox">
<div class="cancel" @click="showReply = false">取消</div>
<div class="ok" @click="handleSubmit">提交</div>
</div>
</div>
</template>
<script setup>
import { ref } from 'vue'
const showReply=ref(false);
const content=ref('')
const props = defineProps({
root_id: {
type: String,
default: ''
},
project_id:{
type: String,
default: ''
},
case_id:{
type: String,
default: ''
},
parent_id: {
type: String,
default: ''
},
});
const handleSubmit=()=>{
showReply.value=false;
};
const openReply=()=>{
showReply.value=true;
};
const closeReply=()=>{
showReply.value=false;
};
defineExpose({
openReply,
closeReply
})
</script>
<style lang='scss' scoped>
.talkbox {
margin: 12px 30px 0px 0;
}
.textbox {
border-radius: 5px;
border: .5px solid #43C9C3;
:deep() .van-cell {
background: none;
}
:deep() .van-field__word-limit {
color: #999999;
}
}
.toolbox {
margin-top: 12px;
display: flex;
justify-content: space-between;
.cancel {
height: 38px;
background: #FFFFFF;
border: 1px solid #EBEBEB;
border-radius: 4px;
font-size: 14px;
display: flex;
justify-content: center;
align-items: center;
color: #737478;
flex: 1;
}
.ok {
margin-left: 12px;
flex: 1;
border-radius: 4px;
height: 38px;
display: flex;
justify-content: center;
align-items: center;
background: #43C9C3;
border: 1px solid #43C9C3;
font-size: 14px;
color: #fff;
}
}
</style>
+76
View File
@@ -0,0 +1,76 @@
<template>
<div class="qbox">
<div class="title">结合患者目前情况,下一步该如何治疗?</div>
<div class="tips">注:本题可选择多个选项!</div>
<div class="options">
<van-radio-group v-model="checked">
<div class="cell">
<van-radio name="a">
复选框 a
<template #icon="props">
<img class="img-icon" :src="props.checked ? activeIcon : inactiveIcon" />
</template>
</van-radio>
</div>
<div class="cell">
<van-radio name="b">
复选框 b
<template #icon="props">
<img class="img-icon" :src="props.checked ? activeIcon : inactiveIcon" />
</template>
</van-radio>
</div>
</van-radio-group>
</div>
</div>
</template>
<script setup>
import { ref } from "vue";
import activeIcon from "@/assets/select.png";
import inactiveIcon from "@/assets/noselect.png";
const checked = ref('');
</script>
<style lang='scss' scoped>
.qbox {
.title {
font-weight: bold;
font-size: 16px;
color: #333333;
}
.tips {
margin-top: 8px;
font-weight: 500;
font-size: 12px;
color: #999999;
}
.cell {
border-radius: 10px;
border: 1px solid #B8B8B8;
padding: 12px;
background: #fff;
margin-bottom: 12px;
}
.active{
border: 1px solid #43C9C3;
}
.cell:last-child {
margin-bottom: 0;
}
.options {
margin-top: 15px;
box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.08);
border-radius: 10px;
padding: 15px 12px;
}
.img-icon{
width: 19px;
height: 19px;
}
}
</style>
+892
View File
@@ -0,0 +1,892 @@
<template>
<van-pull-refresh v-model="pull_loading" @refresh="onRefresh" success-text="刷新成功">
<van-list
v-model="loading"
:finished="finished"
finished-text=""
ref="list"
@load="onLoad"
class="msglist"
>
<div
class="msgcell"
v-for="(item, index) in list"
:key="item.gandanhome_id"
>
<div class="namebox">
<div class="left">
<div class="leftcon">
<img
v-lazy="img_host + item.patient_photo"
alt=""
class="avastar head"
@click="goPage(item.patient_uuid)"
/>
<div class="info">
<div class="name_level">
<div class="name">{{ item.patient_name }}</div>
<img
v-lazy="imgcell.url"
alt=""
class="level"
v-for="imgcell in item.tags"
:key="imgcell.url"
v-if="type != 'mypage'"
/>
<div
class="settop"
v-if="type == 'mypage'|| type =='patient'"
v-show="item.top_flag == 1"
>
<span>置顶</span>
</div>
</div>
<div class="time">{{ item.update_date | fromTimeNow }}</div>
</div>
</div>
</div>
<div
class="more"
v-if="type == 'mypage'"
@click="openMore(index, item.gandanhome_id, item.top_flag)"
>
...
</div>
</div>
<div class="title" @click="goDetail(item.gandanhome_id)">
{{ item.title }}
</div>
<!-- <div @click.stop="goDetail(item.gandanhome_id)"> -->
<clamp
:htmlContent="item.content"
:topics="item.topics"
:id="item.gandanhome_id"
></clamp>
<!-- </div> -->
<div
class="imgbox"
@click="goDetail(item.gandanhome_id)"
v-if="item.imgs.length <= 6 && item.imgs.length != 4"
>
<div class="imgrow" v-for="itemcell in transforPages(item.imgs, 3)">
<div class="imgcell" v-for="imgcell in itemcell">
<van-image
v-if="imgcell.status==1"
lazy-load
fit="cover"
radius="8px"
:src="imgcell.url"
width="110px"
height="110px"
/>
<van-image
v-else
lazy-load
fit="cover"
radius="8px"
:src="require('../assets/weigui.png')"
width="110px"
height="110px"
/>
</div>
</div>
</div>
<div class="imgbox" v-else-if="item.imgs.length == 4">
<div
class="imgrow tworow"
v-for="itemcell in transforPages(item.imgs, 2)"
@click="goDetail(item.gandanhome_id)"
>
<div class="imgcell" v-for="imgcell in itemcell">
<van-image
lazy-load
v-if="imgcell.status==1"
radius="8px"
:src="imgcell.url"
width="110px"
height="110px"
/>
<van-image
lazy-load
v-else
radius="8px"
:src="require('../assets/weigui.png')"
width="110px"
height="110px"
/>
</div>
</div>
</div>
<div class="imgbox" v-else>
<div class="swiperbox">
<van-swipe :height="142" indicator-color="#3CC7C0">
<van-swipe-item
v-for="(imgcell, index) in item.imgs"
:key="index"
@click="goDetail(item.gandanhome_id)"
>
<div class="swipebg" >
<img v-lazy="imgcell.url" alt="" class="swiperImg" v-if="imgcell.status==1"/>
<img src="../assets/weigui.png" alt="" class="swiperImg" v-else>
</div>
<!-- <img v-lazy="imgcell.url" alt="" class="swipebg" v-if="imgcell.status==1"/>
<img src="../assets/weigui.png" alt="" class="swipebg" v-else> -->
<img v-lazy="imgcell.url" alt="" class="swiperImg" v-if="imgcell.status==1"/>
<img src="../assets/weigui.png" alt="" class="swiperImg" v-else>
</van-swipe-item>
</van-swipe>
</div>
</div>
<div class="tool" @click="goDetail(item.gandanhome_id)">
<div class="address">
{{ item.ip_show == 1 ? item.ip_address_province : "" }}
</div>
<div class="zan_comment">
<div
class="zan"
@click.stop="
toggleLike(item.isLike, index, item.gandanhome_id, item.likeNum)
"
>
<img src="../assets/zan.png" alt="" v-if="item.isLike == 1" />
<img src="../assets/unzan.png" alt="" v-else />
<div class="zancount" v-if="item.likeNum >0">{{ item.likeNum }}</div>
</div>
<!-- <div class="collectbox" v-if="type=='mypage' || type=='mycollect'" @click.stop="toggleCollect(item.is_collect,index,item.gandanhome_id)">
<img src="../assets/collect.png" alt="" v-if="item.is_collect == 1"/>
<img src="../assets/uncollect.png" alt="" v-else />
</div> -->
<div class="comment">
<img src="../assets/msg_comment.png" alt="" />
<div class="zancount" v-if="item.commonNum >0">{{ item.commonNum }}</div>
</div>
</div>
</div>
</div>
<div class="nodata" v-show="list.length == 0 ">
<div class="empty">
<img src="../assets/tie_empty.png" alt="" />
<div class="emptydesc">
{{
type == "searchBytitle"
? "暂未搜到相关帖子~"
: type == "homeFollow"
? "关注的人暂无发布哦~"
: type == "homeFriend"
? "好友暂无发布哦~"
: "暂无相关帖子~"
}}
</div>
</div>
</div>
<van-popup
v-model:show="showBottom"
round
position="bottom"
:style="{ height: '236px' }"
>
<div class="dealcell" @click="toggleTop">
{{ top_flag == 0 ? "置顶" : "取消置顶" }}
</div>
<div class="dealcell" @click="goPublic">编辑</div>
<div class="dealcell" @click="confirmDel">删除</div>
<div class="ba"></div>
<div class="dealcell" @click="showBottom = false">取消</div>
</van-popup>
</van-list>
</van-pull-refresh>
</template>
<script>
import img_host from "@/utils/imgHost";
import clamp from "./clamp";
import moment from "moment";
import { Dialog } from "vant";
import { throttle } from "../utils/debounce";
import cookie from "../utils/cookie";
moment.locale("zh-cn");
export default {
components: {
clamp,
},
filters: {
fromTimeNow(val) {
return moment(val).fromNow();
},
},
mounted(){
this.$toast.allowMultiple();
},
data() {
return {
img_host: img_host,
finished: false,
loading: false,
pull_loading: false,
page: 0,
list: [],
top_flag: 0,
showBottom: false,
dealIndex: 0,
};
},
props: {
keyWord: {
type: String,
default: "",
},
patient_uuid: {
type: String,
default: "",
},
type: {
type: String,
default: "",
},
topic_id:{
type: String,
default: "",
},
api: {
type: Function,
},
},
watch: {
keyWord(newVal, oldVal) {
if (newVal) {
if(this.type == "searchBytitle"){
this.freshList();
}
}
},
},
methods: {
closeBottom(){
this.showBottom = false;
},
goPage(uuid) {
let cur_uuid = cookie.readCookie("patient_uuid");
if (uuid == cur_uuid) {
this.$router.push({
path: "/mypage",
});
} else {
this.$router.push({
path: "/patientpage",
query: {
patient_uuid: uuid,
},
});
}
},
confirmDel() {
this.showBottom = false;
Dialog.confirm({
title: "温馨提示",
className: "mydialog",
message: "是否删除该帖子?",
})
.then(() => {
this.handelDelTopic();
})
.catch(() => {
// on cancel
});
},
openMore(index, gandanhome_id, top_flag) {
this.top_flag = top_flag;
this.gandanhome_id = gandanhome_id;
this.dealIndex = index;
this.showBottom = true;
},
toggleTop() {
this.top_flag == 0 ? this.handleTop() : this.handleCancelTop();
this.showBottom = false;
},
goPublic() {
this.showBottom = false;
this.$router.push({
path: "/publish",
query: {
gandanhome_id: this.gandanhome_id,
},
});
},
handelDelTopic() {
this.$api
.delTopic({
gandanhome_id: this.gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.list.splice(this.dealIndex, 1);
this.$toast({
duration: 1000,
message: "删除成功",
});
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
handleTop() {
this.$api
.setTop({
gandanhome_id: this.gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.$set(this.list[this.dealIndex], "top_flag", 1);
this.$toast({
duration: 1000,
message: "置顶成功",
});
this.freshList();
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
handleCompleteTask(id) {
this.$api
.addGrowRecord({
task_unique_id: id,
})
.then((rep) => {
var result = rep.data;
if (result.code == 200) {
if(result.data){
this.$toast({
duration: 2000,
message:'成长值+1',
});
}
}
})
.catch((error) => {
console.log(error);
});
},
handleCancelTop() {
this.$api
.cancelSetTop({
gandanhome_id: this.gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.$set(this.list[this.dealIndex], "top_flag", 0);
this.$toast({
duration: 1000,
message: "已取消置顶",
});
this.freshList();
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
onLoad() {
if (this.type == "searchBytitle") {
let str = this.keyWord.replace(/\s+/g, "");
if (str == "") {
this.page = 1;
this.list = [];
this.loading = false;
this.finished = false;
// this.$toast({
// duration: 1000,
// message: '请输入搜索内容',
// });
return false;
}
}
this.page++;
this.handleList();
},
goDetail(id) {
this.$router.push({
path: "talkDetail",
query: {
id: id,
},
});
},
onRefresh(){
this.freshList()
},
freshList: throttle(function () {
if (this.type == "searchBytitle") {
if (this.keyWord.replace(/\s+/g, "") == "") {
this.page = 1;
this.list = [];
this.loading = false;
this.finished = false;
// this.$toast({
// duration: 1000,
// message: '请输入搜索内容',
// });
return false;
}
}
this.page = 1;
this.pull_loading=false
this.list = [];
this.loading = false;
this.finished = false;
this.handleList();
}, 500),
handleList() {
let jsonData = null;
if (this.type == "searchBytitle") {
if (this.keyWord.replace(/\s+/g, "") == "") {
this.page = 1;
this.list = [];
this.loading = false;
this.finished = false;
// this.$toast({
// duration: 1000,
// message: '请输入搜索内容',
// });
return false;
}
jsonData = {
type: 1,
keyWord: this.keyWord,
page: this.page,
page_size: 10,
};
}else if(this.type =='ralationTopic'){
jsonData = {
topic_id: this.topic_id,
page: this.page,
page_size: 10,
};
} else if (this.type == "patient") {
jsonData = {
patient_uuid: this.patient_uuid,
page: this.page,
page_size: 10,
};
} else {
jsonData = {
page: this.page,
page_size: 10,
};
}
this.api(jsonData).then((rep) => {
var result = rep.data;
this.loading = false;
if (result.code == 200) {
this.list = this.list.concat(result.data.list);
if (result.data.list.length < 10) {
this.finished = true;
}
if (this.type == "homeFollow" && this.list.length > 0) {
this.$emit("getMyFollow", true);
}
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
transforPages(arr, num) {
const pages = [];
arr.forEach((item, index) => {
const page = Math.floor(index / num);
if (!pages[page]) {
pages[page] = [];
}
pages[page].push(item);
});
return pages;
},
handleCancelCollect(index, gandanhome_id) {
this.$api
.cancelCollect({
gandanhome_id: gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.$set(this.list[index], "is_collect", 0);
this.$toast({
duration: 1000,
message: "已取消收藏",
});
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
toggleCollect(iscollect, index, gandanhome_id) {
iscollect == 0
? this.handleCollect(index, gandanhome_id)
: this.handleCancelCollect(index, gandanhome_id);
},
handleCollect(index, gandanhome_id) {
this.$api
.collect({
gandanhome_id: gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.$set(this.list[index], "is_collect", 1);
this.$toast({
duration: 1000,
message: "收藏成功",
});
this.handleCompleteTask('task_add_collect')
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
toggleLike(isLike, index, gandanhome_id, likeNum) {
isLike == 0
? this.handleLike(gandanhome_id, index, likeNum)
: this.handleCancelLike(gandanhome_id, index, likeNum);
},
handleCancelLike(gandanhome_id, index, likeNum) {
this.$api
.cancelLike({
gandanhome_id: gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.$set(this.list[index], "isLike", 0);
this.$set(this.list[index], "likeNum", likeNum - 1);
this.$toast({
duration: 1000,
message: "已取消点赞",
});
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
handleLike(gandanhome_id, index, likeNum) {
this.$api
.like({
gandanhome_id: gandanhome_id,
})
.then((rep) => {
let result = rep.data;
if (result.code == 200) {
this.$set(this.list[index], "isLike", 1);
this.$set(this.list[index], "likeNum", likeNum + 1);
this.$toast({
duration: 1000,
message: "点赞成功",
});
this.handleCompleteTask('task_add_collect')
} else {
this.$toast({
duration: 1000,
message: rep.data.message,
});
}
});
},
},
};
</script>
<style scoped>
.info .time {
font-size: 14px;
color: #666;
}
.swiperbox {
margin-top: 10px;
border-radius: 4px;
overflow: hidden;
}
.swiperbox .van-swipe {
width: 100%;
}
.wraper >>> .van-swipe__indicator {
width: 9px;
height: 9px;
opacity: 1;
background-color: #fff;
}
.swiperbox>>> .van-swipe-item{
display: flex;
justify-content: center;
overflow: hidden;
}
.swiperImg {
margin:0 auto;
width:auto;
opacity: 1;
position: relative;
height:142px;
object-fit: contain;
}
.swipebg{
top:0;
height:142px;
position:absolute;
width: 100%;
opacity: 0.5;
object-fit: contain;
}
.swipebg .swiperImg{
width:100%;
height:auto;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
}
.settop {
width: 35px;
height: 15px;
font-size: 12px;
text-align: center;
line-height: 15px;
margin-left: 5px;
background: linear-gradient(318deg, #3cc7c0 0%, #3cc7c0 0%, #6ef0e9 100%);
border-radius: 8px;
color: #fff;
}
.settop span {
font-size: 12px;
display: block;
transform: scale(0.8);
}
.ba {
width: 100%;
height: 8px;
background: #f3f3f3;
}
.dealcell {
display: flex;
align-items: center;
height: 56px;
font-size: 16px;
color: rgba(0, 0, 0, 0.9);
justify-content: center;
border-bottom: 1px solid #efefef;
}
.dealcell:last-child {
border-bottom: none;
}
.more {
font-size: 16px;
color: #000;
}
.head[lazy="error"] {
background: url("../assets/head.png") no-repeat center center;
background-size: cover;
}
.imgbox {
width: 100%;
}
.imgbox.tworow {
width: 66.66%;
}
.imgbox .imgrow {
margin-top: 10px;
display: flex;
/* justify-content: space-between; */
flex-wrap: wrap;
}
.imgcell {
flex: 1;
max-width: 33.33%;
position: relative;
}
.imgbox .imgcell:nth-child(2n) {
text-align: center;
}
.imgbox .imgcell:nth-child(3n) {
text-align: right;
}
.tulist {
padding-top: 15px;
height: calc(100vh - 180px);
overflow-y: scroll;
-webkit-overflow-scrolling: touch;
}
.tool {
margin-top: 12px;
display: flex;
align-items: center;
justify-content: space-between;
}
.address {
font-size: 12px;
color: #999999;
}
.zan_comment {
min-width: 75px;
display: flex;
font-size: 14px;
color: #333333;
justify-content: space-between;
}
.zan {
display: flex;
align-items: center;
}
.collectbox {
margin: 0 20px;
}
.zan img,
.comment img,
.collectbox img {
width: 20px;
height: 20px;
}
.comment {
align-items: center;
display: flex;
}
.msgcell {
background: #fff;
padding: 8px 15px;
border-bottom: 5px solid #f4f4f4;
}
.namebox {
width:100%;
display: flex;
justify-content: space-between;
}
.namebox .info {
display: flex;
flex: 1;
height: 40px;
justify-content: space-between;
margin-right: 10px;
margin-left: 6px;
flex-direction: column;
}
.namebox .left {
display: flex;
flex: 1;
align-items: center;
}
.msgcell .leftcon {
display: flex;
align-items: center;
}
.msgcell .avastar {
width: 43px;
height: 43px;
border-radius: 50%;
}
.name_level {
display: flex;
align-items: center;
}
.name_level .name {
white-space: nowrap;
font-size: 18px;
color: #000000;
}
.level {
margin-left: 5px;
margin-right: 4px;
height: 15px;
}
.level:first-child {
margin-left: 4px;
}
.listbox {
margin-top: 10px;
}
.listbox .cell {
margin: 0 15px;
padding: 13px 10px;
background: #fff;
display: flex;
align-items: center;
border-radius: 4px;
justify-content: space-between;
border-bottom: 1px solid #efefef;
}
.listbox .cell .head {
width: 50px;
height: 50px;
border-radius: 50%;
}
.fllow {
width: 68px;
height: 25px;
display: flex;
color: #999;
font-size: 12px;
align-items: center;
justify-content: center;
background: #ffffff;
border-radius: 25px;
border: 1px solid #999999;
}
.listbox .cell .name {
font-size: 16px;
color: #333333;
margin-left: 24px;
}
.listbox .cell:last-child {
border-bottom: none;
}
.listbox .cell .left {
display: flex;
align-items: center;
}
.msglist .title {
line-height: 23px;
margin-top: 12px;
font-size: 17px;
color: #000000;
}
.msglist .msgdetail {
margin-top: 4px;
font-size: 15px;
line-height: 22px;
color: #666666;
}
.msglist .msgdetail span {
color: #3cc7c0;
}
.msglist {
background: transparent;
}
</style>
+68
View File
@@ -0,0 +1,68 @@
<template>
<!-- <div> -->
<div class="goTop" v-show="goTopShow" @click="goTop">
<img src="../assets/top.png" alt="">
</div>
<!-- </div> -->
</template>
<script setup>
import { ref, watch,onMounted,onUnmounted } from "vue"
const scrollTop = ref(0);
const goTopShow = ref(false);
watch(scrollTop, () => {
if (scrollTop.value > 250) {
goTopShow.value = true;
} else {
goTopShow.value = false;
}
})
const handleScroll = () => {
scrollTop.value = document.documentElement.scrollTop || document.body.scrollTop;
if (scrollTop.value > 250) {
goTopShow.value = true;
}else{
goTopShow.value = false;
}
};
const goTop = () => {
let timer = setInterval(() => {
let ispeed = Math.floor(-scrollTop.value / 5)
document.body.scrollTop = scrollTop.value + ispeed
document.documentElement.scrollTop = scrollTop.value + ispeed
if (scrollTop.value === 0) {
clearInterval(timer)
}
}, 20)
};
onMounted(() => {
window.addEventListener("scroll", handleScroll);
});
onUnmounted(() => {
window.removeEventListener("scroll", handleScroll);
});
</script>
<style scoped>
.goTop {
position: fixed;
width: 69px;
height: 30px;
right:0px;
bottom:135px;
cursor: pointer;
z-index:999;
overflow: hidden;
border-radius: 15px 0 0 15px;
box-shadow: 0 0 6px rgba(0, 0, 0, 0.12);
}
.goTop img {
width: 100%;
}
</style>