You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
209 lines
4.3 KiB
209 lines
4.3 KiB
2 years ago
|
<template>
|
||
|
<BlogHeader />
|
||
|
<div id="article-create">
|
||
|
<h3>发表文章</h3>
|
||
|
<form>
|
||
|
<div class="form-elem">
|
||
|
<span>标题:</span>
|
||
|
<input v-model="title" type="text" placeholder="输入标题" />
|
||
|
</div>
|
||
|
|
||
|
<div class="form-elem">
|
||
|
<span>分类:</span>
|
||
|
<span v-for="category in categories" :key="category.id">
|
||
|
<!--样式也可以通过 :style 绑定-->
|
||
|
<button
|
||
|
class="category-btn"
|
||
|
:style="categoryStyle(category)"
|
||
|
@click.prevent="chooseCategory(category)"
|
||
|
>
|
||
|
{{ category.title }}
|
||
|
</button>
|
||
|
</span>
|
||
|
</div>
|
||
|
|
||
|
<div class="form-elem">
|
||
|
<span>标签:</span>
|
||
|
<input
|
||
|
v-model="tags"
|
||
|
type="text"
|
||
|
placeholder="输入标签,用逗号分隔"
|
||
|
/>
|
||
|
</div>
|
||
|
|
||
|
<div class="form-elem">
|
||
|
<span>正文:</span>
|
||
|
<textarea
|
||
|
v-model="body"
|
||
|
placeholder="输入正文"
|
||
|
rows="20"
|
||
|
cols="80"
|
||
|
></textarea>
|
||
|
</div>
|
||
|
|
||
|
<div class="form-elem">
|
||
|
<button v-on:click.prevent="submit">提交</button>
|
||
|
</div>
|
||
|
</form>
|
||
|
</div>
|
||
|
<BlogFooter />
|
||
|
</template>
|
||
|
|
||
|
<script>
|
||
|
import BlogHeader from "@/components/BlogHeader.vue";
|
||
|
import BlogFooter from "@/components/BlogFooter.vue";
|
||
|
import authorization from "@/utils/authorization";
|
||
|
import $ from "jquery";
|
||
|
import { onMounted } from "@vue/runtime-core";
|
||
|
import { ref } from "vue";
|
||
|
export default {
|
||
|
name: "ArticleCreate",
|
||
|
components: { BlogHeader, BlogFooter },
|
||
|
data: function () {
|
||
|
return {
|
||
|
// 文章标题
|
||
|
title: "",
|
||
|
// 文章正文
|
||
|
body: "",
|
||
|
// 数据库中所有的分类
|
||
|
// categories: [],
|
||
|
// 选定的分类
|
||
|
selectedCategory: null,
|
||
|
// 标签
|
||
|
tags: "",
|
||
|
};
|
||
|
},
|
||
|
setup() {
|
||
|
let categories = ref([]);
|
||
|
|
||
|
onMounted(() => {
|
||
|
// 页面初始化时获取所有分类
|
||
|
$.ajax({
|
||
|
url: "http://127.0.0.1:6789/api/category",
|
||
|
type: "GET",
|
||
|
success(resp) {
|
||
|
categories.value = resp;
|
||
|
},
|
||
|
});
|
||
|
});
|
||
|
return {
|
||
|
categories,
|
||
|
};
|
||
|
},
|
||
|
methods: {
|
||
|
// 根据分类是否被选中,按钮的颜色发生变化
|
||
|
// 这里可以看出 css 也是可以被 vue 绑定的,很方便
|
||
|
categoryStyle(category) {
|
||
|
if (
|
||
|
this.selectedCategory !== null &&
|
||
|
category.id === this.selectedCategory.id
|
||
|
) {
|
||
|
return {
|
||
|
backgroundColor: "black",
|
||
|
};
|
||
|
}
|
||
|
return {
|
||
|
backgroundColor: "lightgrey",
|
||
|
color: "black",
|
||
|
};
|
||
|
},
|
||
|
// 选取分类的方法
|
||
|
chooseCategory(category) {
|
||
|
// 如果点击已选取的分类,则将 selectedCategory 置空
|
||
|
if (
|
||
|
this.selectedCategory !== null &&
|
||
|
this.selectedCategory.id === category.id
|
||
|
) {
|
||
|
this.selectedCategory = null;
|
||
|
}
|
||
|
// 如果没选中当前分类,则选中它
|
||
|
else {
|
||
|
this.selectedCategory = category;
|
||
|
}
|
||
|
},
|
||
|
// 点击提交按钮
|
||
|
submit() {
|
||
|
const that = this;
|
||
|
// 前面封装的验证函数又用上了
|
||
|
authorization().then(function (response) {
|
||
|
if (response[0]) {
|
||
|
// 需要传给后端的数据字典
|
||
|
let data = {
|
||
|
title: that.title,
|
||
|
body: that.body,
|
||
|
};
|
||
|
// 添加分类
|
||
|
if (that.selectedCategory) {
|
||
|
data.category_id = that.selectedCategory.id;
|
||
|
}
|
||
|
// 标签预处理
|
||
|
data.tags = that.tags
|
||
|
// 用逗号分隔标签
|
||
|
.split(/[,,]/)
|
||
|
// 剔除标签首尾空格
|
||
|
.map((x) => x.trim())
|
||
|
// 剔除长度为零的无效标签
|
||
|
.filter((x) => x.charAt(0) !== "");
|
||
|
|
||
|
// 将发表文章请求发送至接口
|
||
|
// 成功后前往详情页面
|
||
|
const token = localStorage.getItem("access_blog");
|
||
|
$.ajax({
|
||
|
url: "http://127.0.0.1:6789/api/article/",
|
||
|
type: "POST",
|
||
|
data: data,
|
||
|
headers: {
|
||
|
Authorization: "Bearer " + token,
|
||
|
},
|
||
|
success(resp) {
|
||
|
that.$router.push({
|
||
|
name: "detail",
|
||
|
params: { id: resp.id },
|
||
|
});
|
||
|
},
|
||
|
});
|
||
|
} else {
|
||
|
window.alert("令牌过期,请重新登录。");
|
||
|
}
|
||
|
});
|
||
|
},
|
||
|
},
|
||
|
};
|
||
|
</script>
|
||
|
|
||
|
<style scoped>
|
||
|
.category-btn {
|
||
|
margin-right: 10px;
|
||
|
}
|
||
|
#article-create {
|
||
|
text-align: center;
|
||
|
font-size: large;
|
||
|
}
|
||
|
form {
|
||
|
text-align: left;
|
||
|
padding-left: 100px;
|
||
|
padding-right: 10px;
|
||
|
padding-bottom: 100px;
|
||
|
}
|
||
|
.form-elem {
|
||
|
padding: 10px;
|
||
|
}
|
||
|
|
||
|
input {
|
||
|
height: 25px;
|
||
|
padding-left: 10px;
|
||
|
width: 50%;
|
||
|
}
|
||
|
button {
|
||
|
height: 35px;
|
||
|
cursor: pointer;
|
||
|
border: none;
|
||
|
outline: none;
|
||
|
margin: 0 auto;
|
||
|
background-color: steelblue;
|
||
|
color: whitesmoke;
|
||
|
border-radius: 5px;
|
||
|
width: 60px;
|
||
|
}
|
||
|
</style>
|