Browse Source

底部导航栏页面

master
Bobi 2 weeks ago
parent
commit
a3deaecb33
14 changed files with 1979 additions and 62 deletions
  1. +4
    -2
      components/novel/newWorkItem.vue
  2. +6
    -1
      components/novel/novelItem.vue
  3. +16
    -2
      components/novel/workItem.vue
  4. +18
    -0
      pages.json
  5. +160
    -0
      pages/chapter/index.vue
  6. +51
    -43
      pages/index/bookshelf.vue
  7. +6
    -3
      pages/index/center.vue
  8. +6
    -11
      pages/index/index.vue
  9. +137
    -0
      pages_order/novel/Allannouncements.vue
  10. +131
    -0
      pages_order/novel/announcement.vue
  11. +190
    -0
      pages_order/novel/chapterList.vue
  12. +344
    -0
      pages_order/novel/createNovel.vue
  13. +748
    -0
      pages_order/novel/novelDetail.vue
  14. +162
    -0
      pages_order/novel/vote.vue

+ 4
- 2
components/novel/newWorkItem.vue View File

@ -1,7 +1,7 @@
<template>
<view class="newWork">
<!-- 新建作品组件 -->
<view class="new-work-item" @click="handleClick"">
<view class="new-work-item" @click="handleClick">
<view class="plus-icon">+</view>
<text class="text">新建作品</text>
</view>
@ -19,7 +19,9 @@
},
methods: {
handleClick() {
this.$emit('click');
uni.navigateTo({
url: '/pages_order/novel/createNovel'
})
},
handleSettingClick() {
this.$emit('settings');


+ 6
- 1
components/novel/novelItem.vue View File

@ -1,5 +1,5 @@
<template>
<view class="book-item" :class="{'horizontal': horizontal}">
<view class="book-item" :class="{'horizontal': horizontal}" @click="goToNovelDetail">
<image class="book-cover" src="https://bookcover.yuewen.com/qdbimg/349573/1033014772/150.webp" mode="aspectFill"></image>
<view class="book-info">
<view class="book-title">{{book.title}}</view>
@ -50,6 +50,11 @@
return {}
},
methods: {
goToNovelDetail() {
uni.navigateTo({
url: `/pages_order/novel/novelDetail?id=${this.book.id}`
});
}
}
}
</script>


+ 16
- 2
components/novel/workItem.vue View File

@ -26,6 +26,8 @@
</view>
<!-- 添加右箭头图标 -->
<text class="iconfont icon-arrow">&#xe65f;</text>
</view>
</template>
@ -68,7 +70,14 @@
},
methods: {
handleClick() {
this.$emit('click');
if (this.isManaging) {
this.$emit('click');
return;
}
//
uni.navigateTo({
url: '/pages_order/novel/chapterList'
});
},
handleDelete() {
this.$emit('delete');
@ -84,6 +93,7 @@
padding: 24rpx 0;
border-bottom: 1rpx solid #f0f0f0;
position: relative;
align-items: center;
.cover-wrapper {
position: relative;
@ -182,6 +192,10 @@
}
}
.icon-arrow {
color: #999;
font-size: 16px;
margin-left: 10rpx;
}
}
</style>

+ 18
- 0
pages.json View File

@ -51,6 +51,24 @@
},
{
"path": "mine/help"
},
{
"path": "novel/novelDetail"
},
{
"path": "novel/vote"
},
{
"path": "novel/announcement"
},
{
"path": "novel/Allannouncements"
},
{
"path": "novel/createNovel"
},
{
"path": "novel/chapterList"
}
]
}],


+ 160
- 0
pages/chapter/index.vue View File

@ -0,0 +1,160 @@
<template>
<view class="chapter-container">
<view class="header">
<view class="nav-bar">
<view class="back" @click="goBack">
<text class="iconfont icon-back">&#xe60e;</text>
</view>
<view class="tabs">
<view class="tab active">草稿箱</view>
<view class="tab">已发布</view>
</view>
<view class="more">
<text class="iconfont">&#xe612;</text>
</view>
</view>
</view>
<view class="chapter-list">
<view class="chapter-item" v-for="(chapter, index) in chapters" :key="index">
<view class="chapter-info">
<text class="chapter-title">章节名</text>
<text class="chapter-number">{{index + 1}}</text>
</view>
<text class="iconfont icon-arrow">&#xe65f;</text>
</view>
</view>
<view class="bottom-actions">
<button class="btn-settings">设置作品</button>
<button class="btn-new" @click="addNewChapter">新建章节</button>
</view>
</view>
</template>
<script>
export default {
data() {
return {
chapters: Array(8).fill({}) // 8
}
},
methods: {
goBack() {
uni.navigateBack()
},
addNewChapter() {
//
uni.showToast({
title: '新建章节',
icon: 'none'
})
}
}
}
</script>
<style lang="scss" scoped>
.chapter-container {
min-height: 100vh;
background-color: #fff;
.header {
background: #fff;
padding-top: var(--status-bar-height);
.nav-bar {
height: 44px;
display: flex;
align-items: center;
justify-content: space-between;
padding: 0 15px;
.back {
padding: 5px;
.icon-back {
font-size: 20px;
}
}
.tabs {
display: flex;
.tab {
padding: 0 15px;
font-size: 16px;
color: #666;
&.active {
color: #000;
font-weight: bold;
}
}
}
.more {
padding: 5px;
}
}
}
.chapter-list {
padding: 0 15px;
.chapter-item {
display: flex;
justify-content: space-between;
align-items: center;
padding: 15px 0;
border-bottom: 1px solid #eee;
.chapter-info {
.chapter-title {
font-size: 14px;
color: #999;
margin-bottom: 5px;
}
.chapter-number {
font-size: 16px;
color: #333;
}
}
.icon-arrow {
color: #999;
font-size: 16px;
}
}
}
.bottom-actions {
position: fixed;
bottom: 0;
left: 0;
right: 0;
display: flex;
padding: 10px 15px;
background: #fff;
box-shadow: 0 -2px 6px rgba(0,0,0,0.05);
button {
flex: 1;
height: 40px;
border-radius: 20px;
font-size: 16px;
margin: 0 5px;
&.btn-settings {
background: #fff;
border: 1px solid #ddd;
color: #333;
}
&.btn-new {
background: #2b4acb;
color: #fff;
border: none;
}
}
}
}
</style>

+ 51
- 43
pages/index/bookshelf.vue View File

@ -261,42 +261,7 @@
}
],
//
worksList: [
{
id: '1',
title: '兽王进化:从被小萝莉召唤开始',
cover: 'https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain',
readers: '8721',
status: 'ongoing',
publishStatus: '发布审核中',
isOriginal: true
},
{
id: '2',
title: '魔法少女纯爷们',
cover: 'https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain',
readers: '8721',
status: 'ongoing',
publishStatus: '存稿设置审核中'
},
{
id: '3',
title: '我是一条小青龙',
cover: 'https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain',
readers: '8721',
status: 'ongoing',
publishStatus: '发布审核通过'
},
{
id: '4',
title: '女帝:别闹,朕怀孕了!',
cover: 'https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain',
readers: '8721',
status: 'draft',
publishStatus: '',
isOriginal: true
}
]
worksList: [] //
}
},
onLoad() {
@ -304,19 +269,60 @@
const systemInfo = uni.getSystemInfoSync();
this.statusBarHeight = systemInfo.statusBarHeight;
//
//
const savedWorks = uni.getStorageSync('worksList') || []
this.worksList = savedWorks
//
const activeTab = uni.getStorageSync('activeBookshelfTab')
if (activeTab === 'work') {
this.activeTab = 'work'
uni.removeStorageSync('activeBookshelfTab')
}
//
uni.$on('switchToWork', () => {
this.activeTab = 'work'
})
// #ifdef MP-WEIXIN || MP-QQ || MP-TOUTIAO
const menuButtonInfo = uni.getMenuButtonBoundingClientRect();
// = +
const navBarHeight = (menuButtonInfo.top - systemInfo.statusBarHeight) * 2 + menuButtonInfo.height + systemInfo.statusBarHeight;
this.navBarHeight = navBarHeight;
// #endif
},
onShow() {
//
this.isEditMode = false;
this.selectedItems = [];
//
const submittedWork = getApp().globalData.submittedWork
if (submittedWork) {
//
this.worksList.unshift(submittedWork)
//
uni.setStorageSync('worksList', this.worksList)
//
getApp().globalData.submittedWork = null
//
this.activeTab = 'work'
//
if (getApp().globalData.showSubmitSuccess) {
//
getApp().globalData.showSubmitSuccess = false
//
uni.showToast({
title: '提交成功,等待审核',
icon: 'none',
duration: 2000
})
}
}
this.isEditMode = false
this.selectedItems = []
},
onUnload() {
//
uni.$off('switchToWork')
},
methods: {
//
@ -344,7 +350,7 @@
//
createNewWork() {
uni.navigateTo({
url: '/pages/work/create'
url: '/pages_order/novel/createNovel'
})
},
@ -428,6 +434,8 @@
} else {
//
this.worksList = this.worksList.filter(work => !this.selectedItems.includes(work.id));
//
uni.setStorageSync('worksList', this.worksList)
uni.showToast({
title: '删除成功',
icon: 'success'


+ 6
- 3
pages/index/center.vue View File

@ -18,7 +18,7 @@
<!-- 图片区域 -->
<view class="section">
<view class="section-title">图片</view>
<view class="section-title">账户</view>
<view class="section-list">
<view class="section-item" @click="navigateTo('/pages/wallet')">
<view class="section-item-left">
@ -73,8 +73,9 @@
</view>
<view class="section-item" @click="navigateTo('/pages/customer-service')">
<view class="section-item-left">
<uv-icon name="star" size="40rpx" color="#333"></uv-icon>
<text>联系客服</text>
</view>
<uv-icon name="arrow-right" size="36rpx" color="#999"></uv-icon>
</view>
@ -87,7 +88,7 @@
</view>
<view class="section-item" @click="logout">
<view class="section-item-left">
<uv-icon name="star" size="40rpx" color="#333"></uv-icon>
<text>退出登录</text>
</view>
<uv-icon name="arrow-right" size="36rpx" color="#999"></uv-icon>
@ -146,12 +147,14 @@
padding: 20rpx 30rpx;
.user-info {
height: 270rpx;
display: flex;
align-items: center;
padding: 30rpx 20rpx;
background-color: #fff;
border-radius: 20rpx;
margin-bottom: 20rpx;
background: linear-gradient(to right, purple, pink);
.avatar {
width: 120rpx;


+ 6
- 11
pages/index/index.vue View File

@ -59,7 +59,7 @@
</view>
</view>
<view class="notice-center">
<view class="notice-text">
<view class="notice-text" @click="viewNotice">
2025年2月平台福利活动截稿作品公示
</view>
</view>
@ -78,7 +78,7 @@
<scroll-view scroll-x style="width: 100%;">
<view class="recommend-list">
<view class="recommend-item"
@click="navigateToDetail"
@click="navigateToDetail(item.id)"
v-for="(item, index) in novelList" :key="index">
<novel-item horizontal :key="index" :book="item" />
</view>
@ -95,7 +95,7 @@
</view>
<view class="novel-list">
<novel-item v-for="(item, index) in novelList"
@click="navigateToDetail"
@click="navigateToDetail(item.id)"
:key="index" :book="item" />
</view>
</view>
@ -212,16 +212,11 @@
this.$utils.navigateTo(`/pages_order/book/bookDetail?id=${banner.id}`)
}, 500)
},
//
//
viewNotice() {
uni.showToast({
title: '查看通知: 2025年2月平台福利活动截稿作品公示',
icon: 'none'
uni.navigateTo({
url: '/pages_order/novel/Allannouncements'
})
//
setTimeout(() => {
this.$utils.navigateTo('/pages/notice/detail?id=1')
}, 500)
},
navigateToDetail(id) {
//


+ 137
- 0
pages_order/novel/Allannouncements.vue View File

@ -0,0 +1,137 @@
<template>
<view class="announcements-container">
<uv-navbar
title="全部公告"
:autoBack="true"
fixed
placeholder
titleStyle="color: #333; font-weight: 500;"
:border="false"
></uv-navbar>
<view class="announcements-list">
<view
class="announcement-item"
v-for="(item, index) in announcements"
:key="index"
@click="viewAnnouncement(item)"
>
<view class="item-left">
<text class="tag">通讯</text>
<text class="title">{{ item.title }}</text>
</view>
<view class="item-right">
<uv-icon name="arrow-right" color="#C8C8C8" size="28rpx"></uv-icon>
</view>
</view>
</view>
</view>
</template>
<script>
export default {
components: {
'uv-navbar': () => import('@/uni_modules/uv-navbar/components/uv-navbar/uv-navbar.vue')
},
data() {
return {
announcements: [
{
id: 1,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
},
{
id: 2,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
},
{
id: 3,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
},
{
id: 4,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
},
{
id: 5,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
},
{
id: 6,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
},
{
id: 7,
title: '2025年2月平台福利活动拟获奖作品公示',
type: '通讯'
}
]
}
},
methods: {
viewAnnouncement(item) {
uni.navigateTo({
url: `/pages_order/novel/announcement?id=${item.id}`
})
}
}
}
</script>
<style lang="scss">
.announcements-container {
min-height: 100vh;
background-color: #F8F8F8;
.announcements-list {
padding: 20rpx;
.announcement-item {
display: flex;
justify-content: space-between;
align-items: center;
background-color: #FFFFFF;
padding: 30rpx;
margin-bottom: 20rpx;
border-radius: 12rpx;
.item-left {
flex: 1;
margin-right: 20rpx;
.tag {
display: inline-block;
font-size: 24rpx;
color: #666666;
background-color: #F5F5F5;
padding: 4rpx 12rpx;
border-radius: 6rpx;
margin-bottom: 16rpx;
}
.title {
display: block;
font-size: 28rpx;
color: #333333;
line-height: 1.4;
}
}
.item-right {
display: flex;
align-items: center;
}
&:active {
background-color: #F9F9F9;
}
}
}
}
</style>

+ 131
- 0
pages_order/novel/announcement.vue View File

@ -0,0 +1,131 @@
<template>
<view class="announcement-container">
<uv-navbar
title="公告详情"
:autoBack="true"
fixed
placeholder
titleStyle="color: #333; font-weight: 500;"
:border="false"
></uv-navbar>
<view class="header">
<text class="title">2025年2月平台福利活动拟获奖作品公示</text>
<text class="date">岁序更替华章日新2025平台福利内容建设的实施进展载誉前行我们秉持"精品为本,重磅发布"的理念现面向全体作者重磅发布2025年度长篇网文作家福利上线主新潮当中文网作家专属福利全年奖半年奖季度奖月度奖总计奖金超过百万元现将2025年2月平台各项福利活动拟获奖作品公示如下</text>
</view>
<view class="award-section">
<view class="award-item">
<text class="award-title">长篇网文</text>
<view class="award-content">
<view class="sub-award">
<text class="sub-title"> 优质加更奖</text>
<text class="detail">拟获奖作品156本共发放奖金41.5万元查看拟获奖名单请点击</text>
<text class="link">优质加更奖拟获奖名单</text>
</view>
<view class="sub-award">
<text class="sub-title"> 新书扶更奖</text>
<text class="detail">拟获奖作品5574本共发放奖金20万元查看拟获奖名单请点击</text>
<text class="link">新书扶更奖拟获奖名单</text>
</view>
<view class="sub-award">
<text class="sub-title"> 拉新激励奖</text>
<text class="detail">拟获奖作品50部总计奖金65万查看拟获奖名单请点击</text>
<text class="link">2月拉新激励奖</text>
</view>
<view class="sub-award">
<text class="sub-title"> 星火计划奖励</text>
<text class="detail">拟获奖作品4178部总计奖金55万查看拟获奖名单请点击</text>
<text class="link">2月星火计划奖励名单</text>
</view>
</view>
</view>
<view class="award-item">
<text class="award-title">完结专场</text>
<view class="award-content">
<view class="sub-award">
<text class="sub-title"> 脱洞盛宴征文活动</text>
<text class="detail">月度脱洞专题拟获奖作品1260部总计奖金45万查看拟获奖名单请点击</text>
<text class="link">2月完结专题奖励名单</text>
</view>
</view>
</view>
</view>
</view>
</template>
<script>
export default {
components: {
'uv-navbar': () => import('@/uni_modules/uv-navbar/components/uv-navbar/uv-navbar.vue')
},
data() {
return {}
},
methods: {
//
}
}
</script>
<style lang="scss">
.announcement-container {
padding: 30rpx;
background: #fff;
.header {
margin-bottom: 40rpx;
.title {
font-size: 36rpx;
font-weight: bold;
color: #333;
margin-bottom: 20rpx;
display: block;
}
.date {
font-size: 28rpx;
color: #666;
line-height: 1.6;
}
}
.award-section {
.award-item {
margin-bottom: 40rpx;
.award-title {
font-size: 32rpx;
font-weight: bold;
color: #333;
margin-bottom: 20rpx;
display: block;
}
.award-content {
.sub-award {
margin-bottom: 20rpx;
.sub-title {
font-size: 28rpx;
color: #333;
font-weight: 500;
}
.detail {
font-size: 28rpx;
color: #666;
}
.link {
color: #007AFF;
text-decoration: underline;
font-size: 28rpx;
}
}
}
}
}
}
</style>

+ 190
- 0
pages_order/novel/chapterList.vue View File

@ -0,0 +1,190 @@
<template>
<view class="chapter-container">
<view class="header">
<view class="nav-bar">
<view class="back" @click="goBack">
<text class="iconfont icon-back">&#xe60e;</text>
</view>
<view class="tabs">
<view class="tab" :class="{ active: activeTab === 'draft' }" @click="switchTab('draft')">草稿箱</view>
<view class="tab" :class="{ active: activeTab === 'published' }" @click="switchTab('published')">已发布</view>
</view>
<view class="more">
<text class="iconfont">&#xe612;</text>
</view>
</view>
</view>
<view class="chapter-list">
<view class="chapter-item" v-for="(chapter, index) in chapters" :key="index" @click="editChapter(chapter)">
<view class="chapter-info">
<text class="chapter-title">章节名</text>
<text class="chapter-number">{{index + 1}}</text>
</view>
<text class="iconfont icon-arrow">&#xe65f;</text>
</view>
</view>
<view class="bottom-actions">
<button class="btn-settings" @click="handleSettings">设置作品</button>
<button class="btn-new" @click="addNewChapter">新建章节</button>
</view>
</view>
</template>
<script>
export default {
data() {
return {
activeTab: 'draft',
chapters: Array(8).fill({}) // 8
}
},
methods: {
goBack() {
uni.navigateBack()
},
switchTab(tab) {
this.activeTab = tab
// tab
},
addNewChapter() {
uni.navigateTo({
url: '/pages_order/author/editor'
})
},
editChapter(chapter) {
uni.navigateTo({
url: '/pages_order/author/editor?id=' + chapter.id
})
},
handleSettings() {
uni.navigateTo({
url: '/pages_order/novel/createNovel?type=edit'
})
}
}
}
</script>
<style lang="scss" scoped>
.chapter-container {
min-height: 100vh;
background-color: #fff;
padding-bottom: 70px;
.header {
background: #fff;
padding-top: var(--status-bar-height);
.nav-bar {
height: 44px;
display: flex;
align-items: center;
justify-content: space-between;
padding: 0 15px;
.back {
padding: 5px;
.icon-back {
font-size: 20px;
}
}
.tabs {
display: flex;
.tab {
padding: 0 15px;
font-size: 16px;
color: #666;
position: relative;
&.active {
color: #000;
font-weight: bold;
&::after {
content: '';
position: absolute;
bottom: -4px;
left: 50%;
transform: translateX(-50%);
width: 20px;
height: 2px;
background: #2b4acb;
border-radius: 1px;
}
}
}
}
.more {
padding: 5px;
}
}
}
.chapter-list {
padding: 0 15px;
.chapter-item {
display: flex;
justify-content: space-between;
align-items: center;
padding: 15px 0;
border-bottom: 1px solid #eee;
.chapter-info {
.chapter-title {
font-size: 14px;
color: #999;
margin-bottom: 5px;
display: block;
}
.chapter-number {
font-size: 16px;
color: #333;
display: block;
}
}
.icon-arrow {
color: #999;
font-size: 16px;
}
}
}
.bottom-actions {
position: fixed;
bottom: 0;
left: 0;
right: 0;
display: flex;
padding: 10px 15px;
background: #fff;
box-shadow: 0 -2px 6px rgba(0,0,0,0.05);
button {
flex: 1;
height: 40px;
border-radius: 20px;
font-size: 16px;
margin: 0 5px;
&.btn-settings {
background: #fff;
border: 1px solid #ddd;
color: #333;
}
&.btn-new {
background: #2b4acb;
color: #fff;
border: none;
}
}
}
}
</style>

+ 344
- 0
pages_order/novel/createNovel.vue View File

@ -0,0 +1,344 @@
<template>
<!-- 新建作品页面 -->
<view class="create-novel">
<uv-navbar
title="新建作品"
:autoBack="true"
fixed
placeholder
titleStyle="color: #333; font-weight: 500;"
:border="false"
></uv-navbar>
<view class="form-container">
<!-- 封面信息 -->
<view class="section">
<view class="section-title">封面信息</view>
<view class="upload-cover">
<view class="sub-title">上传封面</view>
<view class="cover-box" @click="chooseCover">
<image v-if="formData.cover" :src="formData.cover" mode="aspectFill" class="cover-image"></image>
<view v-else class="upload-placeholder">
<text class="plus">+</text>
</view>
</view>
</view>
</view>
<!-- 作品信息 -->
<view class="section">
<view class="section-title">作品信息</view>
<view class="form-item">
<text class="required">*</text>
<text class="label">作品名称</text>
<input
type="text"
v-model="formData.title"
placeholder="请输入"
placeholder-class="input-placeholder"
/>
</view>
<view class="form-item">
<text class="required">*</text>
<text class="label">作品类型</text>
<input
type="text"
v-model="formData.type"
placeholder="请输入"
placeholder-class="input-placeholder"
/>
</view>
<view class="form-item">
<text class="required">*</text>
<text class="label">作品简介</text>
<textarea
v-model="formData.description"
placeholder="请输入"
placeholder-class="input-placeholder"
:maxlength="500"
></textarea>
</view>
<view class="form-item">
<text class="required">*</text>
<text class="label">作品状态</text>
<view class="status-options">
<view
class="status-item"
:class="{ active: formData.status === 'serial' }"
@click="formData.status = 'serial'"
>
<view class="radio-dot" :class="{ checked: formData.status === 'serial' }"></view>
<text>连载</text>
</view>
<view
class="status-item"
:class="{ active: formData.status === 'completed' }"
@click="formData.status = 'completed'"
>
<view class="radio-dot" :class="{ checked: formData.status === 'completed' }"></view>
<text>完结</text>
</view>
</view>
</view>
</view>
<!-- 书籍信息 -->
<view class="section">
<view class="section-title">书籍信息</view>
<view class="form-item">
<text class="label">书号</text>
<text class="value">9999993339393</text>
</view>
<view class="form-item">
<text class="label">总字数</text>
<text class="value">99999999</text>
</view>
</view>
<!-- 提交按钮 -->
<view class="submit-btn" @click="submitForm">提交申请</view>
</view>
</view>
</template>
<script>
export default {
components: {
'uv-navbar': () => import('@/uni_modules/uv-navbar/components/uv-navbar/uv-navbar.vue')
},
data() {
return {
formData: {
cover: '',
title: '',
type: '',
description: '',
status: 'serial' //
}
}
},
methods: {
//
chooseCover() {
uni.chooseImage({
count: 1,
success: (res) => {
this.formData.cover = res.tempFilePaths[0]
}
})
},
//
submitForm() {
if (!this.formData.title) {
uni.showToast({
title: '请输入作品名称',
icon: 'none'
})
return
}
if (!this.formData.type) {
uni.showToast({
title: '请输入作品类型',
icon: 'none'
})
return
}
if (!this.formData.description) {
uni.showToast({
title: '请输入作品简介',
icon: 'none'
})
return
}
//
const workData = {
id: Date.now().toString(),
title: this.formData.title,
cover: this.formData.cover || 'https://bookcover.yuewen.com/qdbimg/349573/1033014772/150.webp',
readers: '8721',
status: 'ongoing',
publishStatus: '发布审核中',
isOriginal: true
}
//
getApp().globalData.submittedWork = workData
//
getApp().globalData.showSubmitSuccess = true
//
setTimeout(() => {
//
uni.setStorageSync('activeBookshelfTab', 'work')
//
uni.navigateBack({
delta: 1
})
}, 500)
}
}
}
</script>
<style lang="scss">
.create-novel {
min-height: 100vh;
background-color: #F8F8F8;
.form-container {
padding: 20rpx;
.section {
background-color: #FFFFFF;
border-radius: 12rpx;
padding: 30rpx;
margin-bottom: 20rpx;
.section-title {
font-size: 32rpx;
font-weight: bold;
color: #333;
margin-bottom: 30rpx;
}
.upload-cover {
.sub-title {
font-size: 28rpx;
color: #666;
margin-bottom: 20rpx;
}
.cover-box {
width: 200rpx;
height: 266rpx;
background-color: #F5F5F5;
border-radius: 8rpx;
display: flex;
align-items: center;
justify-content: center;
overflow: hidden;
.cover-image {
width: 100%;
height: 100%;
}
.upload-placeholder {
.plus {
font-size: 60rpx;
color: #999;
}
}
}
}
.form-item {
margin-bottom: 30rpx;
position: relative;
&:last-child {
margin-bottom: 0;
}
.required {
color: #FF0000;
margin-right: 4rpx;
}
.label {
font-size: 28rpx;
color: #333;
margin-bottom: 16rpx;
display: block;
}
input, textarea {
width: 100%;
height: 80rpx;
background-color: #F5F5F5;
border-radius: 8rpx;
padding: 20rpx;
font-size: 28rpx;
color: #333;
box-sizing: border-box;
position: relative;
z-index: 1;
}
textarea {
height: 200rpx;
}
.input-placeholder {
color: #999;
}
.status-options {
display: flex;
gap: 40rpx;
.status-item {
display: flex;
align-items: center;
gap: 10rpx;
.radio-dot {
width: 32rpx;
height: 32rpx;
border: 2rpx solid #999;
border-radius: 50%;
position: relative;
&.checked {
border-color: #001351;
&::after {
content: '';
position: absolute;
width: 20rpx;
height: 20rpx;
background-color: #001351;
border-radius: 50%;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
}
}
}
text {
font-size: 28rpx;
color: #333;
}
}
}
.value {
font-size: 28rpx;
color: #999;
}
}
}
.submit-btn {
background-color: #001351;
color: #FFFFFF;
font-size: 32rpx;
text-align: center;
padding: 24rpx 0;
border-radius: 12rpx;
margin-top: 40rpx;
&:active {
opacity: 0.9;
}
}
}
}
</style>

+ 748
- 0
pages_order/novel/novelDetail.vue View File

@ -0,0 +1,748 @@
<template>
<!-- 小说详情页面 -->
<view class="novel-detail">
<!-- 顶部返回导航 -->
<navber></navber>
<!-- 小说基本信息 -->
<view class="novel-info">
<view class="novel-cover">
<image :src="novelData.coverUrl" mode="aspectFill"></image>
</view>
<view class="novel-basic">
<text class="title">{{ novelData.title }}</text>
<view class="author-line">
<text class="label">作者</text>
<text class="author">{{ novelData.author }}</text>
</view>
<view class="status-line">
<text class="label">完结</text>
<text class="status">{{ novelData.status }}</text>
</view>
<view class="score-line">
<text class="score">{{ novelData.score || 2814}}</text>
<text class="score-label">作者累计亲密度值</text>
</view>
</view>
</view>
<!-- 推荐票数显示 -->
<view class="recommendation-section">
<view class="rec-left">
<text class="rec-count">2814</text>
<text class="rec-label">推荐票数</text>
</view>
<view class="rec-divider"></view>
<view class="rec-right">
<button class="recommend-btn" @click="recommendNovel">
<text class="btn-icon">📑</text>
投推荐票
</button>
</view>
</view>
<!-- 阅读和收藏按钮 -->
<!-- 我的等级 -->
<view class="user-level">
<view class="level-left">
<view class="level-title">
<text class="title-icon">👑</text>
<text>我的等级</text>
</view>
<view class="level-info">
<image class="user-avatar" src="https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain" mode="aspectFill"></image>
<view class="user-details">
<text class="username">周海</text>
<view class="user-score">
<text class="score-value">6785452</text>
<text class="score-label">亲密值</text>
</view>
<text class="user-role">护书使者 五级</text>
</view>
</view>
</view>
<view class="level-right">
<view class="rank-btn">
<image class="rank-icon" src="https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain" mode="aspectFit"></image>
<text>读者榜单</text>
<text class="check-text">点击查看</text>
</view>
</view>
</view>
<!-- 小说简介 -->
<view class="novel-intro">
<view class="intro-title">
<text>简介</text>
</view>
<view class="intro-content">
<text>这游戏也太真实了吧</text>
<text>搬砖跑腿捡垃圾送快递......公司最多能让你体会到996的艰辛在这里你能体会到超级加倍的007</text>
<text>好了不废话了伟大的管理者大人嘛就去搬砖了那位大人说了只要我们努力献上自己的肝下个月他又能换一套全新的动力甲到时候候带我们开全新的地图去广阔的废土捡更多的垃圾</text>
<text>穿越到废土世界的基光发现自己解锁了游戏所系统能够从平行世界召唤名为"玩家"的生物</text>
</view>
</view>
<!-- 目录 -->
<view class="novel-catalog">
<view class="catalog-header">
<view class="catalog-title">
<text class="title-icon">📖</text>
<text>目录</text>
</view>
<view class="chapter-nav">
<text class="current-chapter">第九集 - 高去与归来</text>
<text class="nav-arrow">></text>
</view>
</view>
</view>
<!-- 书评区域 -->
<view class="comments-section">
<view class="comments-header">
<view class="header-left">
<text class="title-icon">📝</text>
<text>书评</text>
</view>
<view class="header-right">
<text @click="goToWriteReview">写书评</text>
</view>
</view>
<view class="comment-list">
<view class="comment-item">
<view class="comment-header">
<image class="avatar" src="https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain" mode="aspectFill"></image>
<text class="username">方香橙</text>
</view>
<view class="comment-body">
<text class="content-text">我是本书的作者方香橙这是一本甜文爽文哒请放心入坑五星好评女主又美有个性可爱绝对不圣母不傻白男主身心干净深情独宠媳妇儿一个人...</text>
<view class="comment-footer">
<text class="comment-time">2024.07.09</text>
<view class="comment-likes">
<text class="like-icon">💬</text>
<text class="like-count">17</text>
</view>
</view>
</view>
</view>
<view class="comment-item">
<view class="comment-header">
<image class="avatar" src="https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain" mode="aspectFill"></image>
<text class="username">战斗世界</text>
</view>
<view class="comment-body">
<text class="content-text">这本小说了创意了雄天霸业奇新颖深刻以白色能量为主...</text>
</view>
</view>
</view>
</view>
<!-- 底部操作栏 -->
<view class="novel-bottom">
<view class="bottom-left">
<view class="action-btn" @click="addToBookshelf">
<text class="btn-icon">📚</text>
<text>加入书架</text>
</view>
<view class="action-btn" @click="toggleInteractive">
<text class="btn-icon">🎯</text>
<text>互动打赏</text>
</view>
</view>
<view class="bottom-right">
<button class="read-now-btn" @click="startReading">立即阅读</button>
</view>
</view>
</view>
</template>
<script>
export default {
data() {
return {
novelData: {
id: '1',
title: '这游戏也太真实了',
author: '大宝鉴在在',
category: '玄幻',
wordCount: '2814',
coverUrl: 'https://tse4-mm.cn.bing.net/th/id/OIP-C.iUyxJ_fxLjjX3kEBjteXWwAAAA?rs=1&pid=ImgDetMain',
introduction: '这游戏也太真实了!\n模拟,模拟,模拟,这游戏……公空居然把自己做成了游戏的NPC?这是什么新型的套路啊!好了,不要慌了,作为的管理者人员都在忙碌着,都在工作人员中,只要我们努力就自己的事,下个月他又给一套全新的剧情开始,如何将模拟的开关全新的世界,去广阔的世界去探索吧!'
},
userInfo: {
avatar: '/static/images/avatar.jpg',
level: '67级达人'
},
isCollected: false,
chapterCount: 2814,
comments: [
{
username: '方寒锋',
avatar: '/static/images/user1.jpg',
content: '我是全书中年龄最大的人,这是一本很好的文章!满满心头热,只要对你"安全"文案有兴趣的,都可以不虚,不害怕,不要想太多就去尝试阅读吧!',
time: '2024-07-09'
}
]
}
},
methods: {
goBack() {
uni.navigateBack()
},
startReading() {
uni.navigateTo({
url: '/pages/reader/reader'
})
},
toggleCollect() {
this.isCollected = !this.isCollected
// TODO:
},
recommendNovel() {
if (!this.novelData.id) {
uni.showToast({
title: '无效的小说ID',
icon: 'none'
})
return
}
uni.navigateTo({
url: `/pages_order/novel/vote?id=${this.novelData.id}`
})
},
goToWriteReview() {
// TODO:
},
addToBookshelf() {
// TODO:
uni.showToast({
title: '已加入书架',
icon: 'success'
})
},
toggleInteractive() {
// TODO:
uni.showToast({
title: '打赏功能开发中',
icon: 'none'
})
}
}
}
</script>
<style lang="scss" scoped>
.novel-detail {
min-height: 100vh;
background-color: #f5f5f5;
padding-bottom: 30rpx;
}
.nav-header {
display: flex;
justify-content: space-between;
align-items: center;
padding: 20rpx 30rpx;
background-color: transparent;
position: fixed;
top: 0;
left: 0;
right: 0;
z-index: 100;
}
.novel-info {
padding: 20rpx;
display: flex;
background: #fff;
}
.novel-cover {
width: 200rpx;
height: 280rpx;
margin-right: 20rpx;
}
.novel-cover image {
width: 100%;
height: 100%;
border-radius: 8rpx;
}
.novel-basic {
flex: 1;
display: flex;
flex-direction: column;
justify-content: space-between;
}
.title {
font-size: 36rpx;
font-weight: bold;
margin-bottom: 16rpx;
}
.author-line, .status-line {
display: flex;
align-items: center;
margin-bottom: 12rpx;
font-size: 28rpx;
color: #666;
}
.label {
color: #999;
margin-right: 8rpx;
}
.score-line {
margin-top: 16rpx;
}
.score {
font-size: 32rpx;
color: #333;
font-weight: bold;
}
.score-label {
font-size: 24rpx;
color: #999;
margin-left: 8rpx;
}
.recommendation-section {
padding: 24rpx 32rpx;
background: #fff;
display: flex;
justify-content: space-between;
align-items: center;
position: relative;
}
.rec-left {
display: flex;
flex-direction: column;
align-items: flex-start;
margin-left: 70rpx;
}
.rec-count {
font-size: 44rpx;
font-weight: 500;
color: #333;
line-height: 1.2;
}
.rec-label {
font-size: 26rpx;
color: #999;
margin-top: 4rpx;
}
.rec-divider {
position: absolute;
right: 160rpx;
top: 20rpx;
bottom: 20rpx;
width: 2rpx;
background: #eee;
}
.rec-right {
flex-shrink: 0;
}
.recommend-btn {
background: #fff;
color: #4a90e2;
border: 2rpx solid #4a90e2;
border-radius: 40rpx;
padding: 12rpx 32rpx;
font-size: 28rpx;
display: flex;
align-items: center;
line-height: 1;
height: 64rpx;
}
.btn-icon {
margin-right: 8rpx;
font-size: 32rpx;
}
.action-buttons {
display: flex;
padding: 30rpx;
gap: 20rpx;
button {
flex: 1;
height: 80rpx;
border-radius: 40rpx;
font-size: 32rpx;
display: flex;
align-items: center;
justify-content: center;
}
.read-btn {
background-color: #4a90e2;
color: #fff;
}
.collect-btn {
background-color: #f0f0f0;
color: #666;
}
}
.user-level {
margin: 20rpx 30rpx;
background-color: #fff;
border-radius: 12rpx;
padding: 24rpx 32rpx;
display: flex;
justify-content: space-between;
align-items: stretch;
}
.level-left {
flex: 1;
}
.level-title {
display: flex;
align-items: center;
gap: 8rpx;
margin-bottom: 20rpx;
margin-left: 20rpx;
.title-icon {
font-size: 36rpx;
color: #FFB800;
}
text {
font-size: 32rpx;
font-weight: 500;
color: #333;
}
}
.level-info {
display: flex;
align-items: flex-start;
gap: 20rpx;
}
.user-avatar {
width: 80rpx;
height: 80rpx;
border-radius: 50%;
border: 2rpx solid #f0f0f0;
}
.user-details {
display: flex;
flex-direction: column;
gap: 8rpx;
}
.username {
font-size: 28rpx;
color: #333;
font-weight: 500;
}
.user-score {
display: flex;
align-items: center;
gap: 8rpx;
.score-value {
font-size: 28rpx;
color: #333;
}
.score-label {
font-size: 24rpx;
color: #999;
}
}
.user-role {
font-size: 24rpx;
color: #666;
background: #f5f5f5;
padding: 4rpx 12rpx;
border-radius: 4rpx;
display: inline-block;
}
.level-right {
display: flex;
align-items: center;
}
.rank-btn {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
padding: 0 20rpx;
.rank-icon {
width: 200rpx;
height: 60rpx;
margin-bottom: 8rpx;
}
text {
font-size: 26rpx;
color: #333;
line-height: 1.4;
}
.check-text {
font-size: 22rpx;
color: #999;
}
}
.novel-intro {
margin: 20rpx 30rpx;
background-color: #fff;
border-radius: 12rpx;
padding: 24rpx;
}
.intro-title {
font-size: 32rpx;
font-weight: 500;
color: #333;
margin-bottom: 16rpx;
}
.intro-content {
font-size: 28rpx;
color: #666;
line-height: 1.6;
display: flex;
flex-direction: column;
gap: 16rpx;
text {
display: block;
}
}
.comments-section {
margin: 20rpx 30rpx;
background-color: #fff;
border-radius: 12rpx;
padding: 24rpx;
}
.comments-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 24rpx;
border-bottom: 2rpx solid #f5f5f5;
padding-bottom: 24rpx;
}
.header-left {
display: flex;
align-items: center;
gap: 8rpx;
.title-icon {
font-size: 32rpx;
}
text {
font-size: 32rpx;
font-weight: 500;
color: #333;
}
}
.header-right {
text {
font-size: 28rpx;
color: #666;
}
}
.comment-list {
display: flex;
flex-direction: column;
gap: 32rpx;
}
.comment-item {
display: flex;
flex-direction: column;
gap: 16rpx;
}
.comment-header {
display: flex;
align-items: center;
gap: 12rpx;
}
.avatar {
width: 64rpx;
height: 64rpx;
border-radius: 50%;
}
.username {
font-size: 28rpx;
color: #333;
font-weight: 500;
}
.comment-body {
padding-left: 76rpx;
}
.content-text {
font-size: 28rpx;
color: #333;
line-height: 1.6;
}
.comment-footer {
display: flex;
justify-content: space-between;
align-items: center;
margin-top: 16rpx;
}
.comment-time {
font-size: 24rpx;
color: #999;
}
.comment-likes {
display: flex;
align-items: center;
gap: 4rpx;
}
.like-icon {
font-size: 24rpx;
color: #999;
}
.like-count {
font-size: 24rpx;
color: #999;
}
.novel-catalog {
margin: 20rpx 30rpx;
background-color: #fff;
border-radius: 12rpx;
padding: 24rpx;
}
.catalog-header {
display: flex;
justify-content: space-between;
align-items: center;
border-bottom: 2rpx solid #f5f5f5;
padding-bottom: 24rpx;
}
.catalog-title {
display: flex;
align-items: center;
gap: 8rpx;
.title-icon {
font-size: 32rpx;
}
text {
font-size: 32rpx;
font-weight: 500;
color: #333;
}
}
.chapter-nav {
display: flex;
align-items: center;
gap: 8rpx;
.current-chapter {
font-size: 28rpx;
color: #666;
}
.nav-arrow {
font-size: 28rpx;
color: #999;
}
}
.novel-bottom {
position: fixed;
bottom: 0;
left: 0;
right: 0;
height: 100rpx;
background: #fff;
display: flex;
align-items: center;
padding: 0 30rpx;
box-shadow: 0 -2rpx 10rpx rgba(0, 0, 0, 0.05);
}
.bottom-left {
flex: 1;
display: flex;
gap: 40rpx;
}
.action-btn {
display: flex;
flex-direction: column;
align-items: center;
gap: 4rpx;
.btn-icon {
font-size: 40rpx;
line-height: 1;
}
text {
font-size: 24rpx;
color: #666;
}
}
.bottom-right {
flex-shrink: 0;
}
.read-now-btn {
background: #1a237e;
color: #fff;
font-size: 32rpx;
height: 80rpx;
line-height: 80rpx;
padding: 0 60rpx;
border-radius: 40rpx;
border: none;
}
</style>

+ 162
- 0
pages_order/novel/vote.vue View File

@ -0,0 +1,162 @@
<template>
<view class="vote-container">
<!-- Empty space at the top -->
<view class="empty-space"></view>
<!-- Bottom sheet with voting interface -->
<view class="vote-sheet">
<view class="sheet-header">
<text class="sheet-title">投推荐票</text>
</view>
<view class="vote-options">
<text class="option-label">推荐投票</text>
<view class="quick-options">
<view class="option-btn" @click="setVotes(1)">1</view>
<view class="option-btn" @click="setVotes(5)">5</view>
<view class="option-btn" @click="setVotes(10)">10</view>
</view>
<text class="option-label">手动设置</text>
<view class="manual-input">
<view class="minus-btn" @click="decreaseVotes">-</view>
<view class="vote-count">
<text>x{{voteCount}}</text>
</view>
<view class="plus-btn" @click="increaseVotes">+</view>
</view>
</view>
<button class="submit-btn" @click="submitVote">投票</button>
</view>
</view>
</template>
<script>
export default {
data() {
return {
voteCount: 1
}
},
methods: {
setVotes(count) {
this.voteCount = count
},
increaseVotes() {
this.voteCount++
},
decreaseVotes() {
if (this.voteCount > 1) {
this.voteCount--
}
},
submitVote() {
// TODO: Implement vote submission
uni.showToast({
title: `已投${this.voteCount}`,
icon: 'success'
})
}
}
}
</script>
<style lang="scss">
.vote-container {
display: flex;
flex-direction: column;
height: 100vh;
background-color: rgba(0, 0, 0, 0.4);
}
.empty-space {
flex: 1;
}
.vote-sheet {
background-color: #fff;
border-radius: 20rpx 20rpx 0 0;
padding: 30rpx;
}
.sheet-header {
text-align: center;
margin-bottom: 40rpx;
}
.sheet-title {
font-size: 32rpx;
font-weight: 500;
}
.vote-options {
margin-bottom: 40rpx;
}
.option-label {
font-size: 28rpx;
color: #666;
margin-bottom: 20rpx;
}
.quick-options {
display: flex;
gap: 20rpx;
margin-top: 30rpx;
margin-bottom: 40rpx;
}
.option-btn {
flex: 1;
height: 80rpx;
background-color: #f5f5f5;
display: flex;
align-items: center;
justify-content: center;
border-radius: 8rpx;
font-size: 28rpx;
}
.manual-input {
margin-top: 30rpx;
display: flex;
align-items: center;
justify-content: center;
gap: 20rpx;
}
.minus-btn, .plus-btn {
width: 220rpx;
height: 80rpx;
background-color: #f5f5f5;
display: flex;
align-items: center;
justify-content: center;
border-radius: 8rpx;
font-size: 32rpx;
}
.vote-count {
width: 220rpx;
height: 82rpx;
background-color: #f5f5f5;
display: flex;
align-items: center;
justify-content: center;
border-radius: 8rpx;
font-size: 28rpx;
}
.submit-btn {
width: 100%;
height: 88rpx;
background-color: #000033;
color: #fff;
border-radius: 8rpx;
font-size: 32rpx;
display: flex;
align-items: center;
justify-content: center;
}
</style>

Loading…
Cancel
Save