Make space for windows controls (#635)

This commit is contained in:
Will Chen
2025-07-11 16:28:13 -07:00
committed by GitHub
parent e539cbefdd
commit be1321152e
2 changed files with 149 additions and 97 deletions

View File

@@ -78,13 +78,13 @@ export const TitleBar = () => {
return (
<>
<div className="@container z-11 w-full h-11 bg-(--sidebar) absolute top-0 left-0 app-region-drag flex items-center">
<div className="pl-20"></div>
<img src={logo} alt="Dyad Logo" className="w-6 h-6 mr-2" />
<div className="pl-18"></div>
<img src={logo} alt="Dyad Logo" className="w-6 h-6 mr-0.5" />
<Button
data-testid="title-bar-app-name-button"
variant="outline"
size="sm"
className={`hidden @md:block no-app-region-drag text-sm font-medium ${
className={`hidden @2xl:block no-app-region-drag text-xs max-w-38 truncate font-medium ${
selectedApp ? "cursor-pointer" : ""
}`}
onClick={handleAppClick}
@@ -210,13 +210,15 @@ export function DyadProButton({
}}
variant="outline"
className={cn(
"ml-4 no-app-region-drag h-7 bg-indigo-600 text-white dark:bg-indigo-600 dark:text-white",
"hidden @2xl:block ml-1 no-app-region-drag h-7 bg-indigo-600 text-white dark:bg-indigo-600 dark:text-white text-xs px-2 pt-1 pb-1",
!isDyadProEnabled && "bg-zinc-600 dark:bg-zinc-600",
)}
size="sm"
>
{isDyadProEnabled ? "Dyad Pro" : "Dyad Pro (disabled)"}
{userBudget && <AICreditStatus userBudget={userBudget} />}
{isDyadProEnabled ? "Pro" : "Pro (off)"}
{userBudget && isDyadProEnabled && (
<AICreditStatus userBudget={userBudget} />
)}
</Button>
);
}

View File

@@ -21,6 +21,12 @@ import {
DropdownMenuItem,
DropdownMenuTrigger,
} from "@/components/ui/dropdown-menu";
import {
Tooltip,
TooltipContent,
TooltipProvider,
TooltipTrigger,
} from "@/components/ui/tooltip";
import { showError, showSuccess } from "@/lib/toast";
import { useMutation } from "@tanstack/react-query";
import { useCheckProblems } from "@/hooks/useCheckProblems";
@@ -28,6 +34,9 @@ import { isPreviewOpenAtom } from "@/atoms/viewAtoms";
export type PreviewMode = "preview" | "code" | "problems" | "configure";
const BUTTON_CLASS_NAME =
"cursor-pointer relative flex items-center gap-1 px-2 py-1 rounded-md text-[13px] font-medium z-10 hover:bg-[var(--background)]";
// Preview Header component with preview mode toggle
export const PreviewHeader = () => {
const [previewMode, setPreviewMode] = useAtom(previewModeAtom);
@@ -38,9 +47,22 @@ export const PreviewHeader = () => {
const problemsRef = useRef<HTMLButtonElement>(null);
const configureRef = useRef<HTMLButtonElement>(null);
const [indicatorStyle, setIndicatorStyle] = useState({ left: 0, width: 0 });
const [windowWidth, setWindowWidth] = useState(window.innerWidth);
const { problemReport } = useCheckProblems(selectedAppId);
const { restartApp, refreshAppIframe } = useRunApp();
const isCompact = windowWidth < 840;
// Track window width
useEffect(() => {
const handleResize = () => {
setWindowWidth(window.innerWidth);
};
window.addEventListener("resize", handleResize);
return () => window.removeEventListener("resize", handleResize);
}, []);
const selectPanel = (panel: PreviewMode) => {
if (previewMode === panel) {
setIsPreviewOpen(!isPreviewOpen);
@@ -130,11 +152,47 @@ export const PreviewHeader = () => {
// Small delay to ensure DOM is updated
const timeoutId = setTimeout(updateIndicator, 10);
return () => clearTimeout(timeoutId);
}, [previewMode, displayCount, isPreviewOpen]);
}, [previewMode, displayCount, isPreviewOpen, isCompact]);
const renderButton = (
mode: PreviewMode,
ref: React.RefObject<HTMLButtonElement | null>,
icon: React.ReactNode,
text: string,
testId: string,
badge?: React.ReactNode,
) => {
const buttonContent = (
<button
data-testid={testId}
ref={ref}
className={BUTTON_CLASS_NAME}
onClick={() => selectPanel(mode)}
>
{icon}
{!isCompact && <span>{text}</span>}
{badge}
</button>
);
if (isCompact) {
return (
<Tooltip>
<TooltipTrigger asChild>{buttonContent}</TooltipTrigger>
<TooltipContent>
<p>{text}</p>
</TooltipContent>
</Tooltip>
);
}
return buttonContent;
};
return (
<div className="flex items-center justify-between px-4 py-2 mt-1 border-b border-border">
<div className="relative flex rounded-md p-0.5 gap-2">
<TooltipProvider>
<div className="flex items-center justify-between px-1 py-2 mt-1 border-b border-border">
<div className="relative flex rounded-md p-0.5 gap-0.5">
<motion.div
className="absolute top-0.5 bottom-0.5 bg-[var(--background-lightest)] shadow rounded-md"
animate={{
@@ -148,48 +206,39 @@ export const PreviewHeader = () => {
mass: 0.6,
}}
/>
<button
data-testid="preview-mode-button"
ref={previewRef}
className="cursor-pointer relative flex items-center gap-1 px-2 py-1 rounded-md text-sm font-medium z-10 hover:bg-[var(--background)]"
onClick={() => selectPanel("preview")}
>
<Eye size={14} />
<span>Preview</span>
</button>
<button
data-testid="problems-mode-button"
ref={problemsRef}
className="cursor-pointer relative flex items-center gap-1 px-2 py-1 rounded-md text-sm font-medium z-10 hover:bg-[var(--background)]"
onClick={() => selectPanel("problems")}
>
<AlertTriangle size={14} />
<span>Problems</span>
{displayCount && (
{renderButton(
"preview",
previewRef,
<Eye size={14} />,
"Preview",
"preview-mode-button",
)}
{renderButton(
"problems",
problemsRef,
<AlertTriangle size={14} />,
"Problems",
"problems-mode-button",
displayCount && (
<span className="ml-0.5 px-1 py-0.5 text-xs font-medium bg-red-100 dark:bg-red-900/30 text-red-700 dark:text-red-300 rounded-full min-w-[16px] text-center">
{displayCount}
</span>
),
)}
{renderButton(
"code",
codeRef,
<Code size={14} />,
"Code",
"code-mode-button",
)}
{renderButton(
"configure",
configureRef,
<Wrench size={14} />,
"Configure",
"configure-mode-button",
)}
</button>
<button
data-testid="code-mode-button"
ref={codeRef}
className="cursor-pointer relative flex items-center gap-1 px-2 py-1 rounded-md text-sm font-medium z-10 hover:bg-[var(--background)]"
onClick={() => selectPanel("code")}
>
<Code size={14} />
<span>Code</span>
</button>
<button
data-testid="configure-mode-button"
ref={configureRef}
className="cursor-pointer relative flex items-center gap-1 px-2 py-1 rounded-md text-sm font-medium z-10 hover:bg-[var(--background)]"
onClick={() => selectPanel("configure")}
>
<Wrench size={14} />
<span>Configure</span>
</button>
</div>
<div className="flex items-center">
<DropdownMenu>
@@ -225,5 +274,6 @@ export const PreviewHeader = () => {
</DropdownMenu>
</div>
</div>
</TooltipProvider>
);
};