Skip to content

Implement custom tab bar and introduce core styling utilities#1

Merged
devcedrick merged 2 commits into
mainfrom
develop
Jul 7, 2026
Merged

Implement custom tab bar and introduce core styling utilities#1
devcedrick merged 2 commits into
mainfrom
develop

Conversation

@devcedrick

@devcedrick devcedrick commented Jul 6, 2026

Copy link
Copy Markdown
Owner

This commit establishes the main navigation structure with a custom-designed bottom tab bar, enhancing the user interface and providing a consistent look and feel.

  • Introduces app/(tabs)/_layout.tsx for a custom tab bar implementation using expo-router's Tabs component, complete with bespoke styling and icon handling.
  • Adds constants/theme.ts and constants/data.ts to centralize color schemes, spacing, component dimensions, and tab configuration.
  • Integrates clsx for dynamic class name generation within the tab bar.
  • Moves subscriptions/[id] outside the (tabs) directory, allowing it to function as a standalone detail screen rather than a primary tab.
  • Updates existing tab screens (index, insights, settings, subscriptions) to use SafeAreaView and aligns them with the new theming approach.
  • Adds a comprehensive set of font, icon, and image assets to support the new UI.
  • Includes image.d.ts and type.d.ts for improved TypeScript support for assets and global interfaces.

Summary by CodeRabbit

  • New Features
    • Upgraded the tab bar to a richer design with custom icon rendering, theme-driven sizing, and distinct active-state styling.
    • Added a non-navigable detail route for subscription items so they can open their own detail screen.
  • Bug Fixes
    • Improved screen layouts across tabs to better respect device safe areas.
    • Updated subscription navigation to pass the selected plan as a route parameter.
  • Chores
    • Added a lightweight class-combining utility to support conditional tab styling.

This commit establishes the main navigation structure with a custom-designed bottom tab bar, enhancing the user interface and providing a consistent look and feel.

*   Introduces `app/(tabs)/_layout.tsx` for a custom tab bar implementation using `expo-router`'s `Tabs` component, complete with bespoke styling and icon handling.
*   Adds `constants/theme.ts` and `constants/data.ts` to centralize color schemes, spacing, component dimensions, and tab configuration.
*   Integrates `clsx` for dynamic class name generation within the tab bar.
*   Moves `subscriptions/[id]` outside the `(tabs)` directory, allowing it to function as a standalone detail screen rather than a primary tab.
*   Updates existing tab screens (`index`, `insights`, `settings`, `subscriptions`) to use `SafeAreaView` and aligns them with the new theming approach.
*   Adds a comprehensive set of font, icon, and image assets to support the new UI.
*   Includes `image.d.ts` and `type.d.ts` for improved TypeScript support for assets and global interfaces.
Copilot AI review requested due to automatic review settings July 6, 2026 12:42
@coderabbitai

coderabbitai Bot commented Jul 6, 2026

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 09d2104e-474e-4ece-9d28-12b0f729bcc3

📥 Commits

Reviewing files that changed from the base of the PR and between e25cd7f and 88849bb.

📒 Files selected for processing (1)
  • app/(tabs)/_layout.tsx
🚧 Files skipped from review as they are similar to previous changes (1)
  • app/(tabs)/_layout.tsx

📝 Walkthrough

Walkthrough

This PR replaces the tab root with a custom TabsLayout driven by shared theme, icon, and tab data constants. It also updates tab screens to use styled safe-area wrappers, adds a dynamic subscription route link, and introduces an Expo icon configuration.

Changes

Tab Bar and Theme Infrastructure

Layer / File(s) Summary
Theme, icon, and tab data constants
constants/theme.ts, constants/icons.ts, constants/data.ts, image.d.ts, type.d.ts, package.json
Adds immutable theme constants, icon asset exports, a tabs array, image module declarations, a global TabIconProps interface, and the clsx dependency.
Custom TabsLayout and TabIcon component
app/(tabs)/_layout.tsx
Replaces RootLayout with TabsLayout, adds TabIcon, configures tab bar styling from theme constants and safe-area insets, renders screens from tabs, adds a hidden subscriptions/[id] screen, and updates the default export.
Screen SafeAreaView migration and dynamic route link
app/(tabs)/index.tsx, app/(tabs)/insights.tsx, app/(tabs)/settings.tsx, app/(tabs)/subscriptions.tsx
Wraps tab screens in styled SafeAreaView containers and changes the subscription link to an object href with pathname and params.
Expo icon configuration
assets/expo.icon/icon.json
Adds the Expo icon JSON configuration with gradient, layered composition, shadow/translucency, and platform support settings.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant TabsLayout
  participant tabsData as tabs (constants/data.ts)
  participant TabIcon
  participant Tabs as expo-router Tabs

  TabsLayout->>tabsData: map tabs array
  TabsLayout->>Tabs: render Tabs.Screen per tab
  Tabs->>TabIcon: tabBarIcon(focused, icon)
  TabIcon-->>Tabs: styled icon view
  Tabs-->>TabsLayout: rendered tab bar
