feat: coming soon
This commit is contained in:
@ -1,58 +0,0 @@
|
||||
import { createContext, useContext } from 'react'
|
||||
|
||||
import { NextPage, PaginationData, usePagination } from 'hooks/usePagination'
|
||||
import { useAuthentication } from 'utils/authentication'
|
||||
|
||||
export interface Guild {
|
||||
id: number
|
||||
name: string
|
||||
description: string
|
||||
icon: string
|
||||
isPublic: boolean
|
||||
createdAt: string
|
||||
updatedAt: string
|
||||
}
|
||||
|
||||
interface PaginationGuild {
|
||||
id: number
|
||||
isOwner: boolean
|
||||
lastVisitedChannelId: number
|
||||
userId: number
|
||||
guildId: number
|
||||
createdAt: string
|
||||
updatedAt: string
|
||||
guild: Guild
|
||||
}
|
||||
|
||||
export type Guilds = PaginationData<PaginationGuild>
|
||||
|
||||
export interface GuildsValue {
|
||||
guilds: Guilds
|
||||
nextPage: NextPage
|
||||
}
|
||||
|
||||
export interface GuildsProviderProps {
|
||||
guilds: Guilds
|
||||
}
|
||||
|
||||
const defaultGuildsContext: GuildsValue = {} as any
|
||||
const GuildsContext = createContext<GuildsValue>(defaultGuildsContext)
|
||||
|
||||
export const GuildsProvider: React.FC<GuildsProviderProps> = (props) => {
|
||||
const { authentication } = useAuthentication()
|
||||
const { data: guilds, nextPage } = usePagination<PaginationGuild>({
|
||||
api: authentication.api,
|
||||
url: '/guilds',
|
||||
defaultPaginationData: props.guilds
|
||||
})
|
||||
|
||||
return (
|
||||
<GuildsContext.Provider value={{ guilds, nextPage }}>
|
||||
{props.children}
|
||||
</GuildsContext.Provider>
|
||||
)
|
||||
}
|
||||
|
||||
export const useGuilds = (): GuildsValue => {
|
||||
return useContext(GuildsContext)
|
||||
}
|
@ -1,72 +0,0 @@
|
||||
import { createContext, useContext, useEffect } from 'react'
|
||||
|
||||
import { NextPage, PaginationData, usePagination } from 'hooks/usePagination'
|
||||
import { useAuthentication, User } from 'utils/authentication'
|
||||
import { handleSocketData, SocketData } from 'utils/handleSocketData'
|
||||
|
||||
export type MessageType = 'text' | 'file'
|
||||
|
||||
export interface MessageData {
|
||||
value: string
|
||||
type: MessageType
|
||||
}
|
||||
|
||||
export interface Message extends MessageData {
|
||||
id: number
|
||||
mimetype: string
|
||||
memberId: number
|
||||
channelId: number
|
||||
createdAt: string
|
||||
updatedAt: string
|
||||
user: User
|
||||
}
|
||||
|
||||
export type Messages = PaginationData<Message>
|
||||
|
||||
export interface MessagesValue {
|
||||
messages: Messages
|
||||
nextPage: NextPage
|
||||
}
|
||||
|
||||
export interface MessagesProviderProps {
|
||||
messages: Messages
|
||||
channelId: string
|
||||
}
|
||||
|
||||
const defaultGuildsContext: MessagesValue = {} as any
|
||||
const MessagesContext = createContext<MessagesValue>(defaultGuildsContext)
|
||||
|
||||
export const MessagesProvider: React.FC<MessagesProviderProps> = (props) => {
|
||||
const { authentication } = useAuthentication()
|
||||
const { data: messages, nextPage, setData } = usePagination<Message>({
|
||||
url: `/channels/${props.channelId}/messages`,
|
||||
api: authentication.api,
|
||||
defaultPaginationData: props.messages,
|
||||
inverse: true
|
||||
})
|
||||
|
||||
useEffect(() => {
|
||||
setData(props.messages)
|
||||
}, [props.messages])
|
||||
|
||||
useEffect(() => {
|
||||
authentication.socket.on('messages', (socketData: SocketData) => {
|
||||
const isAtBottom =
|
||||
window.innerHeight + window.scrollY >= document.body.offsetHeight
|
||||
handleSocketData({ setData })(socketData)
|
||||
if (isAtBottom) {
|
||||
window.scrollTo(0, document.body.scrollHeight)
|
||||
}
|
||||
})
|
||||
}, [])
|
||||
|
||||
return (
|
||||
<MessagesContext.Provider value={{ messages, nextPage }}>
|
||||
{props.children}
|
||||
</MessagesContext.Provider>
|
||||
)
|
||||
}
|
||||
|
||||
export const useMessages = (): MessagesValue => {
|
||||
return useContext(MessagesContext)
|
||||
}
|
@ -1,51 +0,0 @@
|
||||
import { createContext, useState, useEffect, useContext } from 'react'
|
||||
|
||||
export const themes = ['light', 'dark'] as const
|
||||
export type Theme = typeof themes[number]
|
||||
|
||||
export interface ThemeValue {
|
||||
theme: Theme
|
||||
handleToggleTheme: () => void
|
||||
setTheme: React.Dispatch<React.SetStateAction<Theme>>
|
||||
}
|
||||
|
||||
const defaultThemeContext: ThemeValue = {} as any
|
||||
const ThemeContext = createContext<ThemeValue>(defaultThemeContext)
|
||||
|
||||
const getOppositeTheme = (theme: Theme): Theme => {
|
||||
return theme === 'dark' ? 'light' : 'dark'
|
||||
}
|
||||
|
||||
export const ThemeProvider: React.FC = (props) => {
|
||||
const [theme, setTheme] = useState<Theme>('dark')
|
||||
|
||||
useEffect(() => {
|
||||
const localTheme = localStorage.getItem('theme') as Theme
|
||||
if (themes.includes(localTheme)) {
|
||||
setTheme(localTheme)
|
||||
}
|
||||
}, [])
|
||||
|
||||
useEffect(() => {
|
||||
const body = document.querySelector('body') as HTMLBodyElement
|
||||
const oppositeTheme = getOppositeTheme(theme)
|
||||
body.classList.add(`theme-${theme}`)
|
||||
body.classList.remove(`theme-${oppositeTheme}`)
|
||||
localStorage.setItem('theme', theme)
|
||||
}, [theme])
|
||||
|
||||
const handleToggleTheme = (): void => {
|
||||
const oppositeTheme = getOppositeTheme(theme)
|
||||
setTheme(oppositeTheme)
|
||||
}
|
||||
|
||||
return (
|
||||
<ThemeContext.Provider value={{ theme, handleToggleTheme, setTheme }}>
|
||||
{props.children}
|
||||
</ThemeContext.Provider>
|
||||
)
|
||||
}
|
||||
|
||||
export const useTheme = (): ThemeValue => {
|
||||
return useContext(ThemeContext)
|
||||
}
|
Reference in New Issue
Block a user