8000 feat(web): replace account up/down buttons with drag-and-drop sorting by InfinityPacer · Pull Request #61 · InfinityPacer/meterleaf · GitHub
[go: up one dir, main page]

Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 15 additions & 4 deletions bun.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion docs/reporting.md
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@

账户管理都在总览的账户区完成,手机首页相同。

- 点击标题右侧的「排序」后,每个账户下方出现上移和下移按钮,点「完成」结束。新账户追加在末尾。
- 点击标题右侧的「排序」后,每个账户右侧出现拖拽手柄,可直接拖动账户或使用方向键调整顺序,点「完成」结束。新账户追加在末尾。
- 每个账户右侧的「⋯」菜单提供合并额度与用量、重命名、设置套餐、归档和删除。设置套餐只对 Claude 账户显示。
- 同一账号从多个来源采集时,在来源账户菜单选择「合并额度与用量」,选定目标账户后确认。全部历史及后续用量都会归入目标,原来源记录仍可在请求明细查看,不做跨来源去重;若两个来源都记录了同一次请求,会累计两次。同一额度窗口使用最新快照,百分比不会相加,未知或到期状态仍如实显示。目标账户的名称和套餐保留。
- 在目标账户的「合并额度与用量」弹窗查看已合并账户,点击「解除合并」恢复各自展示。原始记录不删除,同步不会覆盖合并关系;连续合并多个账户时,解除某一层也会带回合并到它的账户。合并和解除后报表需要重新计算,数据较多时稍等片刻。
Expand Down
3 changes: 3 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,9 @@
},
"dependencies": {
"@base-ui/react": "^1.8.0",
"@dnd-kit/core": "^6.3.1",
"@dnd-kit/sortable": "^10.0.0",
"@dnd-kit/utilities": "^3.2.2",
"@fastify/static": "^10.1.3",
"@fontsource-variable/geist": "^5.3.0",
"@tanstack/react-query": "^5.102.8",
Expand Down
112 changes: 53 additions & 59 deletions src/web/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,6 @@ import { Menu as ActionMenu } from "@base-ui/react/menu";
import {
Activity,
ArrowRight,
ArrowUp,
ArrowDown,
Archive,
ArchiveRestore,
Trash2,
Expand Down Expand Up @@ -90,9 +88,14 @@ import {
import { accountFilterOptions } from "./lib/account-filter";
import {
isEmptyAccount,
moveAccount,
orderedAccounts,
reorderAccount,
} from "./lib/account-order";
import {
AccountDragHandle,
SortableAccountItem,
SortableAccountList,
} from "./components/AccountSortable";
import { useAccountArchive } from "./lib/use-account-archive";
import { accountInitial, withAccountAliases } from "./lib/account-aliases";
import { planBadge } from "./lib/plan";
Expand Down Expand Up @@ -546,6 +549,7 @@ function OverviewQuotas({
onShowArchived,
editingOrder,
onEditingOrder,
onReorderAccount,
asOf,
onOpen,
onRequests,
Expand All @@ -560,6 +564,7 @@ function OverviewQuotas({
onShowArchived: (show: boolean) => void;
editingOrder: boolean;
onEditingOrder: (editing: boolean) => void;
onReorderAccount: (activeId: string, overId: string) => void;
asOf: string;
onOpen: (account: LedgerAccount) => void;
onRequests: (account: LedgerAccount) => void;
Expand All @@ -568,6 +573,7 @@ function OverviewQuotas({
usdBasis: UsdBasis;
compactUsage?: boolean;
}) {
const sorting = editingOrder && !showArchived;
return (
<section
className="overview-quotas"
Expand All @@ -591,29 +597,35 @@ function OverviewQuotas({
className="account-list"
aria-label={showArchived ? "已归档账户列表" : "账户额度摘要"}
>
{accounts.map((account) => (
<div
className="account-list-item"
key={account.id}
data-account-id={account.id}
data-manageable
>
<AccountRow
account={account}
asOf={asOf}
archived={showArchived}
usdBasis={usdBasis}
compactUsage={compactUsage}
usage={accountUsage?.[account.id]}
=>
!showArchived && (account.fiveHour || account.sevenDay)
? onOpen(account)
: onRequests(account)
}
/>
{renderActions(account)}
</div>
))}
<SortableAccountList
accounts={accounts}
enabled={sorting}
>
>
{accounts.map((account) => (
<SortableAccountItem
className="account-list-item"
key={account.id}
id={account.id}
enabled={sorting}
>
<AccountRow
account={account}
asOf={asOf}
archived={showArchived}
usdBasis={usdBasis}
compactUsage={compactUsage}
usage={accountUsage?.[account.id]}
=>
!showArchived && (account.fiveHour || account.sevenDay)
? onOpen(account)
: onRequests(account)
}
/>
{renderActions(account)}
</SortableAccountItem>
))}
</SortableAccountList>
{!accounts.length && (
<p className="empty-chart">
{showArchived ? "暂无归档账户" : "暂无账户"}
Expand Down Expand Up @@ -885,43 +897,22 @@ export function App() {
setEditingAccountOrder(false);
setShowArchived(show);
};
/** 账户区每行的排序按钮与管理菜单,Web 总览和手机首页共用。 */
const reorderVisibleAccount = (activeId: string, overId: string) => {
setAccountOrder(
reorderAccount(
sortedAccounts.map((value) => value.id),
activeId,
overId,
(id) => !archivedIds.has(id),
),
);
};
/** 账户区每行的拖拽手柄与管理菜单,Web 总览和手机首页共用。 */
const renderAccountActions = (account: LedgerAccount) => {
const position = activeAccounts.indexOf(account);
return (
<>
{editingAccountOrder && !showArchived && (
<div
className="account-order-actions"
aria-label={`${account.name} 排序`}
>
{([-1, 1] as const).map((direction) => (
<Button
key={direction}
variant="ghost"
size="icon"
aria-label={`${direction === -1 ? "上移" : "下移"} ${account.name}`}
title={direction === -1 ? "上移账户" : "下移账户"}
disabled={!activeAccounts[position + direction]}
=>
setAccountOrder(
moveAccount(
sortedAccounts.map((value) => value.id),
account.id,
direction,
(id) => !archivedIds.has(id),
),
)
}
>
{direction === -1 ? (
<ArrowUp size={18} />
) : (
<ArrowDown size={18} />
)}
</Button>
))}
</div>
<AccountDragHandle name={account.name} />
)}
<ActionMenu.Root>
<ActionMenu.Trigger
Expand Down Expand Up @@ -1545,6 +1536,8 @@ export function App() {
>
=> openAccountRequests(account.id)}
showArchived={showArchived}
editingOrder={editingAccountOrder}
>
renderAccountActions={renderAccountActions}
accountHeadingActions={
<AccountHeadingActions
Expand Down Expand Up @@ -1581,6 +1574,7 @@ export function App() {
>
editingOrder={editingAccountOrder}
>
>
asOf={quotaAsOf}
accountUsage={snapshot?.view.accountUsage}
compactUsage={smallScreen}
Expand Down
Loading
Loading
0