mirror of
https://github.com/getpaseo/paseo.git
synced 2026-10-24 18:22:38 +00:00
fix(app): make compact git actions menu-only
Keep compact toolbars narrow and require users to choose potentially consequential Git and workspace actions from the menu.
This commit is contained in:
@@ -838,25 +838,36 @@ test("desktop Changes toggles a navigation tree beside the expanded diff documen
|
||||
await testInfo.attach("changes-toolbar", { path: screenshot, contentType: "image/png" });
|
||||
});
|
||||
|
||||
test("compact Changes keeps its options control touch-sized", async ({ page }) => {
|
||||
test("compact Changes keeps its actions compact and menu-only", async ({ page }) => {
|
||||
const workspace = await createWorkspaceWithMountedTabDiff();
|
||||
await useUnwrappedDiffLines(page);
|
||||
await openWorkspaceChanges(page, workspace);
|
||||
await page.setViewportSize({ width: 480, height: 900 });
|
||||
|
||||
const actions = page.getByTestId("changes-actions-menu-trigger").filter({ visible: true });
|
||||
const options = page.getByRole("button", { name: "Diff options" }).filter({ visible: true });
|
||||
const [optionsBox, glyphBox] = await Promise.all([
|
||||
const [actionsBox, optionsBox, glyphBox] = await Promise.all([
|
||||
actions.boundingBox(),
|
||||
options.boundingBox(),
|
||||
options.locator("svg").boundingBox(),
|
||||
]);
|
||||
if (!optionsBox || !glyphBox) {
|
||||
throw new Error("Compact Changes options geometry could not be measured");
|
||||
if (!actionsBox || !optionsBox || !glyphBox) {
|
||||
throw new Error("Compact Changes toolbar geometry could not be measured");
|
||||
}
|
||||
expect(actionsBox.width).toBe(48);
|
||||
expect(actionsBox.height).toBe(28);
|
||||
expect(optionsBox.width).toBe(32);
|
||||
expect(optionsBox.height).toBe(32);
|
||||
expect(glyphBox.width).toBe(18);
|
||||
expect(glyphBox.height).toBe(18);
|
||||
|
||||
await expect(actions).not.toContainText("Commit");
|
||||
await expect(actions.locator("svg")).toHaveCount(2);
|
||||
await actions.click();
|
||||
await expect(page.getByTestId("changes-primary-cta-menu")).toBeVisible();
|
||||
await expect(page.getByTestId("changes-menu-commit")).toContainText("Commit");
|
||||
await page.keyboard.press("Escape");
|
||||
|
||||
await options.click();
|
||||
const wrapLines = page.getByText("Wrap long lines", { exact: true });
|
||||
await expect(wrapLines).toBeVisible();
|
||||
|
||||
@@ -2,7 +2,7 @@ import { LoadingSpinner } from "@/components/ui/loading-spinner";
|
||||
import { useCallback, useMemo } from "react";
|
||||
import { View, Text, Pressable, type PressableStateCallbackType } from "react-native";
|
||||
import { StyleSheet, useUnistyles } from "react-native-unistyles";
|
||||
import { ChevronDown, MoreVertical } from "lucide-react-native";
|
||||
import { ChevronDown, GitBranch, MoreVertical } from "lucide-react-native";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import {
|
||||
DropdownMenu,
|
||||
@@ -22,6 +22,7 @@ import { buttonControlHeight } from "@/components/ui/control-geometry";
|
||||
interface GitActionsSplitButtonProps {
|
||||
gitActions: GitActions;
|
||||
hideLabels?: boolean;
|
||||
menuOnly?: boolean;
|
||||
}
|
||||
|
||||
interface GitActionMenuItemProps {
|
||||
@@ -74,7 +75,11 @@ function GitActionMenuItem({
|
||||
);
|
||||
}
|
||||
|
||||
export function GitActionsSplitButton({ gitActions, hideLabels }: GitActionsSplitButtonProps) {
|
||||
export function GitActionsSplitButton({
|
||||
gitActions,
|
||||
hideLabels,
|
||||
menuOnly = false,
|
||||
}: GitActionsSplitButtonProps) {
|
||||
const { theme } = useUnistyles();
|
||||
const { t } = useTranslation();
|
||||
const runGitAction = useGitActionRunner();
|
||||
@@ -115,6 +120,62 @@ export function GitActionsSplitButton({ gitActions, hideLabels }: GitActionsSpli
|
||||
[theme.colors.surface2],
|
||||
);
|
||||
|
||||
const menuOnlyTriggerStyle = useCallback(
|
||||
({ hovered, pressed, open }: { hovered: boolean; pressed: boolean; open: boolean }) => [
|
||||
styles.menuOnlyTrigger,
|
||||
(hovered || pressed || open) &&
|
||||
inlineUnistylesStyle({ backgroundColor: theme.colors.surface2 }),
|
||||
],
|
||||
[theme.colors.surface2],
|
||||
);
|
||||
|
||||
const menuOnlyActions = useMemo(
|
||||
() => [
|
||||
...(gitActions.primary ? [gitActions.primary] : []),
|
||||
...gitActions.secondary,
|
||||
...gitActions.menu,
|
||||
],
|
||||
[gitActions.menu, gitActions.primary, gitActions.secondary],
|
||||
);
|
||||
|
||||
if (menuOnly) {
|
||||
if (menuOnlyActions.length === 0) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return (
|
||||
<DropdownMenu>
|
||||
<DropdownMenuTrigger
|
||||
testID="changes-actions-menu-trigger"
|
||||
style={menuOnlyTriggerStyle}
|
||||
accessibilityRole="button"
|
||||
accessibilityLabel={t("workspace.header.actions.workspaceActions")}
|
||||
>
|
||||
<GitBranch size={16} color={theme.colors.foregroundMuted} />
|
||||
<ChevronDown size={12} color={theme.colors.foregroundMuted} />
|
||||
</DropdownMenuTrigger>
|
||||
<DropdownMenuContent align="end" testID="changes-primary-cta-menu">
|
||||
{menuOnlyActions.map((action, index) => (
|
||||
<GitActionMenuItem
|
||||
key={action.id}
|
||||
action={action}
|
||||
onSelect={runGitAction}
|
||||
archiveShortcutKeys={archiveShortcutKeys}
|
||||
needsSeparator={action.startsGroup}
|
||||
showSeparator={index > 0}
|
||||
closeOnSelect={
|
||||
action.status === "idle" &&
|
||||
action.id === "pr" &&
|
||||
action.label === action.pendingLabel &&
|
||||
action.label === action.successLabel
|
||||
}
|
||||
/>
|
||||
))}
|
||||
</DropdownMenuContent>
|
||||
</DropdownMenu>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<View style={styles.row}>
|
||||
{gitActions.primary ? (
|
||||
@@ -224,6 +285,17 @@ const styles = StyleSheet.create((theme) => ({
|
||||
justifyContent: "center",
|
||||
position: "relative",
|
||||
},
|
||||
menuOnlyTrigger: {
|
||||
width: 48,
|
||||
height: buttonControlHeight.xs,
|
||||
flexDirection: "row",
|
||||
alignItems: "center",
|
||||
justifyContent: "center",
|
||||
gap: theme.spacing[1],
|
||||
borderRadius: theme.borderRadius.lg,
|
||||
borderWidth: theme.borderWidth[1],
|
||||
borderColor: theme.colors.borderAccent,
|
||||
},
|
||||
splitButtonPrimaryDisabled: {
|
||||
opacity: 0.6,
|
||||
},
|
||||
|
||||
@@ -415,7 +415,7 @@ function ChangesToolbar(props: ChangesToolbarProps) {
|
||||
onToggle={onToggleDesktopTree}
|
||||
/>
|
||||
) : null}
|
||||
{isMobile ? <GitActionsSplitButton gitActions={gitActions} /> : null}
|
||||
{isMobile ? <GitActionsSplitButton gitActions={gitActions} menuOnly /> : null}
|
||||
<ChangesOptionsMenu {...props} />
|
||||
</View>
|
||||
</PaneContentToolbar>
|
||||
|
||||
Reference in New Issue
Block a user