Skip to content

Commit a179f01

Browse files
committed
feat: add insertModeFactory
1 parent 8b92174 commit a179f01

File tree

3 files changed

+57
-4
lines changed

3 files changed

+57
-4
lines changed

packages/dogs_core/lib/src/engine.dart

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -372,13 +372,37 @@ class DogEngine with MetadataMixin {
372372
}
373373

374374
/// Registers a [OperationModeFactory] in this [DogEngine] instance and emits
375-
/// a event to the change stream if [emitChangeToStream] is true.
375+
/// a event to the change stream if [emitChangeToStream] is true. This
376+
/// will override any previously registered factory for the given
377+
/// [type] or the [factory]'s type argument.
376378
void registerModeFactory(OperationModeFactory factory,
377379
{bool emitChangeToStream = true, Type? type}) {
378380
_modeFactories[type ?? factory.typeArgument] = factory;
379381
if (emitChangeToStream) populateChange();
380382
}
381383

384+
/// Modifies the associated [OperationModeFactory] to insert the given
385+
/// [factory] at the given [slot]. If no factory is registered for the given
386+
/// [type] or the [factory]'s type argument, the [factory] will be registered
387+
/// as new factory. If [emitChangeToStream] is true, a change event will be
388+
/// emitted to the change stream.
389+
void insertModeFactory(OperationModeFactory factory,
390+
{bool emitChangeToStream = true,
391+
Type? type,
392+
ModeFactoryInsertionSlot slot = ModeFactoryInsertionSlot.first}) {
393+
final arg = type ?? factory.typeArgument;
394+
final currentFactory = _modeFactories[arg];
395+
if (currentFactory == null) {
396+
_modeFactories[arg] = factory;
397+
if (emitChangeToStream) populateChange();
398+
return;
399+
}
400+
401+
final modified = currentFactory.insert(factory, slot);
402+
_modeFactories[arg] = modified;
403+
if (emitChangeToStream) populateChange();
404+
}
405+
382406
/// Registers multiple converters using [registerAutomatic].
383407
/// For more details see [DogEngine.registerAutomatic].
384408
void registerAllConverters(Iterable<DogConverter> converters) {

packages/dogs_core/lib/src/opmodes/factory.dart

Lines changed: 31 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,8 +39,28 @@ abstract class OperationModeFactory<T extends OperationMode>
3939

4040
/// A [OperationModeFactory] that composes multiple other factories.
4141
static OperationModeFactory<T> compose<T extends OperationMode>(
42-
List<OperationModeFactory> factories) =>
43-
ComposableOperationModeFactory<T>(factories);
42+
List<OperationModeFactory> factories) {
43+
final flattened = <OperationModeFactory>[];
44+
for (var factory in factories) {
45+
if (factory is ComposableOperationModeFactory<T>) {
46+
flattened.addAll(factory._factories);
47+
} else {
48+
flattened.add(factory);
49+
}
50+
}
51+
return ComposableOperationModeFactory<T>(flattened);
52+
}
53+
54+
/// Composes this factory with another [insertion] factory, placing [insertion] in the specified [slot].
55+
OperationModeFactory<T> insert(
56+
OperationModeFactory<T> insertion,
57+
ModeFactoryInsertionSlot slot,
58+
) =>
59+
compose<T>([
60+
if (slot == ModeFactoryInsertionSlot.first) insertion,
61+
this,
62+
if (slot == ModeFactoryInsertionSlot.last) insertion,
63+
]);
4464
}
4565

4666
/// A [OperationModeFactory] that returns a single [OperationMode] for a [DogConverter] of [schema].
@@ -102,3 +122,12 @@ class ComposableOperationModeFactory<T extends OperationMode>
102122
return null;
103123
}
104124
}
125+
126+
/// Specifies where to insert a [OperationModeFactory] when composing with another factory.
127+
enum ModeFactoryInsertionSlot {
128+
/// Insert the factory at the beginning of the composition.
129+
first,
130+
131+
/// Insert the factory at the end of the composition.
132+
last
133+
}

packages/dogs_flutter/lib/dogs_flutter.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ DogPlugin DogsFlutterPlugin({
6969
...?binders,
7070
defaultFactories,
7171
]);
72-
engine.registerModeFactory(modeFactory, type: FlutterWidgetBinder);
72+
engine.insertModeFactory(modeFactory, type: FlutterWidgetBinder, slot: ModeFactoryInsertionSlot.last);
7373

7474
if (addSchemaContributors) {
7575
DogsMaterializer.get(

0 commit comments

Comments
 (0)