-
Notifications
You must be signed in to change notification settings - Fork 144
feat(table): align table design in fe #2102
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Closed
Closed
Changes from 37 commits
Commits
Show all changes
57 commits
Select commit
Hold shift + click to select a range
a08069c
fix(table): set table-body-sort-bg per design spec
Fiona2016 5ff8a6d
fix(table): force header nowrap per design rule §5
Fiona2016 ee0c0cc
fix(table): default pageSize 15 on alert-mutes / alert-subscribes / j…
Fiona2016 1d3dedc
fix(alert-subscribes): combine name + business group into Column1
Fiona2016 f06da5e
fix(alert-mutes): collapse name + datasource type + business group in…
Fiona2016 53afed2
fix(job-tpls): collapse title + ID + business group into Column1
Fiona2016 efa0f94
fix(job-tasks): collapse title + ID + business group into Column1
Fiona2016 3d661d8
fix(users): collapse identity columns into Column1
Fiona2016 f5b951b
fix(alert-rules): collapse name + cate + business group + severity in…
Fiona2016 69be9a3
fix(table): consolidate row actions into overflow menus
Fiona2016 44bce41
fix(table): use overflow menus on route list pages
Fiona2016 412fdac
fix(table): collapse remaining menu route actions
Fiona2016 ad19f99
feat(table): add shared action dropdown
Fiona2016 194da29
fix(table): align ai config actions
Fiona2016 0555ce2
fix(table): align notification actions
Fiona2016 e44a95f
fix(table): align alert event actions
Fiona2016 2fc3e1f
fix(table): align builtin component actions
Fiona2016 77a7986
fix(table): align data route actions
Fiona2016 d39465f
fix(table): align task and user actions
Fiona2016 e5b4a5b
fix(table): forward action dropdown trigger events
Fiona2016 573387d
Merge remote-tracking branch 'origin/main' into feat-table-design-srm…
Fiona2016 84b5a39
Merge remote-tracking branch 'origin/main' into feat-table-design-srm…
Fiona2016 439d4f1
refactor(table): compact primary list metadata columns
Fiona2016 d29310e
feat(table): refine users list primary column
Fiona2016 920cd99
feat(table): refine sorter interaction
Fiona2016 1934313
feat(table): unify route table tags
Fiona2016 0871dc4
style(table): align sorted column body bg with header
Fiona2016 1d4e465
fix(table): keep fixed cells opaque
Fiona2016 fab7e0a
feat(table): fix route table action columns
Fiona2016 617fcfe
fix(table): remove measure-row collapse and tune fixed-column edge
Fiona2016 73b5a4c
fix(table): stabilize task table layouts
Fiona2016 552d2b4
fix(table): refine dropdown interactions and sorter style
Fiona2016 46c0542
fix(table): align sorter icon with title
Fiona2016 8142e2e
fix(table): use fill-2-5 for sorted column bg
Fiona2016 dad392d
fix(table): remove sorted column color override
Fiona2016 f74a5cc
feat(alerts): add event tag collapse toggle
Fiona2016 5de23be
fix(table): apply acceptance feedback on 0517
Fiona2016 0691219
feat(table): normalize table action dropdown alignment and trigger
jsers 60ac063
fix(table): comment out selected row styles to prevent fixed column b…
jsers 1a8f2d9
feat(alertRules): replace event count column icons with Tags component
jsers 79c38e1
refactor(tags): relocate Tags component to shared directory and adopt…
jsers 3bf95de
feat(alertRules): replace TableTags with generic Tags and add severit…
jsers a53ed5c
refactor(alertRules): render null instead of '-' for empty datasource…
jsers d27dde7
refactor(table): unify table styling and Tags component usage
jsers 5338bb0
refactor(table): unify tag rendering and replace TableTags with Tags …
jsers 0d17533
refactor: add explicit type annotations to callback parameters
jsers e6cd901
Merge remote-tracking branch 'origin/main' into feat-table-design-srm…
Fiona2016 1cd69fa
Merge remote-tracking branch 'origin/main' into feat-table-design-srm…
Fiona2016 b781a7c
fix(table): add shared sorter icon theme
Fiona2016 130e222
fix(table): use move icons for sorted columns
Fiona2016 20498d2
fix(table): scope sorter icon style to accepted tables
Fiona2016 f4dd39e
fix(table): opt in sortable fe tables
Fiona2016 5977c84
Revert "fix(table): opt in sortable fe tables"
Fiona2016 4ae5372
fix(table): use global sorter icon theme
Fiona2016 1076c25
fix(table): collapse remaining row actions into dropdown
Fiona2016 fdc085c
feat(table): surface frequent row actions as inline icons beside the …
Fiona2016 45825fb
Merge pull request #2117 from n9e/feat-table-action-expose-0531
Fiona2016 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,77 @@ | ||
| import React from 'react'; | ||
| import { Button } from 'antd'; | ||
| import type { ButtonProps } from 'antd/lib/button'; | ||
| import { | ||
| CheckCircle, | ||
| Copy, | ||
| ExternalLink, | ||
| Eye, | ||
| Link as LinkIcon, | ||
| MoreVertical, | ||
| Network, | ||
| Pencil, | ||
| Play, | ||
| Search, | ||
| Settings, | ||
| ShieldCheck, | ||
| Sparkles, | ||
| Trash2, | ||
| } from 'lucide-react'; | ||
| import classNames from 'classnames'; | ||
| import { Link, LinkProps } from 'react-router-dom'; | ||
|
|
||
| const tableActionIconMap = { | ||
| default: CheckCircle, | ||
| edit: Pencil, | ||
| view: Eye, | ||
| settings: Settings, | ||
| access: Network, | ||
| permission: ShieldCheck, | ||
| copy: Copy, | ||
| delete: Trash2, | ||
| run: Play, | ||
| search: Search, | ||
| open: ExternalLink, | ||
| link: LinkIcon, | ||
| ai: Sparkles, | ||
| }; | ||
|
|
||
| export type TableActionIconName = keyof typeof tableActionIconMap; | ||
|
|
||
| export function TableActionIcon({ name }: { name: TableActionIconName }) { | ||
| const Icon = tableActionIconMap[name]; | ||
| return <Icon className='fc-table-action-menu-icon' />; | ||
| } | ||
|
|
||
| interface TableActionButtonProps extends Omit<ButtonProps, 'icon'> { | ||
| actionIcon?: TableActionIconName; | ||
| icon?: React.ReactNode; | ||
| } | ||
|
|
||
| export function TableActionButton({ actionIcon, icon, className, type = 'link', ...rest }: TableActionButtonProps) { | ||
| return ( | ||
| <Button | ||
| type={type} | ||
| className={classNames('fc-table-action-menu-button', className)} | ||
| icon={icon || (actionIcon ? <TableActionIcon name={actionIcon} /> : undefined)} | ||
| {...rest} | ||
| /> | ||
| ); | ||
| } | ||
|
|
||
| interface TableActionLinkProps extends LinkProps { | ||
| actionIcon?: TableActionIconName; | ||
| } | ||
|
|
||
| export function TableActionLink({ actionIcon, className, children, ...rest }: TableActionLinkProps) { | ||
| return ( | ||
| <Link className={classNames('fc-table-action-menu-link', className)} {...rest}> | ||
| {actionIcon && <TableActionIcon name={actionIcon} />} | ||
| <span>{children}</span> | ||
| </Link> | ||
| ); | ||
| } | ||
|
|
||
| export const TableActionTrigger = React.forwardRef<HTMLElement, ButtonProps>(function TableActionTrigger({ type = 'text', icon, ...rest }, ref) { | ||
| return <Button ref={ref as any} type={type} icon={icon || <MoreVertical size={16} />} {...rest} />; | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,126 @@ | ||
| import React from 'react'; | ||
| import { Popover, Tooltip } from 'antd'; | ||
| import { Link } from 'react-router-dom'; | ||
| import type { LinkProps } from 'react-router-dom'; | ||
| import _ from 'lodash'; | ||
|
|
||
| import './style.less'; | ||
|
|
||
| export interface TableTagItem { | ||
| key?: React.Key; | ||
| label: React.ReactNode; | ||
| tooltip?: React.ReactNode; | ||
| to?: LinkProps['to']; | ||
| onClick?: () => void; | ||
| } | ||
|
|
||
| interface Props<T = any> { | ||
| data?: T[]; | ||
| maxVisible?: number; | ||
| maxTagWidth?: number | string; | ||
| emptyText?: React.ReactNode; | ||
| getKey?: (item: T, index: number) => React.Key; | ||
| getLabel?: (item: T, index: number) => React.ReactNode; | ||
| getTooltip?: (item: T, index: number) => React.ReactNode; | ||
| getLinkTo?: (item: T, index: number) => LinkProps['to'] | undefined; | ||
| linkTarget?: string; | ||
| onTagClick?: (item: T, index: number) => void; | ||
| } | ||
|
|
||
| function getDefaultLabel(item: any) { | ||
| if (_.isObject(item) && 'label' in item) { | ||
| return item.label; | ||
| } | ||
| return item; | ||
| } | ||
|
|
||
| function getDefaultKey(item: any, index: number): React.Key { | ||
| if (_.isObject(item) && 'key' in item && item.key !== undefined) { | ||
| return item.key as React.Key; | ||
| } | ||
| return `${getDefaultLabel(item)}-${index}`; | ||
| } | ||
|
|
||
| function isEmptyLabel(label: React.ReactNode) { | ||
| return label === undefined || label === null || label === ''; | ||
| } | ||
|
|
||
| export default function TableTags<T = any>(props: Props<T>) { | ||
| const { data, maxVisible = 2, maxTagWidth = 160, emptyText = '-', getKey, getLabel, getTooltip, getLinkTo, linkTarget, onTagClick } = props; | ||
| const items = _.filter(data || [], (item, index) => !isEmptyLabel(getLabel ? getLabel(item, index) : getDefaultLabel(item))); | ||
|
|
||
| if (_.isEmpty(items)) { | ||
| return <>{emptyText}</>; | ||
| } | ||
|
|
||
| const getItemLabel = (item: T, index: number) => (getLabel ? getLabel(item, index) : getDefaultLabel(item)); | ||
| const getItemTooltip = (item: T, index: number) => { | ||
| if (getTooltip) return getTooltip(item, index); | ||
| if (_.isObject(item) && 'tooltip' in (item as any)) return (item as any).tooltip; | ||
| return getItemLabel(item, index); | ||
| }; | ||
| const getItemLinkTo = (item: T, index: number) => { | ||
| if (getLinkTo) return getLinkTo(item, index); | ||
| if (_.isObject(item) && 'to' in (item as any)) return (item as any).to; | ||
| return undefined; | ||
| }; | ||
|
|
||
| const renderTag = (item: T, index: number, inPopover = false) => { | ||
| const label = getItemLabel(item, index); | ||
| const tooltip = getItemTooltip(item, index); | ||
| const linkTo = getItemLinkTo(item, index); | ||
| const clickable = !!linkTo || !!onTagClick || (_.isObject(item) && 'onClick' in (item as any)); | ||
| const style: React.CSSProperties = { | ||
| maxWidth: inPopover ? 320 : maxTagWidth, | ||
| }; | ||
| const tag = ( | ||
| <span | ||
| className={`fc-table-tag${clickable ? ' fc-table-tag-clickable' : ''}`} | ||
| style={style} | ||
| onClick={(e) => { | ||
| e.stopPropagation(); | ||
| if (_.isObject(item) && 'onClick' in (item as any)) { | ||
| (item as any).onClick?.(); | ||
| } | ||
| onTagClick?.(item, index); | ||
| }} | ||
|
Comment on lines
+80
to
+86
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Avoid blocking row click for non-interactive tags.
Suggested fix- <span
+ <span
className={`fc-table-tag${clickable ? ' fc-table-tag-clickable' : ''}`}
style={style}
- onClick={(e) => {
- e.stopPropagation();
- if (_.isObject(item) && 'onClick' in (item as any)) {
- (item as any).onClick?.();
- }
- onTagClick?.(item, index);
- }}
+ onClick={
+ clickable
+ ? (e) => {
+ e.stopPropagation();
+ if (_.isObject(item) && 'onClick' in (item as any)) {
+ (item as any).onClick?.();
+ }
+ onTagClick?.(item, index);
+ }
+ : undefined
+ }
>🤖 Prompt for AI Agents |
||
| > | ||
| {label} | ||
| </span> | ||
| ); | ||
|
|
||
| const content = linkTo ? ( | ||
| <Link to={linkTo} target={linkTarget} onClick={(e) => e.stopPropagation()}> | ||
| {tag} | ||
| </Link> | ||
| ) : ( | ||
| tag | ||
| ); | ||
|
|
||
| return ( | ||
| <Tooltip key={String(getKey ? getKey(item, index) : getDefaultKey(item, index))} title={tooltip}> | ||
| {content} | ||
| </Tooltip> | ||
| ); | ||
| }; | ||
|
|
||
| const visibleItems = items.slice(0, maxVisible); | ||
| const overflowItems = items.slice(maxVisible); | ||
|
|
||
| return ( | ||
| <div className='fc-table-tags'> | ||
| {visibleItems.map((item, index) => renderTag(item, index))} | ||
| {overflowItems.length > 0 && ( | ||
| <Popover | ||
| placement='topLeft' | ||
| overlayClassName='fc-table-tags-popover' | ||
| content={<div className='fc-table-tags-popover-content'>{items.map((item, index) => renderTag(item, index, true))}</div>} | ||
| > | ||
| <span className='fc-table-tag fc-table-tag-overflow' onClick={(e) => e.stopPropagation()}> | ||
| +{overflowItems.length} | ||
| </span> | ||
| </Popover> | ||
| )} | ||
| </div> | ||
| ); | ||
| } | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,50 @@ | ||
| .fc-table-tags { | ||
| display: inline-flex; | ||
| max-width: 100%; | ||
| align-items: center; | ||
| gap: 4px; | ||
| white-space: nowrap; | ||
| } | ||
|
|
||
| .fc-table-tag { | ||
| display: inline-block; | ||
| height: 22px; | ||
| max-width: 160px; | ||
| padding: 0 8px; | ||
| overflow: hidden; | ||
| color: var(--fc-text-2); | ||
| font-size: 12px; | ||
| font-weight: 400; | ||
| line-height: 20px; | ||
| text-overflow: ellipsis; | ||
| white-space: nowrap; | ||
| vertical-align: middle; | ||
| background: var(--fc-fill-2-5); | ||
| border: 1px solid var(--fc-border-color); | ||
| border-radius: 4px; | ||
| cursor: default; | ||
| } | ||
|
|
||
| .fc-table-tag-overflow { | ||
| color: var(--fc-text-3); | ||
| cursor: pointer; | ||
| background: var(--fc-fill-3); | ||
| } | ||
|
|
||
| .fc-table-tag-clickable { | ||
| cursor: pointer; | ||
| } | ||
|
|
||
| .fc-table-tag-clickable:hover, | ||
| .fc-table-tag-overflow:hover { | ||
| color: var(--fc-text-1); | ||
| background: var(--fc-fill-3); | ||
| border-color: var(--fc-border-color-hover, var(--fc-border-color)); | ||
| } | ||
|
|
||
| .fc-table-tags-popover-content { | ||
| display: flex; | ||
| max-width: 360px; | ||
| flex-wrap: wrap; | ||
| gap: 6px; | ||
| } |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.