Skip to content

Update design of message dividers#6176

Merged
gpunto merged 2 commits into
v7from
redesign/message-divider
Feb 24, 2026
Merged

Update design of message dividers#6176
gpunto merged 2 commits into
v7from
redesign/message-divider

Conversation

@gpunto
Copy link
Copy Markdown
Contributor

@gpunto gpunto commented Feb 20, 2026

Goal

Update design of message dividers, i.e. date and unread dividers

Implementation

  • Create MessageDivider component and use it for the dividers
  • Removed MessageUnreadSeparatorTheme and MessageDateSeparatorTheme

🎨 UI Changes

Before After
Screenshot_20260220_161935 Screenshot_20260220_161835

Testing

As usual, in the sample

Summary by CodeRabbit

  • New Features

    • Introduced a new MessageDivider component for displaying centered separator labels with circular backgrounds in message lists.
  • Bug Fixes / Improvements

    • Refactored message date and unread separators to use the updated MessageDivider component.
  • Theme Updates

    • Added system text color support to the theme system.
    • Removed deprecated MessageDateSeparatorTheme and MessageUnreadSeparatorTheme from the public API.

@gpunto gpunto added the pr:improvement Improvement label Feb 20, 2026
@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented Feb 20, 2026

PR checklist ✅

All required conditions are satisfied:

  • Title length is OK (or ignored by label).
  • At least one pr: label exists.
  • Sections ### Goal, ### Implementation, and ### Testing are filled.

🎉 Great job! This PR is ready for review.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented Feb 20, 2026

SDK Size Comparison 📏

SDK Before After Difference Status
stream-chat-android-client 5.25 MB 5.69 MB 0.44 MB 🟡
stream-chat-android-ui-components 10.60 MB 10.96 MB 0.36 MB 🟡
stream-chat-android-compose 12.81 MB 11.92 MB -0.89 MB 🚀

@gpunto gpunto marked this pull request as ready for review February 20, 2026 17:01
@gpunto gpunto requested a review from a team as a code owner February 20, 2026 17:01
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Feb 20, 2026

Walkthrough

This PR introduces a new internal MessageDivider Composable component to replace the deleted MessageDateSeparatorTheme and MessageUnreadSeparatorTheme classes. It removes related theme parameters from ChatTheme, updates MessageItem to use the new component, and adds a chatTextSystem color property to StreamColors.

Changes

Cohort / File(s) Summary
Message Divider Component
stream-chat-android-compose/src/main/java/.../MessageDivider.kt, stream-chat-android-compose/src/main/java/.../MessageItem.kt
Introduces new internal MessageDivider Composable that renders centered text with circular background. Updates DefaultMessageDateSeparatorContent and DefaultMessageUnreadSeparatorContent to use MessageDivider instead of Box/Surface composition.
Theme Class Removals
stream-chat-android-compose/src/main/java/.../MessageDateSeparatorTheme.kt, stream-chat-android-compose/src/main/java/.../MessageUnreadSeparatorTheme.kt, stream-chat-android-compose/src/main/java/.../ChatTheme.kt
Deletes MessageDateSeparatorTheme and MessageUnreadSeparatorTheme classes entirely. Removes corresponding theme parameters, accessors, and local composition locals from ChatTheme function and object.
Theme and API Updates
stream-chat-android-compose/src/main/java/.../StreamColors.kt, stream-chat-android-compose/api/stream-chat-android-compose.api
Adds chatTextSystem color property to StreamColors with default value. Updates public API surface to reflect component removals and theme restructuring, including new ComposableSingletons$MessageDividerKt and renamed copy method signatures.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~22 minutes

Possibly related PRs

Suggested reviewers

  • VelikovPetar
  • andremion

Poem

🐰 Dividers dance in circles bright,
Old themes fade into the night,
New colors bloom in system's hue,
Messages flow, fresh and true!

