-
Notifications
You must be signed in to change notification settings - Fork 13
Add pin column to all tables via shared PinButton #694
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
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -29,3 +29,41 @@ summary:hover { | |
| summary:focus { | ||
| outline: none; | ||
| } | ||
|
|
||
| /* The pin column button is only revealed when the row is hovered or the row is | ||
| pinned. The button's appearance lives in pinButton.css. */ | ||
| tbody tr .PinButton { | ||
| visibility: hidden; | ||
| } | ||
|
|
||
| tbody tr:hover .PinButton, | ||
| tbody tr .PinButton.pinned { | ||
| visibility: visible; | ||
| } | ||
|
Collaborator
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. btw While you are there, you can also fix a fun. When I added it, I did not think about conflicting styles so the background row highlight doesn't work for this column. So I would do something similar to before when we add a new value (eg. |
||
|
|
||
| /* The first two body columns (the pin column and the first data column) stay | ||
| pinned to the left edge while the table is scrolled horizontally. */ | ||
| td.alwaysVisible { | ||
| /* Pin column width, reused as the left offset of the second sticky column. */ | ||
| --pin-column-width: 2.75em; | ||
| position: sticky; | ||
| background-color: var(--color-background); | ||
| z-index: 5; /* ZIndex.TableStickyColumn */ | ||
| } | ||
|
|
||
| td.alwaysVisible:first-child { | ||
| left: 0; | ||
| box-sizing: border-box; | ||
| width: var(--pin-column-width); | ||
| min-width: var(--pin-column-width); | ||
| } | ||
|
|
||
| td.alwaysVisible:nth-child(2) { | ||
| left: var(--pin-column-width); | ||
| } | ||
|
|
||
| /* Sticky cells paint an opaque background that would otherwise hide the row | ||
| hover highlight, so re-apply the highlight to them while the row is hovered. */ | ||
| tbody tr:hover td.alwaysVisible { | ||
| background-color: var(--color-background-primary); | ||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -5,6 +5,7 @@ import usePageParams from '@features/params/usePageParams'; | |
|
|
||
| import { ObjectData } from '@entities/types/DataTypes'; | ||
|
|
||
| import { PinColumn } from './CommonColumns'; | ||
| import TableColumn from './TableColumn'; | ||
| import TableID from './TableID'; | ||
|
|
||
|
|
@@ -35,7 +36,10 @@ function useColumnVisibility<T extends ObjectData>( | |
| ); | ||
|
|
||
| const visibleColumns = useMemo( | ||
|
Collaborator
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. perfect |
||
| () => columns.filter((column) => columnVisibility[column.key]), | ||
| () => [ | ||
| PinColumn as TableColumn<T>, | ||
| ...columns.filter((column) => columnVisibility[column.key]), | ||
| ], | ||
| [columns, columnVisibility], | ||
| ); | ||
|
|
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -3,26 +3,29 @@ import React from 'react'; | |
|
|
||
| import HoverableButton from '@features/layers/hovercard/HoverableButton'; | ||
|
|
||
| import './pinButton.css'; | ||
|
|
||
| interface Props { | ||
| className?: string; | ||
| isPinned: boolean; | ||
| onTogglePin: () => void; | ||
| } | ||
|
|
||
| const CardPinButton: React.FC<Props> = ({ isPinned, onTogglePin }) => { | ||
| // The action on a pinned card is always to unpin it, so the label reflects that. | ||
| const PinButton: React.FC<Props> = ({ className, isPinned, onTogglePin }) => { | ||
|
Collaborator
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. great idea to generalize the pin button :) |
||
| // The action on a pinned item is always to unpin it, so the label reflects that. | ||
| const label = isPinned ? 'Unpin from the page' : 'Pin to the page'; | ||
|
|
||
| return ( | ||
| <HoverableButton | ||
| ariaLabel={label} | ||
| className={'CardPinButton' + (isPinned ? ' pinned' : '')} | ||
| className={'PinButton' + (isPinned ? ' pinned' : '') + (className ? ' ' + className : '')} | ||
| hoverContent={label} | ||
| onClick={onTogglePin} | ||
| > | ||
| <PinIcon className="CardPinButton-iconPin" size="1em" /> | ||
| <PinOffIcon className="CardPinButton-iconUnpin" size="1em" /> | ||
| <PinIcon className="PinButton-iconPin" size="1em" /> | ||
| <PinOffIcon className="PinButton-iconUnpin" size="1em" /> | ||
| </HoverableButton> | ||
| ); | ||
| }; | ||
|
|
||
| export default CardPinButton; | ||
| export default PinButton; | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,36 @@ | ||
| .PinButton { | ||
| padding: 0.25rem; | ||
| background: transparent; | ||
| border: none; | ||
| line-height: 0; | ||
| color: var(--color-text); | ||
| } | ||
|
|
||
| /* Keep the icon button transparent even when focused/hovered. Without this the | ||
| global `button:focus`/`button:hover` rules paint a blue background that lingers | ||
| (e.g. after clicking) until focus moves elsewhere. */ | ||
| .PinButton:hover, | ||
| .PinButton:focus { | ||
| background: transparent; | ||
| border-color: transparent; | ||
| color: var(--color-text); | ||
| } | ||
|
|
||
| .PinButton.pinned, | ||
| .PinButton.pinned:hover, | ||
| .PinButton.pinned:focus { | ||
| color: var(--color-button-primary); | ||
| } | ||
|
|
||
| /* Show the "unpin" affordance only while hovering an already-pinned button. */ | ||
| .PinButton-iconUnpin { | ||
| display: none; | ||
| } | ||
|
|
||
| .PinButton.pinned:hover .PinButton-iconPin { | ||
| display: none; | ||
| } | ||
|
|
||
| .PinButton.pinned:hover .PinButton-iconUnpin { | ||
| display: inline-block; | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -17,49 +17,17 @@ | |
| border-color: var(--color-button-primary); | ||
| } | ||
|
|
||
| .CardPinButton { | ||
| /* Position the shared pin button in the card's top-right corner. The button's | ||
| own appearance (colors, icon swap) lives in pinButton.css. */ | ||
| .CardInCardList .PinButton { | ||
|
Collaborator
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. great! |
||
| position: absolute; | ||
| top: 0.5rem; | ||
| right: 0.5rem; | ||
| padding: 0.25rem; | ||
| background: transparent; | ||
| border: none; | ||
| line-height: 0; | ||
| color: var(--color-text); | ||
| /* Hidden until the card is hovered (or the card is pinned, see below). */ | ||
| /* Hidden until the card is hovered (or the item is pinned, see below). */ | ||
| visibility: hidden; | ||
| } | ||
|
|
||
| .CardInCardList:hover .CardPinButton, | ||
| .CardPinButton.pinned { | ||
| .CardInCardList:hover .PinButton, | ||
| .CardInCardList .PinButton.pinned { | ||
| visibility: visible; | ||
| } | ||
|
|
||
| /* Keep the icon button transparent even when focused/hovered. Without this the | ||
| global `button:focus`/`button:hover` rules paint a blue background that lingers | ||
| (e.g. after clicking) until focus moves elsewhere. */ | ||
| .CardPinButton:hover, | ||
| .CardPinButton:focus { | ||
| background: transparent; | ||
| border-color: transparent; | ||
| color: var(--color-text); | ||
| } | ||
|
|
||
| .CardPinButton.pinned, | ||
| .CardPinButton.pinned:hover, | ||
| .CardPinButton.pinned:focus { | ||
| color: var(--color-button-primary); | ||
| } | ||
|
|
||
| /* Show the "unpin" affordance only while hovering an already-pinned button. */ | ||
| .CardPinButton-iconUnpin { | ||
| display: none; | ||
| } | ||
|
|
||
| .CardPinButton.pinned:hover .CardPinButton-iconPin { | ||
| display: none; | ||
| } | ||
|
|
||
| .CardPinButton.pinned:hover .CardPinButton-iconUnpin { | ||
| display: inline-block; | ||
| } | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah! I realize since it is always visible, it will be part of the table export. You should update
TableExportto omit the "Pin" column whenpinnedis empty.