【v3.8.3】前端小改动汇总集合

This commit is contained in:
JEECG
2025-09-14 10:39:48 +08:00
parent d76842ae07
commit 4f46213df6
34 changed files with 466 additions and 64 deletions

View File

@ -58,6 +58,9 @@
</div>
</div>
</template>
<a v-if="noticeFiles.length > 1" :href="downLoadFiles + '?id=' + content.id + '&token=' + getToken()" target="_blank" style="margin: 15px 6px; color: #5ac0fa">
<download-outlined class="item-icon" style="margin-right: 5px" /><span>批量下载所有附件</span>
</a>
</template>
</BasicModal>
</template>
@ -72,15 +75,21 @@
import { getFileAccessHttpUrl } from '@/utils/common/compUtils';
import { useGlobSetting } from '@/hooks/setting';
import { encryptByBase64 } from '@/utils/cipher';
import { getToken } from '@/utils/auth';
const router = useRouter();
const glob = useGlobSetting();
const isUpdate = ref(true);
const content = ref<any>({});
const noticeFiles = ref([]);
/**
* 下载文件路径
*/
const downLoadFiles = `${glob.domainUrl}/sys/annountCement/downLoadFiles`;
const emit = defineEmits(['close', 'register']);
//表单赋值
const [registerModal, { setModalProps, closeModal }] = useModalInner(async (data) => {
isUpdate.value = !!data?.isUpdate;
noticeFiles.value = [];
if (unref(isUpdate)) {
//data.record.msgContent = '<p>2323</p><input onmouseover=alert(1)>xss test';
//update-begin-author:taoyan date:2022-7-14 for: VUEN-1702 【禁止问题】sql注入漏洞
@ -194,6 +203,24 @@
padding: 0;
}
}
.ant-card-meta-detail {
display: flex !important ;
justify-content: center !important;
align-items: center !important;
flex-direction: column !important;
}
.ant-card-meta-title {
font-size: 22px !important;
color: rgba(51, 51, 51, 0.88);
font-weight: 600;
font-size: 16px;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
}
.ant-card .ant-card-meta-description {
color: rgba(51, 51, 51, 0.45);
}
`;
frameDoc.head.appendChild(style);
@ -273,8 +300,8 @@
.print-btn {
position: absolute;
top: 20px;
right: 20px;
top: 80px;
right: 40px;
cursor: pointer;
color: #a3a3a5;
z-index: 999;

View File

@ -78,4 +78,4 @@ export const deleteThirdAppConfig = (params, handleSuccess) => {
return defHttp.delete({ url: Api.deleteThirdAppConfig, params }, { joinParamsToUrl: true }).then(() => {
handleSuccess();
});
};
};

View File

@ -335,7 +335,7 @@
searchParams.realname = options[0].label;
}
}
function openSelectPerson(){
openModal(true, {})
}

View File

@ -161,7 +161,7 @@ export function useSysMessage(setLocaleText) {
}
}
return '去处理'
}else{
} else {
return '查看详情'
}
}

View File

@ -28,6 +28,9 @@
</div>
</div>
</template>
<a v-if="noticeFiles.length > 1" :href="downLoadFiles + '?id=' + noticeId + '&token=' + getToken()" target="_blank" style="margin: 15px 6px;color: #5ac0fa;">
<download-outlined class="item-icon" style="margin-right: 5px" /><span>批量下载所有附件</span>
</a>
</template>
</BasicModal>
</template>
@ -40,16 +43,25 @@
import { DownloadOutlined, EyeOutlined, PaperClipOutlined } from '@ant-design/icons-vue';
import { encryptByBase64 } from '@/utils/cipher';
import { useGlobSetting } from '@/hooks/setting';
import { getToken } from "@/utils/auth";
const glob = useGlobSetting();
// 获取props
defineProps({
frameSrc: propTypes.string.def(''),
});
/**
* 下载文件路径
*/
const downLoadFiles = `${glob.domainUrl}/sys/annountCement/downLoadFiles`;
//附件内容
const noticeFiles = ref([]);
//数据ID
const noticeId = ref('');
//表单赋值
const [registerModal] = useModalInner((data) => {
noticeFiles.value = [];
noticeId.value = data.record.id;
if (data.record?.files && data.record?.files.length > 0) {
noticeFiles.value = data.record.files.split(',').map((item) => {
return {
@ -96,8 +108,8 @@
<style scoped lang="less">
.print-btn {
position: absolute;
top: 20px;
right: 20px;
top: 80px;
right: 40px;
cursor: pointer;
color: #a3a3a5;
z-index: 999;

View File

@ -52,6 +52,13 @@
...data.record,
});
record.value = data.record;
} else {
// update-begin--author:liaozhiyang---date:20250807---for【JHHB-128】转公告
//表单赋值
await setFieldsValue({
...data.record,
});
// update-end--author:liaozhiyang---date:20250807---for【JHHB-128】转公告
}
});
//设置标题

View File

@ -29,7 +29,7 @@
</div>
</template>
<script lang="ts" name="system-notice" setup>
import { ref } from 'vue';
import { ref, onMounted } from 'vue';
import { BasicTable, TableAction } from '/@/components/Table';
import { useModal } from '/@/components/Modal';
import NoticeModal from './NoticeModal.vue';
@ -40,6 +40,9 @@
import { columns, searchFormSchema } from './notice.data';
import { getList, deleteNotice, batchDeleteNotice,editIzTop, getExportUrl, getImportUrl, doReleaseData, doReovkeData } from './notice.api';
import { useListPage } from '/@/hooks/system/useListPage';
import { useAppStore } from '/@/store/modules/app';
const appStore = useAppStore();
const glob = useGlobSetting();
const [registerModal, { openModal }] = useModal();
const [register, { openModal: openDetail }] = useModal();
@ -71,9 +74,10 @@
/**
* 新增事件
*/
function handleAdd() {
function handleAdd(record = {}) {
openModal(true, {
isUpdate: false,
record,
});
}
@ -192,4 +196,15 @@
},
];
}
onMounted(() => {
// update-begin--author:liaozhiyang---date:20250807---for【JHHB-128】转公告
const params = appStore.getMessageHrefParams;
if (params?.add) {
delete params.add;
handleAdd(params);
appStore.setMessageHrefParams('');
}
// update-begin--author:liaozhiyang---date:20250807---for【JHHB-128】转公告
});
</script>

View File

@ -12,9 +12,7 @@ enum Api {
releaseData = '/sys/annountCement/doReleaseData',
reovkeData = '/sys/annountCement/doReovkeData',
editIzTop = '/sys/annountCement/editIzTop',
addVisitsNum = '/sys/annountCement/addVisitsNumber',
tempList = '/sys/message/sysMessageTemplate/list',
}
@ -88,12 +86,6 @@ export const addVisitsNum = (params) => defHttp.get({ url: Api.addVisitsNum, par
* @param id
*/
export const queryById = (params) => defHttp.get({ url: Api.queryById, params }, { isTransformResponse: false });
/**
* 发起流程
* import { startProcess } from '/@/api/common/api';
* @param params
*/
export const startProcess = (params) => defHttp.post({ url: Api.startProcess, params }, { isTransformResponse: false });
/**
* 查询模板列表
* @param params

View File

@ -3,7 +3,10 @@
<template #title>
角色权限配置
<a-dropdown>
<Icon icon="ant-design:more-outlined" class="more-icon" />
<a-button class="more-icon">
更多操作
<Icon icon="ant-design:down-outlined" size="14px" style="position: relative;top: 1px;right: 5px"></Icon>
</a-button>
<template #overlay>
<a-menu @click="treeMenuClick">
<a-menu-item key="checkAll">选择全部</a-menu-item>
@ -294,9 +297,9 @@
border-bottom: 1px solid #f0f0f0;
}
.more-icon {
font-size: 20px !important;
/* font-size: 20px !important;
color: black;
display: inline-flex;
display: inline-flex;*/
float: right;
margin-right: 2px;
cursor: pointer;

View File

@ -57,7 +57,14 @@ export const searchUserFormSchema: FormSchema[] = [
field: 'username',
label: '用户账号',
component: 'Input',
colProps: { span: 12 },
colProps: { span: 8 },
labelWidth: 74,
},
{
field: 'realname',
label: '用户名称',
component: 'Input',
colProps: { span: 8 },
labelWidth: 74,
},
];

View File

@ -10,7 +10,7 @@
@change="updateAvatar"
width="80"
/>
<div class="account-right">
<div class="account-right border-bottom">
<div v-if="!isEdit">
<span class="font-size-17 account-name">{{ userInfo.realname }}</span>
<a-tooltip content="编辑姓名">
@ -27,7 +27,7 @@
</div>
</div>
</div>
<div class="account-data">
<div class="account-data border-bottom">
<!-- 详细资料 -->
<div class="account-detail">
<div class="font-size-15 font-bold font-color-gray" style="margin-bottom: 16px">详细资料</div>
@ -61,6 +61,47 @@
</div>
</div>
</div>
<div class="account-data">
<!-- 个性签名 -->
<div class="account-detail">
<div class="font-size-15 font-bold font-color-gray" style="margin-bottom: 16px">个性签名</div>
<div class="font-size-13 flex">
<span class="gray-75 item-label">签名</span>
<a-upload
accept="jpg,jpeg,png"
:max-count="1"
:multiple="false"
name = "file"
:headers="uploadHeader"
:action="uploadUrl"
v-model:fileList="uploadFileList"
@beforeUpload="beforeUpload"
@change="handleChange"
list-type="picture-card"
@preview="handlePreview"
>
<div v-if="uploadVisible">
<UploadOutlined></UploadOutlined>
<div class="ant-upload-text">上传</div>
</div>
</a-upload>
<a-modal :width="500" :open="previewVisible" :footer="null" @cancel="handleCancel">
<img alt="example" style="width: 100%" :src="previewImage" />
</a-modal>
</div>
<div style="font-size: 12px;color:#93a6aa" class="margin-bottom-10">
<p>建议上传尺寸为200*80大小不超过1M且格式为png或jpeg的图片</p>
<p>生成签名方法一手写扫描进行上传</p>
<p>生成签名方法二使用在线转换生成后进行上传
<a href="http://www.diyiziti.com/qianming" target="_blank">http://www.diyiziti.com/qianming</a>
</p>
</div>
<div class="margin-bottom-10 font-size-13 flex" style="margin-top: 10px">
<span class="gray-75 item-label">开启状态</span>
<a-switch v-model:checked="userInfo.signEnable" :checkedValue="1" :unCheckedValue="0" @change="handleEnableSignChange"></a-switch>
</div>
</div>
</div>
</div>
<UserAccountModal @register="registerModal" @success="getUserDetail"></UserAccountModal>
</template>
@ -73,7 +114,7 @@ import headerImg from '/@/assets/images/header.jpg';
import { defHttp } from '/@/utils/http/axios';
import { useUserStore } from '/@/store/modules/user';
import { uploadImg } from '/@/api/sys/upload';
import { getFileAccessHttpUrl } from '/@/utils/common/compUtils';
import { getFileAccessHttpUrl, getRandom } from '/@/utils/common/compUtils';
import dayjs from 'dayjs';
import { ajaxGetDictItems, getDictItemsByCode, initDictOptions } from '/@/utils/dict';
import { userEdit, getUserData, queryNameByCodes } from './UserSetting.api';
@ -81,6 +122,10 @@ import UserAccountModal from './commponents/UserAccountModal.vue';
import { useModal } from '/@/components/Modal';
import { cloneDeep } from 'lodash-es';
import { useDesign } from '/@/hooks/web/useDesign';
import { getToken } from "@/utils/auth";
import { uploadUrl } from "@/api/common/api";
import { UploadOutlined } from "@ant-design/icons-vue";
//TODO 当字典租户隔离时,数据会查不到,默认一个
const sexOption = getDictItemsByCode("sex") || [{text:'男',value:'1'},{text:'女',value:'2'}];
const { createMessage } = useMessage();
@ -97,6 +142,26 @@ const [registerModal, { openModal }] = useModal();
const avatar = computed(() => {
return getFileAccessHttpUrl(userInfo.value.avatar) || headerImg;
});
//headers
const uploadHeader = computed(() => {
let headers = {};
headers['X-Access-Token'] = getToken();
return headers;
});
const { createMessage: $message } = useMessage();
//上传列表
const uploadFileList = ref<any>([]);
//计算是否可以继续上传
const uploadVisible = computed(() => {
if(!uploadFileList){
return true;
}
return uploadFileList.value.length < 1;
});
//图片预览
const previewVisible = ref<boolean>(false);
//图片预览路径
const previewImage = ref<string>('');
/**
* 更新用户头像
@ -183,6 +248,7 @@ function openEditModal() {
* 获取用户信息
*/
function getUserDetail() {
uploadFileList.value = [];
getUserData().then((async res => {
if (res.success) {
if (res.result) {
@ -190,6 +256,20 @@ function getUserDetail() {
res.result.birthday = getBirthDay(res.result.birthday);
res.result.createTimeText = getDiffDay(res.result.createTime);
userInfo.value = res.result;
if(userInfo.value.sign){
let sign = userInfo.value.sign;
let url = getFileAccessHttpUrl(sign);
uploadFileList.value.push({
uid: getRandom(10),
name: getFileName(sign),
status: 'done',
url: url,
response: {
status: 'history',
message: sign,
},
})
}
} else {
userInfo.value = {};
}
@ -211,6 +291,112 @@ function getDiffDay(date) {
totalDays = Math.floor(diffDate / (1000 * 3600 * 24)) // 向下取整
return totalDays+" 天";
}
/**
* 上传图片之前进行验证
*
* @param file
*/
function beforeUpload({ file }) {
const isJpgOrPng = file.type === "image/jpeg" || file.type === "image/png" || file.type === "image/jpg";
if (!isJpgOrPng) {
$message.error("上传文件格式只能是jpg/png");
return false;
}
const isLimit = file.size / 1024 / 1024 < 1;
if (!isLimit) {
$message.error("上传图片大小不能超过 1MB!");
return false;
}
return true;
}
/**
* 上传成功事件
*/
function handleChange({ file, fileList }) {
if (file.status === 'error') {
createMessage.error(`${file.name} 上传失败.`);
}
if (file.status === 'done' && file.response.success === false) {
const failIndex = uploadFileList.value.findIndex((item) => item.uid === file.uid);
if (failIndex != -1) {
uploadFileList.value.splice(failIndex, 1);
}
createMessage.warning(file.response.message);
return;
}
if (file.status != 'uploading') {
fileList.forEach((file) => {
if (file.status === 'done') {
//上传成功事件
uploadSuccess(file.response.message);
}
});
if (file.status === 'removed') {
handleDelete();
}
}
}
/**
* 移除
*/
function handleDelete() {
updateUser({ sign: "", id: userInfo.value.id },"删除个性签名成功")
}
/**
* 上传成功事件
* @param url
*/
function uploadSuccess(url) {
updateUser({ sign: url, id: userInfo.value.id },"上传个性签名成功")
}
function updateUser(params,message) {
userEdit(params).then((res) => {
if(res.success){
createMessage.success(message);
}
});
}
/**
* 图片预览
* @param file
*/
function handlePreview(file) {
previewImage.value = file.url || file.thumbUrl;
previewVisible.value = true;
}
/**
* 获取文件名
* @param path
*/
function getFileName(path) {
if (path.lastIndexOf('\\') >= 0) {
let reg = new RegExp('\\\\', 'g');
path = path.replace(reg, '/');
}
return path.substring(path.lastIndexOf('/') + 1);
}
/**
* 图片预览关闭
*/
function handleCancel() {
previewVisible.value = false;
}
/**
* 个性签名开启状态更新
*/
function handleEnableSignChange() {
updateUser({ signEnable: userInfo.value.signEnable, id: userInfo.value.id },"修改成功")
}
onMounted(async () => {
getUserDetail();
});
@ -347,6 +533,19 @@ onMounted(async () => {
.font-size-13 {
font-size: 13px;
}
.ant-upload-select,.ant-upload-list-item-container{
width: 200px !important;
height: 80px !important;
}
.ant-upload-list-item-thumbnail .ant-upload-list-item-image {
object-fit: cover !important;
}
p{
margin-bottom: 5px;
}
.border-bottom{
border-bottom: 1px solid @border-color-base;
}
}
// update-end-author:liusq date:20230625 for: [issues/563]暗色主题部分失效
</style>