🚥 Pre-merge checks | ✅ 2 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 50.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (2 passed)
Check name Status Explanation
Title check ✅ Passed The title 'Update design of message dividers' clearly and concisely summarizes the main change: redesigning message dividers (date and unread separators) with a new MessageDivider component.
Description check ✅ Passed The PR description follows the template with Goal and Implementation sections, includes before/after screenshots, and mentions testing. Non-critical sections like detailed patch instructions are omitted, which is acceptable.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
  • 📝 Generate docstrings (stacked PR)
  • 📝 Generate docstrings (commit on current branch)
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch redesign/message-divider

Tip

Issue Planner is now in beta. Read the docs and try it out! Share your feedback on Discord.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 3

🧹 Nitpick comments (3)
stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageItem.kt (2)

147-173: Inconsistent modifier ordering between the two separator functions.

DefaultMessageDateSeparatorContent chains .padding(vertical = 8.dp).fillMaxWidth() (padding first), while DefaultMessageUnreadSeparatorContent uses .fillMaxWidth().padding(bottom = 8.dp) (fill first). Both produce identical layout since only vertical padding is involved, but the inconsistency makes the code harder to reason about.

♻️ Align date separator to the same ordering
 MessageDivider(
     text = ChatTheme.dateFormatter.formatRelativeDate(dateSeparator.date),
     modifier = Modifier
         .semantics(mergeDescendants = true) {
             testTag = "Stream_MessageDateSeparator"
         }
-        .padding(vertical = 8.dp)
-        .fillMaxWidth(),
+        .fillMaxWidth()
+        .padding(vertical = 8.dp),
 )
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageItem.kt`
around lines 147 - 173, The modifiers for the unread separator are ordered
inconsistently with the date separator; update
DefaultMessageUnreadSeparatorContent so its Modifier chains match
DefaultMessageDateSeparatorContent by applying .padding(bottom = 8.dp) (or
vertical padding) before .fillMaxWidth(), keeping the same semantics block and
testTag ("Stream_UnreadMessagesBadge") and preserving the padding value
behavior.

165-173: Prefer idiomatic stringResource() over LocalResources.current.getString() for a plain string lookup.

stringResource (already imported at line 32) is the standard Compose API for this, handles configuration changes identically, and is consistent with how other string resources are fetched in this file (e.g., line 248). LocalResources.current.getString(...) works correctly but is more verbose and non-idiomatic here.

♻️ Proposed simplification
-import androidx.compose.ui.platform.LocalResources
 ...
 `@Composable`
 internal fun DefaultMessageUnreadSeparatorContent(unreadSeparatorItemState: UnreadSeparatorItemState) {
     MessageDivider(
-        text = LocalResources.current.getString(R.string.stream_compose_message_list_unread_separator),
+        text = stringResource(R.string.stream_compose_message_list_unread_separator),
         modifier = Modifier
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageItem.kt`
around lines 165 - 173, Replace the non-idiomatic
LocalResources.current.getString(...) call used in the MessageDivider inside
MessageItem (the MessageDivider invocation that sets the unread separator text)
with the Compose helper stringResource(...) (already imported) so the text
parameter uses
stringResource(R.string.stream_compose_message_list_unread_separator); keep the
same semantics and modifiers (semantics, testTag, fillMaxWidth, padding)
unchanged.
stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageDivider.kt (1)

49-62: Consider adding a Paparazzi snapshot test for MessageDivider.

The preview is a good start, but this component is a visible UI element and a Paparazzi test would guard against unintended regressions.

Based on learnings: "Applies to **/stream-chat-android-compose/**/*Test.kt: Add Paparazzi snapshots for Compose UI regressions and run verifyPaparazziDebug."

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageDivider.kt`
around lines 49 - 62, Add a Paparazzi snapshot test for the MessageDivider
composable by creating a test class (e.g., MessageDividerPaparazziTest) that
uses a Paparazzi rule (`@get`:Rule val paparazzi = Paparazzi(...)) and renders the
same content as MessageDividerPreview (wrap the composables in ChatTheme and a
Column with MessageDivider("Unread messages"), MessageDivider("Today"),
MessageDivider("Tue, 25 Dec")); take a snapshot via paparazzi.snapshot or
equivalent and commit the golden; ensure the test lives under the
stream-chat-android-compose test sources and runs as part of
verifyPaparazziDebug to catch visual regressions.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@stream-chat-android-compose/api/stream-chat-android-compose.api`:
- Around line 3313-3314: The ChatTheme signature was expanded with new defaulted
parameters; run and verify Paparazzi snapshot tests to ensure no Compose UI
regressions by executing the existing tests (e.g., PaparazziComposeTest.kt and
MessageComposerScreenTest.kt) and updating baselines using the
verifyPaparazziDebug task; if snapshots changed, record new golden images and
commit them so ChatTheme consumers continue to render identically.

