Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Added brain.fm support #316

Open
wants to merge 1 commit into
base: staging
Choose a base branch
from
Open
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
1 change: 1 addition & 0 deletions contributors.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,3 +15,4 @@
- cosmiclasagnadev
- trobonox
- zemzelett
- josewal
14 changes: 14 additions & 0 deletions src/components/Nav/SideNav.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import {
useToggleYoutube,
useSideNavOrderStore,
useToggleKanban,
useBrainfmMusic,
} from "@Store";
import { useState, useEffect } from "react";
import useSetDefault from "@App/utils/hooks/useSetDefault";
Expand All @@ -29,6 +30,7 @@ import { defaultToast } from "@Utils/toast";
import { DragDropContext, Droppable, Draggable } from "react-beautiful-dnd";
import { fullscreenChanged, toggleFullScreen } from "@Utils/fullscreen";
import { DraggableNavItem } from "./DraggableNavItem";
import { BrainfmIcon } from "../Player/BrainFm/Icon";

export const SideNav = () => {
const { isDark, toggleDarkMode } = useDarkToggleStore();
Expand All @@ -39,6 +41,7 @@ export const SideNav = () => {
const { isTimerToggled, setIsTimerToggled } = useToggleTimer();
const { isTasksToggled, setIsTasksToggled } = useToggleTasks();
const { isSpotifyToggled, setIsSpotifyToggled } = useSpotifyMusic();
const { isBrainfmToggled, setIsBrainfmToggled } = useBrainfmMusic();
const { isQuoteToggled, setIsQuoteToggled } = useToggleQuote();
const { isTwitchToggled, setIsTwitchToggled } = useToggleTwitch();
const { isYoutubeToggled, setIsYoutubeToggled } = useToggleYoutube();
Expand All @@ -49,6 +52,7 @@ export const SideNav = () => {
const { isMusicShown } = useToggleMusic();
const { isKanbanShown } = useToggleKanban();
const { isSpotifyShown } = useSpotifyMusic();
const { isBrainfmShown } = useBrainfmMusic();
const { isDarkModeShown } = useDarkToggleStore();
const { isFullscreenShown } = useFullScreenToggleStore();
const { isQuoteShown } = useToggleQuote();
Expand Down Expand Up @@ -206,6 +210,16 @@ export const SideNav = () => {
toggleIcon: "▶️",
isShown: isYoutubeShown,
},
{
id: "13",
content: <BrainfmIcon className="h-6 w-6" />,
tooltipTitle: "Brain.fm",
isToggled: isBrainfmToggled,
setToggled: setIsBrainfmToggled,
toggleString: "Brain.fm Toggled",
toggleIcon: "🎧",
isShown: isBrainfmShown,
},
];

// a little function to help us with reordering the result
Expand Down
28 changes: 28 additions & 0 deletions src/components/Player/BrainFm/Icon.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import {} from "react";

export const BrainfmIcon = (props: React.SVGProps<SVGSVGElement>) => {
return (
<svg width="1em" height="1em" viewBox="0 0 54 40" fill="none" xmlns="http://www.w3.org/2000/svg" {...props}>
<path
d="M26.8 0C36.932 0 45.5169 6.63022 48.4594 15.7918C51.436 16.713 53.6 19.4867 53.6 22.7699C53.6 26.0533 51.436 28.8294 48.4594 29.7507C48.3743 29.777 48.2886 29.8019 48.2021 29.8251C47.5973 29.9878 46.9603 30.0742 46.3027 30.0742C45.8597 30.0742 45.4288 30.0349 45.0078 29.9565C45.8841 27.7316 46.3664 25.3084 46.3664 22.7699C46.3664 20.234 45.8841 17.8108 45.0078 15.586C42.1461 8.32336 35.074 3.1853 26.8 3.1853C18.5284 3.1853 11.4539 8.32336 8.59228 15.586C8.48273 15.864 8.37934 16.1454 8.28228 16.4295C7.60289 18.4184 7.23366 20.5511 7.23366 22.7699C7.23366 24.9911 7.60289 27.1241 8.28393 29.113C8.38122 29.397 8.48488 29.6784 8.59473 29.9565C8.54211 29.9663 8.48928 29.9754 8.43627 29.984C8.06519 30.044 7.685 30.0742 7.29731 30.0742C6.54578 30.0742 5.8212 29.9615 5.14067 29.7507C2.16397 28.8294 0 26.0533 0 22.7699C0 19.4867 2.16397 16.713 5.14067 15.7918C8.08309 6.63022 16.668 0 26.8 0Z"
fill="currentColor"
/>
<path
d="M26.8 0C36.932 0 45.5169 6.63022 48.4594 15.7918C51.436 16.713 53.6 19.4867 53.6 22.7699C53.6 26.0533 51.436 28.8294 48.4594 29.7507C48.3743 29.777 48.2886 29.8019 48.2021 29.8251C47.5973 29.9878 46.9603 30.0742 46.3027 30.0742C45.8597 30.0742 45.4288 30.0349 45.0078 29.9565C45.8841 27.7316 46.3664 25.3084 46.3664 22.7699C46.3664 20.234 45.8841 17.8108 45.0078 15.586C42.1461 8.32336 35.074 3.1853 26.8 3.1853C18.5284 3.1853 11.4539 8.32336 8.59228 15.586C8.48273 15.864 8.37934 16.1454 8.28228 16.4295C7.60289 18.4184 7.23366 20.5511 7.23366 22.7699C7.23366 24.9911 7.60289 27.1241 8.28393 29.113C8.38122 29.397 8.48488 29.6784 8.59473 29.9565C8.54211 29.9663 8.48928 29.9754 8.43627 29.984C8.06519 30.044 7.685 30.0742 7.29731 30.0742C6.54578 30.0742 5.8212 29.9615 5.14067 29.7507C2.16397 28.8294 0 26.0533 0 22.7699C0 19.4867 2.16397 16.713 5.14067 15.7918C8.08309 6.63022 16.668 0 26.8 0Z"
fill="currentColor"
/>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M44.0115 22.7699C44.0115 25.0316 43.5757 27.1901 42.785 29.1675C40.249 35.5161 34.0484 40 26.8 40C19.5517 40 13.3511 35.5161 10.815 29.1675C10.0243 27.1901 9.58858 25.0316 9.58858 22.7699C9.58858 20.5085 10.0243 18.3523 10.815 16.3749C13.3511 10.0263 19.5517 5.54245 26.8 5.54245C34.0484 5.54245 40.249 10.0263 42.785 16.3749C43.5757 18.3523 44.0115 20.5085 44.0115 22.7699ZM26.8 33.7273C32.8464 33.7273 37.7472 28.822 37.7472 22.7699H15.8528C15.8528 28.822 20.7536 33.7273 26.8 33.7273Z"
fill="currentColor"
/>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M44.0115 22.7699C44.0115 25.0316 43.5757 27.1901 42.785 29.1675C40.249 35.5161 34.0484 40 26.8 40C19.5517 40 13.3511 35.5161 10.815 29.1675C10.0243 27.1901 9.58858 25.0316 9.58858 22.7699C9.58858 20.5085 10.0243 18.3523 10.815 16.3749C13.3511 10.0263 19.5517 5.54245 26.8 5.54245C34.0484 5.54245 40.249 10.0263 42.785 16.3749C43.5757 18.3523 44.0115 20.5085 44.0115 22.7699ZM26.8 33.7273C32.8464 33.7273 37.7472 28.822 37.7472 22.7699H15.8528C15.8528 28.822 20.7536 33.7273 26.8 33.7273Z"
fill="currentColor"
/>
</svg>
);
};
33 changes: 33 additions & 0 deletions src/components/Player/BrainFm/Player.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { useDarkToggleStore, useBrainfmMusic } from "@Store";
import { useState } from "react";
import { AiOutlineReload } from "react-icons/ai";
import { IoCloseSharp } from "react-icons/io5";
import { WithTooltip } from "../../Tooltip";
import { failureToast } from "@Root/src/utils/toast";

export const BrainFm = () => {
const { setIsBrainfmToggled } = useBrainfmMusic();

return (
<div className="mb-2 w-72 max-w-sm justify-between rounded-lg bg-white/[.96] py-4 px-4 text-gray-800 shadow-md dark:border-gray-700 dark:bg-gray-800/[.96] dark:text-gray-300 sm:w-96">
<div className="handle flex cursor-move items-center justify-between p-1">
<p className="py-2 font-bold">Brain.fm</p>
<IoCloseSharp
className="cursor-pointer rounded bg-gray-800 text-gray-100 hover:bg-gray-900 dark:bg-gray-300 dark:text-gray-800"
onClick={() => setIsBrainfmToggled(false)}
/>
</div>

<div className="cancelDrag justify-center">
<iframe
src={`https://my.brain.fm/`}
height="700"
width="100%"
frameBorder="0"
style={{ borderRadius: "10px" }}
allow="autoplay; clipboard-write; encrypted-media; fullscreen; picture-in-picture"
></iframe>
</div>
</div>
);
};
37 changes: 22 additions & 15 deletions src/components/WidgetControl/WidgetControlModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,7 @@ import { useEffect } from "react";
import { FaSpotify } from "react-icons/fa";
import { IoMusicalNotesOutline, IoCloseSharp } from "react-icons/io5";
import { CgNotes } from "react-icons/cg";
import {
MdOutlineTimer,
MdWbSunny,
MdOutlineNoteAdd,
MdOutlineViewKanban,
} from "react-icons/md";
import { MdOutlineTimer, MdWbSunny, MdOutlineNoteAdd, MdOutlineViewKanban } from "react-icons/md";
import { VscDebugRestartFrame } from "react-icons/vsc";
import { BsArrowsFullscreen, BsFillChatLeftQuoteFill, BsTwitch, BsYoutube } from "react-icons/bs";
import clsx from "clsx";
Expand All @@ -25,13 +20,16 @@ import {
useToggleTwitch,
useToggleYoutube,
useToggleKanban,
useBrainfmMusic,
} from "@Store";
import useMediaQuery from "@Utils/hooks/useMediaQuery";
import { toggledToastNotification } from "@Utils/toast";
import { BrainfmIcon } from "../Player/BrainFm/Icon";

export const WidgetControlModal = ({ isVisible = false, onClose }) => {
const { isMusicShown, setIsMusicShown } = useToggleMusic();
const { isSpotifyShown, setIsSpotifyShown } = useSpotifyMusic();
const { isBrainfmShown, setIsBrainfmShown } = useBrainfmMusic();
const { isTimerShown, setIsTimerShown } = useToggleTimer();
const { isStickyNoteShown, setIsStickyNoteShown } = useToggleStickyNote();
const { isTasksShown, setIsTasksShown } = useToggleTasks();
Expand Down Expand Up @@ -83,6 +81,7 @@ export const WidgetControlModal = ({ isVisible = false, onClose }) => {
Spotify
<FaSpotify className="h-6 w-full" />
</div>

<div
onClick={() => toggledToastNotification(isMusicShown, setIsMusicShown, "Music Widget Added", 750, "🎧")}
className={clsx(
Expand Down Expand Up @@ -213,20 +212,28 @@ export const WidgetControlModal = ({ isVisible = false, onClose }) => {
Youtube
<BsYoutube className="h-6 w-full" />
</div>
{isDesktop && (
<div
onClick={() =>
toggledToastNotification(isBrainfmShown, setIsBrainfmShown, "Brain.fm Widget Added", 750, "🎧")
}
className={clsx(
"grid cursor-pointer content-center justify-center gap-2 rounded md:hover:bg-gray-200 md:hover:text-gray-800 md:dark:hover:bg-violet-500",
isBrainfmShown && "dark:bg-violet-500 md:bg-gray-200 md:text-gray-800"
)}
>
Brain.fm
<BrainfmIcon className="h-6 w-full" />
</div>
)}

<div
onClick={() =>
toggledToastNotification(
isKanbanShown,
setIsKanbanShown,
"Kanban board Widget Added",
750,
"📃"
)
toggledToastNotification(isKanbanShown, setIsKanbanShown, "Kanban board Widget Added", 750, "📃")
}
className={clsx(
"grid cursor-pointer content-center justify-center gap-2 rounded md:hover:bg-gray-200 md:hover:text-gray-800 md:dark:hover:bg-violet-500",
isKanbanShown &&
"dark:bg-violet-500 md:bg-gray-200 md:text-gray-800"
isKanbanShown && "dark:bg-violet-500 md:bg-gray-200 md:text-gray-800"
)}
>
Kanban board
Expand Down
16 changes: 15 additions & 1 deletion src/interfaces.ts
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,20 @@ export interface IPosSpotify {
setSpotifyPosDefault: () => void;
}

export interface IToggleBrainfm {
isBrainfmToggled: boolean;
setIsBrainfmToggled: (isBrainfmToggled: boolean) => void;
isBrainfmShown: boolean;
setIsBrainfmShown: (isBrainfmShown: boolean) => void;
}

export interface IPosBrainfm {
brainfmPosX: number;
brainfmPosY: number;
setBrainfmPos: (X: number, Y: number) => void;
setBrainfmPosDefault: () => void;
}

export interface IToggleTimer {
isTimerToggled: boolean;
setIsTimerToggled: (isTimerToggled: boolean) => void;
Expand Down Expand Up @@ -322,5 +336,5 @@ export interface ISeoContent {
}

export interface ISeoToggle {
onButtonClick: () => void;
onButtonClick: () => void;
}
15 changes: 15 additions & 0 deletions src/pages/Astrostation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@ import {
usePosKanban,
useGrid,
useSetBackground,
useBrainfmMusic,
useBrainfmPos,
} from "@Store";
import { Player } from "@Components/Player/Player";
import { Timer } from "@Components/Timer/Timer";
Expand All @@ -45,12 +47,14 @@ import clsx from "clsx";
import React from "react";
import { Background } from "@App/App";
import BottomButtons from "@Components/Nav/BottomButtons";
import { BrainFm } from "../components/Player/BrainFm/Player";

export const Astrostation = React.forwardRef<HTMLDivElement>((_props, ref) => {
const { isMusicToggled, isMusicShown } = useToggleMusic();
const { isTimerToggled, isTimerShown } = useToggleTimer();
const { isTasksToggled, isTasksShown } = useToggleTasks();
const { isSpotifyToggled, isSpotifyShown } = useSpotifyMusic();
const { isBrainfmToggled, isBrainfmShown } = useBrainfmMusic();
const { isStickyNoteShown } = useToggleStickyNote();
const { isQuoteToggled, isQuoteShown } = useToggleQuote();
const { isTwitchToggled, isTwitchShown } = useToggleTwitch();
Expand All @@ -61,6 +65,7 @@ export const Astrostation = React.forwardRef<HTMLDivElement>((_props, ref) => {
const { taskPosX, taskPosY, setTaskPos } = usePosTask();
const { musicPosX, musicPosY, setMusicPos } = usePosMusic();
const { spotifyPosX, spotifyPosY, setSpotifyPos } = usePosSpotify();
const { brainfmPosX, brainfmPosY, setBrainfmPos } = useBrainfmPos();
const { quotePosX, quotePosY, setQuotePos } = usePosQuote();
const { timerPosX, timerPosY, setTimerPos } = usePosTimer();
const { stickyNotes, setStickyNotesPos } = useStickyNote();
Expand Down Expand Up @@ -189,6 +194,16 @@ export const Astrostation = React.forwardRef<HTMLDivElement>((_props, ref) => {
>
<Spotify />
</DWrapper>
<DWrapper
toggleHook={isBrainfmToggled && isBrainfmShown}
defaultX={brainfmPosX}
defaultY={brainfmPosY}
setPosition={setBrainfmPos}
isSticky={false}
gridValues={grid}
>
<BrainFm />
</DWrapper>
<DWrapper
toggleHook={isQuoteToggled && isQuoteShown}
defaultX={quotePosX}
Expand Down
36 changes: 36 additions & 0 deletions src/store.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ import {
IPosKanban,
ISeoContent,
IKanbanBoardState,
IToggleBrainfm,
IPosBrainfm,
} from "./interfaces";
import { InfoSection } from "./pages/InfoSection";
import { uuid } from "uuidv4";
Expand Down Expand Up @@ -643,6 +645,40 @@ export const usePosSpotify = create<IPosSpotify>(
)
);

/**
* Brain.fm Section Store
* ---
* Handle the Brain.fm section
*/

export const useBrainfmMusic = create<IToggleBrainfm>(
persist(
(set, _) => ({
isBrainfmToggled: true,
setIsBrainfmToggled: isBrainfmToggled => set({ isBrainfmToggled }),
isBrainfmShown: true,
setIsBrainfmShown: isBrainfmShown => set({ isBrainfmShown }),
}),
{
name: "state_brainfm_section",
}
)
);

export const useBrainfmPos = create<IPosBrainfm>(
persist(
(set, _) => ({
brainfmPosX: 400,
brainfmPosY: 158,
setBrainfmPos: (X, Y) => set({ brainfmPosX: X, brainfmPosY: Y }),
setBrainfmPosDefault: () => set(() => ({ brainfmPosX: 400, brainfmPosY: 158 })),
}),
{
name: "set_brainfm_position",
}
)
);

/**
* Timer Section Store
* ---
Expand Down
13 changes: 12 additions & 1 deletion src/utils/hooks/useSetDefault.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,19 @@
import { usePosTask, usePosMusic, usePosSpotify, usePosTimer, usePosQuote, usePosTwitch, usePosYoutube } from "@Store";
import {
usePosTask,
usePosMusic,
usePosSpotify,
usePosTimer,
usePosQuote,
usePosTwitch,
usePosYoutube,
useBrainfmPos,
} from "@Store";

function useSetDefault() {
const { setTaskPosDefault } = usePosTask();
const { setMusicPosDefault } = usePosMusic();
const { setSpotifyPosDefault } = usePosSpotify();
const { setBrainfmPosDefault } = useBrainfmPos();
const { setTimerPosDefault } = usePosTimer();
const { setQuotePosDefault } = usePosQuote();
const { setTwitchPosDefault } = usePosTwitch();
Expand All @@ -14,6 +24,7 @@ function useSetDefault() {
setTaskPosDefault();
setMusicPosDefault();
setSpotifyPosDefault();
setBrainfmPosDefault();
setTimerPosDefault();
setQuotePosDefault();
setTwitchPosDefault();
Expand Down