10
10
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .DEFAULT_DART_ENTRYPOINT ;
11
11
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .DEFAULT_INITIAL_ROUTE ;
12
12
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_BACKGROUND_MODE ;
13
+ import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_CACHED_ENGINE_GROUP_ID ;
13
14
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_CACHED_ENGINE_ID ;
15
+ import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_DART_ENTRYPOINT ;
14
16
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_DART_ENTRYPOINT_ARGS ;
15
17
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_DESTROY_ENGINE_WITH_ACTIVITY ;
16
18
import static io .flutter .embedding .android .FlutterActivityLaunchConfigs .EXTRA_ENABLE_STATE_RESTORATION ;
@@ -276,7 +278,7 @@ public NewEngineIntentBuilder(@NonNull Class<? extends FlutterActivity> activity
276
278
}
277
279
278
280
/**
279
- * The initial route that a Flutter app will render in this {@link FlutterFragment }, defaults to
281
+ * The initial route that a Flutter app will render in this {@link FlutterActivity }, defaults to
280
282
* "/".
281
283
*
282
284
* @param initialRoute The route.
@@ -448,6 +450,149 @@ public Intent build(@NonNull Context context) {
448
450
}
449
451
}
450
452
453
+ /**
454
+ * Creates a {@link NewEngineInGroupIntentBuilder}, which can be used to configure an {@link
455
+ * Intent} to launch a {@code FlutterActivity} by internally creating a FlutterEngine from an
456
+ * existing {@link io.flutter.embedding.engine.FlutterEngineGroup} cached in a specified {@link
457
+ * io.flutter.embedding.engine.FlutterEngineGroupCache}.
458
+ *
459
+ * <pre>{@code
460
+ * // Create a FlutterEngineGroup, such as in the onCreate method of the Application.
461
+ * FlutterEngineGroup engineGroup = new FlutterEngineGroup(this);
462
+ * FlutterEngineGroupCache.getInstance().put("my_cached_engine_group_id", engineGroup);
463
+ *
464
+ * // Start a FlutterActivity with the FlutterEngineGroup by creating an intent with withNewEngineInGroup
465
+ * Intent intent = FlutterActivity.withNewEngineInGroup("my_cached_engine_group_id")
466
+ * .dartEntrypoint("custom_entrypoint")
467
+ * .initialRoute("/custom/route")
468
+ * .backgroundMode(BackgroundMode.transparent)
469
+ * .build(context);
470
+ * startActivity(intent);
471
+ * }</pre>
472
+ *
473
+ * @param engineGroupId A cached engine group ID.
474
+ * @return The builder.
475
+ */
476
+ public static NewEngineInGroupIntentBuilder withNewEngineInGroup (@ NonNull String engineGroupId ) {
477
+ return new NewEngineInGroupIntentBuilder (FlutterActivity .class , engineGroupId );
478
+ }
479
+
480
+ /**
481
+ * Builder to create an {@code Intent} that launches a {@code FlutterActivity} with a new {@link
482
+ * FlutterEngine} created by FlutterEngineGroup#createAndRunEngine.
483
+ */
484
+ public static class NewEngineInGroupIntentBuilder {
485
+ private final Class <? extends FlutterActivity > activityClass ;
486
+ private final String cachedEngineGroupId ;
487
+ private String dartEntrypoint = DEFAULT_DART_ENTRYPOINT ;
488
+ private String initialRoute = DEFAULT_INITIAL_ROUTE ;
489
+ private String backgroundMode = DEFAULT_BACKGROUND_MODE ;
490
+
491
+ /**
492
+ * Constructor that allows this {@code NewEngineInGroupIntentBuilder} to be used by subclasses
493
+ * of {@code FlutterActivity}.
494
+ *
495
+ * <p>Subclasses of {@code FlutterActivity} should provide their own static version of {@link
496
+ * #withNewEngineInGroup}, which returns an instance of {@code NewEngineInGroupIntentBuilder}
497
+ * constructed with a {@code Class} reference to the {@code FlutterActivity} subclass, e.g.:
498
+ *
499
+ * <p>{@code return new NewEngineInGroupIntentBuilder(MyFlutterActivity.class,
500
+ * cacheedEngineGroupId); }
501
+ *
502
+ * <pre>{@code
503
+ * // Create a FlutterEngineGroup, such as in the onCreate method of the Application.
504
+ * FlutterEngineGroup engineGroup = new FlutterEngineGroup(this);
505
+ * FlutterEngineGroupCache.getInstance().put("my_cached_engine_group_id", engineGroup);
506
+ *
507
+ * // Create a NewEngineInGroupIntentBuilder that would build an intent to start my custom FlutterActivity subclass.
508
+ * FlutterActivity.NewEngineInGroupIntentBuilder intentBuilder =
509
+ * new FlutterActivity.NewEngineInGroupIntentBuilder(
510
+ * MyFlutterActivity.class,
511
+ * app.engineGroupId);
512
+ * intentBuilder.dartEntrypoint("main")
513
+ * .initialRoute("/custom/route")
514
+ * .backgroundMode(BackgroundMode.transparent);
515
+ * startActivity(intentBuilder.build(context));
516
+ * }</pre>
517
+ *
518
+ * @param activityClass A subclass of {@code FlutterActivity}.
519
+ * @param engineGroupId The engine group id.
520
+ */
521
+ public NewEngineInGroupIntentBuilder (
522
+ @ NonNull Class <? extends FlutterActivity > activityClass , @ NonNull String engineGroupId ) {
523
+ this .activityClass = activityClass ;
524
+ this .cachedEngineGroupId = engineGroupId ;
525
+ }
526
+
527
+ /**
528
+ * The Dart entrypoint that will be executed in the newly created FlutterEngine as soon as the
529
+ * Dart snapshot is loaded. Default to "main".
530
+ *
531
+ * @param dartEntrypoint The dart entrypoint's name
532
+ * @return The engine group intent builder
533
+ */
534
+ @ NonNull
535
+ public NewEngineInGroupIntentBuilder dartEntrypoint (@ NonNull String dartEntrypoint ) {
536
+ this .dartEntrypoint = dartEntrypoint ;
537
+ return this ;
538
+ }
539
+
540
+ /**
541
+ * The initial route that a Flutter app will render in this {@link FlutterActivity}, defaults to
542
+ * "/".
543
+ *
544
+ * @param initialRoute The route.
545
+ * @return The engine group intent builder.
546
+ */
547
+ @ NonNull
548
+ public NewEngineInGroupIntentBuilder initialRoute (@ NonNull String initialRoute ) {
549
+ this .initialRoute = initialRoute ;
550
+ return this ;
551
+ }
552
+
553
+ /**
554
+ * The mode of {@code FlutterActivity}'s background, either {@link BackgroundMode#opaque} or
555
+ * {@link BackgroundMode#transparent}.
556
+ *
557
+ * <p>The default background mode is {@link BackgroundMode#opaque}.
558
+ *
559
+ * <p>Choosing a background mode of {@link BackgroundMode#transparent} will configure the inner
560
+ * {@link FlutterView} of this {@code FlutterActivity} to be configured with a {@link
561
+ * FlutterTextureView} to support transparency. This choice has a non-trivial performance
562
+ * impact. A transparent background should only be used if it is necessary for the app design
563
+ * being implemented.
564
+ *
565
+ * <p>A {@code FlutterActivity} that is configured with a background mode of {@link
566
+ * BackgroundMode#transparent} must have a theme applied to it that includes the following
567
+ * property: {@code <item name="android:windowIsTranslucent">true</item>}.
568
+ *
569
+ * @param backgroundMode The background mode.
570
+ * @return The engine group intent builder.
571
+ */
572
+ @ NonNull
573
+ public NewEngineInGroupIntentBuilder backgroundMode (@ NonNull BackgroundMode backgroundMode ) {
574
+ this .backgroundMode = backgroundMode .name ();
575
+ return this ;
576
+ }
577
+
578
+ /**
579
+ * Creates and returns an {@link Intent} that will launch a {@code FlutterActivity} with the
580
+ * desired configuration.
581
+ *
582
+ * @param context The context. e.g. An Activity.
583
+ * @return The intent.
584
+ */
585
+ @ NonNull
586
+ public Intent build (@ NonNull Context context ) {
587
+ return new Intent (context , activityClass )
588
+ .putExtra (EXTRA_DART_ENTRYPOINT , dartEntrypoint )
589
+ .putExtra (EXTRA_INITIAL_ROUTE , initialRoute )
590
+ .putExtra (EXTRA_CACHED_ENGINE_GROUP_ID , cachedEngineGroupId )
591
+ .putExtra (EXTRA_BACKGROUND_MODE , backgroundMode )
592
+ .putExtra (EXTRA_DESTROY_ENGINE_WITH_ACTIVITY , true );
593
+ }
594
+ }
595
+
451
596
// Delegate that runs all lifecycle and OS hook logic that is common between
452
597
// FlutterActivity and FlutterFragment. See the FlutterActivityAndFragmentDelegate
453
598
// implementation for details about why it exists.
@@ -866,6 +1011,17 @@ public String getCachedEngineId() {
866
1011
return getIntent ().getStringExtra (EXTRA_CACHED_ENGINE_ID );
867
1012
}
868
1013
1014
+ /**
1015
+ * Returns the ID of a statically cached {@link io.flutter.embedding.engine.FlutterEngineGroup} to
1016
+ * use within this {@code FlutterActivity}, or {@code null} if this {@code FlutterActivity} does
1017
+ * not want to use a cached {@link io.flutter.embedding.engine.FlutterEngineGroup}.
1018
+ */
1019
+ @ Override
1020
+ @ Nullable
1021
+ public String getCachedEngineGroupId () {
1022
+ return getIntent ().getStringExtra (EXTRA_CACHED_ENGINE_GROUP_ID );
1023
+ }
1024
+
869
1025
/**
870
1026
* Returns false if the {@link io.flutter.embedding.engine.FlutterEngine} backing this {@code
871
1027
* FlutterActivity} should outlive this {@code FlutterActivity}, or true to be destroyed when the
@@ -892,14 +1048,26 @@ public boolean shouldDestroyEngineWithHost() {
892
1048
/**
893
1049
* The Dart entrypoint that will be executed as soon as the Dart snapshot is loaded.
894
1050
*
895
- * <p>This preference can be controlled by setting a {@code <meta-data>} called {@link
896
- * FlutterActivityLaunchConfigs#DART_ENTRYPOINT_META_DATA_KEY} within the Android manifest
897
- * definition for this {@code FlutterActivity}.
1051
+ * <p>This preference can be controlled with 2 methods:
1052
+ *
1053
+ * <ol>
1054
+ * <li>Pass a boolean as {@link FlutterActivityLaunchConfigs#EXTRA_DART_ENTRYPOINT} with the
1055
+ * launching {@code Intent}, or
1056
+ * <li>Set a {@code <meta-data>} called {@link
1057
+ * FlutterActivityLaunchConfigs#DART_ENTRYPOINT_META_DATA_KEY} within the Android manifest
1058
+ * definition for this {@code FlutterActivity}
1059
+ * </ol>
1060
+ *
1061
+ * If both preferences are set, the {@code Intent} preference takes priority.
898
1062
*
899
1063
* <p>Subclasses may override this method to directly control the Dart entrypoint.
900
1064
*/
901
1065
@ NonNull
902
1066
public String getDartEntrypointFunctionName () {
1067
+ if (getIntent ().hasExtra (EXTRA_DART_ENTRYPOINT )) {
1068
+ return getIntent ().getStringExtra (EXTRA_DART_ENTRYPOINT );
1069
+ }
1070
+
903
1071
try {
904
1072
Bundle metaData = getMetaData ();
905
1073
String desiredDartEntrypoint =
0 commit comments