فهرست منبع

feat: 可设置默认折叠侧边栏

1808837298@qq.com 2 سال پیش
والد
کامیت
a8f0c5dab2
6فایلهای تغییر یافته به همراه65 افزوده شده و 53 حذف شده
  1. 1 0
      common/constants.go
  2. 1 0
      controller/misc.go
  3. 4 1
      model/option.go
  4. 1 39
      web/src/App.js
  5. 12 1
      web/src/components/OperationSetting.js
  6. 46 12
      web/src/components/SiderBar.js

+ 1 - 0
common/constants.go

@@ -29,6 +29,7 @@ var DrawingEnabled = true
 var DataExportEnabled = true
 var DataExportEnabled = true
 var DataExportInterval = 5         // unit: minute
 var DataExportInterval = 5         // unit: minute
 var DataExportDefaultTime = "hour" // unit: minute
 var DataExportDefaultTime = "hour" // unit: minute
+var DefaultCollapseSidebar = false // default value of collapse sidebar
 
 
 // Any options with "Secret", "Token" in its key won't be return by GetOptions
 // Any options with "Secret", "Token" in its key won't be return by GetOptions
 
 

+ 1 - 0
controller/misc.go

@@ -38,6 +38,7 @@ func GetStatus(c *gin.Context) {
 			"enable_drawing":           common.DrawingEnabled,
 			"enable_drawing":           common.DrawingEnabled,
 			"enable_data_export":       common.DataExportEnabled,
 			"enable_data_export":       common.DataExportEnabled,
 			"data_export_default_time": common.DataExportDefaultTime,
 			"data_export_default_time": common.DataExportDefaultTime,
+			"default_collapse_sidebar": common.DefaultCollapseSidebar,
 			"enable_online_topup":      common.PayAddress != "" && common.EpayId != "" && common.EpayKey != "",
 			"enable_online_topup":      common.PayAddress != "" && common.EpayId != "" && common.EpayKey != "",
 		},
 		},
 	})
 	})

+ 4 - 1
model/option.go

@@ -82,6 +82,7 @@ func InitOptionMap() {
 	common.OptionMap["RetryTimes"] = strconv.Itoa(common.RetryTimes)
 	common.OptionMap["RetryTimes"] = strconv.Itoa(common.RetryTimes)
 	common.OptionMap["DataExportInterval"] = strconv.Itoa(common.DataExportInterval)
 	common.OptionMap["DataExportInterval"] = strconv.Itoa(common.DataExportInterval)
 	common.OptionMap["DataExportDefaultTime"] = common.DataExportDefaultTime
 	common.OptionMap["DataExportDefaultTime"] = common.DataExportDefaultTime
+	common.OptionMap["DefaultCollapseSidebar"] = strconv.FormatBool(common.DefaultCollapseSidebar)
 
 
 	common.OptionMapRWMutex.Unlock()
 	common.OptionMapRWMutex.Unlock()
 	loadOptionsFromDatabase()
 	loadOptionsFromDatabase()
@@ -138,7 +139,7 @@ func updateOptionMap(key string, value string) (err error) {
 			common.ImageDownloadPermission = intValue
 			common.ImageDownloadPermission = intValue
 		}
 		}
 	}
 	}
