Skip to content

Instantly share code, notes, and snippets.

@rafaelcorreiapoli
Last active November 29, 2017 03:42
Show Gist options
  • Save rafaelcorreiapoli/80109e78e19973518675a23ab108b594 to your computer and use it in GitHub Desktop.
Save rafaelcorreiapoli/80109e78e19973518675a23ab108b594 to your computer and use it in GitHub Desktop.
Typescript HOC
interface Options {
upperCase: boolean
intervalMs: number
}
// Props que serão passadas para o WrappedComponent
interface InjectedProps {
name: string
}
// Props que o Componente final recebe
interface ExternalProps {
namePool: string[]
}
// Estado interno do Enhanced Component
interface HOCState {
selectedIndex: number
}
const withRandomName = (options: Options) =>
<TOriginalProps extends {}>(WrappedComponent:
React.ComponentClass<TOriginalProps & InjectedProps> |
React.StatelessComponent<TOriginalProps & InjectedProps>) =>
class extends React.Component<TOriginalProps & ExternalProps, HOCState> {
intervalId: number
constructor(props: TOriginalProps & ExternalProps) {
super(props)
this.state = {
selectedIndex: 0
}
}
public render(): JSX.Element {
const name = this.props.namePool[this.state.selectedIndex]
const formattedName = options.upperCase ? name.toUpperCase() : name
return (
<WrappedComponent
{...this.props}
name={formattedName}
/>
)
}
public componentDidMount() {
this.intervalId = setInterval(this.setNewNameIndex, options.intervalMs)
}
public componentWillUnmount() {
clearInterval(this.intervalId)
}
private setNewNameIndex = () => {
this.setState({
selectedIndex: rnd(0, this.props.namePool.length - 1)
})
}
}
interface IMyComponentProps {
color: string
name: string
}
const DisplayName: React.SFC<IMyComponentProps> = ({
name,
color
}) => (
<Text style={{ color }}>
{name}
</Text>
)
const RandomName = withRandomName({ upperCase: false, intervalMs: 200 })(DisplayName)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment