/// <summary> /// Initializes a new instance of the <see cref="ExtractedResourceInfo" /> class. /// </summary> /// <param name="baseResource">The <see cref="Resource" /> to initialize the instance with.</param> public ExtractedResourceInfo(Resource baseResource) { OriginalIndex = baseResource.Index; Flags = baseResource.Flags; Type = baseResource.Type; Info = baseResource.Info; OriginalParentTagIndex = (baseResource.ParentTag != null) ? baseResource.ParentTag.Index : DatumIndex.Null; Location = (baseResource.Location != null) ? new ExtractedResourcePointer(baseResource.Location) : null; ResourceFixups = new List<ResourceFixup>(baseResource.ResourceFixups); DefinitionFixups = new List<ResourceDefinitionFixup>(baseResource.DefinitionFixups); Unknown1 = baseResource.Unknown1; Unknown2 = baseResource.Unknown2; Unknown3 = baseResource.Unknown3; }
public DatumIndex InjectResource(ExtractedResourceInfo resource, IStream stream) { if (_resources == null) return DatumIndex.Null; if (resource == null) throw new ArgumentNullException("resource is null"); // Don't inject the resource if it's already been injected DatumIndex newIndex; if (_resourceIndices.TryGetValue(resource, out newIndex)) return newIndex; // Create a new datum index for it (0x4152 = 'AR') and associate it LoadResourceTable(stream); newIndex = new DatumIndex(0x4152, (ushort) _resources.Resources.Count); _resourceIndices[resource] = newIndex; // Create a native resource for it var newResource = new Resource(); _resources.Resources.Add(newResource); newResource.Index = newIndex; newResource.Flags = resource.Flags; newResource.Type = resource.Type; newResource.Info = resource.Info; if (resource.OriginalParentTagIndex.IsValid) { DatumIndex parentTagIndex = InjectTag(resource.OriginalParentTagIndex, stream); newResource.ParentTag = _cacheFile.Tags[parentTagIndex]; } if (resource.Location != null) { newResource.Location = new ResourcePointer(); // Primary page pointers if (resource.Location.OriginalPrimaryPageIndex >= 0) { int primaryPageIndex = InjectResourcePage(resource.Location.OriginalPrimaryPageIndex, stream); newResource.Location.PrimaryPage = _resources.Pages[primaryPageIndex]; } newResource.Location.PrimaryOffset = resource.Location.PrimaryOffset; newResource.Location.PrimaryUnknown = resource.Location.PrimaryUnknown; // Secondary page pointers if (resource.Location.OriginalSecondaryPageIndex >= 0) { int secondaryPageIndex = InjectResourcePage(resource.Location.OriginalSecondaryPageIndex, stream); newResource.Location.SecondaryPage = _resources.Pages[secondaryPageIndex]; } newResource.Location.SecondaryOffset = resource.Location.SecondaryOffset; newResource.Location.SecondaryUnknown = resource.Location.SecondaryUnknown; } newResource.ResourceFixups.AddRange(resource.ResourceFixups); newResource.DefinitionFixups.AddRange(resource.DefinitionFixups); newResource.Unknown1 = resource.Unknown1; newResource.Unknown2 = resource.Unknown2; newResource.Unknown3 = resource.Unknown3; // Make it load LoadZoneSets(stream); if (_zoneSets != null && _zoneSets.GlobalZoneSet != null) _zoneSets.GlobalZoneSet.ActivateResource(newResource, true); return newIndex; }
/// <summary> /// Determines whether or not a resource is marked as active. /// </summary> /// <param name="index">The resource to check.</param> /// <returns><c>true</c> if the resource is active, <c>false</c> otherwise.</returns> public bool IsResourceActive(Resource resource) { if (resource == null) return false; return IsResourceActive(resource.Index); }
/// <summary> /// Activates or deactivates a resource in the zone set. /// </summary> /// <param name="resource">The resource to activate or deactivate.</param> /// <param name="activate"><c>true</c> if the resource should be made active, <c>false</c> otherwise.</param> public void ActivateResource(Resource resource, bool activate) { if (resource != null) ActivateResource(resource.Index, activate); }
private StructureValueCollection SerializeResource(Resource resource, int pointerIndex, int infoOffset, IStream stream) { var result = new StructureValueCollection(); if (resource.ParentTag != null) { result.SetInteger("parent tag class magic", (uint) resource.ParentTag.Class.Magic); result.SetInteger("parent tag datum index", resource.ParentTag.Index.Value); } else { result.SetInteger("parent tag class magic", 0xFFFFFFFF); result.SetInteger("parent tag datum index", 0xFFFFFFFF); } result.SetInteger("datum index salt", resource.Index.Salt); result.SetInteger("resource type index", (uint) FindResourceType(resource.Type)); result.SetInteger("flags", resource.Flags); result.SetInteger("resource info offset", (uint) infoOffset); result.SetInteger("resource info size", (resource.Info != null) ? (uint) resource.Info.Length : 0); result.SetInteger("unknown 1", (uint) resource.Unknown1); result.SetInteger("unknown 2", (uint) resource.Unknown2); result.SetInteger("segment index", (uint) pointerIndex); result.SetInteger("unknown 3", (uint) resource.Unknown3); return result; }
private Resource LoadResource(StructureValueCollection values, int index, TagTable tags, IList<ResourcePointer> pointers, byte[] infoBuffer, IReader reader) { var result = new Resource(); var parentTag = new DatumIndex(values.GetInteger("parent tag datum index")); result.ParentTag = parentTag.IsValid ? tags[parentTag] : null; var salt = (ushort) values.GetInteger("datum index salt"); result.Index = new DatumIndex(salt, (ushort) index); var typeIndex = (int) values.GetInteger("resource type index"); if (typeIndex >= 0 && typeIndex < _resourceTypes.Length) result.Type = _resourceTypes[typeIndex].Name; result.Flags = values.GetInteger("flags"); var infoOffset = (int) values.GetInteger("resource info offset"); var infoSize = (int) values.GetInteger("resource info size"); if (infoSize > 0) { // Copy the section of the info buffer that the resource is pointing to result.Info = new byte[infoSize]; Buffer.BlockCopy(infoBuffer, infoOffset, result.Info, 0, infoSize); } result.Unknown1 = (int) values.GetInteger("unknown 1"); result.Unknown2 = (int) values.GetInteger("unknown 2"); var segmentIndex = (int) values.GetInteger("segment index"); result.Location = (segmentIndex >= 0) ? pointers[segmentIndex] : null; result.Unknown3 = (int) values.GetInteger("unknown 3"); result.ResourceFixups.AddRange(LoadResourceFixups(values, reader)); result.DefinitionFixups.AddRange(LoadDefinitionFixups(values, reader)); return result; }
private int AlignInfoBlockOffset(Resource resource, int offset) { if ((resource.Flags & 4) != 0) // hax return (offset + 0xF) & ~0xF; return offset; }
/// <summary> /// Initializes a new instance of the <see cref="ExtractedResourceInfo" /> class. /// </summary> /// <param name="originalIndex">The original datum index of the resource.</param> /// <param name="baseResource">The <see cref="Resource" /> to initialize the instance with.</param> public ExtractedResourceInfo(DatumIndex originalIndex, Resource baseResource) { if (originalIndex.Index != baseResource.Index.Index) throw new InvalidOperationException("originalIndex.Index != baseResource.Index.Index"); OriginalIndex = originalIndex; Flags = baseResource.Flags; Type = baseResource.Type; Info = baseResource.Info; OriginalParentTagIndex = (baseResource.ParentTag != null) ? baseResource.ParentTag.Index : DatumIndex.Null; Location = (baseResource.Location != null) ? new ExtractedResourcePointer(baseResource.Location) : null; ResourceFixups = new List<ResourceFixup>(baseResource.ResourceFixups); DefinitionFixups = new List<ResourceDefinitionFixup>(baseResource.DefinitionFixups); Unknown1 = baseResource.Unknown1; Unknown2 = baseResource.Unknown2; Unknown3 = baseResource.Unknown3; }