Skip to main content
UI Kitten v5.0 is a significant improvement and rework of the previous version. We believe these changes bring UI Kitten to the new level of quality and feature richness. To achieve this and allow UI Kitten to grow faster and better, we had to refactor a lot of internal implementations, as well as public APIs.
We hope that next UI Kitten versions won’t receive such significant upgrades and the amount of breaking changes will be kept as low as possible.

Migration Goals

The v5.0 release focuses on:
  • Flexible styling with new convenient and unified component interfaces
  • Declarative rendering of nested components
  • Better TypeScript support with improved type definitions
  • Better documentation with detailed descriptions for component examples and properties
  • Performance improvements for styled components and style hooks
  • React Native 0.62 support and compatibility with latest dependencies

Prerequisites

Before starting the migration, ensure you have:
  • UI Kitten v4.x installed in your project
  • React Native 0.59 or higher
  • Basic understanding of React and React Native
This is a major version upgrade with breaking changes. We recommend testing thoroughly in a development environment before deploying to production.

Migration Steps

1

Update Package Dependencies

Update your @ui-kitten/* packages to version 5 and @eva-design/* packages to version 2:
npm
npm install @ui-kitten/[email protected] @eva-design/[email protected]
yarn
yarn add @ui-kitten/[email protected] @eva-design/[email protected]
If you use Eva Icons:
npm
npm install @ui-kitten/[email protected]
yarn
yarn add @ui-kitten/[email protected]
The react-native-svg package is now required and included in peer dependencies.
npm
npm install react-native-svg
yarn
yarn add react-native-svg
2

Understand the New API Patterns

Version 5.0 introduces several unified API patterns across components:

Pattern 1: Text Properties Accept Components

Components that previously accepted only strings for text properties now accept strings, numbers, or function components:
Before
<Button text="Click Me" textStyle={myStyle} />
After
<Button>
  {evaProps => <Text {...evaProps} style={[evaProps.style, myStyle]}>Click Me</Text>}
</Button>
This change makes *Style properties (like textStyle, labelStyle) redundant.

Pattern 2: Icon Properties Renamed

Icon properties are renamed to accessoryLeft and accessoryRight:
Before
<Button icon={StarIcon} />
<Input icon={StarIcon} />
After
<Button accessoryRight={StarIcon} />
<Input accessoryLeft={StarIcon} />

Pattern 3: Popover-Based Components

Popover and related components (Tooltip, OverflowMenu) now accept content as children and the anchor as a prop:
Before
<Popover content={renderContent} />
After
<Popover anchor={renderToggleButton}>
  {renderContent}
</Popover>

Pattern 4: Eva Props Combined

HOCs like withStyles and styled now inject a single eva property combining theme, style, and dispatch:
Before
const MyComponent = ({ theme, style }) => (
  <View style={style.container} />
);
After
const MyComponent = ({ eva }) => (
  <View style={eva.style.container} />
);
3

Update Component Usage

Button

Remove textStyle property:
Before
<Button text="Click Me" textStyle={customStyle} />
After
import { Button, Text } from '@ui-kitten/components';

<Button>
  {evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Click Me</Text>}
</Button>
Update icon property:
Before
<Button icon={StarIcon} />
After
<Button accessoryRight={StarIcon} />
// or
<Button accessoryLeft={StarIcon} />

Radio, CheckBox, and Toggle

Move text to children:
Before
<Radio text="Option 1" textStyle={customStyle} />
<CheckBox text="Accept terms" textStyle={customStyle} />
<Toggle text="Enable feature" textStyle={customStyle} />
After
import { Radio, CheckBox, Toggle, Text } from '@ui-kitten/components';

<Radio>Option 1</Radio>
<CheckBox>Accept terms</CheckBox>
<Toggle>Enable feature</Toggle>

// With custom styles:
<Radio>
  {evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Option 1</Text>}
</Radio>

Input

Update icon and style properties:
Before
<Input 
  icon={StarIcon}
  label="Email"
  labelStyle={labelStyle}
  caption="Enter your email"
  captionStyle={captionStyle}
/>
After
import { Input, Text } from '@ui-kitten/components';

<Input 
  accessoryRight={StarIcon}
  label={evaProps => <Text {...evaProps} style={[evaProps.style, labelStyle]}>Email</Text>}
  caption={evaProps => <Text {...evaProps} style={[evaProps.style, captionStyle]}>Enter your email</Text>}
/>

Select

Replace data prop with children:
Before
<Select 
  data={options}
  icon={StarIcon}
  labelStyle={customStyle}
  placeholderStyle={placeholderStyle}
/>
After
import { Select, SelectItem, SelectGroup } from '@ui-kitten/components';

<Select 
  accessoryRight={StarIcon}
  label={evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Label</Text>}
  placeholder={evaProps => <Text {...evaProps} style={[evaProps.style, placeholderStyle]}>Placeholder</Text>}
>
  <SelectItem title='Option 1' />
  <SelectItem title='Option 2' />
  <SelectGroup title='Group'>
    <SelectItem title='Option 2.1' />
    <SelectItem title='Option 2.2' />
  </SelectGroup>
</Select>

Autocomplete

Replace data and renderItem with children:
Before
<Autocomplete 
  data={options}
  renderItem={renderItem}
  icon={StarIcon}
/>
After
import { Autocomplete, AutocompleteItem } from '@ui-kitten/components';

<Autocomplete accessoryRight={StarIcon}>
  <AutocompleteItem title='Option 1' />
  <AutocompleteItem title='Option 2' />
  <AutocompleteItem title='Option 3' />
</Autocomplete>

Datepicker and RangeDatepicker

Update icon and style properties:
Before
<Datepicker 
  icon={CalendarIcon}
  labelStyle={labelStyle}
  captionStyle={captionStyle}
/>
After
<Datepicker 
  accessoryRight={CalendarIcon}
  label={evaProps => <Text {...evaProps} style={[evaProps.style, labelStyle]}>Date</Text>}
  caption={evaProps => <Text {...evaProps} style={[evaProps.style, captionStyle]}>Select date</Text>}
/>
Replace data prop with children:
Before
<Menu data={menuItems} />
<Drawer data={drawerItems} />
After
import { Menu, MenuItem, MenuGroup } from '@ui-kitten/components';
import { Drawer, DrawerItem, DrawerGroup } from '@ui-kitten/components';

<Menu>
  <MenuItem title='Option 1' />
  <MenuGroup title='Group'>
    <MenuItem title='Option 1.1' />
    <MenuItem title='Option 1.2' />
  </MenuGroup>
</Menu>

<Drawer>
  <DrawerItem title='Screen 1' />
  <DrawerGroup title='Section'>
    <DrawerItem title='Screen 2' />
    <DrawerItem title='Screen 3' />
  </DrawerGroup>
</Drawer>

TopNavigation

Update accessory and style properties:
Before
<TopNavigation
  title="Home"
  titleStyle={titleStyle}
  subtitle="Welcome"
  subtitleStyle={subtitleStyle}
  leftControl={BackAction}
  rightControls={[SettingsAction]}
/>
After
import { TopNavigation, TopNavigationAction } from '@ui-kitten/components';

<TopNavigation
  title={evaProps => <Text {...evaProps} style={[evaProps.style, titleStyle]}>Home</Text>}
  subtitle={evaProps => <Text {...evaProps} style={[evaProps.style, subtitleStyle]}>Welcome</Text>}
  accessoryLeft={BackAction}
  accessoryRight={SettingsAction}
/>

// For multiple actions, use React.Fragment:
const RightActions = () => (
  <React.Fragment>
    <TopNavigationAction icon={SearchIcon} />
    <TopNavigationAction icon={SettingsIcon} />
  </React.Fragment>
);

BottomNavigation and TabBar

Update title properties:
Before
<BottomNavigation>
  <BottomNavigationTab title="Home" titleStyle={customStyle} />
  <BottomNavigationTab title="Profile" titleStyle={customStyle} />
</BottomNavigation>

<TabBar>
  <Tab title="Tab 1" titleStyle={customStyle} />
  <Tab title="Tab 2" titleStyle={customStyle} />
</TabBar>
After
<BottomNavigation>
  <BottomNavigationTab 
    title={evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Home</Text>}
  />
  <BottomNavigationTab 
    title={evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Profile</Text>}
  />
</BottomNavigation>

<TabBar>
  <Tab title={evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Tab 1</Text>} />
  <Tab title={evaProps => <Text {...evaProps} style={[evaProps.style, customStyle]}>Tab 2</Text>} />
</TabBar>

List and ListItem

Update accessory and style properties:
Before
<ListItem
  title="Item Title"
  titleStyle={titleStyle}
  description="Item description"
  descriptionStyle={descriptionStyle}
  icon={StarIcon}
  accessory={CheckIcon}
  onPress={(index) => console.log(index)}
/>
After
import { ListItem } from '@ui-kitten/components';

<ListItem
  title={evaProps => <Text {...evaProps} style={[evaProps.style, titleStyle]}>Item Title</Text>}
  description={evaProps => <Text {...evaProps} style={[evaProps.style, descriptionStyle]}>Item description</Text>}
  accessoryLeft={StarIcon}
  accessoryRight={CheckIcon}
  onPress={() => console.log('pressed')} // Note: index is no longer passed
/>
ListItem.onPress no longer receives the item index as a parameter. Store necessary data in closures or use state management.

Card

Update header and footer:
Before
<Card>
  <CardHeader title="Title" description="Description" />
  <Text>Content</Text>
</Card>
After
import { Card, Layout, Text } from '@ui-kitten/components';

const Header = (evaProps) => (
  <Layout {...evaProps}>
    <Text category='h6'>Title</Text>
    <Text category='s1'>Description</Text>
  </Layout>
);

const Footer = (evaProps) => (
  <Layout {...evaProps}>
    <Text category='c2'>Footer</Text>
  </Layout>
);

<Card header={Header} footer={Footer}>
  <Text>Content</Text>
</Card>

Popover, Tooltip, and OverflowMenu

Move content to children and anchor to prop:
Before
<Popover content={renderContent} />

<Tooltip text="Tooltip text" />

<OverflowMenu data={menuData} />
After
import { Popover, Tooltip, OverflowMenu, MenuItem, Button } from '@ui-kitten/components';

const renderToggleButton = () => (
  <Button>Toggle</Button>
);

<Popover anchor={renderToggleButton}>
  <Layout>
    <Text>Popover content</Text>
  </Layout>
</Popover>

<Tooltip anchor={renderToggleButton}>
  Tooltip text
</Tooltip>

<OverflowMenu anchor={renderToggleButton}>
  <MenuItem title='Option 1' />
  <MenuItem title='Option 2' />
</OverflowMenu>
4

Update High-Order Components

withStyles

Update to use combined eva prop:
Before
import { withStyles } from '@ui-kitten/components';

const MyComponent = ({ theme, style }) => (
  <View style={style.container} />
);

export default withStyles(MyComponent, theme => ({
  container: {
    backgroundColor: theme['color-primary-default'],
  },
}));
After
import { withStyles } from '@ui-kitten/components';

const MyComponent = ({ eva }) => (
  <View style={eva.style.container} />
);

export default withStyles(MyComponent, theme => ({
  container: {
    backgroundColor: theme['color-primary-default'],
  },
}));

styled (Decorator)

Update to use decorator syntax and combined eva prop:
Before
import { styled } from '@ui-kitten/components';

class MyComponent extends React.Component {
  render() {
    const { theme, dispatch } = this.props;
    return <View />;
  }
}

MyComponent.styledComponentName = 'MyComponent';
export default styled(MyComponent);
After
import { styled } from '@ui-kitten/components';

@styled('MyComponent')
export class MyComponent extends React.Component {
  render() {
    const { eva, ...restProps } = this.props;
    // eva contains: theme, style, dispatch
    return <View style={eva.style.container} />;
  }
}
The styledComponentName static is no longer needed. The decorator now handles this automatically, leading to better TypeScript support when using refs.
5

Test Your Application

After completing the migration:
  1. Run your application and verify all UI components render correctly
  2. Test user interactions to ensure event handlers work as expected
  3. Check styling to confirm custom styles are applied properly
  4. Review TypeScript errors if using TypeScript - the improved type definitions may reveal previously hidden issues
  5. Test on both iOS and Android to ensure cross-platform compatibility
Pay special attention to components using onPress handlers, especially ListItem, as the callback signature has changed.

New Features in 5.0

After completing the migration, you can take advantage of new features:

Avatar ImageComponent Property

Customize the image rendering component:
import { Avatar } from '@ui-kitten/components';
import FastImage from 'react-native-fast-image';

<Avatar 
  source={{ uri: 'https://example.com/avatar.jpg' }}
  ImageComponent={FastImage}
/>

Datepicker autoDismiss Property

Control whether the datepicker dismisses automatically:
<Datepicker 
  date={date}
  onSelect={setDate}
  autoDismiss={false}
/>

Metro Config CLI

Compile mappings manually for CI environments:
npx @ui-kitten/metro-config

Improved Performance

Version 5.0 includes significant performance improvements for:
  • Style hooks with reduced re-renders
  • Styled components with optimized dispatch handling
  • Large lists with better rendering performance

Breaking Changes Summary

Review this section carefully to ensure you’ve addressed all breaking changes.
ComponentChangeMigration
All styled components*Style properties removedUse function components as children
Buttonicon prop renamedUse accessoryLeft or accessoryRight
Inputicon prop renamedUse accessoryLeft or accessoryRight
Selectdata prop removedUse SelectItem and SelectGroup children
Autocompletedata and renderItem removedUse AutocompleteItem children
Menudata prop removedUse MenuItem and MenuGroup children
Drawerdata prop removedUse DrawerItem and DrawerGroup children
Radio, CheckBox, Toggletext prop removedUse children instead
TopNavigationleftControl and rightControls renamedUse accessoryLeft and accessoryRight
ListItemonPress signature changedNo longer receives index parameter
ListItemicon and accessory renamedUse accessoryLeft and accessoryRight
CardCardHeader component removedUse header and footer render props
Popover, Tooltip, OverflowMenucontent prop removedUse children and anchor prop
withStyles HOCProps combinedAccess via eva.theme and eva.style
styled decoratorProps combinedAccess via eva.theme, eva.style, eva.dispatch

Common Migration Issues

Issue: ListItem onPress Not Working

Problem: onPress expects the item index but it’s no longer provided. Solution: Store necessary data in state or use closures:
// Instead of:
<ListItem onPress={(index) => handlePress(items[index])} />

// Use:
<ListItem onPress={() => handlePress(item)} />

Issue: TypeScript Errors with Eva Props

Problem: TypeScript doesn’t recognize the eva prop. Solution: The component is correctly typed when using HOCs:
interface MyComponentProps {
  eva?: EvaProps; // Import from @ui-kitten/components
  customProp: string;
}

const MyComponent: React.FC<MyComponentProps> = ({ eva, customProp }) => {
  // ...
};

Issue: Icons Not Rendering

Problem: react-native-svg is not installed. Solution: Install the required peer dependency:
npm install react-native-svg

Need Help?

If you encounter issues during migration:

Conclusion

While UI Kitten 5.0 introduces significant API changes, the new patterns provide better flexibility, type safety, and performance. The migration effort is worthwhile for the improved developer experience and future-proofing your application.
Take your time with the migration and test thoroughly. Consider migrating component by component rather than all at once to minimize risk.

Build docs developers (and LLMs) love