Loading

Related Issues: None found in provided context.

Related PRs: None found in provided context.

Suggested labels: enhancement, ui

Suggested reviewers: devcedrick

Poem:
A tab bar dressed in theme and light,
With safe-area frames and icons bright,
A route now points by id in tow,
And Expo’s icon file joins the show.

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately captures the main changes: a custom tab bar plus new shared styling utilities.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch develop

Comment @coderabbitai help to get the list of available commands.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR establishes a custom bottom tab navigation UI (via expo-router Tabs) and introduces centralized styling utilities (theme constants + tab configuration), while moving the subscription details screen to a standalone route outside the tab group.

Changes:

  • Added a custom-styled tab bar in app/(tabs)/_layout.tsx, driven by centralized tab config (constants/data.ts) and theme tokens (constants/theme.ts).
  • Introduced shared constants and asset typing support (constants/*, image.d.ts, type.d.ts) and added clsx for conditional tab icon styling.
  • Moved subscriptions/[id] to app/subscriptions/[id].tsx and updated the Home tab link to use the dynamic route.

Reviewed changes

Copilot reviewed 10 out of 58 changed files in this pull request and generated 5 comments.

Show a summary per file
File Description
type.d.ts Adds global typing for tab icon props used by the custom tab bar.
package.json Adds clsx dependency for conditional class name composition.
package-lock.json Locks clsx dependency.
image.d.ts Adds TypeScript module declarations for image imports.
constants/theme.ts Centralizes colors, spacing scale, and tab bar sizing tokens.
constants/icons.ts Centralizes icon imports/exports for use across the app.
constants/data.ts Defines the tab configuration (name/title/icon) used to generate tab screens.
assets/expo.icon/icon.json Adds/updates Expo icon asset metadata.
assets/expo.icon/Assets/expo-symbol 2.svg Adds an SVG asset used by the Expo icon set.
app/subscriptions/[id].tsx Introduces a standalone subscription details screen using a dynamic route.
app/(tabs)/subscriptions.tsx Updates tab screen wrapper to use SafeAreaView.
app/(tabs)/settings.tsx Updates tab screen wrapper to use SafeAreaView.
app/(tabs)/insights.tsx Updates tab screen wrapper to use SafeAreaView.
app/(tabs)/index.tsx Updates Home tab layout to use SafeAreaView and links to the dynamic subscription details route.
app/(tabs)/_layout.tsx Implements custom tab bar styling and icon rendering based on centralized config/theme.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread app/(tabs)/_layout.tsx
Comment thread app/(tabs)/insights.tsx
Comment thread app/(tabs)/settings.tsx
Comment thread app/(tabs)/subscriptions.tsx
Comment thread constants/icons.ts
Comment on lines +22 to +43
export {
activity,
add,
adobe,
back,
canva,
claude,
dropbox,
figma,
github,
home,
logo,
medium,
menu,
netflix,
notion,
openai,
plus,
setting,
spotify,
wallet
};

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@app/`(tabs)/_layout.tsx:
- Around line 62-67: The Tabs.Screen registration for subscriptions/[id] in the
_layout component no longer matches a child route under app/(tabs)/, so it
should be moved to the parent navigator that owns the subscriptions/[id] route,
or the route file should be kept under (tabs) if it is meant to remain a tab
child. Update the navigator setup in _layout so the screen is registered where
the actual route lives, and remove the mismatched tab-level registration.
- Around line 14-22: `TabIcon` is defined inside `TabsLayout`, which creates a
new component type on every render and can remount the icon tree unnecessarily.
Move `TabIcon` out of the `TabsLayout` function body into module scope, keep
using the existing `TabIconProps`, and pass `focused` and `icon` into it from
`TabsLayout` so the component identity stays stable across re-renders.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 0b1484d1-39a8-45d0-a20f-940c3a3c3c31

📥 Commits

Reviewing files that changed from the base of the PR and between 3ba4a06 and e25cd7f.

⛔ Files ignored due to path filters (45)
  • assets/expo.icon/Assets/expo-symbol 2.svg is excluded by !**/*.svg
  • assets/expo.icon/Assets/grid.png is excluded by !**/*.png
  • assets/fonts/PlusJakartaSans-Bold.ttf is excluded by !**/*.ttf
  • assets/fonts/PlusJakartaSans-ExtraBold.ttf is excluded by !**/*.ttf
  • assets/fonts/PlusJakartaSans-Light.ttf is excluded by !**/*.ttf
  • assets/fonts/PlusJakartaSans-Medium.ttf is excluded by !**/*.ttf
  • assets/fonts/PlusJakartaSans-Regular.ttf is excluded by !**/*.ttf
  • assets/fonts/PlusJakartaSans-SemiBold.ttf is excluded by !**/*.ttf
  • assets/icons/activity.png is excluded by !**/*.png
  • assets/icons/add.png is excluded by !**/*.png
  • assets/icons/adobe.png is excluded by !**/*.png
  • assets/icons/back.png is excluded by !**/*.png
  • assets/icons/canva.png is excluded by !**/*.png
  • assets/icons/claude.png is excluded by !**/*.png
  • assets/icons/dropbox.png is excluded by !**/*.png
  • assets/icons/figma.png is excluded by !**/*.png
  • assets/icons/github.png is excluded by !**/*.png
  • assets/icons/home.png is excluded by !**/*.png
  • assets/icons/logo.png is excluded by !**/*.png
  • assets/icons/medium.png is excluded by !**/*.png
  • assets/icons/menu.png is excluded by !**/*.png
  • assets/icons/netflix.png is excluded by !**/*.png
  • assets/icons/notion.png is excluded by !**/*.png
  • assets/icons/openai.png is excluded by !**/*.png
  • assets/icons/plus.png is excluded by !**/*.png
  • assets/icons/setting.png is excluded by !**/*.png
  • assets/icons/spotify.png is excluded by !**/*.png
  • assets/icons/wallet.png is excluded by !**/*.png
  • assets/images/avatar.png is excluded by !**/*.png
  • assets/images/expo-badge-white.png is excluded by !**/*.png
  • assets/images/expo-badge.png is excluded by !**/*.png
  • assets/images/expo-logo.png is excluded by !**/*.png
  • assets/images/icon.png is excluded by !**/*.png
  • assets/images/logo-glow.png is excluded by !**/*.png
  • assets/images/partial-react-logo.png is excluded by !**/*.png
  • assets/images/splash-icon.png is excluded by !**/*.png
  • assets/images/splash-pattern.png is excluded by !**/*.png
  • assets/images/tabIcons/explore.png is excluded by !**/*.png
  • assets/images/tabIcons/explore@2x.png is excluded by !**/*.png
  • assets/images/tabIcons/explore@3x.png is excluded by !**/*.png
  • assets/images/tabIcons/home.png is excluded by !**/*.png
  • assets/images/tabIcons/home@2x.png is excluded by !**/*.png
  • assets/images/tabIcons/home@3x.png is excluded by !**/*.png
  • assets/images/tutorial-web.png is excluded by !**/*.png
  • package-lock.json is excluded by !**/package-lock.json
📒 Files selected for processing (13)
  • app/(tabs)/_layout.tsx
  • app/(tabs)/index.tsx
  • app/(tabs)/insights.tsx
  • app/(tabs)/settings.tsx
  • app/(tabs)/subscriptions.tsx
  • app/subscriptions/[id].tsx
  • assets/expo.icon/icon.json
  • constants/data.ts
  • constants/icons.ts
  • constants/theme.ts
  • image.d.ts
  • package.json
  • type.d.ts

Comment thread app/(tabs)/_layout.tsx Outdated
Comment thread app/(tabs)/_layout.tsx
Moves the `TabIcon` component out of the `TabsLayout` function. This refactors the component for better organization and prevents its re-declaration on every render of the layout component, improving stability and performance.
@devcedrick
devcedrick merged commit a02d11a into main Jul 7, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants