npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

universaluikitforreactimplementation

v1.0.2

Published

Universal components repository

Downloads

6

Readme

Universal Components Package

What are universal components?

Universal components are React components that can render anywhere. They are platform agnostic, which means you can use them on the web and native without changing any lines of code.

Why architect your components this way? The main benefit is code reuse. By building your components with React Native primitives, you only have to write them once. Since other platforms such as VR & Sketch also share RN primitives, you can eventually expand universal components to include those platforms as well (although some issues such as cross-platform SVGs are still getting ironed out).

To achieve a fully universal component library, we use react-native-web. RNW sits as a layer on top of DOM primitives; for example, <View /> will render to a <div/> on the web. RNW has nearly complete feature parity with RN, so you can be confident that almost any code that works with RN will also work with RNW. Check the RNW explorer for a comprehensive list of supported components & APIs.

Workflow

Components can be developed in isolation with Storybook to eliminate differences between projects. This project uses the web version of Storybook to make sure that all universal components will render on the web.

Folder structure:

  • components/: Where all your universal components live
  • .storybook: Storybook specific configuration
  • storybook-static: Where storybook exports builds to
  • flow-typed/: Shared Flow types

Components are exported in index.js and published to an NPM package (@<YOUR_NPM_USERNAME>/universal-components) so they can be consumed by multiple projects. In order to coordinate publishing multiple packages in this repo, you use Lerna. Run lerna publish from root of project to publish a version of this package. Then, you can upgrade the package within the application (yarn upgrade @<YOUR_NPM_USERNAME>/universal-components) and import the components to use them.

Available Scripts

yarn storybook

Starts up storybook for development of components

yarn build

Builds the production version of storybook

yarn deploy

Deploys the production build of storybook to surge.sh

Styling

For styling, the StyleSheet API is included in RN so you can write your styles as JS objects. RNW supports the StyleSheet API via CSS modules. Don't be alarmed if you open up dev tools and see a huge string of ugly looking class names attached to your DOM elements - this is RNW's way of memoizing styles for fast performance compared to other CSS in JS solutions.

Since the RNW styling API mirrors RN's, it follows the default styling properties of Yoga, Facebook's cross-platform layout engine. The main point to remember about Yoga is that Flexbox is enabled by default with flexDirection: column.

Platform specific code

Sometimes, you might need to account for slight differences between platforms in your components. You can either use the Platform API or platform extensions to accomplish this.

Platform API: Good for styling one-offs

import { Platform } from 'react-native';

switch (Platform.OS) {
  case 'ios':
  case 'android':
    // do something on native
  case 'web':
  default:
    // do something on web
}

You can also write it like this:

import { Platform } from 'react-native';

const styles = StyleSheet.create({
  container: {
    flex: 1,
    ...Platform.select({
      ios: {
        backgroundColor: 'red',
      },
      android: {
        backgroundColor: 'blue',
      },
    }),
  },
});

Platform extensions: Good for differences in component implementation

import { Button } from '../components/button'
// will resolve from '../components/button/index.web.js' on web, '../components/button/index.ios.js' on iOS, etc

This functionality is built into the React Native packager. We've also added the ability to resolve platform extensions on web in the babel config (see .babelrc for an example).

Storybook configuration

Storybook configuration can be found in ./.storybook. The two key parts to notice are:

  • Stories live next to components (see example) and we load them via ./.storybook/config.js
  • Because we use babel-minify over UglifyJS for minifying we have to use full control mode for Webpack ./.storybook/webpack.config.js

How to use React Native modules on the web

⚠️ Warning: This is slightly hacky, but if you should do it anyway because standardizing third party modules & component libraries across platforms is important.

Some examples of RN libraries that can be used on the web include victory-native, react-native-calendars, and react-native-vector-icons. We're able to use these because of RNW's high feature parity with RN, the ability to transpile, and alias with Webpack or Babel.

Steps:

  1. After you install the library, you will need to transpile it with Babel because all RN modules are ES6. To do this, add the module name to the RegExp in babel-loader in .storybook/webpack.config.js:
{
  test: /\.js$/,
  exclude: /node_modules\/(?!svgs)(?!MODULE_NAME_HERE)/,
  loader: 'babel-loader',
  query: { cacheDirectory: true },
},
  1. In some cases, you'll need to create an alias in the Babel config. For example, you alias svgs to react-native-svg for your cross-platform svg implementation. You'll almost always be aliasing a web library's name to its native counterpart because aliasing is currently harder to execute with the RN packager, Metro.

Add the alias to "module-resolver" plugin in .babelrc like this:

"alias": {
  "react-native": "react-native-web",
  "react-native-svg": "svgs",
  1. If you're aliasing, you will need to tell Flow how to resolve the module. Add the module name mapper to .flowconfig:
module.name_mapper='\(react-native\)' -> 'react-native-web'
module.name_mapper='\(react-native-svg\)' -> 'svgs'
  1. If you've made it this far and everything is working, celebrate! 🎉 You can now import your components normally. If you're getting cryptic errors, you might want to reach out to the maintainer of the library. Usually, they're more than happy to offer their help with supporting web. 😊

Resources