Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions lib/cubits/time_machine/time_machine_cubit.dart
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import 'package:bloc/bloc.dart';
import 'package:equatable/equatable.dart';
import 'package:hacki/config/locator.dart';
import 'package:hacki/models/models.dart' show Comment;
import 'package:hacki/models/models.dart' show Comment, Item;
import 'package:hacki/services/services.dart';

part 'time_machine_state.dart';
Expand All @@ -13,13 +13,13 @@ class TimeMachineCubit extends Cubit<TimeMachineState> {

final CommentCache _commentCache;

Future<void> activateTimeMachine(Comment comment) async {
Future<void> activateTimeMachine(Comment comment, Item rootItem) async {
emit(state.copyWith(ancestors: <Comment>[]));

final List<Comment> ancestors = <Comment>[];
Comment? parent = _commentCache.getComment(comment.parent);

while (parent != null) {
while (parent != null && parent.id != rootItem.id) {
ancestors.insert(0, parent);

final int parentId = parent.parent;
Expand Down
19 changes: 8 additions & 11 deletions lib/screens/item/widgets/item_screen_background.dart
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,8 @@ class _ItemScreenBackgroundState extends State<ItemScreenBackground> {
.read<PreferenceCubit>()
.state
.isEyeCandyEnabled;
final bool isDarkModeEnabled =
Theme.of(context).brightness == Brightness.dark;
return BlocConsumer<CommentsCubit, CommentsState>(
listenWhen: (CommentsState previous, CommentsState current) =>
previous.status != current.status,
Expand Down Expand Up @@ -162,24 +164,19 @@ class _ItemScreenBackgroundState extends State<ItemScreenBackground> {
color: ColorUtils.getRainbowColor(
i,
Theme.of(context).canvasColor,
isDarkModeEnabled: isDarkModeEnabled,
).$1,
width: widget.indentLineWidth,
isShining: _shineIndex == i,
)
: Container(
width: widget.indentLineWidth,
height: MediaQuery.of(context).size.height,
color:
ColorUtils.getRainbowColor(
i,
Theme.of(context).canvasColor,
).$1.withValues(
alpha:
Theme.of(context).brightness ==
Brightness.dark
? 0.6
: 1,
),
color: ColorUtils.getRainbowColor(
i,
Theme.of(context).canvasColor,
isDarkModeEnabled: isDarkModeEnabled,
).$1,
),
),
),
Expand Down
9 changes: 9 additions & 0 deletions lib/screens/item/widgets/main_view.dart
Original file line number Diff line number Diff line change
Expand Up @@ -353,8 +353,17 @@ class _ParentItemSection extends StatelessWidget {
),
DeviceGestureWrapper(
child: Slidable(
key: ValueKey<String>('root_item_tile_slidable_${item.id}'),
startActionPane: ActionPane(
motion: const BehindMotion(),
dismissible: DismissiblePane(
closeOnCancel: true,
confirmDismiss: () async {
onUpvoteTapped.call(item);
return false;
},
onDismissed: () {},
),
children: <Widget>[
if (context.read<AuthBloc>().state.user.id != item.by)
CustomSlidableAction(
Expand Down
188 changes: 96 additions & 92 deletions lib/screens/item/widgets/time_machine_dialog.dart
Original file line number Diff line number Diff line change
Expand Up @@ -16,18 +16,20 @@ class TimeMachineDialog extends StatelessWidget {
required this.comment,
required this.commentsCubit,
required this.deviceType,
required this.scrollController,
super.key,
}) : rootItem = commentsCubit.state.item;

final Comment comment;
final CommentsCubit commentsCubit;
final Item rootItem;
final DeviceScreenType deviceType;
final ScrollController scrollController;

@override
Widget build(BuildContext context) {
return BlocProvider<TimeMachineCubit>.value(
value: TimeMachineCubit()..activateTimeMachine(comment),
value: TimeMachineCubit()..activateTimeMachine(comment, rootItem),
child: BlocBuilder<TimeMachineCubit, TimeMachineState>(
builder: (BuildContext context, TimeMachineState state) {
return Material(
Expand All @@ -36,107 +38,109 @@ class TimeMachineDialog extends StatelessWidget {
decoration: const BoxDecoration(
borderRadius: BorderRadius.all(Radius.circular(Dimens.pt4)),
),
child: Padding(
padding: const EdgeInsets.only(right: Dimens.pt4),
child: Column(
children: <Widget>[
Row(
child: Column(
children: <Widget>[
Row(
children: <Widget>[
const SizedBox(width: Dimens.pt12),
Text(
'Ancestors:',
style: TextTheme.of(context).titleMedium,
),
const Spacer(),
IconButton(
icon: const Icon(Icons.close, size: Dimens.pt24),
onPressed: () => context.pop(),
padding: EdgeInsets.zero,
),
],
),
Expanded(
child: ListView(
controller: scrollController,
children: <Widget>[
const SizedBox(width: Dimens.pt8),
Text(
'Ancestors:',
style: TextTheme.of(context).titleMedium,
),
const Spacer(),
IconButton(
icon: const Icon(Icons.close, size: Dimens.pt24),
onPressed: () => context.pop(),
padding: EdgeInsets.zero,
),
],
),
Expanded(
child: ListView(
children: <Widget>[
switch (rootItem) {
Story() => StoryTile(
shouldShowWebPreview: false,
shouldShowPreviewImage: false,
shouldShowMetadata: true,
shouldShowFavicon: true,
shouldShowUrl: true,
isExpandedTileEnabled: false,
isImageLeftAligned: context
.read<PreferenceCubit>()
.state
.isPreviewImageLeftAligned,
story: rootItem as Story,
onTap: () {
final String url = rootItem.url.isNotEmpty
? rootItem.url
: '''${Constants.hackerNewsItemLinkPrefix}${rootItem.id}''';
LinkUtils.launch(
url,
context,
shouldUseHackiForHnLink: false,
);
},
),
Comment() => CommentTile(
switch (rootItem) {
Story() => StoryTile(
shouldShowWebPreview: false,
shouldShowPreviewImage: false,
shouldShowMetadata: true,
shouldShowFavicon: true,
shouldShowUrl: true,
isExpandedTileEnabled: false,
isImageLeftAligned: context
.read<PreferenceCubit>()
.state
.isPreviewImageLeftAligned,
story: rootItem as Story,
onTap: () {
final String url = rootItem.url.isNotEmpty
? rootItem.url
: '''${Constants.hackerNewsItemLinkPrefix}${rootItem.id}''';
LinkUtils.launch(
url,
context,
shouldUseHackiForHnLink: false,
);
},
),
Comment() => Padding(
padding: const EdgeInsets.only(right: Dimens.pt4),
child: CommentTile(
comment: rootItem as Comment,
isActionable: false,
isCollapsable: false,
fetchMode: FetchMode.eager,
),
Item() => const SizedBox.shrink(),
},
for (final (int i, Comment cmt) in <Comment>[
...state.ancestors,
comment,
].indexed) ...<Widget>[
Row(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
for (final int _ in 0.to(i, inclusive: false))
SizedBoxes.pt6,
Padding(
padding: const EdgeInsets.only(
top: Dimens.pt6,
left: Dimens.pt6,
),
child: Icon(
Icons.subdirectory_arrow_right_rounded,
size: TextDimens.pt18,
color: i == state.ancestors.length
? Theme.of(context).colorScheme.primary
: null,
),
),
Item() => const SizedBox.shrink(),
},
for (final (int i, Comment cmt) in <Comment>[
...state.ancestors,
comment,
].indexed) ...<Widget>[
Row(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
for (final int _ in 0.to(i, inclusive: false))
SizedBoxes.pt6,
Padding(
padding: const EdgeInsets.only(
top: Dimens.pt6,
left: Dimens.pt6,
),
Expanded(
child: CommentTile(
comment: i == state.ancestors.length
? comment
: cmt,
isActionable: false,
isCollapsable: false,
isSelectable: false,
fetchMode: FetchMode.eager,
onTap: () {
context.pop();
commentsCubit.scrollToComment(cmt);
},
),
child: Icon(
Icons.subdirectory_arrow_right_rounded,
size: TextDimens.pt18,
color: i == state.ancestors.length
? Theme.of(context).colorScheme.primary
: null,
),
],
),
const Divider(height: Dimens.zero),
],
),
Expanded(
child: CommentTile(
comment: i == state.ancestors.length
? comment
: cmt,
isActionable: false,
isCollapsable: false,
isSelectable: false,
fetchMode: FetchMode.eager,
onTap: () {
context.pop();
commentsCubit.scrollToComment(cmt);
},
),
),
SizedBoxes.pt4,
],
),
const Divider(height: Dimens.zero),
],
),
],
),
],
),
),
],
),
),
);
Expand Down
24 changes: 15 additions & 9 deletions lib/screens/widgets/comment_tile.dart
Original file line number Diff line number Diff line change
Expand Up @@ -85,22 +85,19 @@ class CommentTile extends StatelessWidget {
PreferenceState prefState,
BlocklistState blocklistState,
) {
final bool isDarkModeEnabled =
Theme.of(context).brightness == Brightness.dark;
final (Color, Color) slidableColors = level > 0
? ColorUtils.getRainbowColor(
level,
Theme.of(context).canvasColor,
isDarkModeEnabled: isDarkModeEnabled,
)
: (
Theme.of(context).colorScheme.primaryContainer,
Theme.of(context).colorScheme.onPrimaryContainer,
);
final double backgroundColorAlpha =
Theme.of(context).brightness == Brightness.dark && level > 0
? 0.6
: 1;
final Color backgroundColor = slidableColors.$1.withValues(
alpha: backgroundColorAlpha,
);
final Color backgroundColor = slidableColors.$1;
final Color foregroundColor = slidableColors.$2;

int newCommentsCount = 0;
Expand Down Expand Up @@ -130,7 +127,15 @@ class CommentTile extends StatelessWidget {
),
startActionPane: isActionable
? ActionPane(
motion: const StretchMotion(),
motion: const BehindMotion(),
dismissible: DismissiblePane(
closeOnCancel: true,
confirmDismiss: () async {
onUpvoteTapped?.call(comment);
return false;
},
onDismissed: () {},
),
children: <Widget>[
if (onUpvoteTapped != null &&
context.read<AuthBloc>().state.user.id !=
Expand Down Expand Up @@ -180,9 +185,10 @@ class CommentTile extends StatelessWidget {
: null,
endActionPane: isActionable
? ActionPane(
motion: const StretchMotion(),
motion: const BehindMotion(),
dismissible: DismissiblePane(
closeOnCancel: true,
dismissThreshold: 0.01,
confirmDismiss: () async {
DialogProxy.showTimeMachineDialog(
context,
Expand Down
26 changes: 13 additions & 13 deletions lib/services/dialog_proxy.dart
Original file line number Diff line number Diff line change
Expand Up @@ -68,19 +68,19 @@ abstract final class DialogProxy {
isScrollControlled: true,
showDragHandle: true,
builder: (BuildContext context) {
return SizedBox(
height: MediaQuery.of(context).size.height - Dimens.pt120,
child: Column(
children: <Widget>[
Expanded(
child: TimeMachineDialog(
comment: comment,
commentsCubit: commentsCubit,
deviceType: deviceType,
),
),
],
),
return DraggableScrollableSheet(
expand: false,
initialChildSize: 0.9,
maxChildSize: 0.9,
minChildSize: 0.85,
builder: (BuildContext context, ScrollController scrollController) {
return TimeMachineDialog(
comment: comment,
commentsCubit: commentsCubit,
deviceType: deviceType,
scrollController: scrollController,
);
},
);
},
);
Expand Down
Loading