AdvancedWrap

Pub Version License: MIT Flutter Dart

A production-ready, UX-first Flutter package that supersedes wrap_and_more with advanced layout capabilities, overflow strategies, and responsive design.

โœจ Features

  • ๐ŸŽฏ Multiple Overflow Strategies: Count, Expand, Popup, Scrollable, and Custom
  • ๐ŸŽฎ Controller Support: Programmatic expand/collapse with state management
  • ๐Ÿ“ฑ Responsive Design: Adaptive layouts with breakpoint-based configurations
  • โšก Performance Optimized: Custom render objects for large datasets
  • โ™ฟ Accessibility First: Full semantic support and screen reader compatibility
  • ๐ŸŽจ Customizable: Extensive theming and styling options
  • ๐Ÿงช Well Tested: Comprehensive test coverage
  • ๐Ÿ“š TypeScript-like API: Intuitive and type-safe interface

๐Ÿš€ Quick Start

Installation

Add advanced_wrap to your pubspec.yaml:

dependencies:
  advanced_wrap: ^0.1.0

Basic Usage

import 'package:advanced_wrap/advanced_wrap.dart';

// Simple wrap with overflow count
AdvancedWrap(
  children: [
    Chip(label: Text('Flutter')),
    Chip(label: Text('Dart')),
    Chip(label: Text('Mobile')),
    // ... more children
  ],
  maxRows: 2,
  overflowStrategy: OverflowStrategy.count,
)

๐Ÿ“– Documentation

Core Components

AdvancedWrap Widget

The main widget that provides advanced wrapping capabilities:

AdvancedWrap(
  // Content
  children: <Widget>[], // OR
  itemBuilder: (context, index) => Widget,
  itemCount: int,
  
  // Layout
  maxRows: 3,
  minRows: 1,
  spacing: 8.0,
  runSpacing: 8.0,
  direction: Axis.horizontal,
  alignment: WrapAlignment.start,
  runAlignment: WrapAlignment.start,
  crossAxisAlignment: WrapCrossAlignment.start,
  
  // Overflow
  overflowStrategy: OverflowStrategy.count,
  overflowBuilder: (context, restCount, hiddenChildren) => Widget,
  
  // Control
  controller: AdvancedWrapController(),
  
  // Responsive
  adaptiveConfig: AdvancedWrapConfig(...),
)

AdvancedWrapController

Controller for programmatic state management:

final controller = AdvancedWrapController();

// Control expansion
controller.expand();
controller.collapse();
controller.toggle();

// Listen to state changes
controller.addListener(() {
  print('Expanded: ${controller.isExpanded}');
});

// Listen to overflow changes
controller.onOverflowChanged.listen((hiddenCount) {
  print('Hidden items: $hiddenCount');
});

Overflow Strategies

1. Count Strategy

Shows a "+N more" indicator:

AdvancedWrap(
  overflowStrategy: OverflowStrategy.count,
  maxRows: 2,
  children: widgets,
)

2. Expand Strategy

Provides expand/collapse functionality:

AdvancedWrap(
  overflowStrategy: OverflowStrategy.expand,
  controller: controller,
  maxRows: 2,
  children: widgets,
)

3. Popup Strategy

Shows overflow items in a dialog:

AdvancedWrap(
  overflowStrategy: OverflowStrategy.popup,
  maxRows: 2,
  children: widgets,
)

4. Scrollable Strategy

Displays overflow items in a bottom sheet:

AdvancedWrap(
  overflowStrategy: OverflowStrategy.scrollable,
  maxRows: 2,
  children: widgets,
)

5. Custom Strategy

Fully customizable overflow handling:

AdvancedWrap(
  overflowStrategy: OverflowStrategy.custom,
  overflowBuilder: (context, restCount, hiddenChildren) {
    return GestureDetector(
      onTap: () => showCustomOverflow(hiddenChildren),
      child: Container(
        padding: EdgeInsets.all(8),
        decoration: BoxDecoration(
          color: Colors.blue,
          borderRadius: BorderRadius.circular(16),
        ),
        child: Text('$restCount more', style: TextStyle(color: Colors.white)),
      ),
    );
  },
  children: widgets,
)

Responsive Design

Configure different behaviors for different screen sizes:

