Skip to content

Commit 510e436

Browse files
committed
Fix the repository addition filtering
1 parent 2b6d449 commit 510e436

File tree

1 file changed

+97
-51
lines changed

1 file changed

+97
-51
lines changed

src/browser/components/home.tsx

Lines changed: 97 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -388,7 +388,10 @@ export function Home() {
388388

389389
// Track which repo dropdown is open
390390
const [openRepoDropdown, setOpenRepoDropdown] = useState<string | null>(null);
391+
const [repoDropdownPosition, setRepoDropdownPosition] = useState({ top: 0, left: 0 });
391392
const [showAddRepo, setShowAddRepo] = useState(false);
393+
const [addRepoButtonRef, setAddRepoButtonRef] = useState<HTMLButtonElement | null>(null);
394+
const [addRepoDropdownPosition, setAddRepoDropdownPosition] = useState({ top: 0, right: 0 });
392395

393396
// Show loading/error state while GitHub client initializes
394397
if (!githubReady) {
@@ -457,13 +460,25 @@ export function Home() {
457460
<div
458461
role="button"
459462
tabIndex={0}
460-
onClick={() => {
463+
onClick={(e) => {
464+
if (!isOpen) {
465+
const rect = e.currentTarget.getBoundingClientRect();
466+
setRepoDropdownPosition({
467+
top: rect.bottom + 4,
468+
left: rect.left,
469+
});
470+
}
461471
setOpenRepoDropdown(isOpen ? null : repo.name);
462472
setShowAddRepo(false);
463473
}}
464474
onKeyDown={(e) => {
465475
if (e.key === "Enter" || e.key === " ") {
466476
e.preventDefault();
477+
const rect = e.currentTarget.getBoundingClientRect();
478+
setRepoDropdownPosition({
479+
top: rect.bottom + 4,
480+
left: rect.left,
481+
});
467482
setOpenRepoDropdown(isOpen ? null : repo.name);
468483
setShowAddRepo(false);
469484
}
@@ -499,34 +514,47 @@ export function Home() {
499514
</div>
500515

501516
{isOpen && (
502-
<div className="absolute top-full left-0 mt-1 w-56 bg-card border border-border rounded-lg shadow-xl z-30 overflow-hidden max-w-[calc(100vw-1rem)] sm:max-w-none">
503-
{availableModes.map((option) => (
504-
<button
505-
key={option.value}
506-
onClick={() => {
507-
handleRepoModeChange(repo.name, option.value);
508-
setOpenRepoDropdown(null);
509-
}}
510-
className={cn(
511-
"w-full flex items-start gap-2.5 px-3 py-2 hover:bg-muted/50 transition-colors text-left",
512-
repo.mode === option.value && "bg-muted/50"
513-
)}
514-
>
515-
<option.icon className="w-3.5 h-3.5 mt-0.5 shrink-0" />
516-
<div className="flex-1 min-w-0">
517-
<div className="font-medium text-xs">
518-
{option.label}
519-
</div>
520-
<div className="text-[10px] text-muted-foreground">
521-
{option.description}
517+
<>
518+
{/* Backdrop to close dropdown when clicking outside */}
519+
<div
520+
className="fixed inset-0 z-40"
521+
onClick={() => setOpenRepoDropdown(null)}
522+
/>
523+
<div
524+
className="fixed w-56 bg-card border border-border rounded-lg shadow-xl z-50 max-w-[calc(100vw-1rem)] sm:max-w-none"
525+
style={{
526+
top: repoDropdownPosition.top,
527+
left: repoDropdownPosition.left,
528+
}}
529+
>
530+
{availableModes.map((option) => (
531+
<button
532+
key={option.value}
533+
onClick={() => {
534+
handleRepoModeChange(repo.name, option.value);
535+
setOpenRepoDropdown(null);
536+
}}
537+
className={cn(
538+
"w-full flex items-start gap-2.5 px-3 py-2 hover:bg-muted/50 transition-colors text-left",
539+
repo.mode === option.value && "bg-muted/50"
540+
)}
541+
>
542+
<option.icon className="w-3.5 h-3.5 mt-0.5 shrink-0" />
543+
<div className="flex-1 min-w-0">
544+
<div className="font-medium text-xs">
545+
{option.label}
546+
</div>
547+
<div className="text-[10px] text-muted-foreground">
548+
{option.description}
549+
</div>
522550
</div>
523-
</div>
524-
{repo.mode === option.value && (
525-
<Check className="w-3.5 h-3.5 text-primary mt-0.5" />
526-
)}
527-
</button>
528-
))}
529-
</div>
551+
{repo.mode === option.value && (
552+
<Check className="w-3.5 h-3.5 text-primary mt-0.5" />
553+
)}
554+
</button>
555+
))}
556+
</div>
557+
</>
530558
)}
531559
</div>
532560
);
@@ -550,7 +578,15 @@ export function Home() {
550578
{/* Add Repo Button */}
551579
<div className="relative shrink-0">
552580
<button
581+
ref={setAddRepoButtonRef}
553582
onClick={() => {
583+
if (!showAddRepo && addRepoButtonRef) {
584+
const rect = addRepoButtonRef.getBoundingClientRect();
585+
setAddRepoDropdownPosition({
586+
top: rect.bottom + 4,
587+
right: window.innerWidth - rect.right,
588+
});
589+
}
554590
setShowAddRepo(!showAddRepo);
555591
setOpenRepoDropdown(null);
556592
}}
@@ -567,31 +603,40 @@ export function Home() {
567603

568604
{/* Search Dropdown */}
569605
{showAddRepo && (
570-
<div className="absolute top-full right-0 mt-1 w-72 max-w-[calc(100vw-1rem)] bg-card border border-border rounded-lg shadow-xl overflow-hidden z-30">
571-
<div className="p-2 border-b border-border">
572-
<div className="relative">
573-
<input
574-
type="text"
575-
value={searchQuery}
576-
onChange={(e) => setSearchQuery(e.target.value)}
577-
onBlur={(e) => {
578-
// Close dropdown if not clicking inside it
579-
if (!e.relatedTarget?.closest(".add-repo-dropdown")) {
580-
setTimeout(() => setShowAddRepo(false), 150);
581-
}
582-
}}
583-
placeholder="Search repositories..."
584-
className="w-full h-7 pl-7 pr-3 rounded-md border border-border bg-muted/50 text-xs placeholder:text-muted-foreground/60 focus:outline-none focus:ring-2 focus:ring-ring focus:border-transparent"
585-
autoFocus
586-
/>
587-
<Search className="absolute left-2 top-1/2 -translate-y-1/2 w-3.5 h-3.5 text-muted-foreground" />
588-
{searching && (
589-
<Loader2 className="absolute right-2 top-1/2 -translate-y-1/2 w-3 h-3 animate-spin text-muted-foreground" />
590-
)}
606+
<>
607+
{/* Backdrop to close dropdown when clicking outside */}
608+
<div
609+
className="fixed inset-0 z-40"
610+
onClick={() => {
611+
setShowAddRepo(false);
612+
setSearchQuery("");
613+
}}
614+
/>
615+
<div
616+
className="fixed w-72 max-w-[calc(100vw-1rem)] bg-card border border-border rounded-lg shadow-xl z-50"
617+
style={{
618+
top: addRepoDropdownPosition.top,
619+
right: addRepoDropdownPosition.right,
620+
}}
621+
>
622+
<div className="p-2 border-b border-border">
623+
<div className="relative">
624+
<input
625+
type="text"
626+
value={searchQuery}
627+
onChange={(e) => setSearchQuery(e.target.value)}
628+
placeholder="Search repositories..."
629+
className="w-full h-7 pl-7 pr-3 rounded-md border border-border bg-muted/50 text-xs placeholder:text-muted-foreground/60 focus:outline-none focus:ring-2 focus:ring-ring focus:border-transparent"
630+
autoFocus
631+
/>
632+
<Search className="absolute left-2 top-1/2 -translate-y-1/2 w-3.5 h-3.5 text-muted-foreground" />
633+
{searching && (
634+
<Loader2 className="absolute right-2 top-1/2 -translate-y-1/2 w-3 h-3 animate-spin text-muted-foreground" />
635+
)}
636+
</div>
591637
</div>
592-
</div>
593638

594-
<div className="add-repo-dropdown max-h-64 overflow-auto">
639+
<div className="add-repo-dropdown max-h-64 overflow-auto">
595640
{/* All Repos option - always shown at top when not already added */}
596641
{!config.repos.some(isAllReposFilter) && !searchQuery && (
597642
<button
@@ -650,6 +695,7 @@ export function Home() {
650695
)}
651696
</div>
652697
</div>
698+
</>
653699
)}
654700
</div>
655701
</div>

0 commit comments

Comments
 (0)