no message
This commit is contained in:
parent
911f31668f
commit
c64f3c4430
@ -431,6 +431,82 @@
|
||||
height: 16px;
|
||||
margin-left: 8px;
|
||||
}
|
||||
.ranking {
|
||||
width: 1200px;
|
||||
height: 239px;
|
||||
background-color: #ffffff;
|
||||
border-radius: 12px;
|
||||
padding-left: 30px;
|
||||
}
|
||||
.ranking .synthesize {
|
||||
width: 256px;
|
||||
margin-right: 65px;
|
||||
}
|
||||
.ranking .major {
|
||||
width: 821px;
|
||||
}
|
||||
.ranking .major .head {
|
||||
justify-content: space-between;
|
||||
}
|
||||
.ranking .major .head .more {
|
||||
font-size: 16px;
|
||||
color: #333333;
|
||||
font-weight: 400;
|
||||
}
|
||||
.ranking .major .head .more .icon {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
margin-left: 7px;
|
||||
transform: rotate(270deg);
|
||||
}
|
||||
.ranking .major .list {
|
||||
flex-wrap: wrap;
|
||||
justify-content: space-between;
|
||||
}
|
||||
.ranking .major .list .item {
|
||||
width: 371px;
|
||||
}
|
||||
.ranking .major .list .item .organ {
|
||||
font-family: "PingFangSC-Semibold", "PingFang SC Semibold", "PingFang SC", sans-serif;
|
||||
font-weight: 650;
|
||||
font-size: 14px;
|
||||
color: #000000;
|
||||
}
|
||||
.ranking .major .list .item .arrows {
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
margin: 0 6px;
|
||||
}
|
||||
.ranking .major .list .item .text {
|
||||
max-width: 195px;
|
||||
}
|
||||
.ranking .head {
|
||||
height: 52px;
|
||||
line-height: 52px;
|
||||
font-weight: 650;
|
||||
font-size: 16px;
|
||||
color: #000000;
|
||||
border-bottom: 1px solid #ebebeb;
|
||||
}
|
||||
.ranking .list {
|
||||
padding-top: 11px;
|
||||
}
|
||||
.ranking .list .item {
|
||||
font-size: 14px;
|
||||
color: #333;
|
||||
line-height: 24px;
|
||||
}
|
||||
.ranking .list .item .dot {
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
background-color: #fddf6d;
|
||||
border: 1px solid #cab157;
|
||||
border-radius: 39px;
|
||||
margin-right: 13px;
|
||||
}
|
||||
.ranking .list .item:not(:last-of-type) {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
.recruit {
|
||||
width: 100%;
|
||||
border: 1px solid #ebebeb;
|
||||
|
@ -490,6 +490,88 @@
|
||||
}
|
||||
}
|
||||
|
||||
.ranking {
|
||||
width: 1200px;
|
||||
height: 239px;
|
||||
background-color: rgba(255, 255, 255, 1);
|
||||
border-radius: 12px;
|
||||
padding-left: 30px;
|
||||
.synthesize {
|
||||
width: 256px;
|
||||
margin-right: 65px;
|
||||
}
|
||||
|
||||
.major {
|
||||
width: 821px;
|
||||
.head {
|
||||
justify-content: space-between;
|
||||
.more {
|
||||
font-size: 16px;
|
||||
color: #333333;
|
||||
font-weight: 400;
|
||||
.icon {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
margin-left: 7px;
|
||||
transform: rotate(270deg);
|
||||
}
|
||||
}
|
||||
}
|
||||
.list {
|
||||
flex-wrap: wrap;
|
||||
justify-content: space-between;
|
||||
.item {
|
||||
width: 371px;
|
||||
.organ {
|
||||
font-family: "PingFangSC-Semibold", "PingFang SC Semibold", "PingFang SC", sans-serif;
|
||||
font-weight: 650;
|
||||
font-size: 14px;
|
||||
color: #000000;
|
||||
}
|
||||
|
||||
.arrows {
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
margin: 0 6px;
|
||||
}
|
||||
.text {
|
||||
max-width: 195px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.head {
|
||||
height: 52px;
|
||||
line-height: 52px;
|
||||
font-weight: 650;
|
||||
font-size: 16px;
|
||||
color: #000000;
|
||||
border-bottom: 1px solid #ebebeb;
|
||||
}
|
||||
|
||||
.list {
|
||||
padding-top: 11px;
|
||||
|
||||
.item {
|
||||
.dot {
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
background-color: rgba(253, 223, 109, 1);
|
||||
border: 1px solid rgba(202, 177, 87, 1);
|
||||
border-radius: 39px;
|
||||
margin-right: 13px;
|
||||
}
|
||||
font-size: 14px;
|
||||
color: #333;
|
||||
line-height: 24px;
|
||||
|
||||
&:not(:last-of-type) {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.recruit {
|
||||
width: 100%;
|
||||
// height: 502px;
|
||||
@ -624,7 +706,6 @@
|
||||
font-size: 14px;
|
||||
padding: 0 8px;
|
||||
|
||||
|
||||
.img-add {
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
|
@ -126,44 +126,38 @@
|
||||
color: #000000;
|
||||
width: 62px;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .name {
|
||||
.boxbox .content .content-left .list .item .info .head {
|
||||
justify-content: space-between;
|
||||
align-items: flex-start;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .head .name {
|
||||
font-weight: 650;
|
||||
font-style: normal;
|
||||
font-size: 16px;
|
||||
color: #000000;
|
||||
margin-bottom: 5px;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .head .grade {
|
||||
font-size: 14px;
|
||||
color: #aaaaaa;
|
||||
text-align: right;
|
||||
width: max-content;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .head .grade .sum {
|
||||
font-weight: 650;
|
||||
color: #333333;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .name-en {
|
||||
font-size: 13px;
|
||||
line-height: 20px;
|
||||
color: #333333;
|
||||
margin-bottom: 6px;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .city {
|
||||
font-size: 14px;
|
||||
color: #7f7f7f;
|
||||
line-height: 20px;
|
||||
.boxbox .content .content-left .list .item .info .bottom {
|
||||
justify-content: space-between;
|
||||
align-items: flex-start;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .right {
|
||||
align-items: flex-end;
|
||||
position: relative;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .grade {
|
||||
font-size: 14px;
|
||||
line-height: 28px;
|
||||
color: #aaaaaa;
|
||||
margin-bottom: 16px;
|
||||
text-align: right;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
right: 0;
|
||||
width: max-content;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .grade .sum {
|
||||
font-weight: 650;
|
||||
color: #333333;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .btn {
|
||||
.boxbox .content .content-left .list .item .info .bottom .btn {
|
||||
width: 108px;
|
||||
height: 30px;
|
||||
background-color: #f95d5d;
|
||||
@ -171,11 +165,16 @@
|
||||
font-size: 14px;
|
||||
color: #ffffff;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .btn .icon {
|
||||
.boxbox .content .content-left .list .item .info .bottom .btn .icon {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
margin-left: 7px;
|
||||
}
|
||||
.boxbox .content .content-left .list .item .info .bottom .city {
|
||||
font-size: 14px;
|
||||
color: #7f7f7f;
|
||||
line-height: 20px;
|
||||
}
|
||||
.boxbox .content .screen-box {
|
||||
width: 360px;
|
||||
background-color: #fff;
|
||||
@ -291,10 +290,30 @@
|
||||
z-index: -1;
|
||||
}
|
||||
.boxbox .content .screen-box .screen-item.major .major-box .major-list .major-list-list {
|
||||
margin: 64px 11px 20px;
|
||||
margin: 64px 0 20px 11px;
|
||||
overflow: auto;
|
||||
height: 400px;
|
||||
}
|
||||
.boxbox .content .screen-box .screen-item.major .major-box .major-list .major-list-list::-webkit-scrollbar {
|
||||
width: 0;
|
||||
height: 0;
|
||||
}
|
||||
.boxbox .content .screen-box .screen-item.major .major-box .major-list .initial {
|
||||
flex-direction: column;
|
||||
margin-top: 64px;
|
||||
font-size: 12px;
|
||||
text-align: center;
|
||||
line-height: 17px;
|
||||
color: #aaaaaa;
|
||||
}
|
||||
.boxbox .content .screen-box .screen-item.major .major-box .major-list .initial .select {
|
||||
font-weight: 650;
|
||||
color: #000000;
|
||||
}
|
||||
.boxbox .content .screen-box .screen-item.major .major-box .major-list .initial .item {
|
||||
padding: 0 7px;
|
||||
cursor: pointer;
|
||||
}
|
||||
.boxbox .content .screen-box .screen-item.major .major-box .major-list .major-item {
|
||||
line-height: 26px;
|
||||
font-size: 14px;
|
||||
|
@ -143,12 +143,34 @@
|
||||
}
|
||||
|
||||
.info {
|
||||
.name {
|
||||
font-weight: 650;
|
||||
font-style: normal;
|
||||
font-size: 16px;
|
||||
color: #000000;
|
||||
margin-bottom: 5px;
|
||||
.head {
|
||||
justify-content: space-between;
|
||||
align-items: flex-start;
|
||||
|
||||
.name {
|
||||
font-weight: 650;
|
||||
font-style: normal;
|
||||
font-size: 16px;
|
||||
color: #000000;
|
||||
margin-bottom: 5px;
|
||||
}
|
||||
|
||||
.grade {
|
||||
font-size: 14px;
|
||||
// line-height: 28px;
|
||||
color: #aaaaaa;
|
||||
// margin-bottom: 16px;
|
||||
text-align: right;
|
||||
// position: absolute;
|
||||
// top: 0;
|
||||
// right: 0;
|
||||
width: max-content;
|
||||
|
||||
.sum {
|
||||
font-weight: 650;
|
||||
color: #333333;
|
||||
}
|
||||
}
|
||||
}
|
||||
.name-en {
|
||||
font-size: 13px;
|
||||
@ -156,49 +178,36 @@
|
||||
color: #333333;
|
||||
margin-bottom: 6px;
|
||||
}
|
||||
.city {
|
||||
font-size: 14px;
|
||||
color: #7f7f7f;
|
||||
line-height: 20px;
|
||||
|
||||
.bottom {
|
||||
justify-content: space-between;
|
||||
align-items: flex-start;
|
||||
.btn {
|
||||
width: 108px;
|
||||
height: 30px;
|
||||
background-color: rgba(249, 93, 93, 1);
|
||||
border-radius: 95px;
|
||||
font-size: 14px;
|
||||
color: #ffffff;
|
||||
|
||||
.icon {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
margin-left: 7px;
|
||||
}
|
||||
}
|
||||
.city {
|
||||
font-size: 14px;
|
||||
color: #7f7f7f;
|
||||
line-height: 20px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.right {
|
||||
align-items: flex-end;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.grade {
|
||||
font-size: 14px;
|
||||
line-height: 28px;
|
||||
color: #aaaaaa;
|
||||
margin-bottom: 16px;
|
||||
text-align: right;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
right: 0;
|
||||
width: max-content;
|
||||
|
||||
.sum {
|
||||
font-weight: 650;
|
||||
color: #333333;
|
||||
}
|
||||
}
|
||||
|
||||
.btn {
|
||||
width: 108px;
|
||||
height: 30px;
|
||||
background-color: rgba(249, 93, 93, 1);
|
||||
border-radius: 95px;
|
||||
font-size: 14px;
|
||||
color: #ffffff;
|
||||
|
||||
.icon {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
margin-left: 7px;
|
||||
}
|
||||
}
|
||||
// .right {
|
||||
// align-items: flex-end;
|
||||
// position: relative;
|
||||
// }
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -325,9 +334,33 @@
|
||||
z-index: -1;
|
||||
}
|
||||
.major-list-list {
|
||||
margin: 64px 11px 20px;
|
||||
margin: 64px 0 20px 11px;
|
||||
overflow: auto;
|
||||
height: 400px;
|
||||
|
||||
&::-webkit-scrollbar {
|
||||
width: 0;
|
||||
height: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.initial {
|
||||
flex-direction: column;
|
||||
margin-top: 64px;
|
||||
font-size: 12px;
|
||||
text-align: center;
|
||||
line-height: 17px;
|
||||
color: #aaaaaa;
|
||||
|
||||
.select {
|
||||
font-weight: 650;
|
||||
color: #000000;
|
||||
}
|
||||
|
||||
.item {
|
||||
padding: 0 7px;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
.major-item {
|
||||
line-height: 26px;
|
||||
|
694
html/index.html
694
html/index.html
@ -20,7 +20,6 @@
|
||||
|
||||
<body>
|
||||
<div id="app" class="main" v-cloak>
|
||||
|
||||
<img class="index-icon" src="/img/index-icon.png" />
|
||||
<div class="aaa"></div>
|
||||
|
||||
@ -226,6 +225,37 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 排名 -->
|
||||
<div class="ranking flexflex">
|
||||
<div class="synthesize">
|
||||
<div class="head">综合排名</div>
|
||||
<div class="list">
|
||||
<div class="item flexacenter" v-for="item in 5">
|
||||
<div class="dot"></div>
|
||||
QS世界综合排名(2025年)
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="major">
|
||||
<div class="head flexacenter">
|
||||
专业排名
|
||||
<div class="more flexacenter">
|
||||
more
|
||||
<img class="icon" src="/img/arrows-icon.png" />
|
||||
</div>
|
||||
</div>
|
||||
<div class="list flexflex">
|
||||
<div class="item flexacenter" v-for="item in 10">
|
||||
<div class="dot"></div>
|
||||
<div class="organ">QS</div>
|
||||
<img class="arrows" src="/img/arrows-circle-green.svg" />
|
||||
<div class="text one-line-display">世界综合排名世界综合排名世界综合排名世界综合排名世界综合排名世界综合排名</div>
|
||||
(2025年)
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 招生官 -->
|
||||
<div class="recruit">
|
||||
<div class="title flexacenter">
|
||||
@ -475,61 +505,61 @@
|
||||
</div>
|
||||
</div>
|
||||
<script>
|
||||
const { createApp, ref, onMounted, nextTick, onUnmounted, computed, getCurrentInstance } = Vue
|
||||
const { createApp, ref, onMounted, nextTick, onUnmounted, computed, getCurrentInstance } = Vue;
|
||||
const projectIndex = createApp({
|
||||
setup() {
|
||||
const { proxy } = getCurrentInstance()
|
||||
const { proxy } = getCurrentInstance();
|
||||
|
||||
let dataListRef = ref(null)
|
||||
let dataListRef = ref(null);
|
||||
|
||||
onMounted(() => {
|
||||
window.addEventListener("scroll", handleScroll)
|
||||
window.addEventListener("scroll", handleScroll);
|
||||
|
||||
listMasonryInstance = new Masonry(dataListRef.value, {
|
||||
itemSelector: ".data-item",
|
||||
gutter: 20,
|
||||
})
|
||||
init()
|
||||
})
|
||||
let user = ref({})
|
||||
let university = ref([])
|
||||
let discipline = ref([])
|
||||
let contrastcount = ref({})
|
||||
let encodekey = ref("")
|
||||
});
|
||||
init();
|
||||
});
|
||||
let user = ref({});
|
||||
let university = ref([]);
|
||||
let discipline = ref([]);
|
||||
let contrastcount = ref({});
|
||||
let encodekey = ref("");
|
||||
|
||||
// 初始化
|
||||
const init = () => {
|
||||
$ajaxget("/api/home/basicData").then(result => {
|
||||
const data = result.data || {}
|
||||
user.value = data.user
|
||||
university.value = data.university
|
||||
discipline.value = data.discipline
|
||||
contrastcount.value = data.contrastcount
|
||||
encodekey.value = data.encodekey
|
||||
$ajaxget("/api/home/basicData").then((result) => {
|
||||
const data = result.data || {};
|
||||
user.value = data.user;
|
||||
university.value = data.university;
|
||||
discipline.value = data.discipline;
|
||||
contrastcount.value = data.contrastcount;
|
||||
encodekey.value = data.encodekey;
|
||||
|
||||
getFate()
|
||||
getAdmission()
|
||||
getProjectData()
|
||||
getMyInit()
|
||||
})
|
||||
}
|
||||
getFate();
|
||||
getAdmission();
|
||||
getProjectData();
|
||||
getMyInit();
|
||||
});
|
||||
};
|
||||
|
||||
// 今日缘分项目
|
||||
let fateProject = ref([])
|
||||
let fateProject = ref([]);
|
||||
const getFate = () => {
|
||||
$ajaxget("/api/home/todayFateProject").then(res => {
|
||||
if (res.code != 200) return
|
||||
const data = res.data || []
|
||||
data.forEach(element => {
|
||||
element["random"] = randomString(6)
|
||||
})
|
||||
$ajaxget("/api/home/todayFateProject").then((res) => {
|
||||
if (res.code != 200) return;
|
||||
const data = res.data || [];
|
||||
data.forEach((element) => {
|
||||
element["random"] = randomString(6);
|
||||
});
|
||||
|
||||
fateProject.value = data
|
||||
})
|
||||
}
|
||||
fateProject.value = data;
|
||||
});
|
||||
};
|
||||
|
||||
let admissionList = ref([])
|
||||
let admissionTotalPage = ref(0) // 总页数
|
||||
let admissionList = ref([]);
|
||||
let admissionTotalPage = ref(0); // 总页数
|
||||
|
||||
// 获取 招生官项目
|
||||
const getAdmission = () => {
|
||||
@ -537,355 +567,355 @@
|
||||
limit: 20,
|
||||
page: 1,
|
||||
admissionsproject: 1,
|
||||
}).then(res => {
|
||||
if (res.code != 200) return
|
||||
const data = res.data
|
||||
const list = data.data || []
|
||||
}).then((res) => {
|
||||
if (res.code != 200) return;
|
||||
const data = res.data;
|
||||
const list = data.data || [];
|
||||
|
||||
const targetList = (list || []).map(element => ({
|
||||
const targetList = (list || []).map((element) => ({
|
||||
...element,
|
||||
random: randomString(6),
|
||||
}))
|
||||
}));
|
||||
|
||||
const chunkArray = (array, size) => {
|
||||
const result = []
|
||||
const result = [];
|
||||
for (let i = 0; i < array.length; i += size) {
|
||||
result.push(array.slice(i, i + size))
|
||||
result.push(array.slice(i, i + size));
|
||||
}
|
||||
return result
|
||||
}
|
||||
return result;
|
||||
};
|
||||
|
||||
const groupedAdmissionList = chunkArray(targetList, 4)
|
||||
const groupedAdmissionList = chunkArray(targetList, 4);
|
||||
|
||||
admissionList.value = groupedAdmissionList
|
||||
admissionTotalPage.value = groupedAdmissionList.length
|
||||
})
|
||||
}
|
||||
admissionList.value = groupedAdmissionList;
|
||||
admissionTotalPage.value = groupedAdmissionList.length;
|
||||
});
|
||||
};
|
||||
|
||||
let admissionPage = ref(1)
|
||||
let recruitListRef = ref(null)
|
||||
let admissionPage = ref(1);
|
||||
let recruitListRef = ref(null);
|
||||
// 点击切换 招生官 轮播图 滚动
|
||||
const cutAdmissionPage = type => {
|
||||
const cutAdmissionPage = (type) => {
|
||||
if (type == "left") {
|
||||
if (admissionPage.value > 1) admissionPage.value--
|
||||
if (admissionPage.value > 1) admissionPage.value--;
|
||||
} else {
|
||||
if (admissionPage.value < admissionTotalPage.value) admissionPage.value++
|
||||
if (admissionPage.value < admissionTotalPage.value) admissionPage.value++;
|
||||
}
|
||||
recruitListRef.value.scrollTo({
|
||||
left: 1140 * (admissionPage.value - 1),
|
||||
behavior: "smooth",
|
||||
})
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
// 计算
|
||||
const reversedMessage = type => {
|
||||
const reversedMessage = (type) => {
|
||||
if (type == "left") {
|
||||
if (admissionPage.value == 1) return "/img/arrows-triangle-gray.svg"
|
||||
else return "/img/arrows-triangle-blue.png"
|
||||
if (admissionPage.value == 1) return "/img/arrows-triangle-gray.svg";
|
||||
else return "/img/arrows-triangle-blue.png";
|
||||
} else {
|
||||
if (admissionPage.value == admissionTotalPage.value) return "/img/arrows-triangle-gray.svg"
|
||||
else return "/img/arrows-triangle-blue.png"
|
||||
if (admissionPage.value == admissionTotalPage.value) return "/img/arrows-triangle-gray.svg";
|
||||
else return "/img/arrows-triangle-blue.png";
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
let projectList = ref([])
|
||||
let projectPage = 1
|
||||
let projectList = ref([]);
|
||||
let projectPage = 1;
|
||||
// 获取项目数据
|
||||
const getProjectData = () => {
|
||||
if (projectPage == 0) return
|
||||
if (projectPage == 0) return;
|
||||
$ajaxget("/api/lists", {
|
||||
limit: 20,
|
||||
page: projectPage,
|
||||
}).then(res => {
|
||||
if (res.code != 200) return
|
||||
const data = res.data
|
||||
}).then((res) => {
|
||||
if (res.code != 200) return;
|
||||
const data = res.data;
|
||||
|
||||
const date = new Date()
|
||||
const month = date.getMonth() + 1
|
||||
const year = date.getFullYear()
|
||||
const date = new Date();
|
||||
const month = date.getMonth() + 1;
|
||||
const year = date.getFullYear();
|
||||
|
||||
let list = data.data || []
|
||||
let list = data.data || [];
|
||||
|
||||
list = list.map(element => ({
|
||||
list = list.map((element) => ({
|
||||
...element,
|
||||
random: randomString(6),
|
||||
semesterState: month > element.semester.month && year + 1 <= element.semester.year,
|
||||
tuition_fee_text: formatNumberWithSpaces(element.tuition_fee),
|
||||
}))
|
||||
projectList.value = projectList.value.concat(list)
|
||||
projectPage = data.count > data.limit * data.page ? projectPage + 1 : 0
|
||||
}));
|
||||
projectList.value = projectList.value.concat(list);
|
||||
projectPage = data.count > data.limit * data.page ? projectPage + 1 : 0;
|
||||
nextTick(() => {
|
||||
listMasonryInstance.reloadItems()
|
||||
listMasonryInstance.layout()
|
||||
})
|
||||
})
|
||||
}
|
||||
listMasonryInstance.reloadItems();
|
||||
listMasonryInstance.layout();
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
//瀑布实例
|
||||
let listMasonryInstance = null
|
||||
let listMasonryInstance = null;
|
||||
|
||||
const imageFallLoaded = () => {
|
||||
listMasonryInstance.reloadItems()
|
||||
listMasonryInstance.layout()
|
||||
}
|
||||
listMasonryInstance.reloadItems();
|
||||
listMasonryInstance.layout();
|
||||
};
|
||||
|
||||
const handleScroll = () => {
|
||||
const scrollHeight = document.documentElement.scrollHeight
|
||||
const clientHeight = document.documentElement.clientHeight
|
||||
const scrollTop = window.pageYOffset
|
||||
const scrollHeight = document.documentElement.scrollHeight;
|
||||
const clientHeight = document.documentElement.clientHeight;
|
||||
const scrollTop = window.pageYOffset;
|
||||
|
||||
if (scrollTop + clientHeight >= scrollHeight) {
|
||||
getProjectData()
|
||||
getProjectData();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const baseRef = ref(null)
|
||||
const baseRef = ref(null);
|
||||
|
||||
// 点击事件
|
||||
const handleClick = (type, item, index, i) => {
|
||||
const random = item.random
|
||||
const random = item.random;
|
||||
|
||||
if (item.status == 1) return
|
||||
if (item.status == 1) return;
|
||||
$ajax("/api/contrast/add", {
|
||||
projectid: item.id,
|
||||
}).then(res => {
|
||||
baseRef.value.calculate(random)
|
||||
}).then((res) => {
|
||||
baseRef.value.calculate(random);
|
||||
|
||||
if (type == "fate") fateProject.value[index]["state"] = 1
|
||||
if (type == "fate") fateProject.value[index]["state"] = 1;
|
||||
|
||||
if (type == "admission") {
|
||||
admissionList.value[index][i]["contraststatus"] = {
|
||||
status: 1,
|
||||
ismanage: 1,
|
||||
}
|
||||
admissionList.value[index][i]["moreState"] = false
|
||||
};
|
||||
admissionList.value[index][i]["moreState"] = false;
|
||||
}
|
||||
|
||||
if (type == "list") {
|
||||
projectList.value[index]["contraststatus"] = {
|
||||
status: 1,
|
||||
ismanage: 1,
|
||||
}
|
||||
projectList.value[index]["moreState"] = false
|
||||
};
|
||||
projectList.value[index]["moreState"] = false;
|
||||
}
|
||||
})
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
const openMoreSelect = (type, index, i) => {
|
||||
if (type == "admission") {
|
||||
admissionList.value[index][i]["moreState"] = true
|
||||
admissionList.value[index][i]["moreState"] = true;
|
||||
}
|
||||
if (type == "list") {
|
||||
console.log(222)
|
||||
projectList.value[index]["moreState"] = true
|
||||
console.log(222);
|
||||
projectList.value[index]["moreState"] = true;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// 关闭所有 状态 选择 弹出框
|
||||
const closeMoreSelectAll = type => {
|
||||
const closeMoreSelectAll = (type) => {
|
||||
if (type == "admission") {
|
||||
admissionList.value.forEach(element => {
|
||||
element.forEach(ele => {
|
||||
ele["moreState"] = false
|
||||
})
|
||||
})
|
||||
admissionList.value.forEach((element) => {
|
||||
element.forEach((ele) => {
|
||||
ele["moreState"] = false;
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
if (type == "list") {
|
||||
projectList.value.forEach(element => {
|
||||
element["moreState"] = false
|
||||
})
|
||||
projectList.value.forEach((element) => {
|
||||
element["moreState"] = false;
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
onUnmounted(() => {
|
||||
window.removeEventListener("scroll", handleScroll)
|
||||
})
|
||||
window.removeEventListener("scroll", handleScroll);
|
||||
});
|
||||
|
||||
let contrastList = ref([])
|
||||
let contrastList = ref([]);
|
||||
|
||||
const stateObj = ref({
|
||||
0: "待定",
|
||||
1: "主申",
|
||||
2: "冲刺",
|
||||
3: "保底",
|
||||
})
|
||||
});
|
||||
|
||||
let manageHintState = ref(false)
|
||||
let classify = ref("vs")
|
||||
let manageHintState = ref(false);
|
||||
let classify = ref("vs");
|
||||
|
||||
// 我的项目的初始化
|
||||
const getMyInit = () => {
|
||||
manageHintState.value = localStorage.getItem("PMState") || false
|
||||
manageHintState.value = localStorage.getItem("PMState") || false;
|
||||
|
||||
getList().then(res => {
|
||||
const data = res.data || {}
|
||||
getList().then((res) => {
|
||||
const data = res.data || {};
|
||||
data.nums = {
|
||||
contrast: 0,
|
||||
manage: 10,
|
||||
}
|
||||
const nums = data.nums || {}
|
||||
classify.value = "vs"
|
||||
};
|
||||
const nums = data.nums || {};
|
||||
classify.value = "vs";
|
||||
if (nums["contrast"] == 0 && nums["manage"] != 0) {
|
||||
classify.value = "manage"
|
||||
handleUserProjectData(res)
|
||||
classify.value = "manage";
|
||||
handleUserProjectData(res);
|
||||
} else {
|
||||
getQuickList()
|
||||
handleProjectListData(res)
|
||||
getQuickList();
|
||||
handleProjectListData(res);
|
||||
}
|
||||
})
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
let projectCount = ref(0)
|
||||
handleProjectListData = res => {
|
||||
const data = res.data
|
||||
let list = data.data || []
|
||||
let count = 0
|
||||
list.forEach(element => {
|
||||
if (element.status == 1) count++
|
||||
})
|
||||
projectCount.value = count
|
||||
contrastList.value = list
|
||||
}
|
||||
let projectCount = ref(0);
|
||||
handleProjectListData = (res) => {
|
||||
const data = res.data;
|
||||
let list = data.data || [];
|
||||
let count = 0;
|
||||
list.forEach((element) => {
|
||||
if (element.status == 1) count++;
|
||||
});
|
||||
projectCount.value = count;
|
||||
contrastList.value = list;
|
||||
};
|
||||
|
||||
let typeid = ref("")
|
||||
let typeIndex = ref(0)
|
||||
let typeList = ref([])
|
||||
let typeid = ref("");
|
||||
let typeIndex = ref(0);
|
||||
let typeList = ref([]);
|
||||
// 获取项目管理
|
||||
const getUserProject = () => {
|
||||
getList({
|
||||
page: 1,
|
||||
typeid: typeid.value,
|
||||
}).then(res => {
|
||||
handleUserProjectData(res)
|
||||
})
|
||||
}
|
||||
}).then((res) => {
|
||||
handleUserProjectData(res);
|
||||
});
|
||||
};
|
||||
|
||||
const getProjectList = () => {
|
||||
getList({
|
||||
page: 1,
|
||||
}).then(res => {
|
||||
handleProjectListData(res)
|
||||
})
|
||||
}
|
||||
}).then((res) => {
|
||||
handleProjectListData(res);
|
||||
});
|
||||
};
|
||||
|
||||
let manageList = ref([])
|
||||
const handleUserProjectData = res => {
|
||||
const data = res.data
|
||||
let list = data.data || []
|
||||
let manageList = ref([]);
|
||||
const handleUserProjectData = (res) => {
|
||||
const data = res.data;
|
||||
let list = data.data || [];
|
||||
list.forEach((element, index) => {
|
||||
element["sortKey"] = index
|
||||
})
|
||||
typeList.value = data.typeList
|
||||
manageList.value = list
|
||||
element["sortKey"] = index;
|
||||
});
|
||||
typeList.value = data.typeList;
|
||||
manageList.value = list;
|
||||
|
||||
nextTick(() => {
|
||||
manageList.value.forEach((element, index) => {
|
||||
if (element.ismanage == 1 && element.remarks) {
|
||||
console.log("element", element)
|
||||
const textarea = manageListRef.value.querySelector(`.item[data-index="${index}"] textarea`)
|
||||
element["inputHeight"] = textarea.scrollHeight + "px"
|
||||
console.log("element", element);
|
||||
const textarea = manageListRef.value.querySelector(`.item[data-index="${index}"] textarea`);
|
||||
element["inputHeight"] = textarea.scrollHeight + "px";
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
nextTick(() => {
|
||||
if (manageList.value.length != 0) getAllHeight()
|
||||
})
|
||||
})
|
||||
}
|
||||
if (manageList.value.length != 0) getAllHeight();
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
const getAllHeight = () => {
|
||||
const all = manageListRef.value.querySelectorAll(".item") || []
|
||||
all.forEach(element => {
|
||||
const index = element.getAttribute("data-index") * 1
|
||||
manageList.value[index]["height"] = element.offsetHeight + 20
|
||||
})
|
||||
calculateWaterfall()
|
||||
}
|
||||
const all = manageListRef.value.querySelectorAll(".item") || [];
|
||||
all.forEach((element) => {
|
||||
const index = element.getAttribute("data-index") * 1;
|
||||
manageList.value[index]["height"] = element.offsetHeight + 20;
|
||||
});
|
||||
calculateWaterfall();
|
||||
};
|
||||
|
||||
const calculateWaterfall = () => {
|
||||
let list = JSON.parse(JSON.stringify(manageList.value)) || []
|
||||
list.sort((a, b) => a.sortKey - b.sortKey)
|
||||
let list = JSON.parse(JSON.stringify(manageList.value)) || [];
|
||||
list.sort((a, b) => a.sortKey - b.sortKey);
|
||||
|
||||
let topLeft = 0
|
||||
let topRigth = 0
|
||||
let topLeft = 0;
|
||||
let topRigth = 0;
|
||||
|
||||
for (let i = 0; i < list.length; i++) {
|
||||
const element = list[i]
|
||||
const element = list[i];
|
||||
|
||||
if (element.ismanage == 1) {
|
||||
const height = element.height
|
||||
let top = 0
|
||||
let side = topLeft <= topRigth ? "left" : "right"
|
||||
let left = 0
|
||||
const height = element.height;
|
||||
let top = 0;
|
||||
let side = topLeft <= topRigth ? "left" : "right";
|
||||
let left = 0;
|
||||
if (side == "left") {
|
||||
top = topLeft
|
||||
topLeft += height
|
||||
top = topLeft;
|
||||
topLeft += height;
|
||||
} else {
|
||||
top = topRigth
|
||||
topRigth += height
|
||||
left = 440
|
||||
top = topRigth;
|
||||
topRigth += height;
|
||||
left = 440;
|
||||
}
|
||||
if (!element.load) {
|
||||
element["top"] = top
|
||||
element["left"] = left
|
||||
element["top"] = top;
|
||||
element["left"] = left;
|
||||
}
|
||||
element["height"] = height
|
||||
element["height"] = height;
|
||||
}
|
||||
}
|
||||
|
||||
manageList.value = list
|
||||
}
|
||||
manageList.value = list;
|
||||
};
|
||||
|
||||
const manageEmpty = computed(() => {
|
||||
return typeList.value[typeIndex.value]["count"] == 0
|
||||
})
|
||||
return typeList.value[typeIndex.value]["count"] == 0;
|
||||
});
|
||||
|
||||
const isPitchExceedOne = computed(() => {
|
||||
return contrastList.value.filter(item => item.pitch).length >= 1
|
||||
})
|
||||
return contrastList.value.filter((item) => item.pitch).length >= 1;
|
||||
});
|
||||
|
||||
const isPitchExceedTwo = computed(() => {
|
||||
return contrastList.value.filter(item => item.pitch).length >= 2
|
||||
})
|
||||
return contrastList.value.filter((item) => item.pitch).length >= 2;
|
||||
});
|
||||
|
||||
const isPitchExceedThree = computed(index => {
|
||||
console.log("index", index)
|
||||
return contrastList.value.filter(item => item.pitch).length >= 3
|
||||
})
|
||||
const isPitchExceedThree = computed((index) => {
|
||||
console.log("index", index);
|
||||
return contrastList.value.filter((item) => item.pitch).length >= 3;
|
||||
});
|
||||
|
||||
// 点击选择项目
|
||||
const cutSelect = index => {
|
||||
const item = contrastList.value[index]
|
||||
const state = item["pitch"] || false
|
||||
if (!state && contrastList.value.filter(item => item["pitch"]).length >= 3) return
|
||||
item["pitch"] = !item["pitch"]
|
||||
}
|
||||
const cutSelect = (index) => {
|
||||
const item = contrastList.value[index];
|
||||
const state = item["pitch"] || false;
|
||||
if (!state && contrastList.value.filter((item) => item["pitch"]).length >= 3) return;
|
||||
item["pitch"] = !item["pitch"];
|
||||
};
|
||||
|
||||
let quickList = ref([])
|
||||
let quickList = ref([]);
|
||||
// 获取快速列表
|
||||
const getQuickList = () => {
|
||||
$ajaxget("/api/contrast/getQuickList", {}).then(res => {
|
||||
if (res.code != 200) return
|
||||
const data = res.data
|
||||
quickList.value = data || []
|
||||
})
|
||||
}
|
||||
$ajaxget("/api/contrast/getQuickList", {}).then((res) => {
|
||||
if (res.code != 200) return;
|
||||
const data = res.data;
|
||||
quickList.value = data || [];
|
||||
});
|
||||
};
|
||||
|
||||
// 快速列表点击 显示删除 按钮
|
||||
const quickShowHideDelete = index => {
|
||||
quickList.value[index]["deleteState"] = !quickList.value[index]["deleteState"]
|
||||
}
|
||||
const quickShowHideDelete = (index) => {
|
||||
quickList.value[index]["deleteState"] = !quickList.value[index]["deleteState"];
|
||||
};
|
||||
|
||||
// 点击删除快速对比
|
||||
const quickDelete = index => {
|
||||
const data = quickList.value[index]
|
||||
const quickDelete = (index) => {
|
||||
const data = quickList.value[index];
|
||||
$ajax("/api/contrast/deleteQuick", {
|
||||
id: data.id,
|
||||
}).then(res => {
|
||||
quickList.value.splice(index, 1)
|
||||
})
|
||||
}
|
||||
}).then((res) => {
|
||||
quickList.value.splice(index, 1);
|
||||
});
|
||||
};
|
||||
|
||||
// 点击 删除 我的对比
|
||||
const contrastDelete = () => {
|
||||
@ -893,12 +923,12 @@
|
||||
if (element["pitch"]) {
|
||||
$ajax("/api/contrast/delete", {
|
||||
projectid: element.projectid,
|
||||
}).then(res => {
|
||||
contrastList.value[index]["status"] = false
|
||||
})
|
||||
}).then((res) => {
|
||||
contrastList.value[index]["status"] = false;
|
||||
});
|
||||
}
|
||||
})
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
// 公共的获取列表 方法
|
||||
const getList = (obj = {}) => {
|
||||
@ -907,152 +937,152 @@
|
||||
limit: 2000,
|
||||
page: obj.page || 1,
|
||||
typeid: obj.typeid || "",
|
||||
}).then(res => resolve(res))
|
||||
})
|
||||
}
|
||||
}).then((res) => resolve(res));
|
||||
});
|
||||
};
|
||||
|
||||
// 切换查看类型
|
||||
const cutClassify = type => {
|
||||
const cutClassify = (type) => {
|
||||
// const classify = e.currentTarget.dataset.type
|
||||
if (type == classify.value) return
|
||||
classify.value = type
|
||||
if (type == classify.value) return;
|
||||
classify.value = type;
|
||||
if (classify.value == "manage") {
|
||||
typeid.value = ""
|
||||
manageList.value = []
|
||||
getUserProject()
|
||||
typeid.value = "";
|
||||
manageList.value = [];
|
||||
getUserProject();
|
||||
}
|
||||
if (classify.value == "vs") {
|
||||
quickList.value = []
|
||||
contrastList.value = []
|
||||
getProjectList()
|
||||
getQuickList()
|
||||
quickList.value = [];
|
||||
contrastList.value = [];
|
||||
getProjectList();
|
||||
getQuickList();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const manageListRef = ref(null)
|
||||
const manageListRef = ref(null);
|
||||
|
||||
const inputInput = index => {
|
||||
const textarea = manageListRef.value.querySelector(`.item[data-index="${index}"] textarea`)
|
||||
manageList.value[index]["inputHeight"] = textarea.scrollHeight + "px"
|
||||
}
|
||||
const inputInput = (index) => {
|
||||
const textarea = manageListRef.value.querySelector(`.item[data-index="${index}"] textarea`);
|
||||
manageList.value[index]["inputHeight"] = textarea.scrollHeight + "px";
|
||||
};
|
||||
|
||||
const inputblur = index => {
|
||||
const target = manageList.value[index]
|
||||
const inputblur = (index) => {
|
||||
const target = manageList.value[index];
|
||||
|
||||
$ajax("/api/user/remarks", {
|
||||
token: target.token,
|
||||
remarks: target.remarks,
|
||||
}).then(res => {
|
||||
console.log("message", res.message)
|
||||
}).then((res) => {
|
||||
console.log("message", res.message);
|
||||
|
||||
getAllHeight()
|
||||
})
|
||||
}
|
||||
getAllHeight();
|
||||
});
|
||||
};
|
||||
|
||||
// 关闭 底部提示框
|
||||
const manageClose = () => {
|
||||
manageHintState.value = true
|
||||
localStorage.setItem("PMState", 1)
|
||||
}
|
||||
manageHintState.value = true;
|
||||
localStorage.setItem("PMState", 1);
|
||||
};
|
||||
|
||||
// 点击头部 tab
|
||||
const cutTypeid = index => {
|
||||
typeIndex.value = index
|
||||
typeid.value = typeList.value[index].value
|
||||
manageList.value = []
|
||||
getUserProject()
|
||||
}
|
||||
const cutTypeid = (index) => {
|
||||
typeIndex.value = index;
|
||||
typeid.value = typeList.value[index].value;
|
||||
manageList.value = [];
|
||||
getUserProject();
|
||||
};
|
||||
|
||||
const cutManageStateShow = index => {
|
||||
manageList.value.forEach(element => (element["state"] = false))
|
||||
const cutManageStateShow = (index) => {
|
||||
manageList.value.forEach((element) => (element["state"] = false));
|
||||
|
||||
manageList.value[index]["state"] = !manageList.value[index]["state"]
|
||||
}
|
||||
manageList.value[index]["state"] = !manageList.value[index]["state"];
|
||||
};
|
||||
|
||||
const cutManageState = (typeid, index) => {
|
||||
const target = manageList.value[index] || {}
|
||||
const target = manageList.value[index] || {};
|
||||
|
||||
$ajax("/api/user/changeType", {
|
||||
token: target.token,
|
||||
typeid,
|
||||
}).then(res => {
|
||||
if (res.code != 200) return
|
||||
}).then((res) => {
|
||||
if (res.code != 200) return;
|
||||
|
||||
const stateNameFront = stateObj.value[target.typeid] // 修改前的状态
|
||||
const stateNameAfter = stateObj.value[typeid] // 修改后的状态
|
||||
typeList.value.forEach(element => {
|
||||
if (element.name == stateNameFront) element.count--
|
||||
if (element.name == stateNameAfter) element.count++
|
||||
})
|
||||
const stateNameFront = stateObj.value[target.typeid]; // 修改前的状态
|
||||
const stateNameAfter = stateObj.value[typeid]; // 修改后的状态
|
||||
typeList.value.forEach((element) => {
|
||||
if (element.name == stateNameFront) element.count--;
|
||||
if (element.name == stateNameAfter) element.count++;
|
||||
});
|
||||
|
||||
manageList.value[index]["typeid"] = typeid
|
||||
manageList.value[index]["state"] = false
|
||||
manageList.value[index]["typeid"] = typeid;
|
||||
manageList.value[index]["state"] = false;
|
||||
|
||||
if (typeIndex.value != 0) {
|
||||
manageList.value[index]["ismanage"] = 0
|
||||
manageList.value[index]["height"] = 0
|
||||
manageList.value[index]["ismanage"] = 0;
|
||||
manageList.value[index]["height"] = 0;
|
||||
}
|
||||
})
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
let isDragging = ref(null)
|
||||
const startDrag = index => {
|
||||
isDragging.value = index
|
||||
const target = manageList.value[index]
|
||||
let isDragging = ref(null);
|
||||
const startDrag = (index) => {
|
||||
isDragging.value = index;
|
||||
const target = manageList.value[index];
|
||||
|
||||
manageList.value[index]["load"] = true
|
||||
}
|
||||
manageList.value[index]["load"] = true;
|
||||
};
|
||||
|
||||
let timer = null
|
||||
let timer = null;
|
||||
|
||||
const dragging = index => {
|
||||
if (isDragging.value != index) return
|
||||
manageList.value[index]["left"] += event.movementX
|
||||
manageList.value[index]["top"] += event.movementY
|
||||
const dragging = (index) => {
|
||||
if (isDragging.value != index) return;
|
||||
manageList.value[index]["left"] += event.movementX;
|
||||
manageList.value[index]["top"] += event.movementY;
|
||||
|
||||
const list = JSON.parse(JSON.stringify(manageList.value))
|
||||
let maxOverlapArea = 0
|
||||
let maxOverlapElement = null
|
||||
const list = JSON.parse(JSON.stringify(manageList.value));
|
||||
let maxOverlapArea = 0;
|
||||
let maxOverlapElement = null;
|
||||
|
||||
const target = list[index]
|
||||
const target = list[index];
|
||||
|
||||
for (let i = 0; i < list.length; i++) {
|
||||
const element = list[i]
|
||||
const element = list[i];
|
||||
if (index !== i) {
|
||||
const overlapArea = Math.max(0, Math.min(target.left + 420, element.left + 420) - Math.max(target.left, element.left)) * Math.max(0, Math.min(target.top + target.height, element.top + element.height) - Math.max(target.top, element.top))
|
||||
const overlapArea = Math.max(0, Math.min(target.left + 420, element.left + 420) - Math.max(target.left, element.left)) * Math.max(0, Math.min(target.top + target.height, element.top + element.height) - Math.max(target.top, element.top));
|
||||
|
||||
// 计算重叠面积是否超过另一个元素的一半面积
|
||||
const halfArea = (420 * element.height) / 2
|
||||
const halfArea = (420 * element.height) / 2;
|
||||
if (overlapArea > halfArea && overlapArea > maxOverlapArea) {
|
||||
maxOverlapArea = overlapArea
|
||||
maxOverlapElement = i
|
||||
maxOverlapArea = overlapArea;
|
||||
maxOverlapElement = i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (maxOverlapElement != null) {
|
||||
const over1 = JSON.parse(JSON.stringify(list[maxOverlapElement]))
|
||||
const over2 = JSON.parse(JSON.stringify(list[isDragging.value]))
|
||||
const over1 = JSON.parse(JSON.stringify(list[maxOverlapElement]));
|
||||
const over2 = JSON.parse(JSON.stringify(list[isDragging.value]));
|
||||
|
||||
list[maxOverlapElement]["sortKey"] = over2.sortKey
|
||||
list[isDragging.value]["sortKey"] = over1.sortKey
|
||||
manageList.value = list
|
||||
calculateWaterfall()
|
||||
isDragging.value = maxOverlapElement
|
||||
list[maxOverlapElement]["sortKey"] = over2.sortKey;
|
||||
list[isDragging.value]["sortKey"] = over1.sortKey;
|
||||
manageList.value = list;
|
||||
calculateWaterfall();
|
||||
isDragging.value = maxOverlapElement;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const endDrag = () => {
|
||||
if (isDragging.value == null) return
|
||||
if (isDragging.value == null) return;
|
||||
|
||||
isDragging.value = null
|
||||
isDragging.value = null;
|
||||
|
||||
manageList.value.forEach(element => {
|
||||
element["load"] = false
|
||||
})
|
||||
manageList.value.forEach((element) => {
|
||||
element["load"] = false;
|
||||
});
|
||||
|
||||
calculateWaterfall()
|
||||
}
|
||||
calculateWaterfall();
|
||||
};
|
||||
|
||||
return {
|
||||
user,
|
||||
@ -1106,13 +1136,13 @@
|
||||
dragging,
|
||||
endDrag,
|
||||
isDragging,
|
||||
}
|
||||
};
|
||||
},
|
||||
})
|
||||
});
|
||||
|
||||
projectIndex.component("base-bottom", base)
|
||||
projectIndex.component("base-bottom", base);
|
||||
|
||||
projectIndex.mount("#app")
|
||||
projectIndex.mount("#app");
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
@ -18,46 +18,67 @@
|
||||
|
||||
<div class="boxbox">
|
||||
<div class="tab flexacenter">
|
||||
首页
|
||||
<a target="_blank" href="/">首页</a>
|
||||
<img class="img" src="/img/arrows.svg" />
|
||||
全部榜单
|
||||
<a target="_blank" href="/projectAllList">全部榜单</a>
|
||||
<img class="img" src="/img/arrows.svg" />
|
||||
<div class="current">QS世界综合排名(2025)</div>
|
||||
<div class="current">
|
||||
<template v-if="classify == 'school'">{{ rankingKeyObj[comText.jg] || comText.jg }}世界综合排名({{ comText.year }}年)</template>
|
||||
<template v-else> {{ rankingKeyObj[majText.jg] || majText.jg }}-{{ majText.major }}({{ majText.year }}) </template>
|
||||
</div>
|
||||
</div>
|
||||
<div class="content flexflex">
|
||||
<div class="content-left flex1">
|
||||
<div v-if="classify == 'school'" class="pitch-title">{{ rankingKeyObj[comText.jg] || comText.jg }}世界综合排名({{ comText.year }}年)</div>
|
||||
<div v-else class="major-pitch flexcenter">
|
||||
<span class="organ">QS</span>
|
||||
<img class="icon" src="/img/arrows-circle-green.svg" />
|
||||
世界综合排名(2025)
|
||||
</div>
|
||||
<div class="message flexacenter">
|
||||
<div class="total flexacenter">
|
||||
共
|
||||
<div class="sum">{{ comTotal }}</div>
|
||||
个排名
|
||||
<template v-if="classify == 'school'">
|
||||
<div class="pitch-title">{{ rankingKeyObj[comText.jg] || comText.jg }}世界综合排名({{ comText.year }}年)</div>
|
||||
<div class="message flexacenter">
|
||||
<div class="total flexacenter">
|
||||
共
|
||||
<div class="sum">{{ comTotal }}</div>
|
||||
个排名
|
||||
</div>
|
||||
<div class="only flexacenter" @click="cutOnlyXg">
|
||||
<img v-if="comOnly" class="icon" src="/img/u376.svg" />
|
||||
<img v-else class="icon" src="/img/frame-icon.svg" />
|
||||
仅显示香港学校
|
||||
</div>
|
||||
</div>
|
||||
<div class="only flexacenter" bind:tap="cutOnlyXg">
|
||||
<img v-if="comOnly" class="icon" src="/img/u376.svg" />
|
||||
<img v-else class="icon" src="/img/frame-icon.svg" />
|
||||
仅显示香港学校
|
||||
</template>
|
||||
<template v-else>
|
||||
<div class="major-pitch flexcenter">
|
||||
<span class="organ">{{ rankingKeyObj[majText.jg] || majText.jg }}</span>
|
||||
<img class="icon" src="/img/arrows-circle-green.svg" />
|
||||
{{ majText.major }}({{ majText.year }})
|
||||
</div>
|
||||
</div>
|
||||
<div class="message flexacenter">
|
||||
<div class="total flexacenter">
|
||||
共
|
||||
<div class="sum">{{ majTotal }}</div>
|
||||
个排名
|
||||
</div>
|
||||
<div class="only flexacenter" @click="majOnlyXg">
|
||||
<img v-if="majOnly" class="icon" src="/img/u376.svg" />
|
||||
<img v-else class="icon" src="/img/frame-icon.svg" />
|
||||
仅显示香港学校
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<div class="list">
|
||||
<div class="item flexflex" v-for="(item,index) in classify == 'school' ? comList : majList">
|
||||
<div class="num">{{ item.rank }}</div>
|
||||
<div class="info flex1">
|
||||
<div class="name">{{ item.name || item.subject }}</div>
|
||||
<div class="head flexflex">
|
||||
<div class="name">{{ item.name || item.subject }}</div>
|
||||
<div class="grade" v-if="item.total_score"><span class="sum">{{ item.total_score }}</span>分</div>
|
||||
</div>
|
||||
<div class="name-en">{{ item.enname }} {{ item.simple ? `(${ item.simple })` : ''}}</div>
|
||||
<div class="city">{{ item.city || '' }}</div>
|
||||
</div>
|
||||
<div class="right flexflex">
|
||||
<div class="grade" v-if="item.total_score"><span class="sum">{{ item.total_score }}</span>分</div>
|
||||
<a class="btn flexcenter" v-if="item.sid" target="_blank" :href="'/college/' + item.sid">
|
||||
学校主页
|
||||
<img class="icon" src="/img/arrows-circle.svg" />
|
||||
</a>
|
||||
<div class="bottom flexflex">
|
||||
<div class="city">{{ item.city || '' }}</div>
|
||||
<a class="btn flexcenter" v-if="item.sid" target="_blank" :href="'/college/' + item.sid">
|
||||
学校主页
|
||||
<img class="icon" src="/img/arrows-circle.svg" />
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@ -86,7 +107,7 @@
|
||||
评榜机构
|
||||
</div>
|
||||
<div class="list flexflex">
|
||||
<div class="item" :class="{'pitch': comChoose.jg == item}" v-for="(item,key) in comJgList" @click="selectComJg(item)">{{ item }}</div>
|
||||
<div class="item" :class="{'pitch': comChoose.jg == item}" v-for="(item,key) in comJgList" @click="selectComJg(item)">{{ rankingKeyObj[item] || item }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="screen-item">
|
||||
@ -113,10 +134,13 @@
|
||||
<div class="text one-line-display">{{ majChoose.major || '请选择' }}</div>
|
||||
<img class="icon" src="/img/arrows-black.svg" />
|
||||
</div>
|
||||
<div class="major-list" v-if="majorState">
|
||||
<div class="major-list flexflex" v-if="majorState">
|
||||
<div class="major-list-mask" @click="cutMajorState"></div>
|
||||
<div class="major-list-list">
|
||||
<div class="major-item" :class="{'pitch': item == majChoose.major}" v-for="(item, key) in majMajorList" @click="selectMajMajor(item)">{{ item }}</div>
|
||||
<div class="major-list-list" ref="majorList" @scroll="majorListScroll">
|
||||
<div class="major-item" :class="{'pitch': item == majChoose.major, }" :data-value="item.charAt(0).toLocaleUpperCase()" v-for="(item, key) in majMajorList" @click="selectMajMajor(item)">{{ item }}</div>
|
||||
</div>
|
||||
<div class="initial">
|
||||
<div class="item" :class="{'select': initialKey.includes(item)}" :data-value="item" v-for="item in initialList" @click="jumpToIndex(item)">{{ item }}</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@ -127,7 +151,7 @@
|
||||
评榜机构
|
||||
</div>
|
||||
<div class="list flexflex">
|
||||
<div class="item" :class="{'pitch': majChoose.jg == item}" v-for="(item,key) in majJgList" @click="selectMajJg(item)">{{ item }}</div>
|
||||
<div class="item" :class="{'pitch': majChoose.jg == item}" v-for="(item,key) in majJgList" @click="selectMajJg(item)">{{ rankingKeyObj[item] || item }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="screen-item">
|
||||
@ -156,17 +180,46 @@
|
||||
|
||||
onMounted(() => {
|
||||
window.addEventListener("scroll", handleScroll);
|
||||
const params = parseQueryString(location.search) || {};
|
||||
if (params.type == "school") {
|
||||
comDefault.value = {
|
||||
jg: params.mechanism,
|
||||
year: params.year,
|
||||
};
|
||||
classifySelect.value = classify.value = params.type;
|
||||
} else {
|
||||
majDefault.value = {
|
||||
major: params.subject,
|
||||
jg: params.system,
|
||||
year: params.year,
|
||||
};
|
||||
classifySelect.value = classify.value = params.type;
|
||||
}
|
||||
console.log(111, classifySelect.value);
|
||||
|
||||
getBaseData().then((data) => {
|
||||
const university = JSON.parse(JSON.stringify(data.university || {}));
|
||||
university.forEach((element) => {
|
||||
universityArr.push(element.value);
|
||||
});
|
||||
|
||||
getRankings();
|
||||
});
|
||||
});
|
||||
|
||||
const parseQueryString = (queryString) => {
|
||||
const params = {};
|
||||
const query = queryString.substring(1); // 去掉开头的问号
|
||||
if (!query) return params;
|
||||
const pairs = query.split("&");
|
||||
for (let i = 0; i < pairs.length; i++) {
|
||||
const pair = pairs[i].split("=");
|
||||
const key = decodeURIComponent(pair[0]);
|
||||
const value = pair[1] ? decodeURIComponent(pair[1]) : null;
|
||||
params[key] = value;
|
||||
}
|
||||
return params;
|
||||
};
|
||||
|
||||
let universityArr = [];
|
||||
|
||||
let comOption = ref({});
|
||||
@ -186,6 +239,7 @@
|
||||
|
||||
let majOption = ref({});
|
||||
let majDefault = ref({});
|
||||
let majText = ref({});
|
||||
let majChoose = ref({
|
||||
major: "",
|
||||
jg: "",
|
||||
@ -203,10 +257,9 @@
|
||||
$ajax("https://api.gter.net/v1/program/rankings", {}).then((res) => {
|
||||
if (res.code != 200) return;
|
||||
const data = res.data;
|
||||
console.log(11111, data);
|
||||
|
||||
const comprehensive = data.comprehensive;
|
||||
let com = JSON.parse(JSON.stringify(comChoose.value));
|
||||
let com = JSON.parse(JSON.stringify(comDefault.value));
|
||||
|
||||
for (const key in comprehensive) {
|
||||
let element = comprehensive[key];
|
||||
@ -227,7 +280,7 @@
|
||||
com["token"] = comprehensive[com.jg]?.[com.year] || "";
|
||||
|
||||
const discipline = data.discipline;
|
||||
let maj = JSON.parse(JSON.stringify(majChoose.value));
|
||||
let maj = JSON.parse(JSON.stringify(majDefault.value));
|
||||
const [dOrganizationKey, dOrganizationValue] = Object.entries(discipline)[0];
|
||||
if (!maj["jg"]) maj["jg"] = dOrganizationKey;
|
||||
if (!maj["major"]) maj["major"] = Object.entries(dOrganizationValue)[0][0];
|
||||
@ -253,6 +306,7 @@
|
||||
let majMajorList = ref([]);
|
||||
let majJgList = ref([]);
|
||||
let majYearList = ref([]);
|
||||
let initialList = ref([]);
|
||||
const initMaj = () => {
|
||||
const option = majOption.value;
|
||||
const allMajor = Object.values(option).flatMap((institutionData) => Object.keys(institutionData));
|
||||
@ -262,6 +316,14 @@
|
||||
return 0;
|
||||
});
|
||||
|
||||
// 用于记录每个首字母的数量
|
||||
let initial = [];
|
||||
// 为每个对象添加首字母标识并统计首字母数量
|
||||
majorList.forEach((item) => {
|
||||
initial.push(item.charAt(0).toLocaleUpperCase());
|
||||
});
|
||||
|
||||
initialList.value = [...new Set(initial)];
|
||||
const maj = majDefault.value;
|
||||
|
||||
// if (maj.jg) {
|
||||
@ -338,7 +400,12 @@
|
||||
// 获取 综合排名 数据
|
||||
const getSynthesizeData = () => {
|
||||
let comChooseObj = comChoose.value || {};
|
||||
|
||||
let comDefaultObj = comDefault.value || {};
|
||||
|
||||
console.log(comChooseObj["token"] || comDefaultObj["token"]);
|
||||
|
||||
// return
|
||||
$ajaxget("https://api.gter.net/v1/program/comprehensiverankings", {
|
||||
token: comChooseObj["token"] || comDefaultObj["token"],
|
||||
ishongkong: comOnly.value || 0,
|
||||
@ -361,9 +428,6 @@
|
||||
|
||||
if (comChooseObj["token"]) comText.value = JSON.parse(JSON.stringify(comChooseObj));
|
||||
else comText.value = JSON.parse(JSON.stringify(comDefaultObj));
|
||||
|
||||
comDefault.value = {};
|
||||
|
||||
classify.value = "school";
|
||||
});
|
||||
};
|
||||
@ -383,7 +447,10 @@
|
||||
const scrollHeight = document.documentElement.scrollHeight;
|
||||
const clientHeight = document.documentElement.clientHeight;
|
||||
const scrollTop = window.pageYOffset;
|
||||
if (scrollTop + clientHeight >= scrollHeight - 50) renderComprehensiveList();
|
||||
if (scrollTop + clientHeight >= scrollHeight - 50) {
|
||||
if (classify.value == "school") renderComprehensiveList();
|
||||
else renderDisciplineList();
|
||||
}
|
||||
};
|
||||
|
||||
const sortedYears = computed(() => {
|
||||
@ -411,7 +478,10 @@
|
||||
|
||||
let majorState = ref(false); // 专业选择状态
|
||||
// 切换专业选择状态
|
||||
const cutMajorState = () => (majorState.value = !majorState.value);
|
||||
const cutMajorState = () => {
|
||||
majorState.value = !majorState.value;
|
||||
if (!majorState.value) initialKey.value = ["A"];
|
||||
};
|
||||
|
||||
// 选择专业
|
||||
const selectMajMajor = (value) => {
|
||||
@ -467,9 +537,14 @@
|
||||
let text = "";
|
||||
if (!com.jg) text = "请选择机构";
|
||||
else if (!com.year) text = "请选择年份";
|
||||
console.log("text", text);
|
||||
|
||||
if (text) return;
|
||||
if (text) {
|
||||
creationAlertBox("error", text);
|
||||
return;
|
||||
}
|
||||
comChoose.value["token"] = option[com.jg][com.year];
|
||||
comDefault.value = {};
|
||||
getSynthesizeData();
|
||||
} else {
|
||||
const option = majOption.value;
|
||||
@ -478,10 +553,14 @@
|
||||
if (!maj.major) text = "请选择专业";
|
||||
else if (!maj.jg) text = "请选择机构";
|
||||
else if (!maj.year) text = "请选择年份";
|
||||
console.log("text", text);
|
||||
|
||||
if (text) return;
|
||||
|
||||
majChoose["token"] = option[maj.jg][maj.major][maj.year];
|
||||
if (text) {
|
||||
creationAlertBox("error", text);
|
||||
return;
|
||||
}
|
||||
majChoose.value["token"] = option[maj.jg][maj.major][maj.year];
|
||||
majDefault.value = {};
|
||||
getMajorData();
|
||||
}
|
||||
};
|
||||
@ -520,8 +599,8 @@
|
||||
majPage.value = 1;
|
||||
renderDisciplineList();
|
||||
|
||||
if (comChooseObj["token"]) comText.value = JSON.parse(JSON.stringify(comChooseObj));
|
||||
else comText.value = JSON.parse(JSON.stringify(comDefaultObj));
|
||||
if (majChooseObj["token"]) majText.value = JSON.parse(JSON.stringify(majChooseObj));
|
||||
else majText.value = JSON.parse(JSON.stringify(majDefaultObj));
|
||||
|
||||
classify.value = "subject";
|
||||
});
|
||||
@ -538,7 +617,46 @@
|
||||
majList.value = majList.value.concat(target);
|
||||
};
|
||||
|
||||
return { majList, majOnly, comOnly, comYearList, comJgList, haveChosen, selectMajYear, selectMajJg, majYearList, majJgList, majMajorList, selectMajMajor, majOption, majChoose, cutMajorState, majorState, selectComJg, selectComYear, sortedYears, classify, classifySelect, cutClassify, rankingKeyObj, comText, comChoose, comList, comTotal, comOption };
|
||||
const cutOnlyXg = () => {
|
||||
comOnly.value = comOnly.value ? 0 : 1;
|
||||
getSynthesizeData();
|
||||
};
|
||||
|
||||
const majOnlyXg = () => {
|
||||
majOnly.value = majOnly.value ? 0 : 1;
|
||||
getMajorData();
|
||||
};
|
||||
|
||||
const majorList = ref(null);
|
||||
|
||||
let initialKey = ref(["A"]);
|
||||
const majorListScroll = () => {
|
||||
const itemList = majorList.value.querySelectorAll(".major-item");
|
||||
let keyList = [];
|
||||
itemList.forEach((element) => {
|
||||
const isVisible = isElementVisibleInScrollContainer(element, majorList.value);
|
||||
if (isVisible) keyList.push(element.dataset.value);
|
||||
});
|
||||
initialKey.value = [...new Set(keyList)];
|
||||
};
|
||||
|
||||
const isElementVisibleInScrollContainer = (element, container) => {
|
||||
const elementRect = element.getBoundingClientRect();
|
||||
const containerRect = container.getBoundingClientRect();
|
||||
return elementRect.top >= containerRect.top && elementRect.bottom <= containerRect.bottom;
|
||||
};
|
||||
|
||||
const jumpToIndex = (value) => {
|
||||
const item = majorList.value.querySelector(`.major-item[data-value=${value}]`);
|
||||
3;
|
||||
const offsetTop = item.offsetTop - 64;
|
||||
majorList.value.scrollTo({
|
||||
top: offsetTop,
|
||||
behavior: "smooth",
|
||||
});
|
||||
};
|
||||
|
||||
return { jumpToIndex, initialKey, majorList, majorListScroll, initialList, majOnlyXg, cutOnlyXg, majTotal, majText, majList, majOnly, comOnly, comYearList, comJgList, haveChosen, selectMajYear, selectMajJg, majYearList, majJgList, majMajorList, selectMajMajor, majOption, majChoose, cutMajorState, majorState, selectComJg, selectComYear, sortedYears, classify, classifySelect, cutClassify, rankingKeyObj, comText, comChoose, comList, comTotal, comOption };
|
||||
},
|
||||
});
|
||||
projectIndex.mount("#app");
|
||||
|
Loading…
x
Reference in New Issue
Block a user