Skip to content

Commit 13a20b1

Browse files
committed
msglist [nfc]: Define sliver boundary by messages
This gives a bit more structured of an idea of what `middleItem` is supposed to mean. We'll use this for maintaining `middleItem` as a more dynamic value in upcoming commits.
1 parent ab07916 commit 13a20b1

File tree

2 files changed

+28
-0
lines changed

2 files changed

+28
-0
lines changed

lib/model/message_list.dart

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,9 +76,20 @@ mixin _MessageSequence {
7676
/// conceptually belongs in this message list.
7777
/// That information is expressed in [fetched] and [haveOldest].
7878
///
79+
/// See also [middleMessage], an index which divides this list
80+
/// into a top slice and a bottom slice.
81+
///
7982
/// See also [contents] and [items].
8083
final List<Message> messages = [];
8184

85+
/// An index into [messages] dividing it into a top slice and a bottom slice.
86+
///
87+
/// The indices 0 to before [middleMessage] are the top slice of [messages],
88+
/// and the indices from [middleMessage] to the end are the bottom slice.
89+
///
90+
/// The corresponding item index is [middleItem].
91+
int get middleMessage => messages.isEmpty ? 0 : messages.length - 1;
92+
8293
/// Whether [messages] and [items] represent the results of a fetch.
8394
///
8495
/// This allows the UI to distinguish "still working on fetching messages"
@@ -146,6 +157,12 @@ mixin _MessageSequence {
146157
///
147158
/// The indices 0 to before [middleItem] are the top slice of [items],
148159
/// and the indices from [middleItem] to the end are the bottom slice.
160+
///
161+
/// The top and bottom slices of [items] correspond to
162+
/// the top and bottom slices of [messages] respectively.
163+
/// Either the bottom slices of both [items] and [messages] are empty,
164+
/// or the first item in the bottom slice of [items] is a [MessageListMessageItem]
165+
/// for the first message in the bottom slice of [messages].
149166
int get middleItem => items.isEmpty ? 0 : items.length - 1;
150167

151168
int _findMessageWithId(int messageId) {

test/model/message_list_test.dart

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1960,6 +1960,10 @@ void checkInvariants(MessageListView model) {
19601960
check(isSortedWithoutDuplicates(model.messages.map((m) => m.id).toList()))
19611961
.isTrue();
19621962

1963+
check(model).middleMessage
1964+
..isGreaterOrEqual(0)
1965+
..isLessOrEqual(model.messages.length);
1966+
19631967
check(model).contents.length.equals(model.messages.length);
19641968
for (int i = 0; i < model.contents.length; i++) {
19651969
final poll = model.messages[i].poll;
@@ -2001,6 +2005,12 @@ void checkInvariants(MessageListView model) {
20012005
check(model).middleItem
20022006
..isGreaterOrEqual(0)
20032007
..isLessOrEqual(model.items.length);
2008+
if (model.middleItem == model.items.length) {
2009+
check(model.middleMessage).equals(model.messages.length);
2010+
} else {
2011+
check(model.items[model.middleItem]).isA<MessageListMessageItem>()
2012+
.message.identicalTo(model.messages[model.middleMessage]);
2013+
}
20042014
}
20052015

20062016
extension MessageListRecipientHeaderItemChecks on Subject<MessageListRecipientHeaderItem> {
@@ -2026,6 +2036,7 @@ extension MessageListViewChecks on Subject<MessageListView> {
20262036
Subject<PerAccountStore> get store => has((x) => x.store, 'store');
20272037
Subject<Narrow> get narrow => has((x) => x.narrow, 'narrow');
20282038
Subject<List<Message>> get messages => has((x) => x.messages, 'messages');
2039+
Subject<int> get middleMessage => has((x) => x.middleMessage, 'middleMessage');
20292040
Subject<List<ZulipMessageContent>> get contents => has((x) => x.contents, 'contents');
20302041
Subject<List<MessageListItem>> get items => has((x) => x.items, 'items');
20312042
Subject<int> get middleItem => has((x) => x.middleItem, 'middleItem');

0 commit comments

Comments
 (0)