diff --git a/src/components/doclist/SortControls.tsx b/src/components/doclist/SortControls.tsx
index 8cc2cf8..6d29c99 100644
--- a/src/components/doclist/SortControls.tsx
+++ b/src/components/doclist/SortControls.tsx
@@ -1,5 +1,5 @@
import { Listbox, ListboxButton, ListboxOption, ListboxOptions, Button } from '@headlessui/react';
-import { ChevronUpDownIcon } from '@/components/icons/Icons';
+import { ChevronUpDownIcon, ListIcon, GridIcon } from '@/components/icons/Icons';
import { SortBy, SortDirection } from '@/types/documents';
interface SortControlsProps {
@@ -7,6 +7,8 @@ interface SortControlsProps {
sortDirection: SortDirection;
onSortByChange: (value: SortBy) => void;
onSortDirectionChange: () => void;
+ viewMode: 'list' | 'grid';
+ onViewModeChange: (mode: 'list' | 'grid') => void;
}
export function SortControls({
@@ -14,6 +16,8 @@ export function SortControls({
sortDirection,
onSortByChange,
onSortDirectionChange,
+ viewMode,
+ onViewModeChange,
}: SortControlsProps) {
const sortOptions: Array<{ value: SortBy; label: string, up: string, down: string }> = [
{ value: 'name', label: 'Name', up: 'A-Z', down: 'Z-A' },
@@ -25,34 +29,59 @@ export function SortControls({
const currentSort = sortOptions.find(opt => opt.value === sortBy);
const directionLabel = sortDirection === 'asc' ? currentSort?.up : currentSort?.down;
+ const buttonBaseClass = "h-6 flex items-center justify-center bg-base hover:bg-offbase rounded border border-transparent hover:border-offbase text-xs sm:text-sm transition-all duration-200 ease-in-out hover:scale-[1.04] hover:text-accent";
+ const activeIconClass = "text-accent";
+ const inactiveIconClass = "text-muted";
+
return (
-
- {directionLabel}
-
-
-
-
- {sortOptions.find(opt => opt.value === sortBy)?.label}
-
-
-
- {sortOptions.map((option) => (
-
- `relative cursor-pointer select-none py-0.5 px-1.5 sm:py-2 sm:px-3 ${active ? 'bg-offbase' : ''} ${selected ? 'font-medium' : ''}`
- }
- >
- {option.label}
-
- ))}
-
-
+
+ onViewModeChange('list')}
+ className={`p-0.5 rounded hover:bg-offbase transition-all hover:scale-[1.07] ${viewMode === 'list' ? activeIconClass : inactiveIconClass}`}
+ aria-label="List view"
+ >
+
+
+ onViewModeChange('grid')}
+ className={`p-0.5 rounded hover:bg-offbase transition-all hover:scale-[1.07] ${viewMode === 'grid' ? activeIconClass : inactiveIconClass}`}
+ aria-label="Grid view"
+ >
+
+
+
+
+
+
+
+
+ {directionLabel}
+
+
+
+
+ {sortOptions.find(opt => opt.value === sortBy)?.label}
+
+
+
+ {sortOptions.map((option) => (
+
+ `relative cursor-pointer select-none py-1.5 px-2 rounded text-xs ${active ? 'bg-offbase text-accent' : 'text-foreground'} ${selected ? 'font-medium' : ''}`
+ }
+ >
+ {option.label}
+
+ ))}
+
+
+
);
diff --git a/src/components/icons/Icons.tsx b/src/components/icons/Icons.tsx
index 292e937..f731f81 100644
--- a/src/components/icons/Icons.tsx
+++ b/src/components/icons/Icons.tsx
@@ -458,3 +458,55 @@ export function AudioWaveIcon(props: React.SVGProps
) {
);
}
+
+export function CopyIcon(props: React.SVGProps) {
+ return (
+
+
+
+
+ );
+}
+export function ListIcon(props: React.SVGProps) {
+ return (
+
+
+
+ );
+}
+
+export function GridIcon(props: React.SVGProps) {
+ return (
+
+
+
+ );
+}
diff --git a/src/types/config.ts b/src/types/config.ts
index 950aaa3..92b4af3 100644
--- a/src/types/config.ts
+++ b/src/types/config.ts
@@ -1,5 +1,7 @@
import type { DocumentListState } from '@/types/documents';
+const isDev = process.env.NEXT_PUBLIC_NODE_ENV !== 'production' || process.env.NODE_ENV == null;
+
export type ViewType = 'single' | 'dual' | 'scroll';
export type SavedVoices = Record;
@@ -43,15 +45,15 @@ export const APP_CONFIG_DEFAULTS: AppConfigValues = {
footerMargin: 0,
leftMargin: 0,
rightMargin: 0,
- ttsProvider: 'custom-openai',
- ttsModel: 'kokoro',
+ ttsProvider: isDev ? 'custom-openai' : 'deepinfra',
+ ttsModel: isDev ? 'kokoro' : 'hexgrad/Kokoro-82M',
ttsInstructions: '',
savedVoices: {},
smartSentenceSplitting: true,
pdfHighlightEnabled: true,
- pdfWordHighlightEnabled: true,
+ pdfWordHighlightEnabled: isDev,
epubHighlightEnabled: true,
- epubWordHighlightEnabled: true,
+ epubWordHighlightEnabled: isDev,
firstVisit: false,
documentListState: {
sortBy: 'name',
@@ -59,6 +61,7 @@ export const APP_CONFIG_DEFAULTS: AppConfigValues = {
folders: [],
collapsedFolders: [],
showHint: true,
+ viewMode: 'grid',
},
};
diff --git a/src/types/documents.ts b/src/types/documents.ts
index d21b1af..c93b615 100644
--- a/src/types/documents.ts
+++ b/src/types/documents.ts
@@ -63,4 +63,5 @@ export interface DocumentListState {
folders: Folder[];
collapsedFolders: string[];
showHint: boolean;
+ viewMode?: 'list' | 'grid';
}
diff --git a/tailwind.config.ts b/tailwind.config.ts
index 0058157..5d5c60f 100644
--- a/tailwind.config.ts
+++ b/tailwind.config.ts
@@ -67,6 +67,9 @@ export default {
},
},
},
+ screens: {
+ xs: '410px', // custom xs breakpoint
+ },
},
plugins: [typography],
} satisfies Config;