In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageItem.kt`:
- Line 30: The unread separator in MessageItem.kt uses
LocalResources.current.getString(...) instead of the Compose idiomatic
stringResource(...) and its Modifier ordering differs from the date separator;
replace the
LocalResources.current.getString(R.string.stream_compose_message_list_unread_separator)
call with stringResource(R.string.stream_compose_message_list_unread_separator)
(the stringResource import is already present) and reorder the unread
separator's Modifier to match the date separator (use .padding(vertical =
8.dp).fillMaxWidth() or the same padding semantics as the date separator) so
both separators use consistent resource access and modifier ordering.

In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/theme/StreamColors.kt`:
- Line 208: Add the missing KDoc `@param` for the newly introduced public property
chatTextSystem in the StreamColors KDoc block (in StreamColors.kt) so the public
API is fully documented; update the existing KDoc that documents other chat*
parameters to include a brief description for `@param` chatTextSystem describing
its purpose and how it differs from chatTextPrimary/chatTextSecondary.

---

Nitpick comments:
In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageDivider.kt`:
- Around line 49-62: Add a Paparazzi snapshot test for the MessageDivider
composable by creating a test class (e.g., MessageDividerPaparazziTest) that
uses a Paparazzi rule (`@get`:Rule val paparazzi = Paparazzi(...)) and renders the
same content as MessageDividerPreview (wrap the composables in ChatTheme and a
Column with MessageDivider("Unread messages"), MessageDivider("Today"),
MessageDivider("Tue, 25 Dec")); take a snapshot via paparazzi.snapshot or
equivalent and commit the golden; ensure the test lives under the
stream-chat-android-compose test sources and runs as part of
verifyPaparazziDebug to catch visual regressions.

In
`@stream-chat-android-compose/src/main/java/io/getstream/chat/android/compose/ui/messages/list/MessageItem.kt`:
- Around line 147-173: The modifiers for the unread separator are ordered
inconsistently with the date separator; update
DefaultMessageUnreadSeparatorContent so its Modifier chains match
DefaultMessageDateSeparatorContent by applying .padding(bottom = 8.dp) (or
vertical padding) before .fillMaxWidth(), keeping the same semantics block and
testTag ("Stream_UnreadMessagesBadge") and preserving the padding value
behavior.
- Around line 165-173: Replace the non-idiomatic
LocalResources.current.getString(...) call used in the MessageDivider inside
MessageItem (the MessageDivider invocation that sets the unread separator text)
with the Compose helper stringResource(...) (already imported) so the text
parameter uses
stringResource(R.string.stream_compose_message_list_unread_separator); keep the
same semantics and modifiers (semantics, testTag, fillMaxWidth, padding)
unchanged.

Comment thread stream-chat-android-compose/api/stream-chat-android-compose.api
@gpunto gpunto enabled auto-merge (squash) February 24, 2026 12:40
@sonarqubecloud
Copy link
Copy Markdown

Quality Gate Failed Quality Gate failed

Failed conditions
74.2% Coverage on New Code (required ≥ 80%)

See analysis details on SonarQube Cloud

@gpunto gpunto merged commit 72945a7 into v7 Feb 24, 2026
14 of 15 checks passed
@gpunto gpunto deleted the redesign/message-divider branch February 24, 2026 13:15
@stream-public-bot stream-public-bot added the released Included in a release label Mar 23, 2026
@stream-public-bot
Copy link
Copy Markdown
Contributor

🚀 Available in v7.0.0-beta

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

pr:improvement Improvement released Included in a release

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants