Commit 82defef6 by chengming

header增加消息跑马灯

parent 14388ef9
File added
...@@ -216,3 +216,210 @@ ...@@ -216,3 +216,210 @@
background: #FBB9BC; background: #FBB9BC;
} }
} }
// 跑马灯样式
.marqueeContainer {
display: flex;
align-items: center;
flex: 1;
margin: 0 20px;
height: 100%;
overflow: hidden;
border-radius: 4px;
padding: 0 12px;
.marqueeIcon {
color: #ff6b6b;
font-size: 18px;
margin-right: 12px;
flex-shrink: 0;
animation: bellRing 2s infinite;
}
.marqueeContent {
flex: 1;
height: 100%;
display: flex;
align-items: center;
.marqueeCarousel {
width: 100%;
height: 24px;
line-height: 24px;
:global {
.slick-list {
height: 24px;
}
.slick-track {
height: 24px;
}
.slick-slide {
height: 24px !important;
line-height: 24px !important;
text-align: left;
background: transparent;
border: none;
}
}
}
.marqueeItem {
display: flex;
align-items: center;
height: 24px;
line-height: 24px;
font-size: 14px;
color: #495057;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
font-weight: 500;
.marqueeType {
color: #ffffff;
background: #ff6b6b;
padding: 2px 6px;
border-radius: 3px;
margin-right: 10px;
font-weight: 600;
font-size: 12px;
min-width: 40px;
text-align: center;
}
.marqueeName {
margin-right: 15px;
font-weight: 600;
color: #212529;
max-width: 180px;
overflow: hidden;
text-overflow: ellipsis;
background: linear-gradient(90deg, #212529 0%, #495057 100%);
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
}
.marqueeCreator {
margin-right: 15px;
color: #6c757d;
font-weight: 500;
background: #f8f9fa;
padding: 1px 6px;
border-radius: 3px;
border: 1px solid #e9ecef;
}
.marqueeTime {
color: #868e96;
font-weight: 500;
background: linear-gradient(90deg, #868e96 0%, #adb5bd 100%);
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
}
}
}
}
// 铃铛动画
@keyframes bellRing {
0%, 100% {
transform: rotate(0deg);
}
25% {
transform: rotate(-10deg);
}
75% {
transform: rotate(10deg);
}
}
// 跑马灯悬停效果
.marqueeContainer:hover {
.marqueeIcon {
color: #ff5252;
animation-duration: 1s;
}
}
// 空状态样式
.marqueeItem:only-child {
justify-content: center;
color: #6c757d;
font-style: italic;
width: 100%;
&:before {
content: "📢 ";
margin-right: 5px;
}
}
// 响应式适配
@media (max-width: 1200px) {
.marqueeContainer {
.marqueeContent {
.marqueeItem {
.marqueeName {
max-width: 120px;
}
.marqueeCreator {
display: none;
}
}
}
}
}
@media (max-width: 992px) {
.marqueeContainer {
margin: 0 10px;
padding: 0 8px;
.marqueeContent {
.marqueeItem {
.marqueeTime {
display: none;
}
.marqueeName {
max-width: 100px;
}
}
}
}
}
@media (max-width: 768px) {
.marqueeContainer {
display: none;
}
}
// 特殊类型颜色
.marqueeItem .marqueeType[data-type="考试"] {
background: #4ecdc4;
}
.marqueeItem .marqueeType[data-type="投票"] {
background: #45b7d1;
}
.marqueeItem .marqueeType[data-type="信箱"] {
background: #96ceb4;
}
.marqueeItem .marqueeType[data-type="活动"] {
background: #feca57;
}
.marqueeItem .marqueeType[data-type="投稿"] {
background: #ff9ff3;
}
.marqueeItem .marqueeType[data-type="留言"] {
background: #54a0ff;
}
\ No newline at end of file
...@@ -3,4 +3,5 @@ export default { ...@@ -3,4 +3,5 @@ export default {
siteLanguagePageApi: `GET ${services.webManage}/siteLanguage/public/page`, siteLanguagePageApi: `GET ${services.webManage}/siteLanguage/public/page`,
publicLanguageGetApi: `GET ${services.webManage}/international/public/language/get`, publicLanguageGetApi: `GET ${services.webManage}/international/public/language/get`,
selectLanguageSaveApi: `GET ${services.webManage}/siteLanguage/record/international/selectLanguage/save`, selectLanguageSaveApi: `GET ${services.webManage}/siteLanguage/record/international/selectLanguage/save`,
getPromptScrollDataApi: `POST ${services.webManage}/prompt/scroll/data`,
}; };
\ No newline at end of file
import React, { PureComponent } from "react"; import React, { PureComponent } from "react";
import { withRouter } from "react-router-dom"; import { withRouter } from "react-router-dom";
import { connect } from "react-redux";
import PropTypes from "prop-types"; import PropTypes from "prop-types";
import { Tooltip, Dropdown, Menu, Icon, Layout, Avatar } from "antd"; import { Tooltip, Dropdown, Menu, Icon, Layout, Avatar, Carousel } from "antd";
import classnames from "classnames"; import classnames from "classnames";
import styles from "./Header.less"; import styles from "./Header.less";
import SelectLang from "./SelectLang"; import SelectLang from "./SelectLang";
import { getPromptScrollData } from "./redux/actions";
{ {
/* bug-11961-cwj暂时注释 2期上 */ /* bug-11961-cwj暂时注释 2期上 */
} }
...@@ -15,13 +17,74 @@ import headerLogo from "../../../static/imgs/1logo.png"; ...@@ -15,13 +17,74 @@ import headerLogo from "../../../static/imgs/1logo.png";
class Header extends PureComponent { class Header extends PureComponent {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = {}; this.state = {
scrollData: {
examList: [],
voteManagement: [],
mailboxManagement: [],
activityManagement: [],
submissionManagement: [],
messageManagement: []
}
};
} }
componentDidMount() {}
componentDidMount() {
this.fetchScrollData();
}
fetchScrollData = () => {
const { getPromptScrollData } = this.props;
getPromptScrollData({}, (res) => {
if (res && res.data) {
this.setState({
scrollData: res.data
});
}
});
};
handleClickMenu = e => { handleClickMenu = e => {
e.key === "SignOut" && this.props.onSignOut(); e.key === "SignOut" && this.props.onSignOut();
}; };
// 渲染跑马灯内容
renderMarqueeContent = () => {
const { scrollData } = this.state;
const allItems = [
...scrollData.examList.map(item => ({ ...item, type: '考试' })),
...scrollData.voteManagement.map(item => ({ ...item, type: '投票' })),
...scrollData.mailboxManagement.map(item => ({ ...item, type: '信箱' })),
...scrollData.activityManagement.map(item => ({ ...item, type: '活动' })),
...scrollData.submissionManagement.map(item => ({ ...item, type: '投稿' })),
...scrollData.messageManagement.map(item => ({ ...item, type: '留言' }))
];
if (allItems.length === 0) {
return (
<div className={styles.marqueeItem}>
暂无最新消息
</div>
);
}
return allItems.map((item, index) => (
<div key={index} className={styles.marqueeItem}>
<span
className={styles.marqueeType}
data-type={item.type}
>
[{item.type}]
</span>
<span className={styles.marqueeName}>{item.name}</span>
<span className={styles.marqueeCreator}>创建人:{item.createByName}</span>
<span className={styles.marqueeTime}>
时间:{new Date(item.createTime).toLocaleString()}
</span>
</div>
));
};
render() { render() {
const { const {
fixed, fixed,
...@@ -34,6 +97,7 @@ class Header extends PureComponent { ...@@ -34,6 +97,7 @@ class Header extends PureComponent {
menus, menus,
onToAss, onToAss,
} = this.props; } = this.props;
// 站点选择 // 站点选择
const siteMenu = ( const siteMenu = (
<Menu onClick={onHandleMenuClick}> <Menu onClick={onHandleMenuClick}>
...@@ -42,6 +106,7 @@ class Header extends PureComponent { ...@@ -42,6 +106,7 @@ class Header extends PureComponent {
))} ))}
</Menu> </Menu>
); );
// 个人选择 // 个人选择
const menu = ( const menu = (
<Menu className={styles.menu}> <Menu className={styles.menu}>
...@@ -56,6 +121,7 @@ class Header extends PureComponent { ...@@ -56,6 +121,7 @@ class Header extends PureComponent {
</Menu.Item> </Menu.Item>
</Menu> </Menu>
); );
// 是否开通了社群 // 是否开通了社群
let associationButton = false; let associationButton = false;
let hasAssociation = menus.filter(item => item.name === "社群"); let hasAssociation = menus.filter(item => item.name === "社群");
...@@ -71,52 +137,21 @@ class Header extends PureComponent { ...@@ -71,52 +137,21 @@ class Header extends PureComponent {
})} })}
id="layoutHeader" id="layoutHeader"
> >
<div> <div className={styles.marqueeContainer}>
{/* {collapsed && ( <Icon type="sound" className={styles.marqueeIcon} />
<div <div className={styles.marqueeContent}>
className={styles.button} <Carousel
onClick={onCollapseChange.bind(this, !collapsed)} autoplay
vertical
dots={false}
className={styles.marqueeCarousel}
> >
<Icon {this.renderMarqueeContent()}
type={classnames({ </Carousel>
"menu-unfold": collapsed, </div>
"menu-fold": !collapsed,
})}
/>
</div>
)} */}
{/* <div className={styles.logo}>
<img
className={styles.image}
// src={nav.logo ? nav.logo : headerLogo}
src={headerLogo}
/>
</div> */}
</div> </div>
<div className={styles.rightContainer}> <div className={styles.rightContainer}>
{/* bug-11961-cwj暂时注释 2期上 */}
{/* <Icon type="folder-open" style={{ padding: "0 12px" }} /> */}
{/* 语言 */}
{/* bug-11961-cwj暂时注释 2期上 */}
{/* <SelectLang className={styles.action} /> */}
{/* {associationButton && (
<a className={styles.assDiv} onClick={onToAss.bind(this)}>
<div className={styles.iconDiv}>
<Icon style={{ color: "white" }} type="home" />
</div>
<div className={styles.assText}>社群平台</div>
</a>
)} */}
{/* <Tooltip title={"使用帮助"}>
<a
target="_blank"
href="http://help.fairyclass.cn/hc/"
rel="noopener noreferrer"
className={styles.action}
>
<Icon type="question-circle-o" />
</a>
</Tooltip> */}
<Tooltip title={"站点切换"}> <Tooltip title={"站点切换"}>
<Dropdown <Dropdown
overlay={siteMenu} overlay={siteMenu}
...@@ -154,6 +189,16 @@ Header.propTypes = { ...@@ -154,6 +189,16 @@ Header.propTypes = {
collapsed: PropTypes.bool, collapsed: PropTypes.bool,
onSignOut: PropTypes.func, onSignOut: PropTypes.func,
onCollapseChange: PropTypes.func, onCollapseChange: PropTypes.func,
getPromptScrollData: PropTypes.func,
};
// 连接redux
const mapStateToProps = (state) => ({
// 如果需要从redux state中获取数据,可以在这里添加
});
const mapDispatchToProps = {
getPromptScrollData,
}; };
export default withRouter(Header); export default connect(mapStateToProps, mapDispatchToProps)(withRouter(Header));
\ No newline at end of file
...@@ -4,7 +4,8 @@ import api from "../api"; ...@@ -4,7 +4,8 @@ import api from "../api";
const { const {
siteLanguagePageApi, siteLanguagePageApi,
publicLanguageGetApi, publicLanguageGetApi,
selectLanguageSaveApi selectLanguageSaveApi,
getPromptScrollDataApi,
} = api; } = api;
// 设置语音 // 设置语音
export function langageActions(parms) { export function langageActions(parms) {
...@@ -55,3 +56,13 @@ export function selectLanguageSave(data, callback) { ...@@ -55,3 +56,13 @@ export function selectLanguageSave(data, callback) {
}); });
}; };
} }
export function getPromptScrollData(data, callback) {
return dispath => {
return request({
url: getPromptScrollDataApi,
data: data,
}).then(res => {
if (callback) callback(res);
});
};
}
\ No newline at end of file
...@@ -55,7 +55,6 @@ export function exfetchR(data, cb, check) { ...@@ -55,7 +55,6 @@ export function exfetchR(data, cb, check) {
const authRole = res?.data?.authRole || []; const authRole = res?.data?.authRole || [];
if (authRole.length > 0) { if (authRole.length > 0) {
userPermissions = JSON.stringify(authRole.map(role => role.code)); userPermissions = JSON.stringify(authRole.map(role => role.code));
console.log('userPermissions222222222222222222', userPermissions)
window.localStorage.setItem("userPermissions", userPermissions); window.localStorage.setItem("userPermissions", userPermissions);
}else{ }else{
window.localStorage.setItem("userPermissions", userPermissions); window.localStorage.setItem("userPermissions", userPermissions);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment