Skip to content

Commit

Permalink
优化聊天消息附件支持预览
Browse files Browse the repository at this point in the history
  • Loading branch information
kuaifan committed Jan 27, 2022
1 parent 705d7f3 commit 9e560c7
Show file tree
Hide file tree
Showing 14 changed files with 325 additions and 63 deletions.
14 changes: 9 additions & 5 deletions app/Http/Controllers/Api/DialogController.php
Original file line number Diff line number Diff line change
Expand Up @@ -357,22 +357,26 @@ public function msg__detail()
//
if ($data['type'] == 'file') {
$codeExt = ['txt'];
$fillExt = ['jpg', 'jpeg', 'png', 'gif'];
$officeExt = ['doc', 'docx', 'xls', 'xlsx', 'ppt', 'pptx'];
$localExt = ['jpg', 'jpeg', 'png', 'gif'];
$msg = Base::json2array($dialogMsg->getRawOriginal('msg'));
$filePath = public_path($msg['path']);
if (in_array($msg['ext'], $codeExt) && $msg['size'] < 2 * 1024 * 1024) {
// 文本代码,限制2M内的文件
// 文本预览,限制2M内的文件
$data['content'] = file_get_contents($filePath);
$data['file_mode'] = 1;
} elseif (in_array($msg['ext'], $officeExt)) {
// office预览
$data['file_mode'] = 2;
} else {
// 支持预览
if (in_array($msg['ext'], $fillExt)) {
// 其他预览
if (in_array($msg['ext'], $localExt)) {
$url = Base::fillUrl($msg['path']);
} else {
$url = 'http://' . env('APP_IPPR') . '.3/' . $msg['path'];
}
$data['url'] = base64_encode($url);
$data['file_mode'] = 2;
$data['file_mode'] = 3;
}
}
//
Expand Down
8 changes: 5 additions & 3 deletions app/Http/Controllers/Api/FileController.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,12 @@
use App\Models\FileLink;
use App\Models\FileUser;
use App\Models\User;
use App\Models\WebSocketDialogMsg;
use App\Module\Base;
use App\Module\Ihttp;
use Illuminate\Support\Facades\DB;
use Request;
use Response;

/**
* @apiDefine file
Expand Down Expand Up @@ -379,11 +381,11 @@ public function remove()
* @apiName content
*
* @apiParam {Number|String} id
* - Number 文件ID(需要登录)
* - String 链接码(不需要登录,用于预览)
* - Number: 文件ID(需要登录)
* - String: 链接码(不需要登录,用于预览)
* @apiParam {String} down 直接下载
* - no: 浏览(默认)
* - yes: 下载
* - yes: 下载(office文件直接下载)
*
* @apiSuccess {Number} ret 返回状态码(1正确、0错误)
* @apiSuccess {String} msg 返回信息(错误描述)
Expand Down
54 changes: 54 additions & 0 deletions app/Http/Controllers/Api/ProjectController.php
Original file line number Diff line number Diff line change
Expand Up @@ -1083,6 +1083,60 @@ public function task__filedelete()
return Base::retSuccess('success', $file);
}

/**
* @api {get} api/project/task/filedetail 22. 获取任务文件详情
*
* @apiDescription 需要token身份(限:项目、任务负责人)
* @apiVersion 1.0.0
* @apiGroup project
* @apiName task__filedetail
*
* @apiParam {Number} file_id 文件ID
*
* @apiSuccess {Number} ret 返回状态码(1正确、0错误)
* @apiSuccess {String} msg 返回信息(错误描述)
* @apiSuccess {Object} data 返回数据
*/
public function task__filedetail()
{
User::auth();
//
$file_id = intval(Request::input('file_id'));
//
$file = ProjectTaskFile::find($file_id);
if (empty($file)) {
return Base::retError("文件不存在");
}
$data = $file->toArray();
$data['path'] = $file->getRawOriginal('path');
//
ProjectTask::userTask($file->task_id, true, true);
//
$codeExt = ['txt'];
$officeExt = ['doc', 'docx', 'xls', 'xlsx', 'ppt', 'pptx'];
$localExt = ['jpg', 'jpeg', 'png', 'gif'];
$filePath = public_path($data['path']);
if (in_array($data['ext'], $codeExt) && $data['size'] < 2 * 1024 * 1024) {
// 文本预览,限制2M内的文件
$data['content'] = file_get_contents($filePath);
$data['file_mode'] = 1;
} elseif (in_array($data['ext'], $officeExt)) {
// office预览
$data['file_mode'] = 2;
} else {
// 其他预览
if (in_array($data['ext'], $localExt)) {
$url = Base::fillUrl($data['path']);
} else {
$url = 'http://' . env('APP_IPPR') . '.3/' . $data['path'];
}
$data['url'] = base64_encode($url);
$data['file_mode'] = 3;
}
//
return Base::retSuccess('success', $data);
}

/**
* @api {get} api/project/task/filedown 22. 下载任务文件
*
Expand Down
2 changes: 1 addition & 1 deletion docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ services:

fileview:
container_name: "dootask-fileview-${APP_ID}"
image: "kuaifan/fileview:4.1.0-SNAPSHOT-RC2"
image: "kuaifan/fileview:4.1.0-SNAPSHOT-RC3"
environment:
TZ: "Asia/Shanghai"
KK_CONTEXT_PATH: "/fileview"
Expand Down
2 changes: 1 addition & 1 deletion public/js/ace/theme-dracula-dark.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

10 changes: 8 additions & 2 deletions resources/assets/js/components/OnlyOffice.vue
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,7 @@ export default {
case 'ppt':
return 'pptx'
}
return '';
return type;
},
loadFile() {
Expand All @@ -144,11 +144,12 @@ export default {
}
//
let fileKey = this.code || this.value.id;
let fileName = $A.strExists(this.fileName, '.') ? this.fileName : (this.fileName + '.' + this.fileType);
const config = {
"document": {
"fileType": this.fileType,
"key": this.fileType + '-' + fileKey,
"title": this.fileName + '.' + this.fileType,
"title": fileName,
"url": 'http://nginx/api/file/content/?id=' + fileKey + '&token=' + this.userToken,
},
"editorConfig": {
Expand All @@ -164,6 +165,11 @@ export default {
"callbackUrl": 'http://nginx/api/file/content/office?id=' + fileKey + '&token=' + this.userToken,
}
};
if ($A.leftExists(fileKey, "msgFile_")) {
config.document.url = 'http://nginx/api/dialog/msg/download/?msg_id=' + $A.leftDelete(fileKey, "msgFile_") + '&token=' + this.userToken;
} else if ($A.leftExists(fileKey, "taskFile_")) {
config.document.url = 'http://nginx/api/project/task/filedown/?file_id=' + $A.leftDelete(fileKey, "taskFile_") + '&token=' + this.userToken;
}
if (this.readOnly) {
config.editorConfig.mode = "view";
config.editorConfig.callbackUrl = null;
Expand Down
6 changes: 3 additions & 3 deletions resources/assets/js/pages/manage/components/DialogView.vue
Original file line number Diff line number Diff line change
Expand Up @@ -181,8 +181,8 @@ export default {
this.$Electron.ipcRenderer.send('windowRouter', {
title: `${this.msgData.msg.name} (${$A.bytesToSize(this.msgData.msg.size)})`,
titleFixed: true,
name: 'msgview-' + this.msgData.id,
path: "/single/msgview/" + this.msgData.id,
name: 'file-msg-' + this.msgData.id,
path: "/single/file/msg/" + this.msgData.id,
force: false,
config: {
parent: null,
Expand All @@ -191,7 +191,7 @@ export default {
}
});
} else {
window.open($A.apiUrl(`../single/msgview/${this.msgData.id}`))
window.open($A.apiUrl(`../single/file/msg/${this.msgData.id}`))
}
},
Expand Down
13 changes: 1 addition & 12 deletions resources/assets/js/pages/manage/components/ProjectList.vue
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@
</ETooltip>
</li>
<li :class="['project-icon', searchText!='' ? 'active' : '']">
<Tooltip :always="searchAlways" @on-popper-show="searchFocus" theme="light">
<Tooltip :always="searchText!=''" @on-popper-show="searchFocus" theme="light" :rawIndex="10">
<Icon class="menu-icon" type="ios-search" @click="searchFocus" />
<div slot="content">
<Input v-model="searchText" ref="searchInput" :placeholder="$L('名称、描述...')" class="search-input" clearable/>
Expand Down Expand Up @@ -537,17 +537,6 @@ export default {
...mapGetters(['projectData', 'projectParameter', 'transforTasks']),
searchAlways() {
return !(!this.searchText
|| this.settingShow
|| this.userShow
|| this.inviteShow
|| this.transferShow
|| this.workflowShow
|| this.logShow
|| this.archivedTaskShow);
},
userWaitRemove() {
const {userids, useridbak} = this.userData;
if (!userids) {
Expand Down
45 changes: 34 additions & 11 deletions resources/assets/js/pages/manage/components/TaskDetail.vue
Original file line number Diff line number Diff line change
Expand Up @@ -279,18 +279,22 @@
<li v-for="file in fileList">
<img v-if="file.id" class="file-ext" :src="file.thumb"/>
<Loading v-else class="file-load"/>
<div class="file-name" @click="downFile(file)">{{file.name}}</div>
<div class="file-name">{{file.name}}</div>
<div class="file-size">{{$A.bytesToSize(file.size)}}</div>
<EPopover v-model="file._deling" class="file-delete">
<div class="task-detail-delete-file-popover">
<p>{{$L('你确定要删除这个文件吗?')}}</p>
<div class="buttons">
<Button size="small" type="text" @click="file._deling=false">{{$L('取消')}}</Button>
<Button size="small" type="primary" @click="deleteFile(file)">{{$L('确定')}}</Button>
<div class="file-menu" :class="{show:file._show_menu}">
<Icon @click="viewFile(file)" type="md-eye" />
<Icon @click="downFile(file)" type="md-arrow-round-down" />
<EPopover v-model="file._show_menu" class="file-delete">
<div class="task-detail-delete-file-popover">
<p>{{$L('你确定要删除这个文件吗?')}}</p>
<div class="buttons">
<Button size="small" type="text" @click="file._show_menu=false">{{$L('取消')}}</Button>
<Button size="small" type="primary" @click="deleteFile(file)">{{$L('确定')}}</Button>
</div>
</div>
</div>
<i slot="reference" :class="['taskfont', file._deling ? 'deling' : '']">&#xe6ea;</i>
</EPopover>
<i slot="reference" class="taskfont del">&#xe6ea;</i>
</EPopover>
</div>
</li>
</ul>
<ul class="item-content">
Expand Down Expand Up @@ -1102,7 +1106,7 @@ export default {
},
deleteFile(file) {
this.$set(file, '_deling', false);
this.$set(file, '_show_menu', false);
this.$store.dispatch("forgetTaskFile", file.id)
//
this.$store.dispatch("call", {
Expand Down Expand Up @@ -1166,6 +1170,25 @@ export default {
})
},
viewFile(file) {
if (this.$Electron) {
this.$Electron.ipcRenderer.send('windowRouter', {
title: `${file.name} (${$A.bytesToSize(file.size)})`,
titleFixed: true,
name: 'file-task-' + file.id,
path: "/single/file/task/" + file.id,
force: false,
config: {
parent: null,
width: Math.min(window.screen.availWidth, 1440),
height: Math.min(window.screen.availHeight, 900),
}
});
} else {
window.open($A.apiUrl(`../single/file/task/${file.id}`))
}
},
downFile(file) {
$A.modalConfirm({
title: '下载文件',
Expand Down
Loading

0 comments on commit 9e560c7

Please sign in to comment.