Home > OS >  Create helper functions which has hooks
Create helper functions which has hooks

Time:04-10

I want to create helper functions for my Toasts from nativebase , my code looks like below

import React from "react";

import { useToast } from "native-base";

export const ErrorAlert = (name, desc) => {
  const toast = useToast();
  toast.show({
    duration: 2000,
    placement: "top",
    title: name,
    status: "error",
    description: desc,
  });
};

export const SuccessAlert = (name, desc) => {
  const toast = useToast();
  toast.show({
    duration: 2000,
    placement: "top",
    title: name,
    status: "success",
    description: desc,
  });
};

But I get following error

[Unhandled promise rejection: Error: Invalid hook call. Hooks can only be called inside of the body of a function component.

I know this is not allowed by react , but is there any way i can create custom functions to use Hooks and export it for easier use ?

import { ErrorAlert } from "../Helper/Alert";

Thank you

CodePudding user response:

You have to ways as I wrote in the comment above

solution 1 pass toast as an argument

export const ErrorAlert = (toast,name, desc) => {
  toast.show({
    duration: 2000,
    placement: "top",
    title: name,
    status: "error",
    description: desc,
  });
};

export const SuccessAlert = (toast, name, desc) => {
  toast.show({
    duration: 2000,
    placement: "top",
    title: name,
    status: "success",
    description: desc,
  });
};

solution 2 create a new hook that uses useToast

import React from "react";

import { useToast } from "native-base";

export const useAlert = () => {
   const toast = useToast()
   const SuccessAlert = (name, desc) => {
  
  toast.show({
    duration: 2000,
    placement: "top",
    title: name,
    status: "success",
    description: desc,
  });
};    
const ErrorAlert = (name, desc) => {

  toast.show({
    duration: 2000,
    placement: "top",
    title: name,
    status: "error",
    description: desc,
  });
};
return {ErrorAlert, SuccessAlert }
}

I prefer option 2 because is a bit cleaner than in you component simply use the new hook in this way

const MyComponent = (props) => {
  const {ErrorAlert, SuccessAlert } = useAlert()

 ...
}

CodePudding user response:

Create custom hooks (useErrorAlert for example) that returns a function:

export const useErrorAlert = (title, description) => {
  const toast = useToast();
  
  return useCallback(() => { 
    toast.show({
      duration: 2000,
      placement: "top",
      title,
      status: "error",
      description,
    });
  }, [description, description, toast]);
};

And then use it in your component:

export const Demo = () => {
  const errorAlert = useErrorAlert('title', 'description');
  
  return (
    <button onClick={errorAlert}>Alert</button>
  )
}

And you can make it more generic by creating a factory function that returns custom hooks:

const createUseAlert = (status, duration = 2000, placement = 'top') => 
  (title, description) => {
    const toast = useToast();
  
    return useCallback(() => { 
      toast.show({
        duration,
        placement,
        title,
        status,
        description,
      });
    }, [title, description, toast]);
  }

export const useErrorAlert = createUseAlert('error');

export const useSuccessAlert = createUseAlert('success');
  • Related