-	if strings.HasSuffix(key, "Enabled") {
+	if strings.HasSuffix(key, "Enabled") || key == "DefaultCollapseSidebar" {
 		boolValue := value == "true"
 		boolValue := value == "true"
 		switch key {
 		switch key {
 		case "PasswordRegisterEnabled":
 		case "PasswordRegisterEnabled":
@@ -171,6 +172,8 @@ func updateOptionMap(key string, value string) (err error) {
 			common.DrawingEnabled = boolValue
 			common.DrawingEnabled = boolValue
 		case "DataExportEnabled":
 		case "DataExportEnabled":
 			common.DataExportEnabled = boolValue
 			common.DataExportEnabled = boolValue
+		case "DefaultCollapseSidebar":
+			common.DefaultCollapseSidebar = boolValue
 		}
 		}
 	}
 	}
 	switch key {
 	switch key {

+ 1 - 39
web/src/App.js

@@ -29,7 +29,7 @@ const Home = lazy(() => import('./pages/Home'));
 const About = lazy(() => import('./pages/About'));
 const About = lazy(() => import('./pages/About'));
 function App() {
 function App() {
   const [userState, userDispatch] = useContext(UserContext);
   const [userState, userDispatch] = useContext(UserContext);
-  const [statusState, statusDispatch] = useContext(StatusContext);
+  // const [statusState, statusDispatch] = useContext(StatusContext);
 
 
   const loadUser = () => {
   const loadUser = () => {
     let user = localStorage.getItem('user');
     let user = localStorage.getItem('user');
@@ -38,47 +38,9 @@ function App() {
       userDispatch({ type: 'login', payload: data });
       userDispatch({ type: 'login', payload: data });
     }
     }
   };
   };
-  const loadStatus = async () => {
-    const res = await API.get('/api/status');
-    const { success, data } = res.data;
-    if (success) {
-      localStorage.setItem('status', JSON.stringify(data));
-      statusDispatch({ type: 'set', payload: data });
-      localStorage.setItem('system_name', data.system_name);
-      localStorage.setItem('logo', data.logo);
-      localStorage.setItem('footer_html', data.footer_html);
-      localStorage.setItem('quota_per_unit', data.quota_per_unit);
-      localStorage.setItem('display_in_currency', data.display_in_currency);
-      localStorage.setItem('enable_drawing', data.enable_drawing);
-      localStorage.setItem('enable_data_export', data.enable_data_export);
-      localStorage.setItem('data_export_default_time', data.data_export_default_time);
-      if (data.chat_link) {
-        localStorage.setItem('chat_link', data.chat_link);
-      } else {
-        localStorage.removeItem('chat_link');
-      }
-      if (data.chat_link2) {
-        localStorage.setItem('chat_link2', data.chat_link2);
-      } else {
-        localStorage.removeItem('chat_link2');
-      }
-      // if (
-      //   data.version !== process.env.REACT_APP_VERSION &&
-      //   data.version !== 'v0.0.0' &&
-      //   process.env.REACT_APP_VERSION !== ''
-      // ) {
-      //   showNotice(
-      //     `新版本可用:${data.version},请使用快捷键 Shift + F5 刷新页面`
-      //   );
-      // }
-    } else {
-      showError('无法正常连接至服务器!');
-    }
-  };
 
 
   useEffect(() => {
   useEffect(() => {
     loadUser();
     loadUser();
-    loadStatus().then();
     let systemName = getSystemName();
     let systemName = getSystemName();
     if (systemName) {
     if (systemName) {
       document.title = systemName;
       document.title = systemName;

+ 12 - 1
web/src/components/OperationSetting.js

@@ -27,6 +27,7 @@ const OperationSetting = () => {
         DataExportEnabled: '',
         DataExportEnabled: '',
         DataExportDefaultTime: 'hour',
         DataExportDefaultTime: 'hour',
         DataExportInterval: 5,
         DataExportInterval: 5,
+        DefaultCollapseSidebar: '', // 默认折叠侧边栏
         RetryTimes: 0
         RetryTimes: 0
     });
     });
     const [originInputs, setOriginInputs] = useState({});
     const [originInputs, setOriginInputs] = useState({});
@@ -65,6 +66,10 @@ const OperationSetting = () => {
         if (key.endsWith('Enabled')) {
         if (key.endsWith('Enabled')) {
             value = inputs[key] === 'true' ? 'false' : 'true';
             value = inputs[key] === 'true' ? 'false' : 'true';
         }
         }
+        if (key === 'DefaultCollapseSidebar') {
+            value = inputs[key] === 'true' ? 'false' : 'true';
+        }
+        console.log(key, value)
         const res = await API.put('/api/option/', {
         const res = await API.put('/api/option/', {
             key,
             key,
             value
             value
@@ -79,7 +84,7 @@ const OperationSetting = () => {
     };
     };
 
 
     const handleInputChange = async (e, {name, value}) => {
     const handleInputChange = async (e, {name, value}) => {
-        if (name.endsWith('Enabled') || name === 'DataExportInterval' || name === 'DataExportDefaultTime') {
+        if (name.endsWith('Enabled') || name === 'DataExportInterval' || name === 'DataExportDefaultTime' || name === 'DefaultCollapseSidebar') {
             if (name === 'DataExportDefaultTime') {
             if (name === 'DataExportDefaultTime') {
                 localStorage.setItem('data_export_default_time', value);
                 localStorage.setItem('data_export_default_time', value);
             }
             }
@@ -243,6 +248,12 @@ const OperationSetting = () => {
                             name='DrawingEnabled'
                             name='DrawingEnabled'
                             onChange={handleInputChange}
                             onChange={handleInputChange}
                         />
                         />
+                        <Form.Checkbox
+                          checked={inputs.DefaultCollapseSidebar === 'true'}
+                          label='默认折叠侧边栏'
+                          name='DefaultCollapseSidebar'
+                          onChange={handleInputChange}
+                        />
                     </Form.Group>
                     </Form.Group>
                     <Form.Button onClick={() => {
                     <Form.Button onClick={() => {
                         submitConfig('general').then();
                         submitConfig('general').then();

+ 46 - 12
web/src/components/SiderBar.js

@@ -1,8 +1,8 @@
-import React, {useContext, useMemo, useState} from 'react';
+import React, { useContext, useEffect, useLayoutEffect, useMemo, useState } from 'react';
 import {Link, useNavigate} from 'react-router-dom';
 import {Link, useNavigate} from 'react-router-dom';
 import {UserContext} from '../context/User';
 import {UserContext} from '../context/User';
 
 
-import {API, getLogo, getSystemName, isAdmin, isMobile, showSuccess} from '../helpers';
+import { API, getLogo, getSystemName, isAdmin, isMobile, showError, showSuccess } from '../helpers';
 import '../index.css';
 import '../index.css';
 
 
 import {
 import {
@@ -24,11 +24,14 @@ import {Nav, Avatar, Dropdown, Layout} from '@douyinfe/semi-ui';
 
 
 const SiderBar = () => {
 const SiderBar = () => {
     const [userState, userDispatch] = useContext(UserContext);
     const [userState, userDispatch] = useContext(UserContext);
+    const defaultIsCollapsed = isMobile() || localStorage.getItem('default_collapse_sidebar') === 'true';
+
     let navigate = useNavigate();
     let navigate = useNavigate();
     const [selectedKeys, setSelectedKeys] = useState(['home']);
     const [selectedKeys, setSelectedKeys] = useState(['home']);
-    const [showSidebar, setShowSidebar] = useState(false);
     const systemName = getSystemName();
     const systemName = getSystemName();
     const logo = getLogo();
     const logo = getLogo();
+    const [isCollapsed, setIsCollapsed] = useState(defaultIsCollapsed);
+
     const headerButtons = useMemo(() => [
     const headerButtons = useMemo(() => [
         {
         {
             text: '首页',
             text: '首页',
@@ -110,15 +113,41 @@ const SiderBar = () => {
         // }
         // }
     ], [localStorage.getItem('enable_data_export'), localStorage.getItem('enable_drawing'), localStorage.getItem('chat_link'), isAdmin()]);
     ], [localStorage.getItem('enable_data_export'), localStorage.getItem('enable_drawing'), localStorage.getItem('chat_link'), isAdmin()]);
 
 
+    const loadStatus = async () => {
+        const res = await API.get('/api/status');
+        const { success, data } = res.data;
+        if (success) {
+            localStorage.setItem('status', JSON.stringify(data));
+            // statusDispatch({ type: 'set', payload: data });
+            localStorage.setItem('system_name', data.system_name);
+            localStorage.setItem('logo', data.logo);
+            localStorage.setItem('footer_html', data.footer_html);
+            localStorage.setItem('quota_per_unit', data.quota_per_unit);
+            localStorage.setItem('display_in_currency', data.display_in_currency);
+            localStorage.setItem('enable_drawing', data.enable_drawing);
+            localStorage.setItem('enable_data_export', data.enable_data_export);
+            localStorage.setItem('data_export_default_time', data.data_export_default_time);
+            localStorage.setItem('default_collapse_sidebar', data.default_collapse_sidebar);
+            if (data.chat_link) {
+                localStorage.setItem('chat_link', data.chat_link);
+            } else {
+                localStorage.removeItem('chat_link');
+            }
+            if (data.chat_link2) {
+                localStorage.setItem('chat_link2', data.chat_link2);
+            } else {
+                localStorage.removeItem('chat_link2');
+            }
+        } else {
+            showError('无法正常连接至服务器!');
+        }
+    };
 
 
-    async function logout() {
-        setShowSidebar(false);
-        await API.get('/api/user/logout');
-        showSuccess('注销成功!');
-        userDispatch({type: 'logout'});
-        localStorage.removeItem('user');
-        navigate('/login');
-    }
+    useEffect(() => {
+        loadStatus().then(() => {
+            setIsCollapsed(isMobile() || localStorage.getItem('default_collapse_sidebar') === 'true');
+        });
+    },[])
 
 
     return (
     return (
         <>
         <>
@@ -127,7 +156,12 @@ const SiderBar = () => {
                     <Nav
                     <Nav
                         // mode={'horizontal'}
                         // mode={'horizontal'}
                         // bodyStyle={{ height: 100 }}
                         // bodyStyle={{ height: 100 }}
-                        defaultIsCollapsed={isMobile()}
+                        defaultIsCollapsed={isMobile() || localStorage.getItem('default_collapse_sidebar') === 'true'}
+                        isCollapsed={isCollapsed}
+                        onCollapseChange={collapsed => {
+                            console.log(collapsed);
+                            setIsCollapsed(collapsed);
+                        }}
                         selectedKeys={selectedKeys}
                         selectedKeys={selectedKeys}
                         renderWrapper={({itemElement, isSubNav, isInSubNav, props}) => {
                         renderWrapper={({itemElement, isSubNav, isInSubNav, props}) => {
                             const routerMap = {
                             const routerMap = {