/// <summary> /// Write a key region. /// </summary> /// <param name="k">Key region.</param> /// <param name="a">Sound archive.</param> /// <param name="b">Bank entry.</param> /// <param name="start">Starting note.</param> /// <param name="end">Ending note.</param> /// <param name="x">The writer.</param> public static void WriteKeyRegion(IKeyRegion k, SoundArchive a, BankEntry b, int start, int end, XmlTextWriter x) { //Key region. x.WriteStartElement("KeyRegion"); //Parameters. StartUselessParameters(x); x.WriteElementString("KeyMin", start + ""); x.WriteElementString("KeyMax", end + ""); EndUselessParameters(x); //Items. x.WriteStartElement("Items"); //Write velocity regions. switch (k.GetKeyRegionType()) { //Direct. case KeyRegionType.Direct: var d = k as DirectKeyRegion; WriteVelocityRegion(d.VelocityRegion, a, b, 0, 127, x); break; //Index. case KeyRegionType.Index: var ind = k as IndexKeyRegion; int last = 0; foreach (var v in ind) { if (v.Value != null) { WriteVelocityRegion(v.Value, a, b, last, v.Key, x); } last = v.Key + 1; } break; //Range. case KeyRegionType.Range: var r = k as RangeKeyRegion; int next = 0; foreach (var v in r) { if (v != null) { WriteVelocityRegion(v, a, b, next, next, x); } next++; } break; } //End items. x.WriteEndElement(); //End key region. x.WriteEndElement(); }
/// <summary> /// Create a new instrument range. /// </summary> /// <param name="startNote">Starting note.</param> /// <param name="endNote">Ending note.</param> /// <param name="keyRegion">Key region.</param> public KeyRegionRange(sbyte startNote, sbyte endNote, IKeyRegion keyRegion) { StartNote = startNote; EndNote = endNote; KeyRegion = keyRegion; }
/// <summary> /// Write a key region. /// </summary> /// <param name="bw">The writer.</param> /// <param name="key">Key region.</param> public void WriteKeyRegion(BinaryDataWriter bw, IKeyRegion key, FileWriter FileWriter) { //Instrument is a new structure. FileWriter.StartStructure(bw); //Key region type reference. FileWriter.InitReference(bw, "VelType"); //Get the type of reference. switch (key.GetKeyRegionType()) { //Direct. case KeyRegionType.Direct: FileWriter.CloseReference(bw, ReferenceTypes.BNK_RefTable_Direct, "VelType"); break; //Index. case KeyRegionType.Index: FileWriter.CloseReference(bw, ReferenceTypes.BNK_RefTable_Index, "VelType"); break; //Range. case KeyRegionType.Range: FileWriter.CloseReference(bw, ReferenceTypes.BNK_RefTable_Range, "VelType"); break; } //Key region is a new structure. FileWriter.StartStructure(bw); //Switch the type of reference. switch (key.GetKeyRegionType()) { //Direct. case KeyRegionType.Direct: //Direct. DirectKeyRegion d = (DirectKeyRegion)key; //Write velocity region reference. FileWriter.InitReference(bw, "VelRegion"); //Null region. if (d.VelocityRegion == null) { FileWriter.CloseNullReference(bw, "VelRegion"); } //Not null. else { //Close the reference. FileWriter.CloseReference(bw, ReferenceTypes.BNK_Info_VelocityRegion, "VelRegion"); //Write velocity region. WriteVelocityInfo(bw, d.VelocityRegion); } break; //Ranged. case KeyRegionType.Range: //Set range info. RangeKeyRegion ran = (RangeKeyRegion)key; //Write stuff. bw.Write((byte)ran.StartVelocity); bw.Write((byte)ran.EndVelocity); bw.Write((UInt16)0); //Init each reference. for (int j = 0; j < ran.VelocityCount; j++) { FileWriter.InitReference(bw, "RanKey" + j); } //Write each key region. for (int j = 0; j < ran.VelocityCount; j++) { //Null region. if (ran[j] == null) { FileWriter.CloseNullReference(bw, "RanKey" + j); } //Write key region. else { //Velocity region reference. FileWriter.CloseReference(bw, ReferenceTypes.BNK_Info_VelocityRegion, "RanKey" + j); //Write the velocity region. WriteVelocityInfo(bw, ran[j]); } } break; //Index. case KeyRegionType.Index: //Set index info. IndexKeyRegion ind = (IndexKeyRegion)key; //Write the table of indices. bw.Write((uint)ind.Count); for (int j = 0; j < ind.Count; j++) { bw.Write((byte)ind.Keys.ElementAt(j)); } //Write padding. FileWriter.Align(bw, 4); //Init each index reference. for (int j = 0; j < ind.Count; j++) { FileWriter.InitReference(bw, "IndKey" + j); } //Write each index. for (int j = 0; j < ind.Count; j++) { //Null index. if (ind.Values.ElementAt(j) == null) { FileWriter.CloseNullReference(bw, "IndKey" + j); } //Index exist. else { //Close reference. FileWriter.CloseReference(bw, ReferenceTypes.BNK_Info_VelocityRegion, "IndKey" + j); //Write the velocity region. WriteVelocityInfo(bw, ind.Values.ElementAt(j)); } } break; } //End the key region. FileWriter.EndStructure(); //End the key region structure. FileWriter.EndStructure(); }
/// <summary> /// Return a key region. /// </summary> /// <param name="br">The reader.</param> /// <returns>A key region.</returns> public IKeyRegion ReadKeyRegion(BinaryDataReader br, FileReader FileReader) { //Key region is a structure. FileReader.StartStructure(br); //Set up key region. IKeyRegion keyRegion = null; //Get reference to the velocity type. FileReader.OpenReference(br, "KeyTypeRef"); //Reference is not null. if (!FileReader.ReferenceIsNull("KeyTypeRef")) { //Jump to the reference. FileReader.JumpToReference(br, "KeyTypeRef"); //It's a new structure. FileReader.StartStructure(br); //Switch reference type. switch (FileReader.ReferenceGetType("KeyTypeRef")) { //Direct. case ReferenceTypes.BNK_RefTable_Direct: //New direct key region. DirectKeyRegion dir = new DirectKeyRegion(); //Open reference to velocity region. FileReader.OpenReference(br, "VelRegion"); //Not null velocity region. if (!FileReader.ReferenceIsNull("VelRegion")) { //Jump to the velocity region. FileReader.JumpToReference(br, "VelRegion"); //Open the velocity region. dir.VelocityRegion = ReadVelocityInfo(br, FileReader); } //Close reference to velocity region. FileReader.CloseReference("VelRegion"); //Set the key region. keyRegion = dir; break; //Range. case ReferenceTypes.BNK_RefTable_Range: //New ranged instrument. RangeKeyRegion ran = new RangeKeyRegion(); //Get count. ran.StartVelocity = br.ReadByte(); ran.EndVelocity = br.ReadByte(); br.ReadUInt16(); //Read each reference. for (int j = 0; j < ran.VelocityCount; j++) { FileReader.OpenReference(br, "RanKey" + j); } //Read each key region. for (int j = 0; j < ran.VelocityCount; j++) { //Null region. if (FileReader.ReferenceIsNull("RanKey" + j)) { ran.Add(null); } //Read key region. else { //Jump to reference. FileReader.JumpToReference(br, "RanKey" + j); //Read the velocity region. ran.Add(ReadVelocityInfo(br, FileReader)); } } //Close each reference. for (int j = 0; j < ran.VelocityCount; j++) { FileReader.CloseReference("RanKey" + j); } //Set the key region to this. keyRegion = ran; break; //Index. case ReferenceTypes.BNK_RefTable_Index: //Read the table of indices. uint numInd = br.ReadUInt32(); List <byte> indices = new List <byte>(); for (int j = 0; j < numInd; j++) { indices.Add(br.ReadByte()); } //Read padding. FileReader.SeekAlign(br, 4); //New index key region. IndexKeyRegion ind = new IndexKeyRegion(); //Read each index reference. for (int j = 0; j < numInd; j++) { FileReader.OpenReference(br, "IndKey" + j); } //Read each index. for (int j = 0; j < numInd; j++) { //Null index. if (FileReader.ReferenceIsNull("IndKey" + j)) { ind.Add((sbyte)indices[j], null); } //Index exist. else { //Jump to reference. FileReader.JumpToReference(br, "IndKey" + j); //Read the velocity region. ind.Add((sbyte)indices[j], ReadVelocityInfo(br, FileReader)); } } //Close each index reference. for (int j = 0; j < numInd; j++) { FileReader.CloseReference("IndKey" + j); } //Set the key region to this. keyRegion = ind; break; } //End the vel type stuff. FileReader.EndStructure(); } //Close reference to velocity type. FileReader.CloseReference("KeyTypeRef"); //End the velocity region. FileReader.EndStructure(); //Return the velocity region. return(keyRegion); }