Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(cat-voices): Account popup #857

Merged
merged 15 commits into from
Sep 23, 2024
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
1 change: 1 addition & 0 deletions .config/dictionaries/project.dic
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
aapt
aarch
abnf
addr
addrr
adminer
afinet
Expand Down
253 changes: 253 additions & 0 deletions catalyst_voices/lib/pages/account/account_popup.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,253 @@
import 'package:catalyst_voices/widgets/widgets.dart';
import 'package:catalyst_voices_assets/catalyst_voices_assets.dart';
import 'package:catalyst_voices_brands/catalyst_voices_brands.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';

class AccountPopup extends StatelessWidget {
final String avatarLetter;
final VoidCallback? onProfileKeychainTap;
final VoidCallback? onLockAccountTap;

const AccountPopup({
super.key,
required this.avatarLetter,
this.onProfileKeychainTap,
this.onLockAccountTap,
});

@override
Widget build(BuildContext context) {
return PopupMenuButton<_MenuItemValue>(
color: Theme.of(context).colors.elevationsOnSurfaceNeutralLv1White,
onSelected: (_MenuItemValue value) {
switch (value) {
case _MenuItemValue.profileAndKeychain:
onProfileKeychainTap?.call();
break;
case _MenuItemValue.lock:
onLockAccountTap?.call();
break;
}
},
itemBuilder: (BuildContext bc) {
return [
PopupMenuItem(
padding: EdgeInsets.zero,
enabled: false,
value: null,
child: _Header(
accountLetter: avatarLetter,
walletName: 'Wallet name',
walletBalance: '₳ 1,750,000',
accountType: 'Basis',
walletAddress: 'addr1_H4543...45GH',
),
),
const PopupMenuItem(
height: 48,
padding: EdgeInsets.zero,
enabled: false,
value: null,
child: _Section('My account'),
),
PopupMenuItem(
padding: EdgeInsets.zero,
value: _MenuItemValue.profileAndKeychain,
child: _MenuItem(
'Profile & Keychain',
VoicesAssets.icons.userCircle,
),
),
PopupMenuItem(
padding: EdgeInsets.zero,
value: _MenuItemValue.lock,
child: _MenuItem(
'Lock account',
VoicesAssets.icons.lockClosed,
showDivider: false,
),
),
];
},
offset: const Offset(0, kToolbarHeight),
child: IgnorePointer(
child: VoicesAvatar(
icon: Text(avatarLetter),
),
),
);
}
}

class _Header extends StatelessWidget {
final String accountLetter;
final String walletName;
final String walletBalance;
final String accountType;
final String walletAddress;

const _Header({
required this.accountLetter,
required this.walletName,
required this.walletBalance,
required this.accountType,
required this.walletAddress,
});

@override
Widget build(BuildContext context) {
return Column(
children: [
Padding(
padding: const EdgeInsets.symmetric(horizontal: _padding),
child: Row(
digitalheartxs marked this conversation as resolved.
Show resolved Hide resolved
children: [
VoicesAvatar(
icon: Text(accountLetter),
),
Expanded(
child: Padding(
padding: const EdgeInsets.all(_padding),
child: Wrap(
children: [
Text(
walletName,
style: Theme.of(context).textTheme.bodyLarge,
),
Text(
walletBalance,
style: Theme.of(context).textTheme.bodyMedium,
),
],
),
),
),
VoicesChip.rectangular(
content: Text(
accountType,
style: TextStyle(
color: Theme.of(context).colors.successContainer,
),
),
backgroundColor: Theme.of(context).colors.success,
),
],
),
),
Padding(
padding: const EdgeInsets.only(
left: _padding,
right: _padding,
bottom: _padding,
top: 8,
),
child: Row(
children: [
Expanded(
child: Text(
walletAddress,
style: Theme.of(context).textTheme.bodyLarge,
),
),
InkWell(
onTap: () async {
await Clipboard.setData(
ClipboardData(text: walletAddress),
);
},
child: VoicesAssets.icons.clipboardCopy.buildIcon(),
),
],
),
),
VoicesDivider(
height: 1,
color: Theme.of(context).colors.outlineBorder,
digitalheartxs marked this conversation as resolved.
Show resolved Hide resolved
indent: 0,
endIndent: 0,
),
],
);
}
}

class _MenuItem extends StatelessWidget {
final String text;
final SvgGenImage icon;
final bool showDivider;

const _MenuItem(
this.text,
this.icon, {
this.showDivider = true,
});

@override
Widget build(BuildContext context) {
return Column(
children: [
Container(
height: 47,
alignment: Alignment.centerLeft,
padding: const EdgeInsets.symmetric(horizontal: _padding),
child: Row(
children: [
icon.buildIcon(),
const SizedBox(width: _padding),
Text(
text,
style: Theme.of(context).textTheme.bodyLarge,
),
],
),
),
if (showDivider)
VoicesDivider(
height: 1,
color: Theme.of(context).colors.outlineBorderVariant,
indent: 0,
endIndent: 0,
),
],
);
}
}

class _Section extends StatelessWidget {
final String text;

const _Section(
this.text,
);

@override
Widget build(BuildContext context) {
return Column(
children: [
Container(
height: 47,
alignment: Alignment.centerLeft,
padding: const EdgeInsets.symmetric(horizontal: _padding),
child: Text(
text,
style: Theme.of(context).textTheme.titleSmall,
),
),
VoicesDivider(
height: 1,
color: Theme.of(context).colors.outlineBorderVariant,
indent: 0,
endIndent: 0,
),
],
);
}
}

const _padding = 12.0;

enum _MenuItemValue {
profileAndKeychain,
lock,
}
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import 'package:catalyst_voices/pages/account/account_popup.dart';
import 'package:catalyst_voices/widgets/widgets.dart';
import 'package:catalyst_voices_blocs/catalyst_voices_blocs.dart';
import 'package:catalyst_voices_localization/catalyst_voices_localization.dart';
Expand All @@ -15,8 +16,11 @@ class SessionStateHeader extends StatelessWidget {
return switch (state) {
VisitorSessionState() => const _VisitorButton(),
GuestSessionState() => const _GuestButton(),
ActiveUserSessionState(:final user) =>
_ActiveUserAvatar(letter: user.acronym ?? 'A'),
ActiveUserSessionState(:final user) => AccountPopup(
avatarLetter: user.acronym ?? 'A',
onLockAccountTap: () => debugPrint('Lock account'),
onProfileKeychainTap: () => debugPrint('Open Profile screen'),
),
digitalheartxs marked this conversation as resolved.
Show resolved Hide resolved
};
},
);
Expand Down Expand Up @@ -46,18 +50,3 @@ class _VisitorButton extends StatelessWidget {
);
}
}

class _ActiveUserAvatar extends StatelessWidget {
final String letter;

const _ActiveUserAvatar({
required this.letter,
});

@override
Widget build(BuildContext context) {
return VoicesAvatar(
icon: Text(letter),
);
}
}
Loading