diff --git a/src/features/background/options/BackgroundOptions.jsx b/src/features/background/options/BackgroundOptions.jsx index 9234fddb..ad899747 100644 --- a/src/features/background/options/BackgroundOptions.jsx +++ b/src/features/background/options/BackgroundOptions.jsx @@ -1,8 +1,11 @@ import variables from 'config/variables'; import { memo, useState, useEffect, useCallback, useRef } from 'react'; import { MdSource, MdOutlineAutoAwesome } from 'react-icons/md'; +import { toast } from 'react-toastify'; import EventBus from 'utils/eventbus'; import { clearQueuesOnSettingChange } from 'utils/queueOperations'; +import { uninstall } from 'utils/marketplace'; +import { updateHash } from 'utils/deepLinking'; import { Header } from 'components/Layout/Settings'; import { Dropdown } from 'components/Form/Settings'; @@ -33,6 +36,18 @@ const BackgroundOptions = memo(({ currentSubSection, onSubSectionChange, section ); const [marketplaceEnabled] = useState(localStorage.getItem('photo_packs')); + // Helper function to get installed photo packs + const getInstalledPhotoPacks = () => { + try { + const installed = JSON.parse(localStorage.getItem('installed')) || []; + return installed.filter((item) => item.type === 'photos'); + } catch { + return []; + } + }; + + const [installedPhotoPacks, setInstalledPhotoPacks] = useState(getInstalledPhotoPacks()); + // Auto-show source section for types without effects/display settings const shouldShowSourceByDefault = ['colour', 'random_colour', 'random_gradient'].includes( backgroundType, @@ -106,6 +121,56 @@ const BackgroundOptions = memo(({ currentSubSection, onSubSectionChange, section }; }, [getBackgroundCategories]); + // Listen for installed addons changes + useEffect(() => { + const handleInstalledAddonsChanged = () => { + setInstalledPhotoPacks(getInstalledPhotoPacks()); + // Update backgroundType if it changed (e.g., when all packs are uninstalled) + const currentType = localStorage.getItem('backgroundType') || 'api'; + if (currentType !== backgroundType) { + setBackgroundType(currentType); + } + }; + + window.addEventListener('installedAddonsChanged', handleInstalledAddonsChanged); + return () => window.removeEventListener('installedAddonsChanged', handleInstalledAddonsChanged); + }, [backgroundType]); + + // Handle photo pack uninstall + const handlePhotoPackUninstall = (type, name) => { + uninstall(type, name); + toast(variables.getMessage('toasts.uninstalled')); + variables.stats.postEvent('marketplace-item', `${name} uninstalled`); + setInstalledPhotoPacks(getInstalledPhotoPacks()); + window.dispatchEvent(new window.Event('installedAddonsChanged')); + }; + + // Navigate to photo packs marketplace + const goToPhotoPacks = () => { + variables.updateHash('#discover/photo_packs'); + const event = new window.Event('popstate'); + window.dispatchEvent(event); + }; + + const handleToggle = (pack) => { + // Navigate to discover tab with the item + const itemId = pack.name; + updateHash(`#discover/all?item=${itemId}`); + + // Trigger navigation + const event = new window.Event('popstate'); + window.dispatchEvent(event); + + variables.stats.postEvent('marketplace', 'ItemPage viewed'); + }; + + // Get total count of photos across all installed packs + const getTotalPhotoCount = () => { + return installedPhotoPacks.reduce((total, pack) => { + return total + (pack.photos?.length || 0); + }, 0); + }; + const getBackgroundSettings = () => { switch (backgroundType) { case 'custom': @@ -231,11 +296,16 @@ const BackgroundOptions = memo(({ currentSubSection, onSubSectionChange, section { // Clear prefetch queue when changing background type clearQueuesOnSettingChange('backgroundType'); setBackgroundType(value); }} + onPhotoPackUninstall={handlePhotoPackUninstall} + onGoToPhotoPacks={goToPhotoPacks} + onToggle={handleToggle} /> {getBackgroundSettings()} diff --git a/src/features/background/options/sections/SourceSection.jsx b/src/features/background/options/sections/SourceSection.jsx index 1d4ab14b..21c9abdf 100644 --- a/src/features/background/options/sections/SourceSection.jsx +++ b/src/features/background/options/sections/SourceSection.jsx @@ -1,25 +1,67 @@ import variables from 'config/variables'; +import { MdExplore } from 'react-icons/md'; import { Dropdown } from 'components/Form/Settings'; import { Row, Content, Action } from 'components/Layout/Settings/Item'; +import { Button } from 'components/Elements'; +import Items from 'features/marketplace/components/Items/Items'; import { getBackgroundOptionItems } from '../optionTypes'; -const SourceSection = ({ backgroundType, marketplaceEnabled, onTypeChange }) => { +const SourceSection = ({ + backgroundType, + marketplaceEnabled, + installedPhotoPacks = [], + totalPhotoCount = 0, + onTypeChange, + onPhotoPackUninstall, + onGoToPhotoPacks, + onToggle, +}) => { + const showInstalledPhotoPacks = + backgroundType === 'photo_pack' && + marketplaceEnabled && + installedPhotoPacks.length > 0; + return ( - - - - + + - - + + + + + + {showInstalledPhotoPacks && ( + <> + + + +