Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

@karrotframe/navigator

Package Overview
Dependencies
Maintainers
2
Versions
40
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@karrotframe/navigator

UX Enhancer

  • 0.25.3
  • latest
  • Source
  • npm
  • Socket score

Version published
Maintainers
2
Created
Source

Light-weight stack navigator for React

  • 🗂 History support
  • 💅 Beautiful page transition animation designed for each platform (Android/iOS)
  • ⚙️ Navigation bar designed for each platform
  • 🪄 Automatically attach close or back button for each circumstance

Core logic of Navigator depends on react-router-dom



Setup

$ yarn add @karrotframe/navigator

Should import the CSS of your app

import '@karrotframe/navigator/index.css'

import { ... } from '@karrotframe/navigator'

Support old versions

Now, @karrotframe/navigator is provided from version 0.23.2 or higher.

If you need old versions from version 0.23.1 to lower, you should use @karrotframe/navigator-legacy instead. Link

It is recommended that you should update to the latest version because it would have a subtle difference for @karrotframe/navigator-legacy.

And yarn add <alias-package>@npm:<package> command would be helpful, if you decide to use @karrotframe/navigator-legacy instead of @karrotframe/navigator.

Components

Navigator

The Navigator component includes elements that are necessary to express the screen. Please include it at the top of the component tree

All the props is typed and commented in TypeScript

import { Navigator } from '@karrotframe/navigator'

const App: React.FC = () => {
  return (
    <Navigator
      theme="Cupertino"
      onClose={() => {
        console.log('Close button is pressed')
      }}
    >
      {/*...*/}
    </Navigator>
  )
}

If you use the useCustomRouter option, you can provide a router other than HashRouter.

import { Navigator } from '@karrotframe/navigator'
import { HashRouter } from 'react-router-dom'

const App = () => {
  return (
    <HashRouter>
      <Navigator useCustomRouter>...</Navigator>
    </HashRouter>
  )
}

Screen

The Screen component is used to declare a screen. Declare it inside Navigator.

All the props is typed and commented in TypeScript

import { Navigator, Screen } from '@karrotframe/navigator'

const App: React.FC = () => {
  return (
    <Navigator
      theme="Cupertino"
      onClose={() => {
        console.log('Close button is pressed')
      }}
    >
      <Screen path="/" component={MyComponent} />
      {/* or */}
      <Screen path="/">
        <MyComponent />
      </Screen>
    </Navigator>
  )
}

Be sure to use component or children (if both props are declared at the same time, component takes precedence)

ScreenHelmet

By default, Screen does not include a top navigation bar. To add or modify the built-in top navigation bar, use the ScreenHelmet component.

All the props is typed and commented in TypeScript

import { ScreenHelmet } from '@karrotframe/navigator'

const MyComponent: React.FC = () => {
  return (
    <div>
      <ScreenHelmet
        title="My App"
        appendLeft={<div>Append to Left</div>}
        appendRight={<div>Append to Right</div>}
        customBackButton={<div>Back</div>}
        customCloseButton={<div>Close</div>}
        visible={false}
        preventSwipeBack={true}
        noBackButton={true}
        noCloseButton={true}
      />
    </div>
  )
}

Hooks

useNavigator

Trigger a screen transition.

All arguments are typed and commented in TypeScript

import { useNavigator } from '@karrotframe/navigator'

const Posts: React.FC = () => {
  const { push, pop, replace } = useNavigator()

  const goPost = (postId: string) => () => {
    // Go to a specific path
    push(`/posts/${postId}`)

    // Opens a specific path with some options
    push(`/posts/${postId}`, {
      present: true, // option to prevent swipe back (Cupertino theme only)
      animate: false, // option to control animation effect (default: true)
    })
  }

  const goBack = () => {
    // Go one step back
    pop()

    // Multiple levels can be popped through the depth argument
    pop(1)

    // declare option to control animation effect (default: true)
    pop(1, { animate: false })
  }

  useEffect(() => {
    if (!user) {
      // Move to a specific path (replace)
      // It moves without animation, so it is suitable for redirect behavior.
      replace('/login')
    }
  })

  return (
    <div>
      {posts.map((post) => {
        return (
          <div>
            {/* ... */}
            <button onClick={goPost(post.id)}>View article details</button>
          </div>
        )
      })}
      {/* ... */}
      <button onClick={goBack}>Back</button>
    </div>
  )
}

useCurrentScreen

Get current screen's information

All arguments are typed and commented in TypeScript

import { useCurrentScreen } from '@karrotframe/navigator'

const Posts: React.FC = () => {
  const { isTop, isRoot } = useCurrentScreen()

  return (
    <div>
      {isTop && <span>This screen is in top</span>}
      {isRoot && <span>This screen is in root</span>}
    </div>
  )
}

useParams

To prevent unintentional screen changes due to changes in the path between screen transitions, you can use a path parameter through useParams.

All arguments are typed and commented in TypeScript

import { useParams } from '@karrotframe/navigator'

const Post: React.FC = () => {
  /**
   * Value entered as path parameter (not changed in screen transitions)
   */
  const params = useParams()

  return /* ... */
}

useQueryParams

To prevent unintentional screen changes due to changes in the path between screen transitions, you can use a querystring through useQueryParams.

All arguments are typed and commented in TypeScript

import { useQueryParams } from '@karrotframe/navigator'

const Post: React.FC = () => {
  /**
   * Value entered as querystring (not changed in screen transitions)
   */
  const querystring = useQueryParams()

  return /* ... */
}

Advance

Nested Routes

Use Route in react-router-dom

// <Screen path='/example' component={ExampleScreen} />

import { Route, useHistory } from 'react-router-dom'

const ExampleScreen = () => {
  const history = useHistory()

  const moveToInside2 = () => {
    history.push('/example/inside2')
  }
  const goBack = () => {
    history.goBack()
  }
  const goBackFurther = () => {
    // You can go back by integrating the current internal routing
    // with the previous Karrotframe screen transitions.
    history.go(-4)
  }

  return (
    <div>
      <Route path="/example/inside1">...</Route>
      <Route path="/example/inside2">...</Route>
    </div>
  )
}

If the _si query string is not included in the path, Karrotframe recognizes it as an internal routing and does not perform any separate animation processing.

await push()

You can transfer data between screens through pop().send() and await push() of useNavigator.

When the depth argument in the pop() function is set to 2 or more, it is possible to send over multiple screens.

import { useNavigator } from '@karrotframe/navigator'

const Posts: React.FC = () => {
  const { push } = useNavigator()

  const writePost = () => {
    // Wait for the data to be sent from the next screen
    const data = await push('/posts/write')
    console.log(data)
    // {
    //   hello: 'world',
    // }
  }
  return (
    <div>
      <button onClick={writePost}>Write post</button>
    </div>
  )
}

const PostWriteForm: React.FC = () => {
  const { pop } = useNavigator()

  const onSubmit = () => {
    // Transfer data to previous screen
    pop().send({
      hello: 'world',
    })

    // It is also possible to transfer data by skipping several steps as shown below.
    pop(3).send({
      hello: 'world',
    })
  }

  return /* ... */
}

react-router-dom APIs

You can use useLocation, useRouteMatch and useHistory that exist in react-router-dom.

import { useLocation, useHistory, useRouteMatch } from 'react-router-dom'

const Post: React.FC = () => {
  /**
   * Current location information
   */
  const location = useLocation()

  /**
   * History API
   */
  const history = useHistory()

  /**
   * Compares the current location with a specific path regex and returns the parsed value.
   */
  const match = useRouteMatch({
    path: '/:post_id',
  })

  return /* ... */
}

FAQs

Package last updated on 02 Aug 2022

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc