Unity Cloud BuildではCocoapodが使えません。
なのでCocoapodを使わずにFirebaseの機能をiOSで使う方法を紹介します。
使えた機能
- Analytics
- Realtime Database
- Authentication
- Cloud Messaging
- Dynamic Links
UnityにFirebaseを実装する
FirebaseのSDKを入れる
まず ここ からFirebaseのUnity用のSDKをダウンロードします。
次にダウンロードしたSDKをUnityにインポートします。
[Assets]>[Import Package]>[Custom Package...]
ダウンロードしたzipファイルから使うものを選びます
Downloads\firebase_unity_sdk_6.6.0\firebase_unity_sdk\dotnet4
↑このパスの中の Firebase???.unitypackage
iOSのFrameworkを入れる
次にFirebaseのiOS版のFrameworkを ここ からダウンロードします。
ダウンロードしたzipファイルを解凍し、使いたいFirebaseの機能のファイルを開く。
Analyticsの場合
[Downloads/Firebase-6.11.0/Firebase/Analytics]内のすべての .framework フォルダを
Unityの[Assets/Plugins/iOS]に入れます。
こんな感じでその他のframeworkも入れていきます。
frameworkが入れ終わったら、[Firebase-6.11.0\Firebase]内にある
[Firebase.h]というファイルも[Assets/Plugins/iOS]に入れます。
XcodeをC#で設定する
下のファイルを[Assets/Editor]内に置きます。
BuildProcess.cs
using UnityEngine;
using UnityEditor;
using UnityEditor.Callbacks;
using UnityEditor.iOS.Xcode;
using System.Collections.Generic;
using System.IO;
using System.Text;
using System.Xml;
public class BuildProcess
{
[PostProcessBuild]
public static void OnPostProcessBuild(BuildTarget buildTarget, string path)
{
// iOSじゃなければ処理しない
if (buildTarget != BuildTarget.iOS)
{
return;
}
var project = new PBXProject();
project.ReadFromFile(PBXProject.GetPBXProjectPath(path));
var projectGuid = project.TargetGuidByName(PBXProject.GetUnityTargetName());
// Enable Modules (C and Objective-C)をYESに設定する
project.SetBuildProperty(projectGuid, "CLANG_ENABLE_MODULES", "YES");
project.SetBuildProperty(projectGuid, "ENABLE_BITCODE", "NO");
project.WriteToFile(PBXProject.GetPBXProjectPath(path));
string projPath = Path.Combine(path, "Unity-iPhone.xcodeproj/project.pbxproj");
PBXProject proj = new PBXProject();
proj.ReadFromString(File.ReadAllText(projPath));
string target = proj.TargetGuidByName("Unity-iPhone");
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-ObjC");// 必須!
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-l???");
/*
詳しくは下を参照
*/
List<string> frameworks = new List<string>() {
"???.framework"
};
foreach (var framework in frameworks)
{
proj.AddFrameworkToProject(target, framework, false);
}
File.WriteAllText(projPath, proj.WriteToString());
CreateEntitlements(path, "myapp");
SetCapabilities(path);// Push通知を使わないなら多分いらない
}
private static void CreateEntitlements(string path, string your_appname)
{
XmlDocument document = new XmlDocument();
XmlDocumentType doctype = document.CreateDocumentType("plist", "-//Apple//DTD PLIST 1.0//EN", "http://www.apple.com/DTDs/PropertyList-1.0.dtd", null);
document.AppendChild(doctype);
XmlElement plist = document.CreateElement("plist");
plist.SetAttribute("version", "1.0");
XmlElement dict = document.CreateElement("dict");
plist.AppendChild(dict);
document.AppendChild(plist);
XmlElement e = (XmlElement)document.SelectSingleNode("/plist/dict");
XmlElement key = document.CreateElement("key");
key.InnerText = "aps-environment";
e.AppendChild(key);
XmlElement value = document.CreateElement("string");
value.InnerText = "development";
e.AppendChild(value);
string entitlementsPath= Path.Combine(path, "Unity-iPhone/" + your_appname + ".entitlements");
//= path + "/Unity-iPhone/" + your_appname + ".entitlements";
document.Save(entitlementsPath);
string projPath = Path.Combine(path, "Unity-iPhone.xcodeproj/project.pbxproj");
PBXProject proj = new PBXProject();
proj.ReadFromString(File.ReadAllText(projPath));
string target = proj.TargetGuidByName("Unity-iPhone");
string guid = proj.AddFile(entitlementsPath, entitlementsPath);
proj.AddBuildProperty(target, "CODE_SIGN_ENTITLEMENTS", Path.Combine(path, "Unity-iPhone/" + your_appname + ".entitlements"));
proj.AddFileToBuild(target, guid);
proj.WriteToFile(projPath);
}
private static void SetCapabilities(string path)
{
string projPath = Path.Combine(path, "Unity-iPhone.xcodeproj/project.pbxproj");
PBXProject proj = new PBXProject();
proj.ReadFromString(File.ReadAllText(projPath));
string target = proj.TargetGuidByName("Unity-iPhone");
bool s=proj.AddCapability(target, PBXCapabilityType.PushNotifications);
File.WriteAllText(projPath, proj.WriteToString());
string[] lines = proj.WriteToString().Split('\n');
List<string> newLines = new List<string>();
bool editFinish = false;
for (int i = 0; i < lines.Length; i++)
{
string line = lines[i];
if (editFinish)
{
newLines.Add(line);
}
else if (line.IndexOf("isa = PBXProject;") > -1)
{
do
{
newLines.Add(line);
line = lines[++i];
} while (line.IndexOf("TargetAttributes = {") == -1);
// この下のやつは多分無くても大丈夫 まあ、一応・・・
newLines.Add("TargetAttributes = {");
newLines.Add("********* = {");
newLines.Add("DevelopmentTeam = ****;");
newLines.Add("SystemCapabilities = {");
newLines.Add("com.apple.BackgroundModes = {");
newLines.Add("enabled = 1;");
newLines.Add("};");
newLines.Add("com.apple.Push = {");
newLines.Add("enabled = 1;");
newLines.Add("};");
newLines.Add("};");
newLines.Add("};");
editFinish = true;
}
else
{
newLines.Add(line);
}
}
File.WriteAllText(projPath, string.Join("\n", newLines.ToArray()));
}
}
IOSBuildPostProcessor.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEditor;
using UnityEditor.Callbacks;
using UnityEditor.iOS.Xcode;
public static class IOSBuildPostProcessor
{
[PostProcessBuild]
public static void OnPostprocessBuild(BuildTarget target, string pathToBuiltProject)
{
if (target == BuildTarget.iOS)
{
OnPostprocessBuildIOS(pathToBuiltProject);//Dynamic Links用
OnPostprocessBuildPush(pathToBuiltProject);//Cloud Messaging用
OnPostprocessBuildbg(pathToBuiltProject);//Cloud Messaging用
}
}
private static void OnPostprocessBuildIOS(string pathToBuiltProject)
{
//This is the default path to the default pbxproj file. Yours might be different
string projectPath = "/Unity-iPhone.xcodeproj/project.pbxproj";
//Default target name. Yours might be different
string targetName = "Unity-iPhone";
//Set the entitlements file name to what you want but make sure it has this extension
string entitlementsFileName = "my_app.entitlements";
var entitlements = new ProjectCapabilityManager(pathToBuiltProject + projectPath, entitlementsFileName, targetName);
var domain = "???.page.link"; //ここにはDynamic Linksで設定した、???.page.linkなどを入れる
entitlements.AddAssociatedDomains(new string[] { "applinks:" + domain });
//Apply
entitlements.WriteToFile();
}
private static void OnPostprocessBuildPush(string pathToBuiltProject)
{
//This is the default path to the default pbxproj file. Yours might be different
string projectPath = "/Unity-iPhone.xcodeproj/project.pbxproj";
//Default target name. Yours might be different
string targetName = "Unity-iPhone";
//Set the entitlements file name to what you want but make sure it has this extension
string entitlementsFileName = "my_app_2.entitlements";
var entitlements = new ProjectCapabilityManager(pathToBuiltProject + projectPath, entitlementsFileName, targetName);
entitlements.AddPushNotifications(true);
//Apply
entitlements.WriteToFile();
}
private static void OnPostprocessBuildbg(string pathToBuiltProject)
{
//This is the default path to the default pbxproj file. Yours might be different
string projectPath = "/Unity-iPhone.xcodeproj/project.pbxproj";
//Default target name. Yours might be different
string targetName = "Unity-iPhone";
//Set the entitlements file name to what you want but make sure it has this extension
string entitlementsFileName = "my_app_3.entitlements";
var entitlements = new ProjectCapabilityManager(pathToBuiltProject + projectPath, entitlementsFileName, targetName);
entitlements.AddBackgroundModes(BackgroundModesOptions.RemoteNotifications);
//Apply
entitlements.WriteToFile();
}
}
長いですね・・・
コメントを見て少し書き換えたりしてください。
BuildProcess.csを書き換える
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-ObjC");// 必須!
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-l???");
List<string> frameworks = new List<string>() {
"???.framework"
};
上のBuildProcess.csにこんな行があると思います
ここをframeworkファイル内のmodule.modulemapに沿って書き換えます。
例 Analyticsの場合
場所 [FirebaseAnalytics.framework/Modules/module.modulemap]
framework module FirebaseAnalytics {
umbrella header "FirebaseAnalytics.h"
export *
module * { export * }
link "sqlite3"
link "z"
link framework "CoreData"
link framework "Security"
link framework "StoreKit"
link framework "SystemConfiguration"
link framework "UIKit"
}
と書いてある場合は
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-ObjC");// 必須!
の下に
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-lz");
proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-lsqlite3");
を追加します。
要するに
"-l"+"link の後に書いているもの"
を追加します。
link framework
の部分は、
List<string> frameworks = new List<string>() {
の中に上の例では
"CoreData.framework",
"Security.framework",
"StoreKit.framework",
"SystemConfiguration.framework",
"UIKit.framework"
を追加します。
こんな感じで他のframeworkのmodule.modulemapを見て追加します。
後はビルドしてみましょう!
そうすれば多分できるはずです。
わからないことやエラーが起きたらコメントで知らせてください。