-
Notifications
You must be signed in to change notification settings - Fork 28.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[windows/linux] add ability to enable Impeller on windows and linux desktop. #162684
base: master
Are you sure you want to change the base?
[windows/linux] add ability to enable Impeller on windows and linux desktop. #162684
Conversation
…eller_to_embedder_desktop
…jonahwilliams/flutter into add_enable_impeller_to_embedder_desktop
/// | ||
/// When not provided, this value is treated as false. In a future release, | ||
/// this setting will become a no-op when the Skia backend is fully removed. | ||
bool enable_impeller; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see that in flutter/engine#42639 (comment) this was rejected; I didn't realize that when I proposed it.
I had also forgotten that command_line_argv
is explicitly set up to control things like this in embedder.h, and that for the desktop embedders we explicitly disconnected actual command line arguments from what embedder.h
unfortunately calls command line arguments.
Runtime command line arguments passed to a desktop app are actually piped through dart_entrypoint_arg*
, which becomes the command line arguments that would be seen by Dart main
. What the engine (unfortunately, but we can't change it without breaking the world) calls command_line_arg*
is actually "engine flags", not anything related to what any Flutter dev would think of as command line arguments.
So I led you astray. Having paged all of this back in, we shouldn't need to change embedder.h at all, instead we can have the embedders turn whatever higher-level API we add into engine switches, which they are already set up to do. Going a step further, if we don't want to expose future-dead things in the embedding structs, we could instead expose the actual switches system, and have people use that along with the magic string. It looks like Windows already has SetString
, so we would just have to expose that in the C++ wrapper. For Linux it looks like we haven't plumber switches up to that level, but we could, and it would avoid the same issue (just one level up) raised in the earlier embedder.h review that we don't want to permanently have explicit APIs for something that will become meaningless.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Stuart's suggestion is excellent, but I'm not sure that avoiding future-dead things in the embedding structs is currently worth the effort for Windows/Linux. I'd personally rather we spend our time on iOS/Android/web improvements. I'd be OK with having a no-op setting on Windows.
That said, +1 for avoiding a future-dead embedder API if possible.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure that avoiding future-dead things in the embedding structs is currently worth the effort for Windows/Linux
If we plumb through the ability to set arbitrary engine flags, it won't be future-dead, it'll be available for whatever the next experimental engine features are.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure that avoiding future-dead things in the embedding structs is currently worth the effort for Windows/Linux
If we plumb through the ability to set arbitrary engine flags, it won't be future-dead, it'll be available for whatever the next experimental engine features are.
Right. By "future-dead things in the embedding structs", I was referring to set_enable_impeller
and get_enable_impeller
- I'd be OK adding those future-dead APIs if that's easier for Jonah.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I somehow read "avoiding" as "adding" in the first sentence, which is why my comment doesn't make sense :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've updated this PR so that there is no change in embedder API, instead --enable-impeller is passed via embedder switches.
@@ -601,9 +601,10 @@ - (BOOL)runWithEntrypoint:(NSString*)entrypoint { | |||
std::vector<std::string> switches = self.switches; | |||
|
|||
// Enable Impeller only if specifically asked for from the project or cmdline arguments. | |||
bool enable_impeller = false; | |||
if (_project.enableImpeller || | |||
std::find(switches.begin(), switches.end(), "--enable-impeller=true") != switches.end()) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Out of scope to fix in this specific PR, but this seems like a pretty bad idea to me. Capturing from my comments in the Discord discussion about this PR, I don't think we want to allow end users of Flutter-built software to change the rendering engine. That seems like a decision that should be up to the developer, at the time they build their app, just as it is (IIUC) on Android and iOS.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In fact, we explicitly say not to do this in embedder.h.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I removed this code but even on iOS/Andorid, embedder switches is how we've handled the opt in.
engine/src/flutter/shell/platform/linux/public/flutter_linux/fl_dart_project.h
Outdated
Show resolved
Hide resolved
The Linux changes look good; no opinion on the correct structure for this feature, I'll leave that to the other reviewers. |
…eller_to_embedder_desktop
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks!
void set_enable_impeller(bool value) { enable_impeller_ = value; } | ||
|
||
// Whether the Impeller rendering engine is enabled. | ||
bool get_enable_impeller() const { return enable_impeller_; } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should just be called enable_impeller
; it's more idiomatic for Google C++ style, and it's consistent with the other APIs in this class.
@@ -70,6 +70,9 @@ class FlutterProjectBundle { | |||
return dart_entrypoint_arguments_; | |||
} | |||
|
|||
// Whether the Impeller rendering engine is enabled. | |||
bool ImpellerEnabled() const { return impeller_enabled_; } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
impeller_enabled()
since it's a trivial getter.
…jonahwilliams/flutter into add_enable_impeller_to_embedder_desktop
const bool has_impeller_flag = | ||
std::find_if( | ||
switches.begin(), switches.end(), [](std::string_view value) { | ||
return value.rfind("--enable-impeller=", 0) != std::string::npos; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why rfind
instead of find
for a substring that should be at the start of the string?
// become a no-op when the Skia backend is fully removed. | ||
void set_enable_impeller(bool value) { enable_impeller_ = value; } | ||
|
||
// Whether the Impeller rendering engine is enabled. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think the flag-override behavior—and, importantly, the fact that this getter will not work correctly when there is a runtime flag—needs to be documented on these methods.
const bool has_impeller_flag = | ||
std::find_if( | ||
switches.begin(), switches.end(), [](std::string_view value) { | ||
return value.rfind("--enable-impeller=", 0) != std::string::npos; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same question here about rfind
.
@@ -70,6 +70,9 @@ class FlutterProjectBundle { | |||
return dart_entrypoint_arguments_; | |||
} | |||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where is the setter?
@@ -70,6 +70,9 @@ class FlutterProjectBundle { | |||
return dart_entrypoint_arguments_; | |||
} | |||
|
|||
// Whether the Impeller rendering engine is enabled. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same comment on this comment; this file should explain the interaction with the runtime flag.
Currently the --enable-impeller runtime flag works but there is no compile time option for desktop. This adds a flag that can be enabled via modifying the project source.
For Linux:
For windows: