pathxp 0.1.0 copy "pathxp: ^0.1.0" to clipboard
pathxp: ^0.1.0 copied to clipboard

Like regular expressions but for defining paths in a grid

example/lib/main.dart

// ignore_for_file: public_member_api_docs
import 'package:flutter/material.dart';
import 'package:nes_ui/nes_ui.dart';
import 'package:pathxp/pathxp.dart';

void main() {
  runApp(const MyApp());
}

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

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: flutterNesTheme(),
      home: const MyHomePage(),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key});

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  late final _expressionController = TextEditingController();

  bool _onError = false;
  var _width = 10;
  var _height = 10;
  var _startingPoint = (4, 4);
  var _steps = <(int, int)>[];
  late var _lastStep = _startingPoint;

  @override
  void dispose() {
    _expressionController.dispose();
    super.dispose();
  }

  void incrementWidth() {
    setState(() {
      _width++;
    });
  }

  void decrementWidth() {
    if (_width <= 1) {
      return;
    }
    setState(() {
      _width--;
    });
  }

  void incrementHeight() {
    setState(() {
      _height++;
    });
  }

  void decrementHeight() {
    if (_height <= 1) {
      return;
    }
    setState(() {
      _height--;
    });
  }

  void _onChangeExpression() {
    if (_expressionController.text.isEmpty) {
      setState(() {
        _steps = [];
        _lastStep = _startingPoint;
      });
      return;
    }

    final expression = _expressionController.text;

    try {
      final pathXp = Pathxp(expression);

      setState(() {
        _onError = false;
      });

      final path = pathXp.path;

      var point = _startingPoint;
      final newSteps = <(int, int)>[point];

      for (final direction in path) {
        switch (direction) {
          case PathDirection.T:
            point = (point.$1, point.$2 - 1);
          case PathDirection.B:
            point = (point.$1, point.$2 + 1);
          case PathDirection.L:
            point = (point.$1 - 1, point.$2);
          case PathDirection.R:
            point = (point.$1 + 1, point.$2);
        }
        newSteps.add(point);
      }

      setState(() {
        _steps = newSteps;
        _lastStep = point;
      });
    } catch (_) {
      setState(() {
        _onError = true;
      });
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Padding(
        padding: const EdgeInsets.all(16),
        child: Column(
          children: [
            NesContainer(
              label: 'Expression',
              child: Column(
                children: [
                  TextFormField(
                    controller: _expressionController,
                    onChanged: (_) => _onChangeExpression(),
                    decoration: InputDecoration(
                      errorText: _onError ? 'Invalid expression' : null,
                    ),
                  ),
                  const SizedBox(height: 16),
                  Row(
                    children: [
                      NesContainer(
                        width: 320,
                        padding: const EdgeInsets.all(8),
                        child: Row(
                          mainAxisAlignment: MainAxisAlignment.center,
                          children: [
                            NesIconButton(
                              icon: NesIcons.add,
                              onPress: incrementWidth,
                            ),
                            const SizedBox(width: 8),
                            Text('Width: $_width'),
                            const SizedBox(width: 8),
                            NesIconButton(
                              icon: NesIcons.remove,
                              onPress: decrementWidth,
                            ),
                          ],
                        ),
                      ),
                      const SizedBox(width: 16),
                      NesContainer(
                        width: 320,
                        padding: const EdgeInsets.all(8),
                        child: Row(
                          mainAxisAlignment: MainAxisAlignment.center,
                          children: [
                            NesIconButton(
                              icon: NesIcons.add,
                              onPress: incrementHeight,
                            ),
                            const SizedBox(width: 8),
                            Text('Height: $_height'),
                            const SizedBox(width: 8),
                            NesIconButton(
                              icon: NesIcons.remove,
                              onPress: decrementHeight,
                            ),
                          ],
                        ),
                      ),
                    ],
                  ),
                ],
              ),
            ),
            const SizedBox(height: 16),
            Expanded(
              child: NesContainer(
                width: double.infinity,
                child: Padding(
                  padding: const EdgeInsets.all(16),
                  child: LayoutBuilder(
                    builder: (context, constraints) {
                      final cellSize =
                          constraints.maxWidth < constraints.maxHeight
                              ? constraints.maxWidth / _width
                              : constraints.maxHeight / _height;

                      final stepColor =
                          Theme.of(context).textTheme.bodyMedium?.color ??
                              Colors.black;

                      return Center(
                        child: SizedBox(
                          width: _width * cellSize,
                          height: _height * cellSize,
                          child: Stack(
                            children: [
                              for (var y = 0; y < _height; y++)
                                for (var x = 0; x < _width; x++)
                                  Positioned(
                                    left: x * cellSize,
                                    top: y * cellSize,
                                    width: cellSize,
                                    height: cellSize,
                                    child: NesPressable(
                                      onPress: () {
                                        setState(() {
                                          _startingPoint = (x, y);
                                          _lastStep = _startingPoint;
                                          _onChangeExpression();
                                        });
                                      },
                                      child: NesContainer(
                                        width: cellSize,
                                        height: cellSize,
                                        padding: EdgeInsets.zero,
                                        child: (x, y) == _startingPoint
                                            ? Center(
                                                child: NesIcon(
                                                  size: Size.square(
                                                    cellSize * .6,
                                                  ),
                                                  iconData: NesIcons.flag,
                                                ),
                                              )
                                            : (x, y) == _lastStep
                                                ? Center(
                                                    child: NesIcon(
                                                      size: Size.square(
                                                        cellSize * .6,
                                                      ),
                                                      iconData:
                                                          NesIcons.checkedFlag,
                                                    ),
                                                  )
                                                : _steps.contains((x, y))
                                                    ? Align(
                                                        child: SizedBox.square(
                                                          dimension:
                                                              cellSize * .6,
                                                          child: DecoratedBox(
                                                            decoration:
                                                                BoxDecoration(
                                                              color: stepColor,
                                                            ),
                                                          ),
                                                        ),
                                                      )
                                                    : null,
                                      ),
                                    ),
                                  ),
                            ],
                          ),
                        ),
                      );
                    },
                  ),
                ),
              ),
            ),
          ],
        ),
      ),
    );
  }
}
1
likes
0
pub points
88%
popularity

Publisher

unverified uploader

Like regular expressions but for defining paths in a grid

Repository (GitHub)
View/report issues

License

unknown (license)

More

Packages that depend on pathxp