chore: fix dart doc warnings

This commit is contained in:
appflowy 2022-09-06 11:55:53 +08:00
parent 8f5569a012
commit b5321319cc
16 changed files with 269 additions and 200 deletions

View File

@ -22,7 +22,7 @@ part 'board_bloc.freezed.dart';
class BoardBloc extends Bloc<BoardEvent, BoardState> { class BoardBloc extends Bloc<BoardEvent, BoardState> {
final BoardDataController _gridDataController; final BoardDataController _gridDataController;
late final AppFlowyBoardDataController boardController; late final AppFlowyBoardController boardController;
final MoveRowFFIService _rowService; final MoveRowFFIService _rowService;
LinkedHashMap<String, GroupController> groupControllers = LinkedHashMap(); LinkedHashMap<String, GroupController> groupControllers = LinkedHashMap();
@ -34,7 +34,7 @@ class BoardBloc extends Bloc<BoardEvent, BoardState> {
: _rowService = MoveRowFFIService(gridId: view.id), : _rowService = MoveRowFFIService(gridId: view.id),
_gridDataController = BoardDataController(view: view), _gridDataController = BoardDataController(view: view),
super(BoardState.initial(view.id)) { super(BoardState.initial(view.id)) {
boardController = AppFlowyBoardDataController( boardController = AppFlowyBoardController(
onMoveGroup: ( onMoveGroup: (
fromColumnId, fromColumnId,
fromIndex, fromIndex,
@ -165,10 +165,10 @@ class BoardBloc extends Bloc<BoardEvent, BoardState> {
boardController.clear(); boardController.clear();
// //
List<AppFlowyBoardGroupData> columns = groups List<AppFlowyGroupData> columns = groups
.where((group) => fieldController.getField(group.fieldId) != null) .where((group) => fieldController.getField(group.fieldId) != null)
.map((group) { .map((group) {
return AppFlowyBoardGroupData( return AppFlowyGroupData(
id: group.groupId, id: group.groupId,
name: group.desc, name: group.desc,
items: _buildRows(group), items: _buildRows(group),
@ -350,7 +350,7 @@ class BoardColumnItem extends AppFlowyGroupItem {
class GroupControllerDelegateImpl extends GroupControllerDelegate { class GroupControllerDelegateImpl extends GroupControllerDelegate {
final GridFieldController fieldController; final GridFieldController fieldController;
final AppFlowyBoardDataController controller; final AppFlowyBoardController controller;
final void Function(String, RowPB, int?) onNewColumnItem; final void Function(String, RowPB, int?) onNewColumnItem;
GroupControllerDelegateImpl({ GroupControllerDelegateImpl({

View File

@ -63,7 +63,7 @@ class BoardContent extends StatefulWidget {
class _BoardContentState extends State<BoardContent> { class _BoardContentState extends State<BoardContent> {
late ScrollController scrollController; late ScrollController scrollController;
late AFBoardScrollManager scrollManager; late AppFlowyBoardScrollManager scrollManager;
final config = AppFlowyBoardConfig( final config = AppFlowyBoardConfig(
groupBackgroundColor: HexColor.fromHex('#F7F8FC'), groupBackgroundColor: HexColor.fromHex('#F7F8FC'),
@ -72,7 +72,7 @@ class _BoardContentState extends State<BoardContent> {
@override @override
void initState() { void initState() {
scrollController = ScrollController(); scrollController = ScrollController();
scrollManager = AFBoardScrollManager(); scrollManager = AppFlowyBoardScrollManager();
super.initState(); super.initState();
} }
@ -104,7 +104,7 @@ class _BoardContentState extends State<BoardContent> {
child: AppFlowyBoard( child: AppFlowyBoard(
scrollManager: scrollManager, scrollManager: scrollManager,
scrollController: scrollController, scrollController: scrollController,
dataController: context.read<BoardBloc>().boardController, controller: context.read<BoardBloc>().boardController,
headerBuilder: _buildHeader, headerBuilder: _buildHeader,
footerBuilder: _buildFooter, footerBuilder: _buildFooter,
cardBuilder: (_, column, columnItem) => _buildCard( cardBuilder: (_, column, columnItem) => _buildCard(
@ -149,7 +149,7 @@ class _BoardContentState extends State<BoardContent> {
Widget _buildHeader( Widget _buildHeader(
BuildContext context, BuildContext context,
AppFlowyBoardGroupData columnData, AppFlowyGroupData columnData,
) { ) {
final boardCustomData = columnData.customData as BoardCustomData; final boardCustomData = columnData.customData as BoardCustomData;
return AppFlowyGroupHeader( return AppFlowyGroupHeader(
@ -181,7 +181,7 @@ class _BoardContentState extends State<BoardContent> {
); );
} }
Widget _buildFooter(BuildContext context, AppFlowyBoardGroupData columnData) { Widget _buildFooter(BuildContext context, AppFlowyGroupData columnData) {
final boardCustomData = columnData.customData as BoardCustomData; final boardCustomData = columnData.customData as BoardCustomData;
final group = boardCustomData.group; final group = boardCustomData.group;
@ -215,7 +215,7 @@ class _BoardContentState extends State<BoardContent> {
Widget _buildCard( Widget _buildCard(
BuildContext context, BuildContext context,
AppFlowyBoardGroupData column, AppFlowyGroupData column,
AppFlowyGroupItem columnItem, AppFlowyGroupItem columnItem,
) { ) {
final boardColumnItem = columnItem as BoardColumnItem; final boardColumnItem = columnItem as BoardColumnItem;
@ -242,7 +242,7 @@ class _BoardContentState extends State<BoardContent> {
}, },
); );
return AppFlowyGroupItemCard( return AppFlowyGroupCard(
key: ValueKey(columnItem.id), key: ValueKey(columnItem.id),
margin: config.cardPadding, margin: config.cardPadding,
decoration: _makeBoxDecoration(context), decoration: _makeBoxDecoration(context),

View File

@ -34,17 +34,83 @@ flutter pub add appflowy_board
flutter pub get flutter pub get
``` ```
This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get): This will add a line like this to your package's pubspec.yaml:
```dart ```dart
dependencies: dependencies:
appflowy_board: ^0.0.6 appflowy_board: ^0.0.6
``` ```
## Create board ## Create your first board
Initialize an `AppFlowyBoardController` for the board. It contains the data used by the board. You can
register callbacks to receive the changes of the board.
Import the package in your Dart file:
```dart ```dart
import 'package:appflowy_board/appflowy_board.dart';
final AppFlowyBoardController controller = AppFlowyBoardController(
onMoveGroup: (fromGroupId, fromIndex, toGroupId, toIndex) {
debugPrint('Move item from $fromIndex to $toIndex');
},
onMoveGroupItem: (groupId, fromIndex, toIndex) {
debugPrint('Move $groupId:$fromIndex to $groupId:$toIndex');
},
onMoveGroupItemToGroup: (fromGroupId, fromIndex, toGroupId, toIndex) {
debugPrint('Move $fromGroupId:$fromIndex to $toGroupId:$toIndex');
},
);
```
Provide an initial value of the board by initializing the `AppFlowyGroupData`. It represents a group data and contains list of items. Each item displayed in the group requires to implement the `AppFlowyGroupItem` class.
```dart
void initState() {
final group1 = AppFlowyGroupData(id: "To Do", items: [
TextItem("Card 1"),
TextItem("Card 2"),
]);
final group2 = AppFlowyGroupData(id: "In Progress", items: [
TextItem("Card 3"),
TextItem("Card 4"),
]);
final group3 = AppFlowyGroupData(id: "Done", items: []);
controller.addGroup(group1);
controller.addGroup(group2);
controller.addGroup(group3);
super.initState();
}
class TextItem extends AppFlowyGroupItem {
final String s;
TextItem(this.s);
@override
String get id => s;
}
```
Finally, return a `AppFlowyBoard` widget in the build method.
```dart
@override
Widget build(BuildContext context) {
return AppFlowyBoard(
controller: controller,
cardBuilder: (context, group, groupItem) {
final textItem = groupItem as TextItem;
return AppFlowyGroupCard(
key: ObjectKey(textItem),
child: Text(textItem.s),
);
},
groupConstraints: const BoxConstraints.tightFor(width: 240),
);
}
``` ```
## Usage Example ## Usage Example
@ -53,16 +119,14 @@ First, run main.dart to play with the demo.
Second, let's delve into multi_board_list_example.dart to understand a few key components: Second, let's delve into multi_board_list_example.dart to understand a few key components:
* A Board widget is created via instantiating an AFBoard() object. * A Board widget is created via instantiating an `AppFlowyBoard` object.
* In the AFBoard() object, you can find: * In the `AppFlowyBoard` object, you can find the `AppFlowyBoardController`, which is defined in board_data.dart, is feeded with prepopulated mock data. It also contains callback functions to materialize future user data.
* AFBoardDataController, which is defined in board_data.dart, is feeded with prepopulated mock data. It also contains callback functions to materialize future user data. * Three builders: AppFlowyBoardHeaderBuilder, AppFlowyBoardFooterBuilder, AppFlowyBoardCardBuilder. See below image for what they are used for.
* Three builders: AppFlowyColumnHeader, AppFlowyColumnFooter, AppFlowyColumnItemCard. See below image for what they are used for.
<p>
<!-- <p> <img src="https://github.com/AppFlowy-IO/AppFlowy/blob/main/frontend/app_flowy/packages/appflowy_board/example/gifs/appflowy_board_builders.jpg?raw=true" width="200" title="AppFlowyBoard">
<img src="https://github.com/AppFlowy-IO/AppFlowy/blob/main/frontend/app_flowy/packages/appflowy_board/example/gifs/appflowy_board_builders.jpg?raw=true" width="100%" title="AppFlowyBoard"> </p>
</p> -->
## Glossary ## Glossary
Please refer to the API documentation. Please refer to the API documentation.
@ -74,6 +138,3 @@ Please look at [CONTRIBUTING.md](https://appflowy.gitbook.io/docs/essential-docu
## License ## License
Distributed under the AGPLv3 License. See [LICENSE](https://github.com/AppFlowy-IO/AppFlowy-Docs/blob/main/LICENSE) for more information. Distributed under the AGPLv3 License. See [LICENSE](https://github.com/AppFlowy-IO/AppFlowy-Docs/blob/main/LICENSE) for more information.
d

View File

@ -9,22 +9,21 @@ class MultiBoardListExample extends StatefulWidget {
} }
class _MultiBoardListExampleState extends State<MultiBoardListExample> { class _MultiBoardListExampleState extends State<MultiBoardListExample> {
final AppFlowyBoardDataController boardDataController = final AppFlowyBoardController controller = AppFlowyBoardController(
AppFlowyBoardDataController( onMoveGroup: (fromGroupId, fromIndex, toGroupId, toIndex) {
onMoveGroup: (fromColumnId, fromIndex, toColumnId, toIndex) { debugPrint('Move item from $fromIndex to $toIndex');
// debugPrint('Move column from $fromIndex to $toIndex');
}, },
onMoveGroupItem: (columnId, fromIndex, toIndex) { onMoveGroupItem: (groupId, fromIndex, toIndex) {
// debugPrint('Move $columnId:$fromIndex to $columnId:$toIndex'); debugPrint('Move $groupId:$fromIndex to $groupId:$toIndex');
}, },
onMoveGroupItemToGroup: (fromColumnId, fromIndex, toColumnId, toIndex) { onMoveGroupItemToGroup: (fromGroupId, fromIndex, toGroupId, toIndex) {
// debugPrint('Move $fromColumnId:$fromIndex to $toColumnId:$toIndex'); debugPrint('Move $fromGroupId:$fromIndex to $toGroupId:$toIndex');
}, },
); );
@override @override
void initState() { void initState() {
List<AppFlowyGroupItem> a = [ final group1 = AppFlowyGroupData(id: "To Do", name: "To Do", items: [
TextItem("Card 1"), TextItem("Card 1"),
TextItem("Card 2"), TextItem("Card 2"),
RichTextItem(title: "Card 3", subtitle: 'Aug 1, 2020 4:05 PM'), RichTextItem(title: "Card 3", subtitle: 'Aug 1, 2020 4:05 PM'),
@ -34,11 +33,9 @@ class _MultiBoardListExampleState extends State<MultiBoardListExample> {
RichTextItem(title: "Card 7", subtitle: 'Aug 1, 2020 4:05 PM'), RichTextItem(title: "Card 7", subtitle: 'Aug 1, 2020 4:05 PM'),
RichTextItem(title: "Card 8", subtitle: 'Aug 1, 2020 4:05 PM'), RichTextItem(title: "Card 8", subtitle: 'Aug 1, 2020 4:05 PM'),
TextItem("Card 9"), TextItem("Card 9"),
]; ]);
final column1 = final group2 = AppFlowyGroupData(
AppFlowyBoardGroupData(id: "To Do", name: "To Do", items: a);
final column2 = AppFlowyBoardGroupData(
id: "In Progress", id: "In Progress",
name: "In Progress", name: "In Progress",
items: <AppFlowyGroupItem>[ items: <AppFlowyGroupItem>[
@ -47,12 +44,12 @@ class _MultiBoardListExampleState extends State<MultiBoardListExample> {
], ],
); );
final column3 = AppFlowyBoardGroupData( final group3 = AppFlowyGroupData(
id: "Done", name: "Done", items: <AppFlowyGroupItem>[]); id: "Done", name: "Done", items: <AppFlowyGroupItem>[]);
boardDataController.addGroup(column1); controller.addGroup(group1);
boardDataController.addGroup(column2); controller.addGroup(group2);
boardDataController.addGroup(column3); controller.addGroup(group3);
super.initState(); super.initState();
} }
@ -62,54 +59,45 @@ class _MultiBoardListExampleState extends State<MultiBoardListExample> {
final config = AppFlowyBoardConfig( final config = AppFlowyBoardConfig(
groupBackgroundColor: HexColor.fromHex('#F7F8FC'), groupBackgroundColor: HexColor.fromHex('#F7F8FC'),
); );
return Container( return AppFlowyBoard(
color: Colors.white, controller: controller,
child: Padding( cardBuilder: (context, group, groupItem) {
padding: const EdgeInsets.symmetric(vertical: 30, horizontal: 20), return AppFlowyGroupCard(
child: AppFlowyBoard( key: ValueKey(groupItem.id),
dataController: boardDataController, child: _buildCard(groupItem),
footerBuilder: (context, columnData) { );
return AppFlowyGroupFooter( },
icon: const Icon(Icons.add, size: 20), footerBuilder: (context, columnData) {
title: const Text('New'), return AppFlowyGroupFooter(
height: 50, icon: const Icon(Icons.add, size: 20),
margin: config.groupItemPadding, title: const Text('New'),
); height: 50,
}, margin: config.groupItemPadding,
headerBuilder: (context, columnData) { );
return AppFlowyGroupHeader( },
icon: const Icon(Icons.lightbulb_circle), headerBuilder: (context, columnData) {
title: SizedBox( return AppFlowyGroupHeader(
width: 60, icon: const Icon(Icons.lightbulb_circle),
child: TextField( title: SizedBox(
controller: TextEditingController() width: 60,
..text = columnData.headerData.groupName, child: TextField(
onSubmitted: (val) { controller: TextEditingController()
boardDataController ..text = columnData.headerData.groupName,
.getGroupController(columnData.headerData.groupId)! onSubmitted: (val) {
.updateGroupName(val); controller
}, .getGroupController(columnData.headerData.groupId)!
), .updateGroupName(val);
},
), ),
addIcon: const Icon(Icons.add, size: 20), ),
moreIcon: const Icon(Icons.more_horiz, size: 20), addIcon: const Icon(Icons.add, size: 20),
height: 50, moreIcon: const Icon(Icons.more_horiz, size: 20),
margin: config.groupItemPadding, height: 50,
); margin: config.groupItemPadding,
}, );
cardBuilder: (context, column, columnItem) { },
return AppFlowyGroupItemCard( groupConstraints: const BoxConstraints.tightFor(width: 240),
key: ValueKey(columnItem.id), config: config);
child: _buildCard(columnItem),
);
},
groupConstraints: const BoxConstraints.tightFor(width: 240),
config: AppFlowyBoardConfig(
groupBackgroundColor: HexColor.fromHex('#F7F8FC'),
),
),
),
);
} }
Widget _buildCard(AppFlowyGroupItem item) { Widget _buildCard(AppFlowyGroupItem item) {

View File

@ -9,11 +9,11 @@ class SingleBoardListExample extends StatefulWidget {
} }
class _SingleBoardListExampleState extends State<SingleBoardListExample> { class _SingleBoardListExampleState extends State<SingleBoardListExample> {
final AppFlowyBoardDataController boardData = AppFlowyBoardDataController(); final AppFlowyBoardController boardData = AppFlowyBoardController();
@override @override
void initState() { void initState() {
final column = AppFlowyBoardGroupData( final column = AppFlowyGroupData(
id: "1", id: "1",
name: "1", name: "1",
items: [ items: [
@ -31,7 +31,7 @@ class _SingleBoardListExampleState extends State<SingleBoardListExample> {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return AppFlowyBoard( return AppFlowyBoard(
dataController: boardData, controller: boardData,
cardBuilder: (context, column, columnItem) { cardBuilder: (context, column, columnItem) {
return _RowWidget( return _RowWidget(
item: columnItem as TextItem, key: ObjectKey(columnItem)); item: columnItem as TextItem, key: ObjectKey(columnItem));

View File

@ -1,6 +1,7 @@
/// AppFlowyBoard library
library appflowy_board; library appflowy_board;
export 'src/widgets/board_column/board_column_data.dart'; export 'src/widgets/board_group/group_data.dart';
export 'src/widgets/board_data.dart'; export 'src/widgets/board_data.dart';
export 'src/widgets/styled_widgets/appflowy_styled_widgets.dart'; export 'src/widgets/styled_widgets/widgets.dart';
export 'src/widgets/board.dart'; export 'src/widgets/board.dart';

View File

@ -1,17 +1,17 @@
import 'package:appflowy_board/src/utils/log.dart'; import 'package:appflowy_board/src/utils/log.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:provider/provider.dart'; import 'package:provider/provider.dart';
import 'board_column/board_column.dart';
import 'board_column/board_column_data.dart';
import 'board_data.dart'; import 'board_data.dart';
import 'board_group/group.dart';
import 'board_group/group_data.dart';
import 'reorder_flex/drag_state.dart'; import 'reorder_flex/drag_state.dart';
import 'reorder_flex/drag_target_interceptor.dart'; import 'reorder_flex/drag_target_interceptor.dart';
import 'reorder_flex/reorder_flex.dart'; import 'reorder_flex/reorder_flex.dart';
import 'reorder_phantom/phantom_controller.dart'; import 'reorder_phantom/phantom_controller.dart';
import '../rendering/board_overlay.dart'; import '../rendering/board_overlay.dart';
class AFBoardScrollManager { class AppFlowyBoardScrollManager {
BoardGroupsState? _groupState; AppFlowyBoardState? _groupState;
void scrollToBottom(String groupId, VoidCallback? completed) { void scrollToBottom(String groupId, VoidCallback? completed) {
_groupState _groupState
@ -48,26 +48,36 @@ class AppFlowyBoard extends StatelessWidget {
final Widget? background; final Widget? background;
/// The [cardBuilder] function which will be invoked on each card build. /// The [cardBuilder] function which will be invoked on each card build.
/// The [cardBuilder] takes the [BuildContext],[AppFlowyBoardGroupData] and /// The [cardBuilder] takes the [BuildContext],[AppFlowyGroupData] and
/// the corresponding [AppFlowyGroupItem]. /// the corresponding [AppFlowyGroupItem].
/// ///
/// must return a widget. /// must return a widget.
final AppFlowyBoardCardBuilder cardBuilder; final AppFlowyBoardCardBuilder cardBuilder;
/// The [headerBuilder] function which will be invoked on each group build. /// The [headerBuilder] function which will be invoked on each group build.
/// The [headerBuilder] takes the [BuildContext] and [AppFlowyBoardGroupData]. /// The [headerBuilder] takes the [BuildContext] and [AppFlowyGroupData].
/// ///
/// must return a widget. /// must return a widget.
final AppFlowyBoardHeaderBuilder? headerBuilder; final AppFlowyBoardHeaderBuilder? headerBuilder;
/// The [footerBuilder] function which will be invoked on each group build. /// The [footerBuilder] function which will be invoked on each group build.
/// The [footerBuilder] takes the [BuildContext] and [AppFlowyBoardGroupData]. /// The [footerBuilder] takes the [BuildContext] and [AppFlowyGroupData].
/// ///
/// must return a widget. /// must return a widget.
final AppFlowyBoardFooterBuilder? footerBuilder; final AppFlowyBoardFooterBuilder? footerBuilder;
/// A controller for [AppFlowyBoard] widget.
/// ///
final AppFlowyBoardDataController dataController; /// A [AppFlowyBoardController] can be used to provide an initial value of
/// the board by calling `addGroup` method with the passed in parameter
/// [AppFlowyGroupData]. A [AppFlowyGroupData] represents one
/// group data. Whenever the user modifies the board, this controller will
/// update the corresponding group data.
///
/// Also, you can register the callbacks that receive the changes. Check out
/// the [AppFlowyBoardController] for more information.
///
final AppFlowyBoardController controller;
final BoxConstraints groupConstraints; final BoxConstraints groupConstraints;
@ -78,12 +88,12 @@ class AppFlowyBoard extends StatelessWidget {
final AppFlowyBoardConfig config; final AppFlowyBoardConfig config;
final AFBoardScrollManager? scrollManager; final AppFlowyBoardScrollManager? scrollManager;
final BoardGroupsState _groupState = BoardGroupsState(); final AppFlowyBoardState _groupState = AppFlowyBoardState();
AppFlowyBoard({ AppFlowyBoard({
required this.dataController, required this.controller,
required this.cardBuilder, required this.cardBuilder,
this.background, this.background,
this.footerBuilder, this.footerBuilder,
@ -95,7 +105,7 @@ class AppFlowyBoard extends StatelessWidget {
Key? key, Key? key,
}) : super(key: key) { }) : super(key: key) {
phantomController = BoardPhantomController( phantomController = BoardPhantomController(
delegate: dataController, delegate: controller,
groupsState: _groupState, groupsState: _groupState,
); );
} }
@ -103,16 +113,16 @@ class AppFlowyBoard extends StatelessWidget {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return ChangeNotifierProvider.value( return ChangeNotifierProvider.value(
value: dataController, value: controller,
child: Consumer<AppFlowyBoardDataController>( child: Consumer<AppFlowyBoardController>(
builder: (context, notifier, child) { builder: (context, notifier, child) {
if (scrollManager != null) { if (scrollManager != null) {
scrollManager!._groupState = _groupState; scrollManager!._groupState = _groupState;
} }
return _AppFlolwyBoardContent( return _AppFlowyBoardContent(
config: config, config: config,
dataController: dataController, dataController: controller,
scrollController: scrollController, scrollController: scrollController,
scrollManager: scrollManager, scrollManager: scrollManager,
columnsState: _groupState, columnsState: _groupState,
@ -123,7 +133,7 @@ class AppFlowyBoard extends StatelessWidget {
footerBuilder: footerBuilder, footerBuilder: footerBuilder,
headerBuilder: headerBuilder, headerBuilder: headerBuilder,
phantomController: phantomController, phantomController: phantomController,
onReorder: dataController.moveGroup, onReorder: controller.moveGroup,
); );
}, },
), ),
@ -131,25 +141,25 @@ class AppFlowyBoard extends StatelessWidget {
} }
} }
class _AppFlolwyBoardContent extends StatefulWidget { class _AppFlowyBoardContent extends StatefulWidget {
final ScrollController? scrollController; final ScrollController? scrollController;
final OnDragStarted? onDragStarted; final OnDragStarted? onDragStarted;
final OnReorder onReorder; final OnReorder onReorder;
final OnDragEnded? onDragEnded; final OnDragEnded? onDragEnded;
final AppFlowyBoardDataController dataController; final AppFlowyBoardController dataController;
final Widget? background; final Widget? background;
final AppFlowyBoardConfig config; final AppFlowyBoardConfig config;
final ReorderFlexConfig reorderFlexConfig; final ReorderFlexConfig reorderFlexConfig;
final BoxConstraints columnConstraints; final BoxConstraints columnConstraints;
final AFBoardScrollManager? scrollManager; final AppFlowyBoardScrollManager? scrollManager;
final BoardGroupsState columnsState; final AppFlowyBoardState columnsState;
final AppFlowyBoardCardBuilder cardBuilder; final AppFlowyBoardCardBuilder cardBuilder;
final AppFlowyBoardHeaderBuilder? headerBuilder; final AppFlowyBoardHeaderBuilder? headerBuilder;
final AppFlowyBoardFooterBuilder? footerBuilder; final AppFlowyBoardFooterBuilder? footerBuilder;
final OverlapDragTargetDelegate delegate; final OverlapDragTargetDelegate delegate;
final BoardPhantomController phantomController; final BoardPhantomController phantomController;
const _AppFlolwyBoardContent({ const _AppFlowyBoardContent({
required this.config, required this.config,
required this.onReorder, required this.onReorder,
required this.delegate, required this.delegate,
@ -170,12 +180,12 @@ class _AppFlolwyBoardContent extends StatefulWidget {
super(key: key); super(key: key);
@override @override
State<_AppFlolwyBoardContent> createState() => _AppFlowyBoardContentState(); State<_AppFlowyBoardContent> createState() => _AppFlowyBoardContentState();
} }
class _AppFlowyBoardContentState extends State<_AppFlolwyBoardContent> { class _AppFlowyBoardContentState extends State<_AppFlowyBoardContent> {
final GlobalKey _boardContentKey = final GlobalKey _boardContentKey =
GlobalKey(debugLabel: '$_AppFlolwyBoardContent overlay key'); GlobalKey(debugLabel: '$_AppFlowyBoardContent overlay key');
late BoardOverlayEntry _overlayEntry; late BoardOverlayEntry _overlayEntry;
final Map<String, GlobalObjectKey> _reorderFlexKeys = {}; final Map<String, GlobalObjectKey> _reorderFlexKeys = {};
@ -253,7 +263,7 @@ class _AppFlowyBoardContentState extends State<_AppFlolwyBoardContent> {
return ChangeNotifierProvider.value( return ChangeNotifierProvider.value(
key: ValueKey(columnData.id), key: ValueKey(columnData.id),
value: widget.dataController.getGroupController(columnData.id), value: widget.dataController.getGroupController(columnData.id),
child: Consumer<AFBoardGroupDataController>( child: Consumer<AppFlowyGroupController>(
builder: (context, value, child) { builder: (context, value, child) {
final boardColumn = AppFlowyBoardGroup( final boardColumn = AppFlowyBoardGroup(
reorderFlexKey: reorderFlexKey, reorderFlexKey: reorderFlexKey,
@ -289,12 +299,12 @@ class _AppFlowyBoardContentState extends State<_AppFlolwyBoardContent> {
Widget? _buildHeader( Widget? _buildHeader(
BuildContext context, BuildContext context,
AppFlowyBoardGroupData groupData, AppFlowyGroupData groupData,
) { ) {
if (widget.headerBuilder == null) { if (widget.headerBuilder == null) {
return null; return null;
} }
return Selector<AFBoardGroupDataController, AppFlowyBoardGroupHeaderData>( return Selector<AppFlowyGroupController, AppFlowyGroupHeaderData>(
selector: (context, controller) => controller.groupData.headerData, selector: (context, controller) => controller.groupData.headerData,
builder: (context, headerData, _) { builder: (context, headerData, _) {
return widget.headerBuilder!(context, groupData)!; return widget.headerBuilder!(context, groupData)!;
@ -319,9 +329,9 @@ class _AppFlowyBoardContentState extends State<_AppFlolwyBoardContent> {
} }
} }
class _BoardGroupDataSourceImpl extends AppFlowyBoardGroupDataDataSource { class _BoardGroupDataSourceImpl extends AppFlowyGroupDataDataSource {
String groupId; String groupId;
final AppFlowyBoardDataController dataController; final AppFlowyBoardController dataController;
_BoardGroupDataSourceImpl({ _BoardGroupDataSourceImpl({
required this.groupId, required this.groupId,
@ -329,31 +339,34 @@ class _BoardGroupDataSourceImpl extends AppFlowyBoardGroupDataDataSource {
}); });
@override @override
AppFlowyBoardGroupData get groupData => AppFlowyGroupData get groupData =>
dataController.getGroupController(groupId)!.groupData; dataController.getGroupController(groupId)!.groupData;
@override @override
List<String> get acceptedGroupIds => dataController.groupIds; List<String> get acceptedGroupIds => dataController.groupIds;
} }
class BoardGroupContext { /// A context contains the group states including the draggingState.
GlobalKey? groupKey; ///
/// [draggingState] represents the dragging state of the group.
class AppFlowyGroupContext {
DraggingState? draggingState; DraggingState? draggingState;
} }
class BoardGroupsState extends DraggingStateStorage class AppFlowyBoardState extends DraggingStateStorage
with ReorderDragTargetIndexKeyStorage { with ReorderDragTargetIndexKeyStorage {
/// Quick access to the [AppFlowyBoardGroup] /// Quick access to the [AppFlowyBoardGroup], the [GlobalKey] is bind to the
final Map<String, GlobalKey> groupKeys = {}; /// AppFlowyBoardGroup's [ReorderFlex] widget.
final Map<String, GlobalKey> groupReorderFlexKeys = {};
final Map<String, DraggingState> groupDragStates = {}; final Map<String, DraggingState> groupDragStates = {};
final Map<String, Map<String, GlobalObjectKey>> groupDragDragTargets = {}; final Map<String, Map<String, GlobalObjectKey>> groupDragDragTargets = {};
void addGroup(String groupId, AppFlowyBoardGroup groupWidget) { void addGroup(String groupId, AppFlowyBoardGroup groupWidget) {
groupKeys[groupId] = groupWidget.reorderFlexKey; groupReorderFlexKeys[groupId] = groupWidget.reorderFlexKey;
} }
ReorderFlexState? getReorderFlexState({required String groupId}) { ReorderFlexState? getReorderFlexState({required String groupId}) {
final flexGlobalKey = groupKeys[groupId]; final flexGlobalKey = groupReorderFlexKeys[groupId];
if (flexGlobalKey == null) return null; if (flexGlobalKey == null) return null;
if (flexGlobalKey.currentState is! ReorderFlexState) return null; if (flexGlobalKey.currentState is! ReorderFlexState) return null;
final state = flexGlobalKey.currentState as ReorderFlexState; final state = flexGlobalKey.currentState as ReorderFlexState;
@ -361,7 +374,7 @@ class BoardGroupsState extends DraggingStateStorage
} }
ReorderFlex? getReorderFlex({required String groupId}) { ReorderFlex? getReorderFlex({required String groupId}) {
final flexGlobalKey = groupKeys[groupId]; final flexGlobalKey = groupReorderFlexKeys[groupId];
if (flexGlobalKey == null) return null; if (flexGlobalKey == null) return null;
if (flexGlobalKey.currentWidget is! ReorderFlex) return null; if (flexGlobalKey.currentWidget is! ReorderFlex) return null;
final widget = flexGlobalKey.currentWidget as ReorderFlex; final widget = flexGlobalKey.currentWidget as ReorderFlex;

View File

@ -1,9 +1,9 @@
import 'dart:collection'; import 'dart:collection';
import 'package:appflowy_board/src/widgets/board_group/group_data.dart';
import 'package:equatable/equatable.dart'; import 'package:equatable/equatable.dart';
import '../utils/log.dart'; import '../utils/log.dart';
import 'board_column/board_column_data.dart';
import 'reorder_flex/reorder_flex.dart'; import 'reorder_flex/reorder_flex.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'reorder_phantom/phantom_controller.dart'; import 'reorder_phantom/phantom_controller.dart';
@ -30,9 +30,9 @@ typedef OnMoveGroupItemToGroup = void Function(
/// A controller for [AppFlowyBoard] widget. /// A controller for [AppFlowyBoard] widget.
/// ///
/// A [AppFlowyBoardDataController] can be used to provide an initial value of /// A [AppFlowyBoardController] can be used to provide an initial value of
/// the board by calling [addGroup] method with the passed in parameter /// the board by calling `addGroup` method with the passed in parameter
/// [AppFlowyBoardGroupData]. A [AppFlowyBoardGroupData] represents one /// [AppFlowyGroupData]. A [AppFlowyGroupData] represents one
/// group data. Whenever the user modifies the board, this controller will /// group data. Whenever the user modifies the board, this controller will
/// update the corresponding group data. /// update the corresponding group data.
/// ///
@ -44,9 +44,9 @@ typedef OnMoveGroupItemToGroup = void Function(
/// ///
/// [onMoveGroupItemToGroup] will get called when moving the group's item from /// [onMoveGroupItemToGroup] will get called when moving the group's item from
/// one group to another group. /// one group to another group.
class AppFlowyBoardDataController extends ChangeNotifier class AppFlowyBoardController extends ChangeNotifier
with EquatableMixin, BoardPhantomControllerDelegate, ReoderFlexDataSource { with EquatableMixin, BoardPhantomControllerDelegate, ReoderFlexDataSource {
final List<AppFlowyBoardGroupData> _groupDatas = []; final List<AppFlowyGroupData> _groupDatas = [];
/// [onMoveGroup] will get called when moving the group from one position to /// [onMoveGroup] will get called when moving the group from one position to
/// another. /// another.
@ -59,18 +59,18 @@ class AppFlowyBoardDataController extends ChangeNotifier
/// one group to another group. /// one group to another group.
final OnMoveGroupItemToGroup? onMoveGroupItemToGroup; final OnMoveGroupItemToGroup? onMoveGroupItemToGroup;
/// Returns the unmodifiable list of [AppFlowyBoardGroupData] /// Returns the unmodifiable list of [AppFlowyGroupData]
UnmodifiableListView<AppFlowyBoardGroupData> get groupDatas => UnmodifiableListView<AppFlowyGroupData> get groupDatas =>
UnmodifiableListView(_groupDatas); UnmodifiableListView(_groupDatas);
/// Returns list of group id /// Returns list of group id
List<String> get groupIds => List<String> get groupIds =>
_groupDatas.map((groupData) => groupData.id).toList(); _groupDatas.map((groupData) => groupData.id).toList();
final LinkedHashMap<String, AFBoardGroupDataController> _groupControllers = final LinkedHashMap<String, AppFlowyGroupController> _groupControllers =
LinkedHashMap(); LinkedHashMap();
AppFlowyBoardDataController({ AppFlowyBoardController({
this.onMoveGroup, this.onMoveGroup,
this.onMoveGroupItem, this.onMoveGroupItem,
this.onMoveGroupItemToGroup, this.onMoveGroupItemToGroup,
@ -80,10 +80,10 @@ class AppFlowyBoardDataController extends ChangeNotifier
/// ///
/// If you don't want to notify the listener after adding a new group, the /// If you don't want to notify the listener after adding a new group, the
/// [notify] should set to false. Default value is true. /// [notify] should set to false. Default value is true.
void addGroup(AppFlowyBoardGroupData groupData, {bool notify = true}) { void addGroup(AppFlowyGroupData groupData, {bool notify = true}) {
if (_groupControllers[groupData.id] != null) return; if (_groupControllers[groupData.id] != null) return;
final controller = AFBoardGroupDataController(groupData: groupData); final controller = AppFlowyGroupController(groupData: groupData);
_groupDatas.add(groupData); _groupDatas.add(groupData);
_groupControllers[groupData.id] = controller; _groupControllers[groupData.id] = controller;
if (notify) notifyListeners(); if (notify) notifyListeners();
@ -93,7 +93,7 @@ class AppFlowyBoardDataController extends ChangeNotifier
/// ///
/// If you don't want to notify the listener after adding the groups, the /// If you don't want to notify the listener after adding the groups, the
/// [notify] should set to false. Default value is true. /// [notify] should set to false. Default value is true.
void addGroups(List<AppFlowyBoardGroupData> groups, {bool notify = true}) { void addGroups(List<AppFlowyGroupData> groups, {bool notify = true}) {
for (final column in groups) { for (final column in groups) {
addGroup(column, notify: false); addGroup(column, notify: false);
} }
@ -133,6 +133,7 @@ class AppFlowyBoardDataController extends ChangeNotifier
} }
/// Remove all the groups controller. /// Remove all the groups controller.
///
/// This method should get called when you want to remove all the current /// This method should get called when you want to remove all the current
/// groups or get ready to reinitialize the [AppFlowyBoard]. /// groups or get ready to reinitialize the [AppFlowyBoard].
void clear() { void clear() {
@ -141,8 +142,8 @@ class AppFlowyBoardDataController extends ChangeNotifier
notifyListeners(); notifyListeners();
} }
/// Returns the [AFBoardGroupDataController] with id [groupId]. /// Returns the [AppFlowyGroupController] with id [groupId].
AFBoardGroupDataController? getGroupController(String groupId) { AppFlowyGroupController? getGroupController(String groupId) {
final groupController = _groupControllers[groupId]; final groupController = _groupControllers[groupId];
if (groupController == null) { if (groupController == null) {
Log.warn('Group:[$groupId] \'s controller is not exist'); Log.warn('Group:[$groupId] \'s controller is not exist');
@ -174,30 +175,35 @@ class AppFlowyBoardDataController extends ChangeNotifier
} }
/// Adds the [AppFlowyGroupItem] to the end of the group /// Adds the [AppFlowyGroupItem] to the end of the group
///
/// If the group with id [groupId] is not exist, this method will do nothing. /// If the group with id [groupId] is not exist, this method will do nothing.
void addGroupItem(String groupId, AppFlowyGroupItem item) { void addGroupItem(String groupId, AppFlowyGroupItem item) {
getGroupController(groupId)?.add(item); getGroupController(groupId)?.add(item);
} }
/// Inserts the [AppFlowyGroupItem] at [index] in the group /// Inserts the [AppFlowyGroupItem] at [index] in the group
///
/// It will do nothing if the group with id [groupId] is not exist /// It will do nothing if the group with id [groupId] is not exist
void insertGroupItem(String groupId, int index, AppFlowyGroupItem item) { void insertGroupItem(String groupId, int index, AppFlowyGroupItem item) {
getGroupController(groupId)?.insert(index, item); getGroupController(groupId)?.insert(index, item);
} }
/// Removes the item with id [itemId] from the group /// Removes the item with id [itemId] from the group
///
/// It will do nothing if the group with id [groupId] is not exist /// It will do nothing if the group with id [groupId] is not exist
void removeGroupItem(String groupId, String itemId) { void removeGroupItem(String groupId, String itemId) {
getGroupController(groupId)?.removeWhere((item) => item.id == itemId); getGroupController(groupId)?.removeWhere((item) => item.id == itemId);
} }
/// Replaces or inserts the [AppFlowyGroupItem] to the end of the group. /// Replaces or inserts the [AppFlowyGroupItem] to the end of the group.
///
/// If the group with id [groupId] is not exist, this method will do nothing. /// If the group with id [groupId] is not exist, this method will do nothing.
void updateGroupItem(String groupId, AppFlowyGroupItem item) { void updateGroupItem(String groupId, AppFlowyGroupItem item) {
getGroupController(groupId)?.replaceOrInsertItem(item); getGroupController(groupId)?.replaceOrInsertItem(item);
} }
/// Swap the /// Moves the item at [fromGroupIndex] in group with id [fromGroupId] to
/// group with id [toGroupId] at [toGroupIndex]
@override @override
@protected @protected
void moveGroupItemToAnotherGroup( void moveGroupItemToAnotherGroup(
@ -228,12 +234,12 @@ class AppFlowyBoardDataController extends ChangeNotifier
} }
@override @override
AFBoardGroupDataController? controller(String groupId) { AppFlowyGroupController? controller(String groupId) {
return _groupControllers[groupId]; return _groupControllers[groupId];
} }
@override @override
String get identifier => '$AppFlowyBoardDataController'; String get identifier => '$AppFlowyBoardController';
@override @override
UnmodifiableListView<ReoderFlexItem> get items => UnmodifiableListView<ReoderFlexItem> get items =>
@ -253,7 +259,7 @@ class AppFlowyBoardDataController extends ChangeNotifier
groupController.removeAt(index); groupController.removeAt(index);
Log.debug( Log.debug(
'[$AppFlowyBoardDataController] Group:[$groupId] remove phantom, current count: ${groupController.items.length}'); '[$AppFlowyBoardController] Group:[$groupId] remove phantom, current count: ${groupController.items.length}');
} }
return isExist; return isExist;
} }

View File

@ -7,40 +7,40 @@ import '../../utils/log.dart';
import '../reorder_phantom/phantom_controller.dart'; import '../reorder_phantom/phantom_controller.dart';
import '../reorder_flex/reorder_flex.dart'; import '../reorder_flex/reorder_flex.dart';
import '../reorder_flex/drag_target_interceptor.dart'; import '../reorder_flex/drag_target_interceptor.dart';
import 'board_column_data.dart'; import 'group_data.dart';
typedef OnGroupDragStarted = void Function(int index); typedef OnGroupDragStarted = void Function(int index);
typedef OnGroupDragEnded = void Function(String listId); typedef OnGroupDragEnded = void Function(String groupId);
typedef OnGroupReorder = void Function( typedef OnGroupReorder = void Function(
String listId, String groupId,
int fromIndex, int fromIndex,
int toIndex, int toIndex,
); );
typedef OnGroupDeleted = void Function(String listId, int deletedIndex); typedef OnGroupDeleted = void Function(String groupId, int deletedIndex);
typedef OnGroupInserted = void Function(String listId, int insertedIndex); typedef OnGroupInserted = void Function(String groupId, int insertedIndex);
typedef AppFlowyBoardCardBuilder = Widget Function( typedef AppFlowyBoardCardBuilder = Widget Function(
BuildContext context, BuildContext context,
AppFlowyBoardGroupData groupData, AppFlowyGroupData groupData,
AppFlowyGroupItem item, AppFlowyGroupItem item,
); );
typedef AppFlowyBoardHeaderBuilder = Widget? Function( typedef AppFlowyBoardHeaderBuilder = Widget? Function(
BuildContext context, BuildContext context,
AppFlowyBoardGroupData groupData, AppFlowyGroupData groupData,
); );
typedef AppFlowyBoardFooterBuilder = Widget Function( typedef AppFlowyBoardFooterBuilder = Widget Function(
BuildContext context, BuildContext context,
AppFlowyBoardGroupData groupData, AppFlowyGroupData groupData,
); );
abstract class AppFlowyBoardGroupDataDataSource extends ReoderFlexDataSource { abstract class AppFlowyGroupDataDataSource extends ReoderFlexDataSource {
AppFlowyBoardGroupData get groupData; AppFlowyGroupData get groupData;
List<String> get acceptedGroupIds; List<String> get acceptedGroupIds;
@ -51,7 +51,7 @@ abstract class AppFlowyBoardGroupDataDataSource extends ReoderFlexDataSource {
UnmodifiableListView<AppFlowyGroupItem> get items => groupData.items; UnmodifiableListView<AppFlowyGroupItem> get items => groupData.items;
void debugPrint() { void debugPrint() {
String msg = '[$AppFlowyBoardGroupDataDataSource] $groupData data: '; String msg = '[$AppFlowyGroupDataDataSource] $groupData data: ';
for (var element in items) { for (var element in items) {
msg = '$msg$element,'; msg = '$msg$element,';
} }
@ -60,10 +60,10 @@ abstract class AppFlowyBoardGroupDataDataSource extends ReoderFlexDataSource {
} }
} }
/// [AppFlowyBoardGroup] represents the group of the Board. /// A [AppFlowyBoardGroup] represents the group UI of the Board.
/// ///
class AppFlowyBoardGroup extends StatefulWidget { class AppFlowyBoardGroup extends StatefulWidget {
final AppFlowyBoardGroupDataDataSource dataSource; final AppFlowyGroupDataDataSource dataSource;
final ScrollController? scrollController; final ScrollController? scrollController;
final ReorderFlexConfig config; final ReorderFlexConfig config;
final OnGroupDragStarted? onDragStarted; final OnGroupDragStarted? onDragStarted;

View File

@ -1,10 +1,13 @@
import 'dart:collection'; import 'dart:collection';
import 'package:appflowy_board/src/utils/log.dart';
import 'package:appflowy_board/src/widgets/reorder_flex/reorder_flex.dart';
import 'package:equatable/equatable.dart'; import 'package:equatable/equatable.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import '../../utils/log.dart';
import '../reorder_flex/reorder_flex.dart';
/// A item represents the generic data model of each group card.
///
/// Each item displayed in the group required to implement this class.
abstract class AppFlowyGroupItem extends ReoderFlexItem { abstract class AppFlowyGroupItem extends ReoderFlexItem {
bool get isPhantom => false; bool get isPhantom => false;
@ -12,7 +15,8 @@ abstract class AppFlowyGroupItem extends ReoderFlexItem {
String toString() => id; String toString() => id;
} }
/// [AFBoardGroupDataController] is used to handle the [AppFlowyBoardGroupData]. /// [AppFlowyGroupController] is used to handle the [AppFlowyGroupData].
///
/// * Remove an item by calling [removeAt] method. /// * Remove an item by calling [removeAt] method.
/// * Move item to another position by calling [move] method. /// * Move item to another position by calling [move] method.
/// * Insert item to index by calling [insert] method /// * Insert item to index by calling [insert] method
@ -20,10 +24,10 @@ abstract class AppFlowyGroupItem extends ReoderFlexItem {
/// ///
/// All there operations will notify listeners by default. /// All there operations will notify listeners by default.
/// ///
class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin { class AppFlowyGroupController extends ChangeNotifier with EquatableMixin {
final AppFlowyBoardGroupData groupData; final AppFlowyGroupData groupData;
AFBoardGroupDataController({ AppFlowyGroupController({
required this.groupData, required this.groupData,
}); });
@ -44,12 +48,12 @@ class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin {
/// Remove the item at [index]. /// Remove the item at [index].
/// * [index] the index of the item you want to remove /// * [index] the index of the item you want to remove
/// * [notify] the default value of [notify] is true, it will notify the /// * [notify] the default value of [notify] is true, it will notify the
/// listener. Set to [false] if you do not want to notify the listeners. /// listener. Set to false if you do not want to notify the listeners.
/// ///
AppFlowyGroupItem removeAt(int index, {bool notify = true}) { AppFlowyGroupItem removeAt(int index, {bool notify = true}) {
assert(index >= 0); assert(index >= 0);
Log.debug('[$AFBoardGroupDataController] $groupData remove item at $index'); Log.debug('[$AppFlowyGroupController] $groupData remove item at $index');
final item = groupData._items.removeAt(index); final item = groupData._items.removeAt(index);
if (notify) { if (notify) {
notifyListeners(); notifyListeners();
@ -74,7 +78,7 @@ class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin {
return false; return false;
} }
Log.debug( Log.debug(
'[$AFBoardGroupDataController] $groupData move item from $fromIndex to $toIndex'); '[$AppFlowyGroupController] $groupData move item from $fromIndex to $toIndex');
final item = groupData._items.removeAt(fromIndex); final item = groupData._items.removeAt(fromIndex);
groupData._items.insert(toIndex, item); groupData._items.insert(toIndex, item);
notifyListeners(); notifyListeners();
@ -87,8 +91,7 @@ class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin {
/// The default value of [notify] is true. /// The default value of [notify] is true.
bool insert(int index, AppFlowyGroupItem item, {bool notify = true}) { bool insert(int index, AppFlowyGroupItem item, {bool notify = true}) {
assert(index >= 0); assert(index >= 0);
Log.debug( Log.debug('[$AppFlowyGroupController] $groupData insert $item at $index');
'[$AFBoardGroupDataController] $groupData insert $item at $index');
if (_containsItem(item)) { if (_containsItem(item)) {
return false; return false;
@ -118,7 +121,7 @@ class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin {
void replace(int index, AppFlowyGroupItem newItem) { void replace(int index, AppFlowyGroupItem newItem) {
if (groupData._items.isEmpty) { if (groupData._items.isEmpty) {
groupData._items.add(newItem); groupData._items.add(newItem);
Log.debug('[$AFBoardGroupDataController] $groupData add $newItem'); Log.debug('[$AppFlowyGroupController] $groupData add $newItem');
} else { } else {
if (index >= groupData._items.length) { if (index >= groupData._items.length) {
return; return;
@ -127,7 +130,7 @@ class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin {
final removedItem = groupData._items.removeAt(index); final removedItem = groupData._items.removeAt(index);
groupData._items.insert(index, newItem); groupData._items.insert(index, newItem);
Log.debug( Log.debug(
'[$AFBoardGroupDataController] $groupData replace $removedItem with $newItem at $index'); '[$AppFlowyGroupController] $groupData replace $removedItem with $newItem at $index');
} }
notifyListeners(); notifyListeners();
@ -151,22 +154,21 @@ class AFBoardGroupDataController extends ChangeNotifier with EquatableMixin {
} }
} }
/// [AppFlowyBoardGroupData] represents the data of each group of the Board. /// [AppFlowyGroupData] represents the data of each group of the Board.
class AppFlowyBoardGroupData<CustomData> extends ReoderFlexItem class AppFlowyGroupData<CustomData> extends ReoderFlexItem with EquatableMixin {
with EquatableMixin {
@override @override
final String id; final String id;
AppFlowyBoardGroupHeaderData headerData; AppFlowyGroupHeaderData headerData;
final List<AppFlowyGroupItem> _items; final List<AppFlowyGroupItem> _items;
final CustomData? customData; final CustomData? customData;
AppFlowyBoardGroupData({ AppFlowyGroupData({
this.customData, this.customData,
required this.id, required this.id,
required String name, required String name,
List<AppFlowyGroupItem> items = const [], List<AppFlowyGroupItem> items = const [],
}) : _items = items, }) : _items = items,
headerData = AppFlowyBoardGroupHeaderData( headerData = AppFlowyGroupHeaderData(
groupId: id, groupId: id,
groupName: name, groupName: name,
); );
@ -184,10 +186,9 @@ class AppFlowyBoardGroupData<CustomData> extends ReoderFlexItem
} }
} }
class AppFlowyBoardGroupHeaderData { class AppFlowyGroupHeaderData {
String groupId; String groupId;
String groupName; String groupName;
AppFlowyBoardGroupHeaderData( AppFlowyGroupHeaderData({required this.groupId, required this.groupName});
{required this.groupId, required this.groupName});
} }

View File

@ -55,7 +55,7 @@ class OverlappingDragTargetInterceptor extends DragTargetInterceptor {
final String reorderFlexId; final String reorderFlexId;
final List<String> acceptedReorderFlexId; final List<String> acceptedReorderFlexId;
final OverlapDragTargetDelegate delegate; final OverlapDragTargetDelegate delegate;
final BoardGroupsState columnsState; final AppFlowyBoardState columnsState;
Timer? _delayOperation; Timer? _delayOperation;
OverlappingDragTargetInterceptor({ OverlappingDragTargetInterceptor({

View File

@ -8,14 +8,14 @@ import '../reorder_flex/drag_target_interceptor.dart';
import 'phantom_state.dart'; import 'phantom_state.dart';
abstract class BoardPhantomControllerDelegate { abstract class BoardPhantomControllerDelegate {
AFBoardGroupDataController? controller(String groupId); AppFlowyGroupController? controller(String groupId);
bool removePhantom(String groupId); bool removePhantom(String groupId);
/// Insert the phantom into the group /// Insert the phantom into the group
/// ///
/// * [groupId] id of the group /// * [groupId] id of the group
/// * [phantomIndex] the phantom occupies index /// * [index] the phantom occupies index
void insertPhantom( void insertPhantom(
String groupId, String groupId,
int index, int index,
@ -24,7 +24,7 @@ abstract class BoardPhantomControllerDelegate {
/// Update the group's phantom index if it exists. /// Update the group's phantom index if it exists.
/// [toGroupId] the id of the group /// [toGroupId] the id of the group
/// [dragTargetIndex] the index of the dragTarget /// [newIndex] the index of the dragTarget
void updatePhantom(String groupId, int newIndex); void updatePhantom(String groupId, int newIndex);
void moveGroupItemToAnotherGroup( void moveGroupItemToAnotherGroup(
@ -39,7 +39,7 @@ class BoardPhantomController extends OverlapDragTargetDelegate
with CrossReorderFlexDragTargetDelegate { with CrossReorderFlexDragTargetDelegate {
PhantomRecord? phantomRecord; PhantomRecord? phantomRecord;
final BoardPhantomControllerDelegate delegate; final BoardPhantomControllerDelegate delegate;
final BoardGroupsState groupsState; final AppFlowyBoardState groupsState;
final phantomState = GroupPhantomState(); final phantomState = GroupPhantomState();
BoardPhantomController({ BoardPhantomController({
required this.delegate, required this.delegate,

View File

@ -1,12 +1,12 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
class AppFlowyGroupItemCard extends StatefulWidget { class AppFlowyGroupCard extends StatefulWidget {
final Widget? child; final Widget? child;
final EdgeInsets margin; final EdgeInsets margin;
final BoxConstraints boxConstraints; final BoxConstraints boxConstraints;
final BoxDecoration decoration; final BoxDecoration decoration;
const AppFlowyGroupItemCard({ const AppFlowyGroupCard({
this.child, this.child,
this.margin = const EdgeInsets.all(4), this.margin = const EdgeInsets.all(4),
this.decoration = const BoxDecoration( this.decoration = const BoxDecoration(
@ -18,10 +18,10 @@ class AppFlowyGroupItemCard extends StatefulWidget {
}) : super(key: key); }) : super(key: key);
@override @override
State<AppFlowyGroupItemCard> createState() => _AppFlowyGroupItemCardState(); State<AppFlowyGroupCard> createState() => _AppFlowyGroupCardState();
} }
class _AppFlowyGroupItemCardState extends State<AppFlowyGroupItemCard> { class _AppFlowyGroupCardState extends State<AppFlowyGroupCard> {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return Padding( return Padding(

View File

@ -1,5 +1,4 @@
import 'package:flutter/widgets.dart'; import 'package:flutter/widgets.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/rendering.dart'; import 'package:flutter/rendering.dart';
class SizeTransitionWithIntrinsicSize extends SingleChildRenderObjectWidget { class SizeTransitionWithIntrinsicSize extends SingleChildRenderObjectWidget {

View File

@ -1,5 +1,5 @@
name: appflowy_board name: appflowy_board
description: AppFlowy board implementation. description: AppFlowyBoard is a board-style widget that consists of multi-groups. It supports drag and drop between different groups.
version: 0.0.6 version: 0.0.6
homepage: https://github.com/AppFlowy-IO/AppFlowy homepage: https://github.com/AppFlowy-IO/AppFlowy
repository: https://github.com/AppFlowy-IO/AppFlowy/tree/main/frontend/app_flowy/packages/appflowy_board repository: https://github.com/AppFlowy-IO/AppFlowy/tree/main/frontend/app_flowy/packages/appflowy_board