/// <summary> /// Using the Compatible code path, this setup is limited to be the same as legacy pipeline. /// With this setup an array of content for each AssetBundle is passed into the pipeline. /// ContentBuildInterface.GeneratAssetBundleBuilds can be used to get an array for the bundleNames /// set in the AssetImporters in your project (as seen at the bottom of the inspector when selecting an asset) /// There are two arrays, /// .assetNames which contains the fullpath to the Asset to be included /// .addressableNames which is the string used when loading the Asset. /// These are connected by index, so assigning .addressableNames[8] = "Robo" is assigning the asset at .assetNames[8] /// to load via AssetBundle.LoadAsset<T>( "Robo" ); /// </summary> /// <param name="outputPath"></param> /// <param name="forceRebuild"></param> /// <param name="compression"></param> /// <param name="buildTarget"></param> /// <returns></returns> public static bool BuildCompatibilityAssetBundles(string outputPath, bool forceRebuild, CompressionType compression, BuildTarget buildTarget) { var options = BuildAssetBundleOptions.None; switch (compression) { case CompressionType.None: options |= BuildAssetBundleOptions.UncompressedAssetBundle; break; case CompressionType.Lz4: options |= BuildAssetBundleOptions.ChunkBasedCompression; break; } if (forceRebuild) { options |= BuildAssetBundleOptions.ForceRebuildAssetBundle; } AssetBundleBuild[] bundles = ContentBuildInterface.GenerateAssetBundleBuilds(); // go through each asset in the bundle and assign the addressable name to filename for (int i = 0; i < bundles.Length; i++) { bundles[i].addressableNames = bundles[i].assetNames.Select(Path.GetFileNameWithoutExtension).ToArray(); } var manifest = CompatibilityBuildPipeline.BuildAssetBundles(outputPath, bundles, options, buildTarget); return(manifest != null); }
public static void BuildAssetBundlesWithShaderBundleSRPCompat() { AssetBundleBuild[] content = SetupBundles(); var outputPath = k_OutputBasePath + "urp_bundle_srp_compat"; PrepareOutputPath(outputPath); CompatibilityBuildPipeline.BuildAssetBundles(outputPath, content, BuildAssetBundleOptions.None, EditorUserBuildSettings.activeBuildTarget); }
public static void TestSbpDryRun() { foreach (var target in Targets) { var sbpBundlePath = Path.Combine("SbpAssetBundles", target.ToString()); var sbpManifest = CompatibilityBuildPipeline.BuildAssetBundles( sbpBundlePath, BuildAssetBundleOptions.DryRunBuild, target); } }
private static CompatibilityAssetBundleManifest PackAssetBundle(PackerData packerData, BundleBuildData buildData, string outputDir) { List <AssetBundleBuild> bundleBuilds = new List <AssetBundleBuild>(); foreach (var group in packerData.groupDatas) { foreach (var bundle in group.bundleDatas) { AssetBundleBuild build = new AssetBundleBuild(); build.assetBundleName = bundle.Path; build.assetNames = (from asset in bundle.assetDatas select asset.Path).ToArray(); bundleBuilds.Add(build); } } var manifest = CompatibilityBuildPipeline.BuildAssetBundles(outputDir, bundleBuilds.ToArray(), buildData.GetBundleOptions(), buildData.GetBuildTarget()); return(manifest); }
static void Build(string folder, BuildTarget target) { var bundles = ContentBuildInterface.GenerateAssetBundleBuilds(); for (var i = 0; i < bundles.Length; i++) { bundles[i].addressableNames = bundles[i].assetNames.Select(Path.GetFileNameWithoutExtension).ToArray(); } var result = CompatibilityBuildPipeline.BuildAssetBundles($"{Application.streamingAssetsPath}", BuildAssetBundleOptions.None, target); var manifest = new HybirdResManifest(); var createdBundeNames = result.GetAllAssetBundles(); foreach (var bunde in createdBundeNames) { HybirdRes res = new HybirdRes(); res.Name = bunde; res.Crc = result.GetAssetBundleCrc(bunde); res.Dependence = result.GetAllDependencies(bunde); manifest.Res[bunde] = res; } var resPath = Application.streamingAssetsPath; var infoPath = Path.Combine(resPath, "res.manifest"); var json = LitJson.JsonMapper.ToJson(manifest); File.WriteAllText(infoPath, json); if (File.Exists($"{resPath}/StreamingAssets.manifest")) { File.Delete($"{resPath}/StreamingAssets.manifest"); } AssetDatabase.Refresh(); }
public static CompatibilityAssetBundleManifest BuildAssetBundles(string outputPath, bool forceRebuild, CompressionType compressionMode, BuildTarget buildTarget) { var options = BuildAssetBundleOptions.None; switch (compressionMode) { case CompressionType.None: options |= BuildAssetBundleOptions.UncompressedAssetBundle; break; case CompressionType.Lz4: options |= BuildAssetBundleOptions.ChunkBasedCompression; break; } if (forceRebuild) { options |= BuildAssetBundleOptions.ForceRebuildAssetBundle; } Directory.CreateDirectory(outputPath); return(CompatibilityBuildPipeline.BuildAssetBundles(outputPath, options, buildTarget)); }
public static void Pack(BuildTarget build_target) { asset_ab_build_mapper.Clear(); asset_ab_mapper.Clear(); dynamic_ab_blacklist.Clear(); EditorUtility.ClearProgressBar(); // 准备打包 初始化Packer string platform = GetPlatformForPackRes(build_target); string out_path = Application.dataPath + "/StreamingAssets/AssetBundle/" + platform; if (!Directory.Exists(out_path)) { Directory.CreateDirectory(out_path); } BuildAssetBundleOptions option = BuildAssetBundleOptions.ChunkBasedCompression | BuildAssetBundleOptions.DeterministicAssetBundle //| BuildAssetBundleOptions.DisableWriteTypeTree ; SetPack("Animations", "*", PackFolderToABOption.UseABName, "animations"); SetPack("Materials", "*", PackFolderToABOption.UseABName, "materials"); SetPack("Materials", "*.shader", PackFolderToABOption.UseABName, "shaders"); SetPack("Models", "*", PackFolderToABOption.UseABName, "models"); SetPack("Fonts", "*", PackFolderToABOption.UseABName, "fonts"); SetPack("Resources/SpriteAtlas", "*.spriteatlas", PackFolderToABOption.UseFileName, "atlas"); SetPack("Resources/Audios/sfx", "*", PackFolderToABOption.UseABName, "audio_sfx"); SetPack("Resources/Audios/bgm", "*", PackFolderToABOption.UseFileNamePrefix, "audio_bgm"); SetPack("Textures", "*.png", PackFolderToABOption.UseSubFolderName, "textures"); SetPack("Textures/Card", "*.png", PackFolderToABOption.UseSubFolderName, "textures_card"); SetPack("Textures/Card/CardComponents", "*.png", PackFolderToABOption.UseSubFolderName, "textures_card_cardcomponents"); SetPack("Textures/UI", "*.png", PackFolderToABOption.UseSubFolderName, "textures_ui"); SetPack("Resources/Prefabs", "*.prefab", PackFolderToABOption.UseABName, "prefabs"); CompatibilityBuildPipeline.BuildAssetBundles(out_path, GetAssetBundleBuild(), option, build_target); }
public AssetBundleConfig PackAssetBundle(AssetPackerConfig packerConfig, BundleBuildConfig buildConfig, string outputDir) { var manifest = CompatibilityBuildPipeline.BuildAssetBundles(outputDir, buildConfig.GetBundleOptions(), buildConfig.GetBuildTarget()); return(ConvertToBundleConfig(packerConfig, manifest, outputDir)); }
public override void Execute(Pipeline pipeline) { var excludedExtensions = new[] { ".dll", ".cs", ".meta" }; AssetDatabase.SaveAssets(); var assetBundleDefs = pipeline.Datums.OfType <AssetBundleDefinitions>().ToArray(); var bundleArtifactPath = BundleArtifactPath.Resolve(pipeline, this); Directory.CreateDirectory(bundleArtifactPath); var builds = new AssetBundleBuild[assetBundleDefs.Sum(abd => abd.assetBundles.Length)]; var buildsIndex = 0; for (int defIndex = 0; defIndex < assetBundleDefs.Length; defIndex++) { var assetBundleDef = assetBundleDefs[defIndex]; var playerAssemblies = CompilationPipeline.GetAssemblies(); var assemblyFiles = playerAssemblies.Select(pa => pa.outputPath).ToArray(); var sourceFiles = playerAssemblies.SelectMany(pa => pa.sourceFiles).ToArray(); var fileCount = 0; var logBuilder = new StringBuilder(); logBuilder.AppendLine("Constructing AssetBundles"); for (int i = 0; i < assetBundleDef.assetBundles.Length; i++) { var def = assetBundleDef.assetBundles[i]; var explicitAssets = assetBundleDef.assetBundles.Where((ab, abi) => abi != i).SelectMany(ab => ab.assets).Select(asset => AssetDatabase.GetAssetPath(asset)).ToArray(); var build = builds[buildsIndex]; var assets = new List <string>(); logBuilder.AppendLine($"Building bundle: {def.assetBundleName}"); if (def.assets.OfType <SceneAsset>().Any()) { assets.Add(AssetDatabase.GetAssetPath(def.assets.OfType <SceneAsset>().First())); } else { foreach (var asset in def.assets) { var assetPath = AssetDatabase.GetAssetPath(asset); if (AssetDatabase.IsValidFolder(assetPath)) { assets.AddRange(Directory.EnumerateFiles(assetPath, "*", SearchOption.AllDirectories) .SelectMany(ap => AssetDatabase.GetDependencies(ap).Append(ap))); } else if (asset is UnityPackage up) { if (up.exportPackageOptions.HasFlag(ExportPackageOptions.Recurse)) { foreach (var upAsset in up.AssetFiles) { var path = AssetDatabase.GetAssetPath(upAsset); if (AssetDatabase.IsValidFolder(path)) { assets.AddRange(Directory.EnumerateFiles(path, "*", SearchOption.AllDirectories) .SelectMany(ap => AssetDatabase.GetDependencies(ap).Append(ap))); } else { assets.Add(path); } } } } else { assets.AddRange(AssetDatabase.GetDependencies(assetPath) .Where(ap => AssetDatabase.GetMainAssetTypeAtPath(ap) != typeof(UnityPackage)) .Append(assetPath)); } } } build.assetNames = assets .Select(ap => ap.Replace("\\", "/")) //.Where(dap => !explicitDownstreamAssets.Contains(dap)) .Where(dap => !explicitAssets.Contains(dap)) .Where(dap => !excludedExtensions.Contains(Path.GetExtension(dap))) .Where(ap => !sourceFiles.Contains(ap)) .Where(ap => !assemblyFiles.Contains(ap)) .Where(path => !AssetDatabase.IsValidFolder(path)) .Distinct() .ToArray(); build.assetBundleName = def.assetBundleName; builds[buildsIndex] = build; buildsIndex++; fileCount += build.assetNames.Length; foreach (var asset in build.assetNames) { logBuilder.AppendLine(asset); } } logBuilder.AppendLine($"Constructed {builds.Length} AssetBundleBuilds with {fileCount} files."); Debug.Log(logBuilder.ToString()); } if (!simulate) { var allBuilds = builds.ToArray(); CompatibilityBuildPipeline.BuildAssetBundles(bundleArtifactPath, allBuilds, AssetBundleBuildOptions, buildTarget); for (pipeline.ManifestIndex = 0; pipeline.ManifestIndex < pipeline.manifests.Length; pipeline.ManifestIndex++) { var manifest = pipeline.Manifest; foreach (var assetBundleDef in manifest.Data.OfType <AssetBundleDefinitions>()) { var bundleNames = assetBundleDef.assetBundles.Select(ab => ab.assetBundleName).ToArray(); foreach (var outputPath in assetBundleDef.StagingPaths.Select(path => path.Resolve(pipeline, this))) { foreach (string dirPath in Directory.GetDirectories(bundleArtifactPath, "*", SearchOption.AllDirectories)) { Directory.CreateDirectory(dirPath.Replace(bundleArtifactPath, outputPath)); } foreach (string filePath in Directory.GetFiles(bundleArtifactPath, "*", SearchOption.AllDirectories)) { var fileName = Path.GetFileName(filePath); bool found = false; foreach (var bundleName in bundleNames) { if (filePath.ToLower().Contains(bundleName.ToLower())) { found = true; break; } } if (!found) { continue; } string destFileName = filePath.Replace(bundleArtifactPath, outputPath); Directory.CreateDirectory(Path.GetDirectoryName(destFileName)); File.Copy(filePath, destFileName, true); } File.Copy(Path.Combine(bundleArtifactPath, $"{Path.GetFileName(bundleArtifactPath)}.manifest"), Path.Combine(outputPath, $"{manifest.Identity.Name}.manifest"), true); } } } pipeline.ManifestIndex = -1; } }
public static void BuildTestBundles() { var builder = new StringBuilder(); builder.AppendLine($"Running with active build target: {EditorUserBuildSettings.activeBuildTarget}"); foreach (var target in Targets) { builder.AppendLine(); builder.AppendLine($"Testing bundles for target: {target}"); builder.AppendLine("-------------------------"); var dryRunHashes = new Dictionary <string, Hash128>(); var buildHashes = new Dictionary <string, Hash128>(); var sbpDryRunHashes = new Dictionary <string, Hash128>(); var sbpBuildHashes = new Dictionary <string, Hash128>(); // Run asset bundle builds using the built-in build pipeline. // ---------------------------------------------------------- var bundlePath = Path.Combine("AssetBundles", target.ToString()); if (!Directory.Exists(bundlePath)) { Directory.CreateDirectory(bundlePath); } var manifest = BuildPipeline.BuildAssetBundles( bundlePath, BuildAssetBundleOptions.DryRunBuild, target); foreach (var bundleName in manifest.GetAllAssetBundles()) { dryRunHashes[bundleName] = manifest.GetAssetBundleHash(bundleName); } manifest = BuildPipeline.BuildAssetBundles( bundlePath, BuildAssetBundleOptions.None, target); foreach (var bundleName in manifest.GetAllAssetBundles()) { buildHashes[bundleName] = manifest.GetAssetBundleHash(bundleName); } // Run asset bundle builds using the Scriptable Build Pipeline. // ------------------------------------------------------------ var sbpBundlePath = Path.Combine("SbpAssetBundles", target.ToString()); if (!Directory.Exists(sbpBundlePath)) { Directory.CreateDirectory(sbpBundlePath); } var sbpManifest = CompatibilityBuildPipeline.BuildAssetBundles( sbpBundlePath, BuildAssetBundleOptions.DryRunBuild, target); foreach (var bundleName in sbpManifest.GetAllAssetBundles()) { sbpDryRunHashes[bundleName] = sbpManifest.GetAssetBundleHash(bundleName); } sbpManifest = CompatibilityBuildPipeline.BuildAssetBundles( sbpBundlePath, BuildAssetBundleOptions.None, target); foreach (var bundleName in sbpManifest.GetAllAssetBundles()) { sbpBuildHashes[bundleName] = sbpManifest.GetAssetBundleHash(bundleName); } // Build the results table for the current build target. // ----------------------------------------------------- foreach (var bundleName in dryRunHashes.Keys) { builder.AppendLine( $"Bundle: {bundleName},\t" + $"dry run hash: {dryRunHashes[bundleName]},\t" + $"build hash: {buildHashes[bundleName]},\t" + $"SBP dry run: {sbpDryRunHashes[bundleName]},\t" + $"SBP build: {sbpBuildHashes[bundleName]}"); } } Debug.Log(builder); }