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 🙏

© 2026 – Pkg Stats / Ryan Hefner

@easylivechat/react-native-ui

v0.1.5

Published

Prebuilt, themeable React Native chat UI for EasyLiveChat live customer support: launcher bubble, chat screen, pre-chat form, attachments and CSAT, driven by your widget config.

Readme

@easylivechat/react-native-ui

Prebuilt, themeable React Native chat UI for EasyLiveChat: launcher bubble, chat screen, pre-chat form, attachments, voice notes, CSAT and post-chat survey — all driven by your workspace's widget config.

Re-exports the whole headless core, so this is the only package you install.


Install

npx expo install \
  @easylivechat/react-native-ui \
  expo-crypto expo-secure-store @react-native-async-storage/async-storage

Those three are required. expo-crypto also needs one line of wiring — see the core README:

import * as Crypto from 'expo-crypto';
import { setUuidGenerator } from '@easylivechat/react-native-ui';
setUuidGenerator(Crypto.randomUUID);

Everything else is optional, and only pulled in when the matching feature is used:

| optional peer | needed for | if missing | |---|---|---| | expo-image | disk-cached avatars and image attachments | falls back to RN's Image (no disk cache) | | expo-image-picker | the built-in "Photo" attach option | supply onPickAttachments instead | | expo-document-picker | the built-in "File" attach option | supply onPickAttachments instead | | expo-audio | voice notes and the incoming-message chime | both degrade to silence |

A host that will never enable voice messages should not install expo-audio and should not ship a microphone permission. When you do enable it, add NSMicrophoneUsageDescription (iOS) and RECORD_AUDIO (Android) to your own app — without them the OS terminates the app the moment recording starts.

No icon font and no SVG peer: every glyph is drawn from plain Views.

Quick start

import {
  EasyLiveChat,
  EasyLiveChatLauncher,
  SecureAsyncStorage,
} from '@easylivechat/react-native-ui';

await EasyLiveChat.instance.boot(
  { apiBase: 'https://api.livechattools.com', tenantSlug: 'acme' },
  { storage: new SecureAsyncStorage() },
);

export default function App() {
  return (
    <View style={{ flex: 1 }}>
      <YourApp />
      <EasyLiveChatLauncher />
    </View>
  );
}

Or push the screen yourself:

<EasyLiveChatScreen showAppBar onRequestClose={() => navigation.goBack()} />

Leaving vs ending

They are different actions, deliberately.

  • Backing out of the chat screen does not end the conversation — the visitor can leave mid-chat and be resumed right where they were.
  • Ending is explicit: <EasyLiveChatEndChatButton /> confirms first, and the post-chat survey then appears in place on the screen.

endChat() returns whether a post-chat step will follow. Use the return value; you cannot infer it from the phase afterwards, because the phase is driven by the server's close echo, which is deliberately ignored for a conversation already closed or already rated.

Theming

<EasyLiveChatScreen themeOverride={{ primary: '#111827', background: '#0B1120' }} />

Colours come from the workspace config; any field you pass wins. direction is never taken from the override — layout direction is a function of locale and content, not branding, so a colours-only override cannot silently force an RTL workspace to LTR. Use the explicit directionOverride prop if you genuinely need to force it.

Localization and RTL

53+ chrome strings ship in 13 locales (en ar ckb de es fr hi it kmr pt tr ur zh). Resolution order: host-forced locale → the locale prop → server workspace locale → device locale → en, matching on the language subtag only (pt-BR → pt). ku maps to ckb (Sorani); kmr is Badini/Kurmanji.

<EasyLiveChatScreen
  locale="ckb"
  strings={{ send: 'Send it' }}                    // every locale
  stringsByLocale={{ ckb: { send: 'بنێرە' } }}      // wins, key by key
/>

stringsByLocale also lets you add a language the SDK does not ship, without waiting on a release.

Tenant-authored copy is never localized. welcomeTitle, welcomeSubtitle, offlineMessage and every form label come from the dashboard per language and are rendered verbatim.

The chat mirrors for ar/ckb/kmr/ur while your host app stays LTR. The SDK never calls I18nManager.forceRTL — that is process-global, needs an app restart, and would flip your app too. Direction is passed down through context and applied with row-reverse, textAlign and writingDirection.

The composer additionally follows the text: it turns around on the first strongly-directional character the visitor types, remembers what they last wrote for when the box is empty, and falls back to the device language and then the workspace direction.

Attachments

The built-in pickers upload a { uri } file reference, which RN's FormData streams straight off disk. To use your own sheet:

<EasyLiveChatScreen
  onPickAttachments={async () => [
    { data: { uri }, filename: 'photo.jpg', contentType: 'image/jpeg' },
  ]}
/>

Limitations

Background push is not implemented — see the core package's README. Web is not supported. customCss is a documented no-op.

License

MIT