private static void ProcessOBJDB(Span <byte> buffer, Dictionary <KTIDReference, string> ndbFiles, Dictionary <KTIDReference, string> filelist, Dictionary <KTIDReference, string> propertyList, HashSet <KTIDReference> filters, DatabaseFlags flags, HashSet <KTIDReference> missingProperties) { var db = new OBJDB(buffer); var ndb = new NDB(); if (ndbFiles.TryGetValue(db.Header.NameKTID, out var ndbPath)) { ndb = new NDB(File.ReadAllBytes(ndbPath)); } foreach (var(ktid, (entry, properties)) in db.Entries) { if (filters.Count != 0 && !filters.Contains(entry.TypeInfoKTID)) { continue; } var lines = new List <string> { $"KTID: {GetKTIDNameValue(ktid, flags.ShowKTIDs, ndb, filelist, propertyList)}", $"TypeInfo: {GetKTIDNameValue(entry.TypeInfoKTID, flags.ShowKTIDs, ndb, filelist, propertyList)}", $"Parent: {GetKTIDNameValue(entry.ParentKTID, flags.ShowKTIDs, ndb, filelist, propertyList)}" }; foreach (var(property, values) in properties) { if (flags.CreateMissingList && !HasKTIDNameValue(property.PropertyKTID, ndb, propertyList)) { missingProperties.Add(property.PropertyKTID); } lines.Add($"{property.TypeId} {GetKTIDNameValue(property.PropertyKTID, flags.ShowKTIDs, ndb, propertyList)}: {(values.Length == 0 ? "NULL" : string.Join(", ", values.Select(x => property.TypeId == OBJDBPropertyType.UInt32 && x != null ? GetKTIDNameValue((uint) x, flags.ShowKTIDs, ndb, filelist, propertyList) : x?.ToString() ?? "NULL")))}"); } foreach (var line in lines) { Console.Out.WriteLine(line); } Console.Out.WriteLine(); } }
private static void Main(string[] args) { Logger.PrintVersion("Nyotengu"); var flags = CommandLineFlags.ParseFlags <KTIDFlags>(CommandLineFlags.PrintHelp, args); if (flags == null) { return; } var ndb = new NDB(); if (!string.IsNullOrEmpty(flags.NDBPath) && File.Exists(flags.NDBPath)) { ndb = new NDB(File.ReadAllBytes(flags.NDBPath)); } var objdb = new OBJDB(File.ReadAllBytes(flags.OBJDBPath)); var filelist = Cethleann.ManagedFS.Nyotengu.LoadKTIDFileList(flags.FileList, flags.GameId); var textureSection = new ResourceSectionHeader { Magic = DataType.TextureGroup, Version = 0x30303630 }; var textureHeader = new TextureGroupHeader { System = objdb.Header.System }; foreach (var ktid in flags.Paths) { if (!File.Exists(ktid)) { continue; } var ktidgroup = new KTIDTextureSet(File.ReadAllBytes(ktid)); var ktidsystem = ktidgroup.Textures.Select(x => objdb.Entries.TryGetValue(x, out var tuple) ? tuple : default).ToArray();
private static void Main(string[] args) { Logger.PrintVersion("Nyotengu"); var flags = CommandLineFlags.ParseFlags <AnimationGraphFlags>(CommandLineFlags.PrintHelp, args); if (flags == null) { return; } var objdbNdb = new NDB(); var singletonNdb = new NDB(); if (!string.IsNullOrEmpty(flags.OBJDBNDBPath) && File.Exists(flags.OBJDBNDBPath)) { objdbNdb = new NDB(File.ReadAllBytes(flags.OBJDBNDBPath)); } if (!string.IsNullOrEmpty(flags.SingletonDBNDBPath) && File.Exists(flags.SingletonDBNDBPath)) { singletonNdb = new NDB(File.ReadAllBytes(flags.SingletonDBNDBPath)); } // ReSharper disable InconsistentNaming var CE1DB = new OBJDB(File.ReadAllBytes(flags.OBJDBPath)); var CE1Singleton = new OBJDB(File.ReadAllBytes(flags.SingletonPath)); // ReSharper restore InconsistentNaming var filelist = Cethleann.ManagedFS.Nyotengu.LoadKTIDFileList(flags.FileList, flags.GameId); var animationFiles = new Dictionary <KTIDReference, string>(); foreach (var directory in flags.AnimationDirectories ?? new HashSet <string?>()) { if (directory == null || !Directory.Exists(directory)) { continue; } foreach (var file in Directory.GetFiles(directory)) { var basename = Path.GetFileNameWithoutExtension(file); if (basename.Length != 8 || !KTIDReference.TryParse(basename, out var reference)) { reference = RDB.Hash(file, "G1A"); } animationFiles[reference] = file; } } var typeKTID = RDB.Hash("TypeInfo::Object::MotorCharacterSetting"); foreach (var entry in CE1DB.Entries.Select(x => x.Value).Where(entry => entry.Record.TypeInfoKTID == typeKTID)) { var(_, values) = entry.GetProperty("CharacterModelNameHash"); if (values == null) { continue; } var(_, actions) = entry.GetProperty("CharacterActionObjectNameHashArray"); if (actions == null || actions.Length == 0) { continue; } var nameHashes = values.Where(x => x != null).Select(x => new KTIDReference(x)).ToArray(); if (!nameHashes.Any(x => flags.Hashes.Contains(x))) { continue; } Logger.Info("ANIM", $"Found Character Settings: {string.Join(", ", nameHashes.Select(x => GetKTIDNameValue(x, false, objdbNdb, filelist)))}"); var done = new HashSet <KTIDReference>(); foreach (var actionHash in actions.Select(x => new KTIDReference(x))) { if (!CE1Singleton.Entries.TryGetValue(actionHash, out var player)) { Logger.Error("ANIM", $"Can't find animation player settings for {GetKTIDNameValue(actionHash, false, singletonNdb, filelist)}"); continue; } var properties = player.GetProperties("AnimationDataObjectNameHashArray", "SrcAnimationDataObjectNameHash", "DstAnimationDataObjectNameHash", "FCurveAnimationDataObjectNameHash"); var animationDataHashes = properties.SelectMany(x => x.values ?? Array.Empty <object?>()).ToArray(); var ktidHashes = animationDataHashes.Where(x => x != null).Select(x => new KTIDReference(x)).ToArray(); foreach (var animationDataHash in ktidHashes) { if (!CE1Singleton.Entries.TryGetValue(animationDataHash, out var animationData)) { Logger.Error("ANIM", $"Can't find animation data for {GetKTIDNameValue(animationDataHash, false, singletonNdb, filelist)}"); continue; } var(_, animationHashes) = animationData.GetProperty("G1AFileResourceHash"); if (animationHashes == null) { Logger.Error("ANIM", $"Can't find animation references for {GetKTIDNameValue(animationDataHash, false, singletonNdb, filelist)}"); continue; } foreach (var animationHashActual in animationHashes.Where(x => x != null).Select(x => new KTIDReference(x))) { if (!done.Add(animationHashActual)) { continue; } Logger.Info("ANIM", GetKTIDNameValue(animationHashActual, false, singletonNdb, filelist)); if (string.IsNullOrWhiteSpace(flags.Output) || !animationFiles.TryGetValue(animationHashActual, out var path)) { continue; } if (!Directory.Exists(flags.Output)) { Directory.CreateDirectory(flags.Output); } File.Copy(path, Path.Combine(flags.Output, Path.GetFileName(path)), true); } } } Console.WriteLine(); } }