Skip to content

Commit

Permalink
✨ feat: improve pin mode about session group (#369)
Browse files Browse the repository at this point in the history
* 🚧 wip: add pin group

* 💄 style: improve styles

* ✨ feat: improve pin mode session group
  • Loading branch information
arvinxx authored Oct 27, 2023
1 parent e78d893 commit 75c5883
Show file tree
Hide file tree
Showing 13 changed files with 106 additions and 41 deletions.
14 changes: 12 additions & 2 deletions src/app/chat/(desktop)/features/SessionList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,15 +7,25 @@ import FolderPanel from '@/features/FolderPanel';
import SessionListContent from '../../features/SessionListContent';
import Header from './SessionHeader';

const useStyles = createStyles(({ stylish }) => stylish.noScrollbar);
const useStyles = createStyles(({ stylish, css, cx }) =>
cx(
stylish.noScrollbar,
css`
padding: 0 6px;
display: flex;
flex-direction: column;
gap: 2px;
`,
),
);

const Sessions = memo(() => {
const { styles } = useStyles();

return (
<FolderPanel>
<Header />
<DraggablePanelBody className={styles} style={{ padding: 0 }}>
<DraggablePanelBody className={styles}>
<SessionListContent />
</DraggablePanelBody>
</FolderPanel>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,10 @@ import { memo } from 'react';

const useStyles = createStyles(({ css, prefixCls, token }) => ({
container: css`
border-radius: 0;
.${prefixCls}-collapse-header {
padding-inline: 16px !important;
color: ${token.colorTextDescription} !important;
border-radius: 8px !important;
&:hover {
color: ${token.colorText} !important;
Expand Down
2 changes: 1 addition & 1 deletion src/app/chat/features/SessionListContent/Inbox/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ const Inbox = memo(() => {
active={mobile ? false : activeId === INBOX_SESSION_ID}
avatar={avatarRender}
ref={ref}
style={{ alignItems: 'center' }}
style={{ alignItems: 'center', borderRadius: 8 }}
title={t('inbox.title')}
/>
</Link>
Expand Down
33 changes: 18 additions & 15 deletions src/app/chat/features/SessionListContent/List/Item/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ const useStyles = createStyles(({ css }) => {
return {
container: css`
position: relative;
border-radius: 8px;
`,

modalRoot: css`
Expand Down Expand Up @@ -96,21 +97,23 @@ const SessionItem = memo<SessionItemProps>(({ id }) => {
);

return (
<Item
actions={actions}
// needn't active state in mobile
active={mobile ? false : active}
addon={addon}
avatar={avatarRender}
className={styles.container}
date={updateAt}
description={description || systemRole}
loading={loading}
pin={pin}
ref={ref}
showAction={open || isHovering}
title={title}
/>
<Flexbox paddingBlock={1}>
<Item
actions={actions}
// needn't active state in mobile
active={mobile ? false : active}
addon={addon}
avatar={avatarRender}
className={styles.container}
date={updateAt}
description={description || systemRole}
loading={loading}
pin={pin}
ref={ref}
showAction={open || isHovering}
title={title}
/>
</Flexbox>
);
}, shallow);

Expand Down
13 changes: 7 additions & 6 deletions src/app/chat/features/SessionListContent/List/index.tsx
Original file line number Diff line number Diff line change
@@ -1,12 +1,11 @@
import { createStyles, useResponsive } from 'antd-style';
import isEqual from 'fast-deep-equal';
import Link from 'next/link';
import { memo } from 'react';
import LazyLoad from 'react-lazy-load';

import { SESSION_CHAT_URL } from '@/const/url';
import { useSessionHydrated, useSessionStore } from '@/store/session';
import { sessionSelectors } from '@/store/session/selectors';
import { LobeAgentSession } from '@/types/session';

import AddButton from './AddButton';
import SessionItem from './Item';
Expand All @@ -18,8 +17,10 @@ const useStyles = createStyles(
`,
);

const SessionList = memo(() => {
const list = useSessionStore(sessionSelectors.sessionList, isEqual);
interface SessionListProps {
dataSource: LobeAgentSession[];
}
const SessionList = memo<SessionListProps>(({ dataSource }) => {
const [activeSession, switchSession] = useSessionStore((s) => [s.activeSession, s.switchSession]);
const { styles } = useStyles();
const isInit = useSessionHydrated();
Expand All @@ -28,8 +29,8 @@ const SessionList = memo(() => {

return !isInit ? (
<SkeletonList />
) : list.length > 0 ? (
list.map(({ id }) => (
) : dataSource.length > 0 ? (
dataSource.map(({ id }) => (
<LazyLoad className={styles} key={id}>
<Link
aria-label={id}
Expand Down
50 changes: 37 additions & 13 deletions src/app/chat/features/SessionListContent/index.tsx
Original file line number Diff line number Diff line change
@@ -1,28 +1,52 @@
import { CollapseProps } from 'antd';
import { memo, useMemo } from 'react';
import isEqual from 'fast-deep-equal';
import { memo } from 'react';
import { useTranslation } from 'react-i18next';

import { preferenceSelectors, useGlobalStore } from '@/store/global';
import { useSessionStore } from '@/store/session';
import { sessionSelectors } from '@/store/session/selectors';

import CollapseGroup from './CollapseGroup';
import Inbox from './Inbox';
import SessionList from './List';

const SessionListContent = memo(() => {
const { t } = useTranslation('common');
const items: CollapseProps['items'] = useMemo(
() => [
{
children: <SessionList />,
key: 'sessionList',
label: t('sessionList'),
},
],
[],
);
const { t } = useTranslation('chat');
const unpinnedSessionList = useSessionStore(sessionSelectors.unpinnedSessionList, isEqual);
const pinnedList = useSessionStore(sessionSelectors.pinnedSessionList, isEqual);
const hasPinnedSessionList = useSessionStore(sessionSelectors.hasPinnedSessionList);

const [sessionGroupKeys, updatePreference] = useGlobalStore((s) => [
preferenceSelectors.sessionGroupKeys(s),
s.updatePreference,
]);

const items = [
hasPinnedSessionList && {
children: <SessionList dataSource={pinnedList} />,
key: 'pinned',
label: t('pin'),
},
{
children: <SessionList dataSource={unpinnedSessionList} />,
key: 'sessionList',
label: t('sessionList'),
},
].filter(Boolean) as CollapseProps['items'];

return (
<>
<Inbox />
<CollapseGroup defaultActiveKey={['sessionList']} items={items} />
<CollapseGroup
activeKey={sessionGroupKeys}
items={items}
onChange={(keys) => {
const sessionGroupKeys = typeof keys === 'string' ? [keys] : keys;

updatePreference({ sessionGroupKeys });
}}
/>
</>
);
});
Expand Down
4 changes: 3 additions & 1 deletion src/locales/default/chat.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,14 @@ export default {
newAgent: '新建助手',
noDescription: '暂无描述',

pin: '置顶',
pinOff: '取消置顶',
regenerate: '重新生成',

roleAndArchive: '角色与记录',
searchAgentPlaceholder: '搜索助手和对话...',
send: '发送',
sendPlaceholder: '输入聊天内容...',
sessionList: '助手列表',
shareModal: {
download: '下载截图',
imageType: '图片格式',
Expand Down
3 changes: 1 addition & 2 deletions src/locales/default/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,14 +45,14 @@ export default {
noDescription: '暂无描述',
ok: '确定',
password: '密码',

pin: '置顶',
pinOff: '取消置顶',
regenerate: '重新生成',
rename: '重命名',
reset: '重置',
retry: '重试',
send: '发送',
sessionList: '助手列表',
setting: '设置',
share: '分享',
stop: '停止',
Expand All @@ -62,7 +62,6 @@ export default {
setting: '设置',
},
temp: '临时',

updateAgent: '更新助理信息',
upgradeVersion: {
action: '立即升级',
Expand Down
2 changes: 2 additions & 0 deletions src/store/global/initialState.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ export interface GlobalPreference {
guide?: Guide;
inputHeight: number;
mobileShowTopic?: boolean;
sessionGroupKeys: string[];
sessionsWidth: number;
showChatSideBar?: boolean;
showSessionPanel?: boolean;
Expand Down Expand Up @@ -49,6 +50,7 @@ export const initialState: GlobalState = {
guide: {},
inputHeight: 200,
mobileShowTopic: false,
sessionGroupKeys: ['pinned', 'sessionList'],
sessionsWidth: 320,
showChatSideBar: true,
showSessionPanel: true,
Expand Down
1 change: 1 addition & 0 deletions src/store/global/selectors.ts
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
export * from './selectors/preference';
export * from './selectors/settings';
10 changes: 10 additions & 0 deletions src/store/global/selectors/preference.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import { GlobalStore } from '@/store/global';

import { initialState } from '../initialState';

const sessionGroupKeys = (s: GlobalStore): string[] =>
s.preference.sessionGroupKeys || initialState.preference.sessionGroupKeys;

export const preferenceSelectors = {
sessionGroupKeys: sessionGroupKeys,
};
6 changes: 6 additions & 0 deletions src/store/session/slices/session/selectors/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,11 @@ import {
currentSessionSafe,
getSessionById,
getSessionMetaById,
hasPinnedSessionList,
hasSessionList,
pinnedSessionList,
sessionList,
unpinnedSessionList,
} from './list';

const isInboxSession = (s: SessionStore) => s.activeId === INBOX_SESSION_ID;
Expand All @@ -21,7 +24,10 @@ export const sessionSelectors = {
getExportAgent,
getSessionById,
getSessionMetaById,
hasPinnedSessionList,
hasSessionList,
isInboxSession,
pinnedSessionList,
sessionList,
unpinnedSessionList,
};
7 changes: 7 additions & 0 deletions src/store/session/slices/session/selectors/list.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,17 @@ export const sessionList = (s: SessionStore) => {
});
};

export const pinnedSessionList = (s: SessionStore) => sessionList(s).filter((s) => s.pinned);
export const unpinnedSessionList = (s: SessionStore) => sessionList(s).filter((s) => !s.pinned);

export const hasSessionList = (s: SessionStore) => {
const list = sessionList(s);
return list?.length > 0;
};
export const hasPinnedSessionList = (s: SessionStore) => {
const list = pinnedSessionList(s);
return list?.length > 0;
};

export const getSessionById =
(id: string) =>
Expand Down

0 comments on commit 75c5883

Please sign in to comment.