2022-05-24 16:17:09 +10:00
|
|
|
import { useAtom } from "jotai";
|
|
|
|
|
|
|
|
|
|
import { Tooltip, IconButton } from "@mui/material";
|
|
|
|
|
import SortDescIcon from "@mui/icons-material/ArrowDownward";
|
2022-05-30 13:26:57 +10:00
|
|
|
import IconSlash, {
|
|
|
|
|
ICON_SLASH_STROKE_DASHOFFSET,
|
|
|
|
|
} from "@src/components/IconSlash";
|
2022-05-24 16:17:09 +10:00
|
|
|
|
|
|
|
|
import { tableScope, tableOrdersAtom } from "@src/atoms/tableScope";
|
|
|
|
|
import { FieldType } from "@src/constants/fields";
|
|
|
|
|
import { getFieldProp } from "@src/components/fields";
|
|
|
|
|
|
|
|
|
|
import { ColumnConfig } from "@src/types/table";
|
|
|
|
|
|
2022-05-26 19:31:56 +10:00
|
|
|
import { colord, extend } from "colord";
|
|
|
|
|
import mixPlugin from "colord/plugins/lch";
|
|
|
|
|
extend([mixPlugin]);
|
|
|
|
|
|
2022-05-24 16:17:09 +10:00
|
|
|
const SORT_STATES = ["none", "desc", "asc"] as const;
|
|
|
|
|
|
|
|
|
|
export interface IColumnHeaderSortProps {
|
|
|
|
|
column: ColumnConfig;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
export default function ColumnHeaderSort({ column }: IColumnHeaderSortProps) {
|
|
|
|
|
const [tableOrders, setTableOrders] = useAtom(tableOrdersAtom, tableScope);
|
|
|
|
|
|
|
|
|
|
const _sortKey = getFieldProp("sortKey", (column as any).type);
|
|
|
|
|
const sortKey = _sortKey ? `${column.key}.${_sortKey}` : column.key;
|
|
|
|
|
|
|
|
|
|
const currentSort: typeof SORT_STATES[number] =
|
|
|
|
|
tableOrders[0]?.key !== sortKey
|
|
|
|
|
? "none"
|
|
|
|
|
: tableOrders[0]?.direction || "none";
|
|
|
|
|
const nextSort =
|
|
|
|
|
SORT_STATES[SORT_STATES.indexOf(currentSort) + 1] ?? SORT_STATES[0];
|
|
|
|
|
|
|
|
|
|
const handleSortClick = () => {
|
|
|
|
|
if (nextSort === "none") setTableOrders([]);
|
|
|
|
|
else setTableOrders([{ key: sortKey, direction: nextSort }]);
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
if (column.type === FieldType.id) return null;
|
|
|
|
|
|
|
|
|
|
return (
|
|
|
|
|
<Tooltip
|
|
|
|
|
title={nextSort === "none" ? "Unsort" : `Sort by ${nextSort}ending`}
|
|
|
|
|
>
|
|
|
|
|
<IconButton
|
|
|
|
|
disableFocusRipple={true}
|
|
|
|
|
size="small"
|
|
|
|
|
onClick={handleSortClick}
|
|
|
|
|
color="inherit"
|
|
|
|
|
sx={{
|
2022-05-26 19:31:56 +10:00
|
|
|
bgcolor: "background.default",
|
|
|
|
|
"&:hover": {
|
|
|
|
|
backgroundColor: (theme) =>
|
|
|
|
|
colord(theme.palette.background.default)
|
|
|
|
|
.mix(
|
|
|
|
|
theme.palette.action.hover,
|
|
|
|
|
theme.palette.action.hoverOpacity
|
|
|
|
|
)
|
|
|
|
|
.alpha(1)
|
|
|
|
|
.toHslString(),
|
2022-05-26 19:59:59 +10:00
|
|
|
|
2022-05-30 13:26:57 +10:00
|
|
|
"& .icon-slash-mask": {
|
2022-05-26 19:59:59 +10:00
|
|
|
stroke: (theme) =>
|
|
|
|
|
colord(theme.palette.background.default)
|
|
|
|
|
.mix(
|
|
|
|
|
theme.palette.action.hover,
|
|
|
|
|
theme.palette.action.hoverOpacity
|
|
|
|
|
)
|
|
|
|
|
.alpha(1)
|
|
|
|
|
.toHslString(),
|
|
|
|
|
},
|
2022-05-26 19:31:56 +10:00
|
|
|
},
|
|
|
|
|
|
2022-05-24 16:17:09 +10:00
|
|
|
position: "relative",
|
|
|
|
|
opacity: currentSort !== "none" ? 1 : 0,
|
|
|
|
|
".column-header:hover &": { opacity: 1 },
|
|
|
|
|
|
|
|
|
|
transition: (theme) =>
|
2022-05-26 19:59:59 +10:00
|
|
|
theme.transitions.create(["background-color", "opacity"], {
|
|
|
|
|
duration: theme.transitions.duration.short,
|
|
|
|
|
}),
|
|
|
|
|
|
|
|
|
|
"& .arrow": {
|
|
|
|
|
transition: (theme) =>
|
|
|
|
|
theme.transitions.create("transform", {
|
2022-05-24 16:17:09 +10:00
|
|
|
duration: theme.transitions.duration.short,
|
2022-05-26 19:59:59 +10:00
|
|
|
}),
|
2022-05-24 16:17:09 +10:00
|
|
|
|
2022-05-26 19:59:59 +10:00
|
|
|
transform: currentSort === "asc" ? "rotate(180deg)" : "none",
|
|
|
|
|
},
|
|
|
|
|
"&:hover .arrow": {
|
2022-05-24 16:17:09 +10:00
|
|
|
transform:
|
|
|
|
|
currentSort === "asc" || nextSort === "asc"
|
|
|
|
|
? "rotate(180deg)"
|
|
|
|
|
: "none",
|
|
|
|
|
},
|
|
|
|
|
|
2022-05-30 13:26:57 +10:00
|
|
|
"& .icon-slash": {
|
|
|
|
|
strokeDashoffset:
|
|
|
|
|
currentSort === "none" ? 0 : ICON_SLASH_STROKE_DASHOFFSET,
|
2022-05-26 19:59:59 +10:00
|
|
|
},
|
2022-05-30 13:26:57 +10:00
|
|
|
"&:hover .icon-slash": {
|
|
|
|
|
strokeDashoffset:
|
|
|
|
|
nextSort === "none" ? 0 : ICON_SLASH_STROKE_DASHOFFSET,
|
2022-05-26 19:59:59 +10:00
|
|
|
},
|
2022-05-24 16:17:09 +10:00
|
|
|
}}
|
|
|
|
|
>
|
2022-05-30 14:06:19 +10:00
|
|
|
<div style={{ position: "relative" }}>
|
|
|
|
|
<SortDescIcon className="arrow" />
|
|
|
|
|
<IconSlash />
|
|
|
|
|
</div>
|
2022-05-24 16:17:09 +10:00
|
|
|
</IconButton>
|
|
|
|
|
</Tooltip>
|
|
|
|
|
);
|
|
|
|
|
}
|