Skip to content

Commit

Permalink
Merge pull request #22 from erickzanardo/feat/key_button
Browse files Browse the repository at this point in the history
feat: adding nes key icon
  • Loading branch information
erickzanardo authored Feb 15, 2023
2 parents 90a00d5 + fc217a9 commit 33915e5
Show file tree
Hide file tree
Showing 10 changed files with 182 additions and 1 deletion.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,9 @@
- feat: add `NesIcons.redo`
- feat: add `customExtensions`
- feat: add keyboard support
- feat: add `NesIcons.unpressedButton`
- feat: add `NesIcons.pressedButton`
- feat: add `NesKeyButton`

# 0.1.0

Expand Down
2 changes: 2 additions & 0 deletions example/lib/gallery/gallery_page.dart
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,8 @@ class GalleryPage extends StatelessWidget {
const SizedBox(height: 32),
const TextSection(),
const SizedBox(height: 32),
const KeyIconsSection(),
const SizedBox(height: 32),
const SelectionListSection(),
const SizedBox(height: 32),
const CheckBoxesSection(),
Expand Down
54 changes: 54 additions & 0 deletions example/lib/gallery/sections/key_icons.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import 'package:flutter/material.dart';
import 'package:nes_ui/nes_ui.dart';
import 'package:phased/phased.dart';

class KeyIconsSection extends StatelessWidget {
const KeyIconsSection({super.key});

@override
Widget build(BuildContext context) {
final theme = Theme.of(context);
return Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
'Key Icons',
style: theme.textTheme.displayMedium,
),
const SizedBox(height: 16),
Wrap(
children: [
const NesKeyIcon(
buttonKey: 'a',
),
const SizedBox(width: 16),
const NesKeyIcon(
buttonKey: 'a',
pressed: true,
),
const SizedBox(width: 16),
_Toogler(),
],
),
],
);
}
}

class _Toogler extends Phased<bool> {
_Toogler()
: super(
state: PhasedState<bool>(
values: [true, false],
ticker: const Duration(milliseconds: 500),
),
);

@override
Widget build(BuildContext context) {
return NesKeyIcon(
buttonKey: 'a',
pressed: state.value,
);
}
}
1 change: 1 addition & 0 deletions example/lib/gallery/sections/sections.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ export 'checkboxes.dart';
export 'containers.dart';
export 'custom_extensions.dart';
export 'icons.dart';
export 'key_icons.dart';
export 'selection_list.dart';
export 'text_fields.dart';
export 'texts.dart';
2 changes: 1 addition & 1 deletion example/pubspec.lock
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,7 @@ packages:
source: hosted
version: "2.1.3"
phased:
dependency: transitive
dependency: "direct main"
description:
name: phased
sha256: "4dc19d589fd059268b07357767ac96eef2861eb5e8ceedf9d23fb933f0128396"
Expand Down
1 change: 1 addition & 0 deletions example/pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ dependencies:
flutter_bloc: ^8.1.1
nes_ui:
path: ../
phased: ^0.0.3

dev_dependencies:
very_good_analysis: ^3.1.0
Expand Down
14 changes: 14 additions & 0 deletions lib/src/widgets/nes_icon.dart
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,20 @@ class NesIcons {
'8,8;2,-1;4,0;3,-1;1,0;4,-1;1,0;1,-1;1,0;6,-1;1,0;2,-1;1,0;4,-1;1,0;1,-1;1,0;1,-1;1,0;3,-1;2,0;1,-1;1,0;1,-1;1,0;2,-1;1,0;2,-1;1,0;3,-1;1,0;4,-1;3,0;2,-1',
),
);

/// An unpressed button icon.
late final unpressedButton = NesIconData(
MiniSprite.fromDataString(
'8,8;2,-1;4,0;3,-1;6,0;1,-1;25,0;1,1;4,0;1,1;1,0;1,-1;1,0;4,1;1,0;3,-1;4,0;2,-1',
),
);

/// A pressed button icon.
late final pressedButton = NesIconData(
MiniSprite.fromDataString(
'8,8;10,-1;4,0;3,-1;6,0;1,-1;24,0;1,-1;6,0;3,-1;4,0;2,-1',
),
);
}

/// {@template nes_icon}
Expand Down
67 changes: 67 additions & 0 deletions lib/src/widgets/nes_key_icon.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
import 'package:flutter/material.dart';
import 'package:nes_ui/nes_ui.dart';

/// {@template nes_key_icon}
/// A pressable icon, representing a single key.
///
/// This widget by itself doesn't handle touch/key events
/// use it in combination with other widgets to make it
/// interactive.
/// {@endtemplate}
class NesKeyIcon extends StatelessWidget {
/// {@macro nes_key_icon}
const NesKeyIcon({
super.key,
required this.buttonKey,
this.pressed = false,
this.size,
}) : assert(buttonKey.length == 1, 'buttonKey must be a single character');

/// The key that this icon represents.
final String buttonKey;

/// If this button is in a pressed state or not.
final bool pressed;

/// Size.
final Size? size;

@override
Widget build(BuildContext context) {
final nesTheme = context.nesThemeExtension<NesTheme>();
final nesIconTheme = context.nesThemeExtension<NesIconTheme>();

final pixelSize = nesTheme.pixelSize.toDouble();

final iconData = pressed
? NesIcons.instance.pressedButton
: NesIcons.instance.unpressedButton;

final buttonSize = size ??
Size(
iconData.sprite.pixels[0].length * pixelSize,
iconData.sprite.pixels.length * pixelSize,
);

return Stack(
children: [
Positioned(
child: NesIcon(
size: buttonSize,
iconData: iconData,
),
),
Positioned(
left: buttonSize.width / 2 - 5,
top: buttonSize.height / 2 - (pressed ? 4 : 8),
child: Text(
buttonKey.toUpperCase(),
style: Theme.of(context).textTheme.bodySmall?.copyWith(
color: nesIconTheme.secondary,
),
),
),
],
);
}
}
1 change: 1 addition & 0 deletions lib/src/widgets/widgets.dart
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,5 @@ export 'nes_container.dart';
export 'nes_controller_focus.dart';
export 'nes_icon.dart';
export 'nes_input.dart';
export 'nes_key_icon.dart';
export 'nes_selection_list.dart';
38 changes: 38 additions & 0 deletions test/src/widgets/nes_key_icon_test.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import 'package:flutter/material.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:nes_ui/nes_ui.dart';

void main() {
group('NesIcon', () {
testWidgets('renders correctly', (tester) async {
await tester.pumpWidget(
MaterialApp(
theme: flutterNesTheme(),
home: const Scaffold(
body: NesKeyIcon(
buttonKey: 'A',
),
),
),
);

expect(find.byType(NesKeyIcon), findsOneWidget);
});

testWidgets('renders pressed correctly', (tester) async {
await tester.pumpWidget(
MaterialApp(
theme: flutterNesTheme(),
home: const Scaffold(
body: NesKeyIcon(
buttonKey: 'A',
pressed: true,
),
),
),
);

expect(find.byType(NesKeyIcon), findsOneWidget);
});
});
}

0 comments on commit 33915e5

Please sign in to comment.