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
14 changes: 13 additions & 1 deletion frontend/package-lock.json

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

17 changes: 12 additions & 5 deletions frontend/src/components/Button.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,15 @@ interface ButtonProps {
}

const variantClasses = {
primary: "bg-purple-600 text-white text-xl font-semibold hover:bg-purple-800 focus:ring-purple-400",
secondary: "bg-purple-200 text-purple-700 hover:bg-purple-300 focus:ring-purple-300",
// Workable Green
primary: "bg-[#00835C] text-white hover:bg-[#006e4d] focus:ring-[#00835C]",
// Clean Slate Gray (Neutral)
secondary:
"bg-slate-100 text-slate-700 hover:bg-slate-200 focus:ring-slate-300",
};

const defaultStyles =
"px-4 py-2 rounded-xl font-medium flex items-center justify-center gap-2 transition-colors duration-200 shadow-sm focus:outline-none focus:ring-2 focus:ring-offset-2 disabled:opacity-50 disabled:cursor-not-allowed border-2 border-black";
"px-4 py-2 rounded-md text-sm font-medium flex items-center justify-center gap-2 transition-colors duration-200 shadow-sm focus:outline-none focus:ring-2 focus:ring-offset-1 disabled:opacity-50 disabled:cursor-not-allowed";

export function Button({
variant,
Expand All @@ -26,6 +29,7 @@ export function Button({
onClick,
loading = false,
fullWidth = false,
className,
}: ButtonProps) {
const fullWidthClass = fullWidth ? "w-full" : "";

Expand All @@ -36,7 +40,10 @@ export function Button({
disabled={loading}
aria-busy={loading}
className={twMerge(
`${variantClasses[variant]} ${defaultStyles} ${fullWidthClass}`
variantClasses[variant],
defaultStyles,
fullWidthClass,
className
)}
>
{loading ? (
Expand All @@ -55,7 +62,7 @@ export function Button({
function Spinner() {
return (
<svg
className="animate-spin h-5 w-5 text-white"
className="animate-spin h-5 w-5 text-current"
xmlns="http://www.w3.org/2000/svg"
fill="none"
viewBox="0 0 24 24"
Expand Down
33 changes: 19 additions & 14 deletions frontend/src/components/Card.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -50,20 +50,24 @@ export function Card({

return (
<div className="w-full h-full">
<div className="p-4 bg-gray-50 rounded-lg border border-gray-300 shadow-sm w-full h-full flex flex-col">
<div className="flex justify-between items-start">
<div className="flex items-center text-md font-medium text-gray-800">
<div className="pr-2 text-gray-600">
{/* Changed: bg-gray-50 -> bg-white, softer border */}
<div className="p-5 bg-white rounded-lg border border-slate-200 shadow-sm hover:shadow-md transition-all duration-200 w-full h-full flex flex-col">
<div className="flex justify-between items-start mb-4">
{/* Changed: text-gray-800 -> text-[#1C2939] (Dark Navy) */}
<div className="flex items-center text-md font-semibold text-[#1C2939] leading-snug">
{/* Changed: text-gray-600 -> text-[#00835C] (Workable Green) */}
<div className="pr-3 text-[#00835C]">
{type === "twitter" && <TwitterIcon />}
{type === "youtube" && <YoutubeIcon />}
{type === "document" && <DocumentIcon />}
</div>
{title}
</div>

{!readOnly && (
<div className="flex items-center gap-2">
<div className="flex items-center gap-3">
<div
className="text-gray-600 cursor-pointer"
className="text-slate-400 hover:text-[#00835C] cursor-pointer transition-colors"
onClick={async () => {
try {
await navigator.clipboard.writeText(link);
Expand All @@ -77,7 +81,7 @@ export function Card({
{(type === "twitter" || type === "youtube") && <ShareIcon />}
</div>

<div className="text-gray-600 cursor-pointer">
<div className="text-slate-400 hover:text-red-500 cursor-pointer transition-colors">
<a
href="#"
onClick={(e) => {
Expand All @@ -95,11 +99,11 @@ export function Card({
)}
</div>

<div className="pt-4 flex-1">
<div className="flex-1">
{type === "youtube" && (
<div>
<iframe
className="w-full aspect-video rounded-md border border-gray-300"
className="w-full aspect-video rounded-md border border-slate-100 bg-slate-50"
src={embedUrl}
title={title}
allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share"
Expand All @@ -110,13 +114,13 @@ export function Card({
}}
/>
{iframeError && (
<div className="mt-2 p-2 bg-red-50 text-red-700 rounded text-sm">
<div className="mt-2 p-3 bg-red-50 text-red-600 rounded text-sm border border-red-100">
Failed to load video.
<a
href={link}
target="_blank"
rel="noopener noreferrer"
className="underline ml-1"
className="underline ml-1 font-medium"
>
Open in YouTube
</a>
Expand All @@ -132,14 +136,15 @@ export function Card({
)}

{type === "document" && description && (
<div className="bg-gray-100 rounded-lg p-3 border border-gray-300">
<div className="text-gray-700 text-sm leading-relaxed whitespace-pre-wrap">
// Changed: bg-gray-100 -> bg-slate-50, border-slate-100
<div className="bg-slate-50 rounded-lg p-4 border border-slate-100 mt-1">
<div className="text-slate-600 text-sm leading-relaxed whitespace-pre-wrap">
{isExpanded ? description : truncateText(description, 150)}
</div>
{description.length > 150 && (
<button
onClick={() => setIsExpanded(!isExpanded)}
className="mt-2 text-gray-600 hover:text-gray-800 text-xs font-medium"
className="mt-2 text-[#00835C] hover:text-[#006e4d] text-xs font-semibold uppercase tracking-wide"
>
{isExpanded ? "Show Less" : "Show More"}
</button>
Expand Down
16 changes: 10 additions & 6 deletions frontend/src/components/Sidebar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ export function Sidebar({
{/* Mobile Overlay */}
{isOpen && (
<div
className="fixed inset-0 bg-black bg-opacity-50 z-40 sm:hidden"
className="fixed inset-0 bg-slate-900/50 backdrop-blur-sm z-40 sm:hidden"
onClick={handleClose}
/>
)}
Expand All @@ -45,22 +45,25 @@ export function Sidebar({
className={`
h-screen pl-6 pr-4 py-6
flex flex-col w-64 flex-shrink-0
bg-gradient-to-b from-purple-50 via-purple-100 to-purple-200
border-r-8 border-purple-300
bg-[#1C2939] text-white
border-r border-slate-800
transition-transform duration-300 ease-in-out
${isOpen ? "translate-x-0" : "-translate-x-full sm:translate-x-0"}
fixed top-0 left-0 z-50 sm:static sm:z-auto
shadow-xl sm:shadow-none
`}
>
{/* Header with close button for mobile */}
<div className="flex items-center justify-between mb-8">
<div className="flex items-center space-x-2 text-purple-600">
<div className="flex items-center space-x-2 text-[#00835C]">
<Logo />
<span className="text-xl font-semibold text-gray-800">Brainly</span>
<span className="text-xl font-bold text-white tracking-tight">
Brainly
</span>
</div>
<button
onClick={handleClose}
className="sm:hidden text-gray-600 hover:text-gray-800"
className="sm:hidden text-slate-400 hover:text-white transition-colors"
>
<CrossIcon />
</button>
Expand Down Expand Up @@ -99,6 +102,7 @@ export function Sidebar({
text="Logout"
startIcon={<Logout />}
fullWidth={true}
className="bg-[#00835C] hover:bg-[#006e4d] text-white border-none shadow-sm"
/>
</div>
</div>
Expand Down
6 changes: 3 additions & 3 deletions frontend/src/components/SidebarItem.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,11 @@ export function SidebarItem({
}) {
return (
<div
className="flex text-gray-700 py-2 cursor-pointer hover:bg-purple-300 rounded max-w-48 pl-4 transition-all duration-150"
className="flex items-center text-slate-300 py-3 px-4 cursor-pointer hover:bg-white/10 hover:text-white rounded-md transition-all duration-200"
Copy link

Copilot AI Dec 3, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The group-hover:text-white class will not work because the parent div element (line 13) does not have the group class. Either add group to the parent div's className or change group-hover:text-white to hover:text-white for this div to respond to its own hover state.

Suggested change
className="flex items-center text-slate-300 py-3 px-4 cursor-pointer hover:bg-white/10 hover:text-white rounded-md transition-all duration-200"
className="group flex items-center text-slate-300 py-3 px-4 cursor-pointer hover:bg-white/10 hover:text-white rounded-md transition-all duration-200"

Copilot uses AI. Check for mistakes.
onClick={onClick}
>
<div className="pr-2">{icon}</div>
<div>{text}</div>
<div className="mr-3 text-[#00835C] group-hover:text-white">{icon}</div>
<div className="font-medium text-sm">{text}</div>
</div>
);
}
35 changes: 22 additions & 13 deletions frontend/src/components/input.tsx
Original file line number Diff line number Diff line change
@@ -1,18 +1,27 @@
interface InputProps {
placeholder: string;
reference?: React.Ref<HTMLInputElement>;
placeholder: string;
reference?: React.Ref<HTMLInputElement>;
}

export function Input({ placeholder, reference }: InputProps) {
return (
<div className="w-full">
<input
ref={reference}
placeholder={placeholder}
type="text"
className="w-full px-4 py-2 border border-gray-300 rounded focus:outline-none focus:ring-2 focus:ring-purple-500 m-2"
/>
</div>
);
return (
<div className="w-full">
<input
ref={reference}
placeholder={placeholder}
type="text"
className="
w-full px-4 py-2
border border-slate-300
rounded-md
text-[#1C2939]
placeholder-slate-400
focus:outline-none
focus:ring-2
focus:ring-[#00835C]/30
focus:border-[#00835C]
"
/>
</div>
);
}

19 changes: 12 additions & 7 deletions frontend/src/components/landing/ButtonL.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,20 @@ export interface ButtonLProps extends ButtonHTMLAttributes<HTMLButtonElement> {

const sizeClasses = {
sm: "h-8 px-3 text-sm",
md: "h-9 px-4 text-sm",
lg: "h-11 px-6 text-base",
md: "h-10 px-5 text-sm", // Adjusted height slightly for better touch target
lg: "h-12 px-8 text-base",
};

const variantClasses = {
default: "text-primary-foreground bg-gradient-to-r from-blue-600 to-purple-600 hover:bg-primary/90",
outline: "border-[0.2px] border-black bg-transparent hover:bg-black hover:text-white transition-colors",
// Workable Green Solid
default: "text-white bg-[#00835C] hover:bg-[#006e4d] shadow-sm",

secondary: "bg-secondary text-secondary-foreground hover:bg-secondary/80",
// Clean Gray Outline -> Hover Green
outline:
"border border-slate-300 bg-white text-slate-700 hover:border-[#00835C] hover:text-[#00835C] hover:bg-slate-50 transition-all",

// Secondary Gray
secondary: "bg-slate-100 text-slate-900 hover:bg-slate-200",
};

export const ButtonL = forwardRef<HTMLButtonElement, ButtonLProps>(
Expand All @@ -25,8 +30,8 @@ export const ButtonL = forwardRef<HTMLButtonElement, ButtonLProps>(
<button
ref={ref}
className={twMerge(
"inline-flex items-center justify-center gap-2 whitespace-nowrap font-medium rounded-md transition-colors",
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background",
"inline-flex items-center justify-center gap-2 whitespace-nowrap font-medium rounded-md transition-colors duration-200",
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[#00835C] focus-visible:ring-offset-2 ring-offset-white",
"disabled:opacity-50 disabled:pointer-events-none",
"[&_svg]:pointer-events-none [&_svg]:size-4 [&_svg]:shrink-0",
sizeClasses[size],
Expand Down
Loading