Created
October 5, 2020 08:53
-
-
Save sp0033212000/ed220d8cc4d4bda0163938080ac2e805 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { createContext, Dispatch, useReducer } from "react"; | |
export type DispatchType<S, R = any> = (dispatch: Dispatch<S>) => R; | |
type ActionType<A extends Action> = { | |
[key: string]: <T extends any[], R = any>( | |
...any: T | |
) => (dispatch: Dispatch<A>) => R; | |
}; | |
type ReducerType<S, A extends Action> = (state: S, actions: A) => S; | |
type BoundActionsProps<A extends Action> = { | |
[key: string]: (action: Action, dispatch: Dispatch<A>) => any; | |
}; | |
interface Action { | |
type: string; | |
payload?: any; | |
} | |
export default <S, A extends Action>( | |
reducer: ReducerType<S, A>, | |
actions: ActionType<A>, | |
defaultValue: S | |
) => { | |
const Context = createContext<{ | |
state: S; | |
actions: Record<keyof typeof actions, any>; | |
} | null>({ state: defaultValue, actions }); | |
const Provider: React.FC = ({ children }) => { | |
const [state, dispatch] = useReducer<ReducerType<S, A>>( | |
reducer, | |
defaultValue | |
); | |
const boundActions: BoundActionsProps<A> = {}; | |
Object.keys(actions).forEach((key) => { | |
boundActions[key] = ((_action, _dispatch) => { | |
return (...argument: any[]) => _action(...argument)(_dispatch); | |
})(actions[key], dispatch); | |
}); | |
return ( | |
<Context.Provider value={{ state, actions: { ...boundActions } }}> | |
{children} | |
</Context.Provider> | |
); | |
}; | |
return { Context, Provider }; | |
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { useContext } from "react"; | |
import { PageContext } from "../../context/PageContext"; | |
import PageContainer from "../Genenal/PageContainer/PageContainer"; | |
const PageOne: React.FC = () => { | |
const {state, actions: { | |
forwardPage // <= auto refer | |
} } = useContext(PageContext)!; | |
return ( | |
<PageContainer zIndex={6}> | |
<div className="main"> | |
<div className="main__background"> | |
<img | |
alt="hero" | |
src={`${require("../../assets/img/hun_p1_main1_img.png")}`} | |
srcSet={[ | |
`${require("../../assets/img/hun_p1_main1_img.png")} 1x`, | |
`${require("../../assets/img/hun_p1_main1_img@2x.png")} 2x`, | |
`${require("../../assets/img/hun_p1_main1_img@3x.png")} 3x`, | |
].join(", ")} | |
className={["main__background--img", "main__background--1"].join( | |
" " | |
)} | |
/> | |
<img | |
alt="hero" | |
src={`${require("../../assets/img/hun_p1_main2_img.png")}`} | |
srcSet={[ | |
`${require("../../assets/img/hun_p1_main2_img.png")} 1x`, | |
`${require("../../assets/img/hun_p1_main2_img@2x.png")} 2x`, | |
`${require("../../assets/img/hun_p1_main2_img@3x.png")} 3x`, | |
].join(", ")} | |
className={["main__background--img", "main__background--2"].join( | |
" " | |
)} | |
/> | |
</div> | |
<div className="main__content"> | |
<h1 className="heading__1 main__heading fadeInContent"> | |
簡單找到 | |
<br /> | |
好客人 | |
</h1> | |
<p className="main__pg fadeInContent"> | |
會員系統 × 訂單管理 × 數據分析 × 行銷工具 | |
</p> | |
</div> | |
</div> | |
</PageContainer> | |
); | |
}; | |
export default PageOne; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import createCusContext, { DispatchType } from "./createCusContext"; | |
export type PageState = { | |
currentPage: number; | |
totalPage: number; | |
}; | |
export enum PageTypesEnums { | |
FORWARD_PAGE = "FORWARD_PAGE", | |
BACKWARD_PAGE = "BACKWARD_PAGE", | |
} | |
interface ForwardPageInterface { | |
type: typeof PageTypesEnums.FORWARD_PAGE; | |
} | |
interface BackwardPageInterface { | |
type: typeof PageTypesEnums.BACKWARD_PAGE; | |
} | |
type PageActions = ForwardPageInterface | BackwardPageInterface; | |
const forwardPageActions = () => ({ | |
type: PageTypesEnums.FORWARD_PAGE, | |
}); | |
const pageReducer = (state: PageState, actions: PageActions) => { | |
switch (actions.type) { | |
case PageTypesEnums.FORWARD_PAGE: | |
return { ...state, currentPage: state.currentPage + 1 }; | |
case PageTypesEnums.BACKWARD_PAGE: | |
return { ...state, currentPage: state.currentPage - 1 }; | |
default: | |
return state; | |
} | |
}; | |
const forwardPage = (): DispatchType<PageActions> => (dispatch) => { | |
dispatch(forwardPageActions()); | |
}; | |
export const { | |
Context: PageContext, | |
Provider: PageProvider, | |
} = createCusContext<PageState, PageActions>( | |
pageReducer, | |
{ forwardPage }, // I want to refer this key where I import this context | |
{ currentPage: 1, totalPage: 0 } | |
); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment