Lightning-fast, modern in-app browser for React Native powered by Nitro Modules β‘
Experience the next generation of React Native performance with direct JSI bindings, zero bridge overhead, and beautiful native browser experiences on both iOS and Android.
- Direct JSI Communication: Bypass the React Native bridge entirely for instant native calls
- Zero Serialization Overhead: No JSON marshalling between JavaScript and native code
- Native-Speed Execution: Execute at native performance levels, not bridge speeds
- Optimal Memory Usage: Minimal memory footprint with efficient resource management
- Auto-Generated Types: TypeScript definitions generated directly from native code
- Compile-Time Safety: Catch interface mismatches before runtime
- Intellisense Support: Full IDE autocompletion for all native methods and properties
- Future-Proof Architecture: Built for React Native's New Architecture from day one
- Hermes Optimized: Designed specifically for Hermes JavaScript engine
- Fabric Compatible: Seamlessly works with the new Fabric renderer
- TurboModule Ready: Native support for TurboModules ecosystem
- Concurrent Features: Safe to use with React 18's concurrent features
- β‘ Lightning Fast: Nitro modules with direct JSI bindings
- π― Modern API: Clean TypeScript interface with React hooks support
- π Authentication: Full OAuth/SSO flow support with deep linking
- π¨ Customizable: Extensive styling options for iOS and Android
- π± Native Feel: Uses SafariViewController (iOS) and Chrome Custom Tabs (Android)
- π Secure: Supports incognito mode and ephemeral sessions
- π Simple & Elegant: Intuitive API designed for modern React Native apps
- Minimum iOS Version: 11.0+
- Xcode: 14.0+
- React Native: 0.70+
- Frameworks: SafariServices, AuthenticationServices
- Minimum API Level: 23 (Android 6.0+)
- Target API Level: 33+
- React Native: 0.70+
- Dependencies: androidx.browser:browser:1.8.0
- Version: 0.70.0+
- New Architecture: β Fully supported
- Hermes: β Recommended
- Expo: β Not compatible (requires native modules)
npm install react-native-inappbrowser-nitro react-native-nitro-modules
or
yarn add react-native-inappbrowser-nitro react-native-nitro-modules
Note:
react-native-nitro-modules
is required as this library leverages the powerful Nitro framework.
For iOS, the library uses CocoaPods for linking:
-
Navigate to your iOS project directory:
cd ios
-
Install pods:
pod install
For Android, the library is automatically linked via Gradle.
import { InAppBrowser } from 'react-native-inappbrowser-nitro';
const openBrowser = async () => {
try {
if (await InAppBrowser.isAvailable()) {
const result = await InAppBrowser.open('https://github.com', {
// iOS options
preferredBarTintColor: '#453AA4',
preferredControlTintColor: 'white',
// Android options
toolbarColor: '#6200EE',
showTitle: true,
});
console.log('π Success:', result);
}
} catch (error) {
console.error('β Error:', error);
}
};
import { useInAppBrowser } from 'react-native-inappbrowser-nitro';
function MyComponent() {
const { open, isLoading, error } = useInAppBrowser();
const handleOpenBrowser = async () => {
try {
const result = await open('https://github.com', {
preferredBarTintColor: '#453AA4',
toolbarColor: '#6200EE',
});
console.log('π Browser opened:', result);
} catch (err) {
console.error('β Failed to open browser:', err);
}
};
return (
<Button
title={isLoading ? "Opening..." : "Open Browser"}
onPress={handleOpenBrowser}
disabled={isLoading}
/>
);
}
import { InAppBrowser } from 'react-native-inappbrowser-nitro';
const authenticateUser = async () => {
try {
const result = await InAppBrowser.openAuth(
'https://provider.com/oauth/authorize?client_id=...',
'your-app://oauth', // redirect URL scheme
{
ephemeralWebSession: true, // π΅οΈ iOS incognito mode
showTitle: false,
}
);
if (result.type === 'success' && result.url) {
console.log('π Auth successful:', result.url);
// Handle successful authentication
}
} catch (error) {
console.error('β Auth failed:', error);
}
};
-
isLoading
behavior
On Android, theopen()
promise resolves immediately after launching Chrome Custom Tabs, so the React hookβsisLoading
toggles off right away. On iOS we updatedopen()
to resolve immediately after presenting SafariViewController (instead of waiting for user dismissal), matching Android behavior. -
partialCurl
transition
The iOSmodalTransitionStyle
valuepartialCurl
is only supported when paired with afullScreen
presentation. If you specifypartialCurl
, the library now forcesmodalPresentationStyle
tofullScreen
under the hood to prevent UIKit crashes withoverFullScreen
.
Method | Description | Platform | Performance |
---|---|---|---|
isAvailable() |
Check if InAppBrowser is supported | iOS, Android | β‘ Instant |
open(url, options?) |
Open URL in in-app browser | iOS, Android | β‘ Native speed |
openAuth(url, redirectUrl, options?) |
Open URL for authentication | iOS, Android | β‘ Native speed |
close() |
Close the browser | iOS, Android | β‘ Instant |
closeAuth() |
Close authentication session | iOS, Android | β‘ Instant |
Option | Type | Description | Default |
---|---|---|---|
dismissButtonStyle |
'done' | 'close' | 'cancel' |
Style of dismiss button | 'done' |
preferredBarTintColor |
string |
Navigation bar background color | System default |
preferredControlTintColor |
string |
Control elements color | System default |
readerMode |
boolean |
Enable Reader mode if available | false |
animated |
boolean |
Animate presentation | true |
modalPresentationStyle |
string |
Modal presentation style | 'automatic' |
modalTransitionStyle |
string |
Modal transition style | 'coverVertical' |
modalEnabled |
boolean |
Present modally vs push | true |
enableBarCollapsing |
boolean |
Allow toolbar collapsing | false |
ephemeralWebSession |
boolean |
Use incognito mode (auth only) | false |
Option | Type | Description | Default |
---|---|---|---|
showTitle |
boolean |
Show page title in toolbar | true |
toolbarColor |
string |
Toolbar background color | System default |
secondaryToolbarColor |
string |
Secondary toolbar color | System default |
navigationBarColor |
string |
Navigation bar color | System default |
enableUrlBarHiding |
boolean |
Hide URL bar on scroll | false |
enableDefaultShare |
boolean |
Show share button | false |
animations |
object |
Custom enter/exit animations | System default |
headers |
object |
Additional HTTP headers | {} |
forceCloseOnRedirection |
boolean |
Close on redirect | false |
hasBackButton |
boolean |
Show back arrow instead of X | false |
showInRecents |
boolean |
Show in Android recents | true |
Android emulators often lack pre-installed browsers. The library handles this gracefully:
- π₯ First: Attempts Chrome Custom Tabs
- π₯ Fallback: Uses system browser chooser
- π₯ Last resort: Directs to Play Store for browser installation
For Development:
- Install Chrome on your emulator via Play Store
- Use a real device (recommended)
- Use the Web Browser app that comes with some emulators
Safari View Controller has limited functionality on iOS Simulator:
- Use a real iOS device for full testing
- Some features like Reader mode may not work on simulator
Since this library uses Nitro modules, you get optimal performance out of the box! But here are some additional tips:
// π± Check availability once and cache the result
const [isSupported, setIsSupported] = useState<boolean>();
useEffect(() => {
InAppBrowser.isAvailable().then(setIsSupported);
}, []);
// π¨ Reuse options objects to avoid recreating them
const browserOptions = useMemo(() => ({
preferredBarTintColor: '#453AA4',
toolbarColor: '#6200EE',
}), []);
We welcome contributions! See the contributing guide to learn how to contribute to the repository and development workflow.
MIT
Built with β€οΈ using Nitro Modules for the React Native community
Experience the future of React Native performance today! π