Unverified Commit be2e7bb1 authored by Dan Field's avatar Dan Field Committed by GitHub

Revert "Revert "Allow any iOS app to be added to an existing host app (#70647)" (#70739)" (#70740)

This reverts commit aab9a76e.
parent aab9a76e
...@@ -113,7 +113,7 @@ class BuildIOSFrameworkCommand extends BuildSubCommand { ...@@ -113,7 +113,7 @@ class BuildIOSFrameworkCommand extends BuildSubCommand {
final String name = 'ios-framework'; final String name = 'ios-framework';
@override @override
final String description = 'Produces a .framework directory for a Flutter module ' final String description = 'Produces .frameworks for a Flutter project '
'and its plugins for integration into existing, plain Xcode projects.\n' 'and its plugins for integration into existing, plain Xcode projects.\n'
'This can only be run on macOS hosts.'; 'This can only be run on macOS hosts.';
...@@ -144,10 +144,6 @@ class BuildIOSFrameworkCommand extends BuildSubCommand { ...@@ -144,10 +144,6 @@ class BuildIOSFrameworkCommand extends BuildSubCommand {
Future<void> validateCommand() async { Future<void> validateCommand() async {
await super.validateCommand(); await super.validateCommand();
_project = FlutterProject.current(); _project = FlutterProject.current();
if (!_project.isModule) {
throwToolExit('Building frameworks for iOS is only supported from a module.');
}
if (!_platform.isMacOS) { if (!_platform.isMacOS) {
throwToolExit('Building frameworks for iOS is only supported on the Mac.'); throwToolExit('Building frameworks for iOS is only supported on the Mac.');
} }
...@@ -178,7 +174,7 @@ class BuildIOSFrameworkCommand extends BuildSubCommand { ...@@ -178,7 +174,7 @@ class BuildIOSFrameworkCommand extends BuildSubCommand {
} }
if (!_project.ios.existsSync()) { if (!_project.ios.existsSync()) {
throwToolExit('Module does not support iOS'); throwToolExit('Project does not support iOS');
} }
final Directory outputDirectory = globals.fs.directory(globals.fs.path.absolute(globals.fs.path.normalize(outputArgument))); final Directory outputDirectory = globals.fs.directory(globals.fs.path.absolute(globals.fs.path.normalize(outputArgument)));
...@@ -233,6 +229,23 @@ class BuildIOSFrameworkCommand extends BuildSubCommand { ...@@ -233,6 +229,23 @@ class BuildIOSFrameworkCommand extends BuildSubCommand {
} }
globals.printStatus('Frameworks written to ${outputDirectory.path}.'); globals.printStatus('Frameworks written to ${outputDirectory.path}.');
if (!_project.isModule && hasPlugins(_project)) {
// Apps do not generate a FlutterPluginRegistrant.framework. Users will need
// to copy the GeneratedPluginRegistrant class to their project manually.
final File pluginRegistrantHeader = _project.ios.pluginRegistrantHeader;
final File pluginRegistrantImplementation =
_project.ios.pluginRegistrantImplementation;
pluginRegistrantHeader.copySync(
outputDirectory.childFile(pluginRegistrantHeader.basename).path);
pluginRegistrantImplementation.copySync(outputDirectory
.childFile(pluginRegistrantImplementation.basename)
.path);
globals.printStatus(
'\nCopy the ${globals.fs.path.basenameWithoutExtension(pluginRegistrantHeader.path)} class into your project.\n'
'See https://flutter.dev/docs/development/add-to-app/ios/add-flutter-screen#create-a-flutterengine for more information.');
}
return FlutterCommandResult.success(); return FlutterCommandResult.success();
} }
...@@ -459,6 +472,7 @@ end ...@@ -459,6 +472,7 @@ end
xcodeBuildConfiguration, xcodeBuildConfiguration,
'SYMROOT=${iPhoneBuildOutput.path}', 'SYMROOT=${iPhoneBuildOutput.path}',
'BITCODE_GENERATION_MODE=$bitcodeGenerationMode', 'BITCODE_GENERATION_MODE=$bitcodeGenerationMode',
'ENABLE_BITCODE=YES', // Support host apps with bitcode enabled.
'ONLY_ACTIVE_ARCH=NO', // No device targeted, so build all valid architectures. 'ONLY_ACTIVE_ARCH=NO', // No device targeted, so build all valid architectures.
'BUILD_LIBRARY_FOR_DISTRIBUTION=YES', 'BUILD_LIBRARY_FOR_DISTRIBUTION=YES',
]; ];
...@@ -483,6 +497,7 @@ end ...@@ -483,6 +497,7 @@ end
'-configuration', '-configuration',
xcodeBuildConfiguration, xcodeBuildConfiguration,
'SYMROOT=${simulatorBuildOutput.path}', 'SYMROOT=${simulatorBuildOutput.path}',
'ENABLE_BITCODE=YES', // Support host apps with bitcode enabled.
'ARCHS=x86_64', 'ARCHS=x86_64',
'ONLY_ACTIVE_ARCH=NO', // No device targeted, so build all valid architectures. 'ONLY_ACTIVE_ARCH=NO', // No device targeted, so build all valid architectures.
'BUILD_LIBRARY_FOR_DISTRIBUTION=YES', 'BUILD_LIBRARY_FOR_DISTRIBUTION=YES',
......
...@@ -897,36 +897,24 @@ Future<void> _writeIOSPluginRegistrant(FlutterProject project, List<Plugin> plug ...@@ -897,36 +897,24 @@ Future<void> _writeIOSPluginRegistrant(FlutterProject project, List<Plugin> plug
'framework': 'Flutter', 'framework': 'Flutter',
'plugins': iosPlugins, 'plugins': iosPlugins,
}; };
final String registryDirectory = project.ios.pluginRegistrantHost.path;
if (project.isModule) { if (project.isModule) {
final String registryClassesDirectory = globals.fs.path.join(registryDirectory, 'Classes'); final String registryDirectory = project.ios.pluginRegistrantHost.path;
_renderTemplateToFile( _renderTemplateToFile(
_pluginRegistrantPodspecTemplate, _pluginRegistrantPodspecTemplate,
context, context,
globals.fs.path.join(registryDirectory, 'FlutterPluginRegistrant.podspec'), globals.fs.path.join(registryDirectory, 'FlutterPluginRegistrant.podspec'),
); );
_renderTemplateToFile(
_objcPluginRegistryHeaderTemplate,
context,
globals.fs.path.join(registryClassesDirectory, 'GeneratedPluginRegistrant.h'),
);
_renderTemplateToFile(
_objcPluginRegistryImplementationTemplate,
context,
globals.fs.path.join(registryClassesDirectory, 'GeneratedPluginRegistrant.m'),
);
} else {
_renderTemplateToFile(
_objcPluginRegistryHeaderTemplate,
context,
globals.fs.path.join(registryDirectory, 'GeneratedPluginRegistrant.h'),
);
_renderTemplateToFile(
_objcPluginRegistryImplementationTemplate,
context,
globals.fs.path.join(registryDirectory, 'GeneratedPluginRegistrant.m'),
);
} }
_renderTemplateToFile(
_objcPluginRegistryHeaderTemplate,
context,
project.ios.pluginRegistrantHeader.path,
);
_renderTemplateToFile(
_objcPluginRegistryImplementationTemplate,
context,
project.ios.pluginRegistrantImplementation.path,
);
} }
/// The relative path from a project's main CMake file to the plugin symlink /// The relative path from a project's main CMake file to the plugin symlink
......
...@@ -665,15 +665,12 @@ class IosProject extends FlutterProjectPlatform implements XcodeBasedProject { ...@@ -665,15 +665,12 @@ class IosProject extends FlutterProjectPlatform implements XcodeBasedProject {
) )
); );
if (framework.existsSync()) { if (framework.existsSync()) {
final Directory engineDest = ephemeralDirectory
.childDirectory('Flutter')
.childDirectory('engine');
final File podspec = framework.parent.childFile('Flutter.podspec'); final File podspec = framework.parent.childFile('Flutter.podspec');
globals.fsUtils.copyDirectorySync( globals.fsUtils.copyDirectorySync(
framework, framework,
engineDest.childDirectory('Flutter.framework'), engineCopyDirectory.childDirectory('Flutter.framework'),
); );
podspec.copySync(engineDest.childFile('Flutter.podspec').path); podspec.copySync(engineCopyDirectory.childFile('Flutter.podspec').path);
} }
} }
...@@ -704,6 +701,22 @@ class IosProject extends FlutterProjectPlatform implements XcodeBasedProject { ...@@ -704,6 +701,22 @@ class IosProject extends FlutterProjectPlatform implements XcodeBasedProject {
: hostAppRoot.childDirectory(_hostAppProjectName); : hostAppRoot.childDirectory(_hostAppProjectName);
} }
File get pluginRegistrantHeader {
final Directory registryDirectory = isModule ? pluginRegistrantHost.childDirectory('Classes') : pluginRegistrantHost;
return registryDirectory.childFile('GeneratedPluginRegistrant.h');
}
File get pluginRegistrantImplementation {
final Directory registryDirectory = isModule ? pluginRegistrantHost.childDirectory('Classes') : pluginRegistrantHost;
return registryDirectory.childFile('GeneratedPluginRegistrant.m');
}
Directory get engineCopyDirectory {
return isModule
? ephemeralDirectory.childDirectory('Flutter').childDirectory('engine')
: hostAppRoot.childDirectory('Flutter');
}
Future<void> _overwriteFromTemplate(String path, Directory target) async { Future<void> _overwriteFromTemplate(String path, Directory target) async {
final Template template = await Template.fromName( final Template template = await Template.fromName(
path, path,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment