mirror of
https://github.com/yangjian102621/geekai.git
synced 2025-09-17 16:56:38 +08:00
feat: mobile mj list page is ready
This commit is contained in:
parent
68cda968a1
commit
49e9f41ef2
@ -340,20 +340,22 @@ func (h *MidJourneyHandler) JobList(c *gin.Context) {
|
||||
continue
|
||||
}
|
||||
|
||||
// 失败的任务直接删除
|
||||
if job.Progress == -1 {
|
||||
h.db.Delete(&model.MidJourneyJob{Id: job.Id})
|
||||
jobs = append(jobs, job)
|
||||
continue
|
||||
}
|
||||
|
||||
if item.Progress < 100 && item.ImgURL == "" && item.OrgURL != "" {
|
||||
// 正在运行中任务使用代理访问图片
|
||||
if job.UseProxy {
|
||||
job.ImgURL = job.OrgURL
|
||||
} else {
|
||||
// discord 服务器图片需要使用代理转发图片数据流
|
||||
if strings.HasPrefix(item.OrgURL, "https://cdn.discordapp.com") {
|
||||
image, err := utils.DownloadImage(item.OrgURL, h.App.Config.ProxyURL)
|
||||
if err == nil {
|
||||
job.ImgURL = "data:image/png;base64," + base64.StdEncoding.EncodeToString(image)
|
||||
}
|
||||
} else {
|
||||
job.ImgURL = job.OrgURL
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -108,7 +108,7 @@ func (s *Service) Run() {
|
||||
s.taskStartTimes[int(task.Id)] = time.Now()
|
||||
atomic.AddInt32(&s.HandledTaskNum, 1)
|
||||
// 更新任务 ID/频道
|
||||
s.db.Debug().Model(&model.MidJourneyJob{Id: task.Id}).UpdateColumns(map[string]interface{}{
|
||||
s.db.Model(&model.MidJourneyJob{Id: task.Id}).UpdateColumns(map[string]interface{}{
|
||||
"task_id": res.Result,
|
||||
"channel_id": s.Name,
|
||||
})
|
||||
|
@ -201,7 +201,7 @@ func (p *ServicePool) SyncTaskProgress() {
|
||||
for _, v := range items {
|
||||
// 30 分钟还没完成的任务直接删除
|
||||
if time.Now().Sub(v.CreatedAt) > time.Minute*30 {
|
||||
//p.db.Delete(&v)
|
||||
p.db.Delete(&v)
|
||||
// 非放大任务,退回绘图次数
|
||||
if v.Type != types.TaskUpscale.String() {
|
||||
p.db.Model(&model.User{}).Where("id = ?", v.UserId).UpdateColumn("img_calls", gorm.Expr("img_calls + ?", 1))
|
||||
|
@ -55,7 +55,8 @@
|
||||
padding: 0;
|
||||
position: relative;
|
||||
}
|
||||
.mobile-mj .content .running-job-list .van-grid .van-grid-item .van-grid-item__content .van-image {
|
||||
.mobile-mj .content .running-job-list .van-grid .van-grid-item .van-grid-item__content .van-image,
|
||||
.mobile-mj .content .running-job-list .van-grid .van-grid-item .van-grid-item__content .task-in-queue {
|
||||
min-height: 100px;
|
||||
}
|
||||
.mobile-mj .content .running-job-list .van-grid .van-grid-item .van-grid-item__content .progress {
|
||||
@ -95,40 +96,38 @@
|
||||
overflow: hidden;
|
||||
border-radius: 6px;
|
||||
position: relative;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-line {
|
||||
margin: 6px 0;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-line ul {
|
||||
display: flex;
|
||||
flex-flow: row;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-line ul li {
|
||||
margin-right: 6px;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-line ul li a {
|
||||
padding: 3px 0;
|
||||
width: 40px;
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-btn {
|
||||
padding: 3px 10px;
|
||||
text-align: center;
|
||||
border-radius: 5px;
|
||||
margin: 3px 0;
|
||||
display: block;
|
||||
cursor: pointer;
|
||||
background-color: #4e5058;
|
||||
color: #fff;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-line ul li a:hover {
|
||||
background-color: #6d6f78;
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .el-image {
|
||||
width: 100%;
|
||||
height: 200px;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .opt .opt-line ul .show-prompt {
|
||||
font-size: 20px;
|
||||
cursor: pointer;
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .el-image .image-slot {
|
||||
height: 100%;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .el-image .image-slot .iconfont {
|
||||
margin-right: 5px;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .upscale {
|
||||
height: 260px;
|
||||
width: 100%;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item .remove {
|
||||
display: none;
|
||||
position: absolute;
|
||||
right: 10px;
|
||||
top: 10px;
|
||||
}
|
||||
.mobile-mj .content .finish-job-list .van-grid .van-grid-item .van-grid-item__content .job-item:hover .remove {
|
||||
display: block;
|
||||
right: 5px;
|
||||
top: 5px;
|
||||
}
|
||||
|
@ -76,7 +76,7 @@
|
||||
padding 0
|
||||
position relative
|
||||
|
||||
.van-image {
|
||||
.van-image, .task-in-queue {
|
||||
min-height 100px
|
||||
}
|
||||
|
||||
@ -134,53 +134,47 @@
|
||||
overflow hidden
|
||||
border-radius 6px
|
||||
position relative
|
||||
height 100%
|
||||
width 100%
|
||||
|
||||
.opt {
|
||||
.opt-line {
|
||||
margin 6px 0
|
||||
|
||||
ul {
|
||||
display flex
|
||||
flex-flow row
|
||||
|
||||
li {
|
||||
margin-right 6px
|
||||
|
||||
a {
|
||||
padding 3px 0
|
||||
width 40px
|
||||
.opt-btn {
|
||||
padding 3px 10px
|
||||
text-align center
|
||||
border-radius 5px
|
||||
margin 3px 0
|
||||
display block
|
||||
cursor pointer
|
||||
background-color #4E5058
|
||||
color #ffffff
|
||||
}
|
||||
}
|
||||
|
||||
&:hover {
|
||||
background-color #6D6F78
|
||||
.el-image {
|
||||
width 100%
|
||||
height 200px
|
||||
|
||||
.image-slot {
|
||||
height 100%
|
||||
display flex
|
||||
justify-content center
|
||||
align-items center
|
||||
|
||||
.iconfont {
|
||||
margin-right 5px
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.show-prompt {
|
||||
font-size 20px
|
||||
cursor pointer
|
||||
}
|
||||
}
|
||||
}
|
||||
.upscale {
|
||||
height 260px
|
||||
width 100%
|
||||
}
|
||||
|
||||
.remove {
|
||||
display none
|
||||
position absolute
|
||||
right 10px
|
||||
top 10px
|
||||
}
|
||||
|
||||
&:hover {
|
||||
.remove {
|
||||
display block
|
||||
}
|
||||
right 5px
|
||||
top 5px
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -824,7 +824,7 @@ const reGenerate = function () {
|
||||
icon: loginUser.value.avatar,
|
||||
content: md.render(text)
|
||||
});
|
||||
socket.value.send(previousText);
|
||||
socket.value.send(previousText.value);
|
||||
}
|
||||
|
||||
const chatName = ref('')
|
||||
|
@ -504,7 +504,7 @@ import Clipboard from "clipboard";
|
||||
import {checkSession} from "@/action/session";
|
||||
import {useRouter} from "vue-router";
|
||||
import {getSessionId} from "@/store/session";
|
||||
import {removeArrayItem} from "@/utils/libs";
|
||||
import {isMobile, removeArrayItem} from "@/utils/libs";
|
||||
|
||||
const listBoxHeight = ref(window.innerHeight - 40)
|
||||
const mjBoxHeight = ref(window.innerHeight - 150)
|
||||
@ -560,7 +560,7 @@ const params = ref({
|
||||
rate: rates[0].value,
|
||||
model: models[0].value,
|
||||
chaos: 0,
|
||||
stylize: 100,
|
||||
stylize: 0,
|
||||
seed: 0,
|
||||
img_arr: [],
|
||||
raw: false,
|
||||
@ -584,6 +584,10 @@ const imgCalls = ref(0)
|
||||
const loading = ref(false)
|
||||
const userId = ref(0)
|
||||
|
||||
if (isMobile()) {
|
||||
router.replace("/mobile/mj")
|
||||
}
|
||||
|
||||
const rewritePrompt = () => {
|
||||
loading.value = true
|
||||
httpPost("/api/prompt/rewrite", {"prompt": params.value.prompt}).then(res => {
|
||||
|
@ -377,6 +377,7 @@ const sendMessage = () => {
|
||||
}
|
||||
|
||||
if (prompt.value.trim().length === 0) {
|
||||
showToast("请输入需要 AI 回答的问题")
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -417,7 +418,7 @@ const reGenerate = () => {
|
||||
icon: loginUser.value.avatar,
|
||||
content: renderInputText(text)
|
||||
});
|
||||
socket.value.send(text);
|
||||
socket.value.send(previousText.value);
|
||||
}
|
||||
|
||||
const showShare = ref(false)
|
||||
|
@ -140,7 +140,7 @@
|
||||
image-size="80"
|
||||
description="暂无记录"
|
||||
/>
|
||||
<van-grid :gutter="10" :column-num="3" v-else>
|
||||
<van-grid :gutter="10" :column-num="2" v-else>
|
||||
<van-grid-item v-for="item in finishedJobs">
|
||||
<div class="job-item">
|
||||
<el-image
|
||||
@ -168,43 +168,17 @@
|
||||
</el-image>
|
||||
|
||||
<div class="opt" v-if="item['can_opt']">
|
||||
<div class="opt-line">
|
||||
<ul>
|
||||
<li><a @click="upscale(1, item)">U1</a></li>
|
||||
<li><a @click="upscale(2, item)">U2</a></li>
|
||||
<li><a @click="upscale(3, item)">U3</a></li>
|
||||
<li><a @click="upscale(4, item)">U4</a></li>
|
||||
<li class="show-prompt">
|
||||
|
||||
<el-popover placement="left" title="提示词" :width="240" trigger="hover">
|
||||
<template #reference>
|
||||
<el-icon>
|
||||
<ChromeFilled/>
|
||||
</el-icon>
|
||||
</template>
|
||||
|
||||
<template #default>
|
||||
<div class="mj-list-item-prompt">
|
||||
<span>{{ item.prompt }}</span>
|
||||
<el-icon class="copy-prompt"
|
||||
:data-clipboard-text="item.prompt">
|
||||
<DocumentCopy/>
|
||||
</el-icon>
|
||||
</div>
|
||||
</template>
|
||||
</el-popover>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="opt-line">
|
||||
<ul>
|
||||
<li><a @click="variation(1, item)">V1</a></li>
|
||||
<li><a @click="variation(2, item)">V2</a></li>
|
||||
<li><a @click="variation(3, item)">V3</a></li>
|
||||
<li><a @click="variation(4, item)">V4</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
<van-grid :gutter="0" :column-num="4">
|
||||
<van-grid-item><a @click="upscale(1, item)" class="opt-btn">U1</a></van-grid-item>
|
||||
<van-grid-item><a @click="upscale(2, item)" class="opt-btn">U2</a></van-grid-item>
|
||||
<van-grid-item><a @click="upscale(3, item)" class="opt-btn">U3</a></van-grid-item>
|
||||
<van-grid-item><a @click="upscale(4, item)" class="opt-btn">U4</a></van-grid-item>
|
||||
<van-grid-item><a @click="variation(1, item)" class="opt-btn">V1</a></van-grid-item>
|
||||
<van-grid-item><a @click="variation(2, item)" class="opt-btn">V2</a></van-grid-item>
|
||||
<van-grid-item><a @click="variation(3, item)" class="opt-btn">V3</a></van-grid-item>
|
||||
<van-grid-item><a @click="variation(4, item)" class="opt-btn">V4</a></van-grid-item>
|
||||
</van-grid>
|
||||
</div>
|
||||
|
||||
<div class="remove">
|
||||
@ -236,7 +210,7 @@ import {getSessionId} from "@/store/session";
|
||||
import {checkSession} from "@/action/session";
|
||||
import Clipboard from "clipboard";
|
||||
import {useRouter} from "vue-router";
|
||||
import {ChromeFilled, Delete, DocumentCopy, Picture} from "@element-plus/icons-vue";
|
||||
import {Delete, Picture} from "@element-plus/icons-vue";
|
||||
|
||||
const title = ref('MidJourney 绘画')
|
||||
const activeColspan = ref([""])
|
||||
@ -263,7 +237,7 @@ const params = ref({
|
||||
rate: rates[0].value,
|
||||
model: models[0].value,
|
||||
chaos: 0,
|
||||
stylize: 100,
|
||||
stylize: 0,
|
||||
seed: 0,
|
||||
img_arr: [],
|
||||
raw: false,
|
||||
@ -356,7 +330,7 @@ const fetchRunningJobs = (userId) => {
|
||||
if (jobs[i].progress === -1) {
|
||||
showNotify({
|
||||
message: `任务执行失败:${jobs[i]['err_msg']}`,
|
||||
type: 'error',
|
||||
type: 'danger',
|
||||
})
|
||||
imgCalls.value += 1
|
||||
continue
|
||||
@ -439,10 +413,10 @@ const generate = () => {
|
||||
params.value.session_id = getSessionId()
|
||||
params.value.img_arr = imgList.value.map(img => img.url)
|
||||
httpPost("/api/mj/image", params.value).then(() => {
|
||||
ElMessage.success("绘画任务推送成功,请耐心等待任务执行...")
|
||||
showToast("绘画任务推送成功,请耐心等待任务执行")
|
||||
imgCalls.value -= 1
|
||||
}).catch(e => {
|
||||
ElMessage.error("任务推送失败:" + e.message)
|
||||
showFailToast("任务推送失败:" + e.message)
|
||||
})
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user