Page Menu
Home
Phabricator
Search
Configure Global Search
Log In
Files
F3357571
D6160.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
6 KB
Referenced Files
None
Subscribers
None
D6160.diff
View Options
diff --git a/web/sidebar/community-drawer-item-community.react.js b/web/sidebar/community-drawer-item-community.react.js
new file mode 100644
--- /dev/null
+++ b/web/sidebar/community-drawer-item-community.react.js
@@ -0,0 +1,25 @@
+// @flow
+
+import classnames from 'classnames';
+import * as React from 'react';
+
+import css from './community-drawer-item.css';
+import type { DrawerItemProps } from './community-drawer-item.react.js';
+import CommunityDrawerItem from './community-drawer-item.react.js';
+
+function CommunityDrawerItemCommunity(props: DrawerItemProps): React.Node {
+ const classes = classnames({
+ [css.communityBase]: true,
+ [css.communityExpanded]: props.expanded,
+ });
+ return (
+ <div className={classes}>
+ <CommunityDrawerItem {...props} />
+ </div>
+ );
+}
+
+const MemoizedCommunityDrawerItemCommunity: React.ComponentType<DrawerItemProps> = React.memo(
+ CommunityDrawerItemCommunity,
+);
+export default MemoizedCommunityDrawerItemCommunity;
diff --git a/web/sidebar/community-drawer-item.css b/web/sidebar/community-drawer-item.css
new file mode 100644
--- /dev/null
+++ b/web/sidebar/community-drawer-item.css
@@ -0,0 +1,66 @@
+.threadEntry {
+ display: flex;
+ flex-direction: row;
+ margin-top: 8px;
+ margin-bottom: 8px;
+}
+
+.threadListContainer {
+ display: flex;
+ flex-direction: column;
+}
+
+.titleWrapper {
+ overflow: hidden;
+}
+
+.title {
+ text-overflow: ellipsis;
+ white-space: nowrap;
+ overflow: hidden;
+ color: var(--drawer-item-color);
+ line-height: 24px;
+}
+
+.titleLevel0 {
+ font-size: var(--l-font-18);
+ font-weight: var(--semi-bold);
+}
+
+.titleLevel1,
+.titleLevel2 {
+ font-size: var(--m-font-16);
+ font-weight: var(--semi-bold);
+}
+
+.buttonContainer {
+ width: 24px;
+ align-items: center;
+ justify-content: center;
+ display: flex;
+}
+
+.chatItem {
+ margin-left: 16px;
+}
+
+.communityBase {
+ padding: 2px;
+ padding-right: 24px;
+ padding-left: 8px;
+ overflow: hidden;
+}
+
+.communityExpanded {
+ background-color: var(--drawer-open-community-bg);
+ border-top-right-radius: 8px;
+ border-bottom-right-radius: 8px;
+}
+
+.subchannelsButton {
+ margin-left: 24px;
+ margin-bottom: 6px;
+ margin-top: 4px;
+ display: flex;
+ align-items: center;
+}
diff --git a/web/sidebar/community-drawer-item.react.js b/web/sidebar/community-drawer-item.react.js
new file mode 100644
--- /dev/null
+++ b/web/sidebar/community-drawer-item.react.js
@@ -0,0 +1,135 @@
+// @flow
+
+import classnames from 'classnames';
+import * as React from 'react';
+
+import type { CommunityDrawerItemData } from 'lib/utils/drawer-utils.react.js';
+import { useResolvedThreadInfo } from 'lib/utils/entity-helpers.js';
+
+import css from './community-drawer-item.css';
+import { ExpandButton } from './expand-buttons.react.js';
+import SubchannelsButton from './subchannels-button.react.js';
+import { useSelector } from '../redux/redux-utils.js';
+import {
+ useOnClickThread,
+ useThreadIsActive,
+} from '../selectors/thread-selectors.js';
+
+export type DrawerItemProps = {
+ +itemData: CommunityDrawerItemData<string>,
+ +toggleExpanded: (threadID: string) => void,
+ +expanded: boolean,
+};
+
+function CommunityDrawerItem(props: DrawerItemProps): React.Node {
+ const {
+ itemData: { threadInfo, itemChildren, hasSubchannelsButton, labelStyle },
+ expanded,
+ toggleExpanded,
+ } = props;
+
+ const children = React.useMemo(() => {
+ if (!expanded) {
+ return null;
+ }
+ if (hasSubchannelsButton) {
+ return (
+ <div className={css.subchannelsButton}>
+ <SubchannelsButton threadInfo={threadInfo} />
+ </div>
+ );
+ }
+ if (!itemChildren) {
+ return null;
+ }
+ return itemChildren.map(item => (
+ <MemoizedCommunityDrawerItemChat
+ itemData={item}
+ key={item.threadInfo.id}
+ />
+ ));
+ }, [expanded, hasSubchannelsButton, itemChildren, threadInfo]);
+
+ const onExpandToggled = React.useCallback(
+ () => toggleExpanded(threadInfo.id),
+ [toggleExpanded, threadInfo.id],
+ );
+
+ const itemExpandButton = React.useMemo(() => {
+ if (itemChildren?.length === 0 && !hasSubchannelsButton) {
+ return (
+ <div className={css.buttonContainer}>
+ <ExpandButton disabled={true} />
+ </div>
+ );
+ }
+ return (
+ <div className={css.buttonContainer}>
+ <ExpandButton onClick={onExpandToggled} expanded={expanded} />
+ </div>
+ );
+ }, [itemChildren?.length, hasSubchannelsButton, onExpandToggled, expanded]);
+
+ const active = useThreadIsActive(threadInfo.id);
+ const isCreateMode = useSelector(
+ state => state.navInfo.chatMode === 'create',
+ );
+ const onClick = useOnClickThread(threadInfo);
+ const selectItemIfNotActiveCreation = React.useCallback(
+ (event: SyntheticEvent<HTMLAnchorElement>) => {
+ if (!isCreateMode || !active) {
+ onClick(event);
+ }
+ },
+ [isCreateMode, active, onClick],
+ );
+
+ const { uiName } = useResolvedThreadInfo(threadInfo);
+ const titleLabel = classnames(css.title, css[labelStyle]);
+
+ return (
+ <>
+ <div className={css.threadEntry}>
+ {itemExpandButton}
+ <a onClick={selectItemIfNotActiveCreation} className={css.titleWrapper}>
+ <div className={titleLabel}>{uiName}</div>
+ </a>
+ </div>
+ <div className={css.threadListContainer}>{children}</div>
+ </>
+ );
+}
+
+export type CommunityDrawerItemChatProps = {
+ +itemData: CommunityDrawerItemData<string>,
+};
+
+function CommunityDrawerItemChat(
+ props: CommunityDrawerItemChatProps,
+): React.Node {
+ const [expanded, setExpanded] = React.useState(false);
+
+ const toggleExpanded = React.useCallback(() => {
+ setExpanded(isExpanded => !isExpanded);
+ }, []);
+
+ return (
+ <div className={css.chatItem}>
+ <MemoizedCommunityDrawerItem
+ {...props}
+ expanded={expanded}
+ toggleExpanded={toggleExpanded}
+ />
+ </div>
+ );
+}
+
+const MemoizedCommunityDrawerItemChat: React.ComponentType<CommunityDrawerItemChatProps> = React.memo(
+ CommunityDrawerItemChat,
+);
+
+const MemoizedCommunityDrawerItem: React.ComponentType<DrawerItemProps> = React.memo(
+ CommunityDrawerItem,
+);
+
+export default MemoizedCommunityDrawerItem;
diff --git a/web/theme.css b/web/theme.css
--- a/web/theme.css
+++ b/web/theme.css
@@ -196,4 +196,6 @@
--purple-link: var(--violet-light-100);
--drawer-expand-button: var(--shades-black-60);
--drawer-expand-button-disabled: var(--shades-black-80);
+ --drawer-item-color: var(--shades-white-60);
+ --drawer-open-community-bg: #191919;
}
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Mon, Nov 25, 12:19 AM (21 h, 52 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
2577784
Default Alt Text
D6160.diff (6 KB)
Attached To
Mode
D6160: [web] Add drawer item implementations
Attached
Detach File
Event Timeline
Log In to Comment