AdvancedWrap(
  adaptiveConfig: AdvancedWrapConfig(
    xs: AdvancedWrapConfig(maxRows: 1, overflowStrategy: OverflowStrategy.popup),
    sm: AdvancedWrapConfig(maxRows: 2, overflowStrategy: OverflowStrategy.count),
    md: AdvancedWrapConfig(maxRows: 3, overflowStrategy: OverflowStrategy.expand),
    lg: AdvancedWrapConfig(maxRows: 4, overflowStrategy: OverflowStrategy.expand),
  ),
  children: widgets,
)

ItemBuilder Pattern

For large datasets, use the itemBuilder pattern for better performance:

AdvancedWrap(
  itemCount: 1000,
  itemBuilder: (context, index) {
    return Chip(
      label: Text('Item $index'),
      onDeleted: () => removeItem(index),
    );
  },
  maxRows: 3,
  overflowStrategy: OverflowStrategy.scrollable,
)

๐ŸŽจ Customization

Theming

AdvancedWrap respects your app's theme:

// The overflow widgets automatically use:
// - Theme.of(context).primaryColor
// - Theme.of(context).colorScheme.secondary
// - Theme.of(context).colorScheme.tertiary
// - Theme.of(context).textTheme

Custom Overflow Builder

Create completely custom overflow indicators:

Widget customOverflowBuilder(BuildContext context, int restCount, List<Widget> hiddenChildren) {
  return PopupMenuButton<int>(
    child: Chip(
      avatar: Icon(Icons.more_horiz),
      label: Text('$restCount more'),
    ),
    itemBuilder: (context) => hiddenChildren.asMap().entries.map((entry) {
      return PopupMenuItem<int>(
        value: entry.key,
        child: entry.value,
      );
    }).toList(),
  );
}

โ™ฟ Accessibility

AdvancedWrap includes comprehensive accessibility support:

  • Semantic Labels: All overflow indicators have descriptive labels
  • Screen Reader Support: Proper announcements for state changes
  • Keyboard Navigation: Full keyboard accessibility
  • Focus Management: Proper focus handling in popups and dialogs
// Accessibility is built-in, but you can customize:
AdvancedWrap(
  semanticLabel: 'Tag list with overflow',
  children: widgets,
)

๐Ÿ”„ Migration from wrap_and_more

Before (wrap_and_more)

WrapAndMore(
  children: widgets,
  maxLines: 2,
  contentPadding: EdgeInsets.all(8),
)

After (AdvancedWrap)

AdvancedWrap(
  children: widgets,
  maxRows: 2,
  spacing: 8.0,
  runSpacing: 8.0,
  overflowStrategy: OverflowStrategy.count,
)

Key Changes

  • maxLines โ†’ maxRows
  • contentPadding โ†’ spacing and runSpacing
  • Enhanced overflow strategies
  • Added controller support
  • Improved performance
  • Better accessibility

๐Ÿ“Š Performance

AdvancedWrap is optimized for performance:

  • Custom RenderObject: Efficient layout calculations
  • Lazy Building: Only builds visible items when using itemBuilder
  • Memory Efficient: Minimal memory footprint
  • Smooth Animations: 60fps animations with proper curve handling

Benchmarks

Scenario Items Build Time Memory Usage
Static Children 100 ~2ms ~1MB
ItemBuilder 1000 ~5ms ~2MB
ItemBuilder 10000 ~15ms ~5MB

๐Ÿงช Testing

AdvancedWrap includes comprehensive test utilities:

import 'package:advanced_wrap/testing.dart';

testWidgets('should handle overflow correctly', (tester) async {
  await tester.pumpWidget(
    MaterialApp(
      home: AdvancedWrap(
        children: List.generate(10, (i) => Chip(label: Text('$i'))),
        maxRows: 2,
      ),
    ),
  );
  
  // Test overflow indicator
  expect(find.text('+'), findsOneWidget);
});

๐Ÿค Contributing

We welcome contributions! Please see our Contributing Guide for details.

Development Setup

# Clone the repository
git clone https://github.com/sdkwala/advanced_wrap.git

# Install dependencies
flutter pub get

# Run tests
flutter test

# Run example
cd example
flutter run

๐Ÿ“„ License

This project is licensed under the MIT License - see the LICENSE file for details.

๐Ÿ™ Acknowledgments

  • Inspired by the original wrap_and_more package
  • Built with โค๏ธ for the Flutter community
  • Special thanks to all contributors

๐Ÿ“ž Support


Made with โค๏ธ by sdkwala.com

Libraries

advanced_wrap
A production-ready, UX-first Flutter package that extends Flutter Wrap with powerful overflow strategies, controller-driven expand/collapse, responsive behavior, and accessibility features.