Exemplo n.º 1
0
        public static BCMFile FromUassetFile(string fileName)
        {
            byte[] fileBytes = File.ReadAllBytes(fileName);

            byte[] UassetHeaderBytes = Common.GetUassetHeader(fileBytes);
            fileBytes = Common.RemoveUassetHeader(fileBytes);

            List <Move>       MoveList    = new List <Move>();
            List <CancelList> CancelLists = new List <CancelList>();
            List <Input>      InputList   = new List <Input>();
            List <Charge>     ChargeList  = new List <Charge>();

            Debug.WriteLine("READING");
            using (var ms = new MemoryStream(fileBytes))
                using (var inFile = new BinaryReader(ms))
                {
                    string bcmString = new string(inFile.ReadChars(4));

                    if (bcmString != "#BCM")
                    {
                        throw new Exception("Error: Not a valid KWBCM file!");
                    }

                    Debug.WriteLine(bcmString);

                    inFile.BaseStream.Seek(0xA, SeekOrigin.Begin);
                    short BCMVER = inFile.ReadInt16();
                    Debug.WriteLine("BCMVER: " + BCMVER);
                    short ChargeCount = inFile.ReadInt16();
                    Debug.WriteLine("ChargeCount: " + ChargeCount);
                    short InputCount = inFile.ReadInt16();
                    Debug.WriteLine("InputCount: " + InputCount);
                    short MoveCount = inFile.ReadInt16();
                    Debug.WriteLine("Movecount: " + MoveCount);
                    short CancelCount = inFile.ReadInt16(); //last cancel index
                    Debug.WriteLine("Cancelcount: " + CancelCount);

                    int startOfCharges     = inFile.ReadInt32();
                    int startOfInputs      = inFile.ReadInt32();
                    int startOfMoves       = inFile.ReadInt32();
                    int startOfNames       = inFile.ReadInt32();
                    int startOfCancelLists = inFile.ReadInt32();
                    Debug.WriteLine("StartOfCharges: " + startOfCharges);
                    Debug.WriteLine("StartOfInputs: " + startOfInputs);

                    Debug.WriteLine("StartOfMoves: " + startOfMoves);
                    Debug.WriteLine("StartOfNames: " + startOfNames);

                    Debug.WriteLine("StartOfCancelLists: " + startOfCancelLists);

                    Debug.WriteLine("Current pos: " + inFile.BaseStream.Position.ToString("X"));
                    Debug.WriteLine("\n\n");

                    inFile.BaseStream.Seek(startOfCharges, SeekOrigin.Begin);

                    List <int> ChargeAddresses = new List <int>();

                    for (int i = 0; i < ChargeCount; i++)
                    {
                        ChargeAddresses.Add(inFile.ReadInt32());
                    }

                    for (int i = 0; i < ChargeAddresses.Count; i++)
                    {
                        Charge thisCharge        = new Charge();
                        int    thisChargeAddress = ChargeAddresses[i];
                        inFile.BaseStream.Seek(thisChargeAddress, SeekOrigin.Begin);
                        Debug.WriteLine("ChargeAddress: " + thisChargeAddress.ToString("X"));

                        thisCharge.ChargeDirection = inFile.ReadInt16();
                        thisCharge.Unknown1        = inFile.ReadInt16();
                        thisCharge.Unknown2        = inFile.ReadInt16();
                        thisCharge.Unknown3        = inFile.ReadInt16();
                        thisCharge.ChargeFrames    = inFile.ReadInt16();
                        thisCharge.Flags           = inFile.ReadInt16();
                        thisCharge.ChargeIndex     = inFile.ReadInt16();
                        thisCharge.Unknown4        = inFile.ReadInt16();

                        thisCharge.Index = i;
                        ChargeList.Add(thisCharge);
                    }

                    inFile.BaseStream.Seek(startOfInputs, SeekOrigin.Begin);

                    List <int> InputAddresses = new List <int>();

                    for (int i = 0; i < InputCount; i++)
                    {
                        InputAddresses.Add(inFile.ReadInt32());
                    }

                    for (int i = 0; i < InputAddresses.Count; i++)
                    {
                        Input thisInput        = new Input();
                        int   thisInputAddress = InputAddresses[i];
                        inFile.BaseStream.Seek(thisInputAddress, SeekOrigin.Begin);
                        Debug.WriteLine("InputAddress: " + thisInputAddress.ToString("X"));

                        List <int> moveEntryOffsets = new List <int>();

                        moveEntryOffsets.Add(inFile.ReadInt32());
                        moveEntryOffsets.Add(inFile.ReadInt32());
                        moveEntryOffsets.Add(inFile.ReadInt32());
                        moveEntryOffsets.Add(inFile.ReadInt32());

                        var entries = new List <InputEntry>();

                        foreach (var entryOffset in moveEntryOffsets)
                        {
                            if (entryOffset == 0)
                            {
                                entries.Add(new InputEntry());
                                continue;
                            }

                            inFile.BaseStream.Seek(entryOffset + thisInputAddress, SeekOrigin.Begin);
                            var partCount = inFile.ReadInt32();

                            InputEntry       thisInputEntry = new InputEntry();
                            List <InputPart> parts          = new List <InputPart>();

                            for (int j = 0; j < partCount; j++)
                            {
                                InputPart thisPart = new InputPart()
                                {
                                    InputType      = (InputType)inFile.ReadInt16(),
                                    Buffer         = inFile.ReadInt16(),
                                    InputDirection = (InputDirection)inFile.ReadInt16(),
                                    Unknown1       = inFile.ReadInt16(),
                                    Unknown2       = inFile.ReadInt16(),
                                    Unknown3       = inFile.ReadInt16(),
                                    Unknown4       = inFile.ReadInt16(),
                                    Unknown5       = inFile.ReadInt16(),
                                };

                                parts.Add(thisPart);
                            }

                            for (int j = 0; j < 16 - partCount; j++) //There can be up to 16 parts, but even if they are empty they are still there, only filled with 0x00
                            {
                                var unused = inFile.ReadBytes(16);
                                foreach (var b in unused)
                                {
                                    if (b != 0)
                                    {
                                        Debug.WriteLine("Read unexpected byte in what was thought to be an empty part of an input.");
                                    }
                                }
                            }

                            thisInputEntry.InputParts = parts.ToArray();
                            entries.Add(thisInputEntry);
                        }

                        thisInput.InputEntries = entries.ToArray();

                        thisInput.Index = i;
                        InputList.Add(thisInput);
                        Debug.WriteLine("Created input with index: " + i);
                    }

                    for (int i = 0; i < MoveCount * 4; i += 0x4)
                    {
                        long thisMovePosition = startOfMoves + i;
                        long thisNamePosition = startOfNames + i;

                        inFile.BaseStream.Seek(thisNamePosition, SeekOrigin.Begin);
                        int    NameAddress = inFile.ReadInt32();
                        string Name        = GetName(NameAddress, inFile);

                        inFile.BaseStream.Seek(thisMovePosition, SeekOrigin.Begin);
                        int offset = inFile.ReadInt32();
                        Debug.WriteLine("Adding move at: " + offset.ToString("X"));

                        inFile.BaseStream.Seek(offset, SeekOrigin.Begin);

                        short input            = inFile.ReadInt16();
                        short inputFlags       = inFile.ReadInt16();
                        int   restrict         = inFile.ReadInt32();
                        int   restrict2        = inFile.ReadInt32();
                        float restrictDistance = inFile.ReadSingle();
                        int   unknown4         = (BCMVER > 0) ? inFile.ReadInt32() : 0;
                        // CHANGED: split projectileRestrict into 2 16bit properties.
                        var   projectileGroup    = inFile.ReadInt16();
                        var   projectileMaxCount = inFile.ReadInt16();
                        int   unknown6           = inFile.ReadInt16();
                        int   unknown7           = inFile.ReadInt16();
                        short unknown8           = inFile.ReadInt16();
                        short unknown9           = inFile.ReadInt16();

                        short MeterRequirement    = inFile.ReadInt16();
                        short MeterUsed           = inFile.ReadInt16();
                        short unknown10           = inFile.ReadInt16();
                        short unknown11           = inFile.ReadInt16();
                        int   VtriggerRequirement = inFile.ReadInt16();
                        int   VtriggerUsed        = inFile.ReadInt16();
                        int   Unknown16           = inFile.ReadInt32();
                        int   InputMotionIndex    = inFile.ReadInt16();
                        int   ScriptIndex         = inFile.ReadInt16();

                        Move thisMove = new Move()
                        {
                            Name                = Name,
                            Index               = (short)(i == 0 ? 0 : (i / 4)),
                            Input               = input,
                            InputFlags          = inputFlags,
                            PositionRestriction = restrict,
                            Unknown3            = restrict2,
                            RestrictionDistance = restrictDistance,
                            Unknown4            = unknown4,
                            ProjectileGroup     = projectileGroup,
                            ProjectileMaxCount  = projectileMaxCount,
                            Unknown6            = (short)unknown6,
                            Unknown7            = (short)unknown7,
                            Unknown8            = unknown8,
                            Unknown9            = unknown9,
                            Unknown10           = unknown10,
                            Unknown11           = unknown11,
                            MeterRequirement    = (short)MeterRequirement,
                            MeterUsed           = (short)MeterUsed,
                            VtriggerRequirement = (short)VtriggerRequirement,
                            VtriggerUsed        = (short)VtriggerUsed,
                            Unknown16           = Unknown16,
                            InputMotionIndex    = (short)InputMotionIndex,
                            ScriptIndex         = (short)ScriptIndex,
                            Unknown17           = inFile.ReadInt32(),
                            Unknown18           = inFile.ReadInt32(),
                            Unknown19           = (BCMVER == 0) ? inFile.ReadInt32() : 0,
                            Unknown20           = inFile.ReadSingle(),
                            Unknown21           = inFile.ReadSingle(),
                            Unknown22           = inFile.ReadInt32(),
                            Unknown23           = inFile.ReadInt32(),
                            Unknown24           = inFile.ReadInt32(),
                            Unknown25           = inFile.ReadInt32(),
                            Unknown26           = inFile.ReadInt16(),
                            NormalOrVtrigger    = inFile.ReadInt16(),
                            Unknown28           = inFile.ReadInt32()
                        };

                        if (thisMove.InputMotionIndex != -1) //Just for debugging...
                        {
                            InputList.Where(x => x.Index == thisMove.InputMotionIndex).ToList()[0].Name += thisMove.Name + ", ";
                        }

                        MoveList.Add(thisMove);

                        Debug.WriteLine("MOVE: " + "Index: " + (i == 0 ? 0 : (i / 4)) +
                                        "\nName: " + Name +
                                        "\nOffset: " + offset.ToString("X") +
                                        "\nNameOffet: " + NameAddress.ToString("X") +
                                        "\nInput: " + input +
                                        "\nflags: " + inputFlags
                                        + "\nRestrict: " + restrict
                                        + "\nRestrict2: " + restrict2
                                        + "\nRestrictDistance: " + restrictDistance
                                        + "\nUnknown4: " + unknown4
                                        + "\nProjectileGroup: " + projectileGroup
                                        + "\nProjectileMaxCount: " + projectileMaxCount
                                        + "\nUnknown6: " + unknown6
                                        + "\nUnknown7: " + unknown7
                                        + "\nUnknown8: " + unknown8
                                        + "\nUnknown9: " + unknown9
                                        + "\nUnknown10: " + unknown10
                                        + "\nUnknown11: " + unknown11
                                        + "\nMeterReq: " + MeterRequirement
                                        + "\nMeterUsed: " + MeterUsed
                                        + "\nVtriggerReq: " + VtriggerRequirement
                                        + "\nVtriggerUsed: " + VtriggerUsed
                                        + "\nUnknown16: " + Unknown16
                                        + "\nInputMotionIndex: " + InputMotionIndex
                                        + "\nScriptIndex: " + ScriptIndex
                                        + "\nUnknown17: " + thisMove.Unknown17
                                        + "\nUnknown18: " + thisMove.Unknown18
                                        + "\nUnknown19: " + thisMove.Unknown19
                                        + "\nUnknown20: " + thisMove.Unknown20
                                        + "\nUnknown21: " + thisMove.Unknown21
                                        + "\nUnknown22: " + thisMove.Unknown22
                                        + "\nUnknown23: " + thisMove.Unknown23
                                        + "\nUnknown24: " + thisMove.Unknown24
                                        + "\nUnknown25: " + thisMove.Unknown25
                                        + "\nUnknown26: " + thisMove.Unknown26
                                        + "\nUnknown27: " + thisMove.NormalOrVtrigger
                                        + "\nUnknown28: " + thisMove.Unknown28
                                        + "\n\n");
                    }

                    inFile.BaseStream.Seek(startOfCancelLists, SeekOrigin.Begin);
                    List <int> CancelAddresses = new List <int>();
                    for (int i = 0; i < CancelCount; i++)
                    {
                        int thisCancelAddress = inFile.ReadInt32();
                        Debug.WriteLine("Cancel " + (i) + ": " + thisCancelAddress.ToString("X"));
                        CancelAddresses.Add(thisCancelAddress);
                    }

                    for (int i = 0; i < CancelAddresses.Count; i++)
                    {
                        CancelList thisCancelList = new CancelList();
                        int        thisAddress    = CancelAddresses[i];

                        if (thisAddress == 0)
                        {
                            CancelLists.Add(thisCancelList);
                            continue;
                        }

                        inFile.BaseStream.Seek(thisAddress, SeekOrigin.Begin);

                        thisCancelList.Unknown1 = inFile.ReadInt32();
                        int MovesInList        = inFile.ReadInt32();
                        int LastIndex          = inFile.ReadInt32(); //last move index in list -1...
                        int StartOffset        = inFile.ReadInt32(); //offset until real list FROM START OF CANCEL!!!
                        int StartOfCancelInts  = inFile.ReadInt32();
                        int StartOfCancelBytes = inFile.ReadInt32();

                        Debug.WriteLine("ThisCancelAddress: " + thisAddress.ToString("X"));
                        Debug.WriteLine($"Cancel {i}:\nCU1: {thisCancelList.Unknown1}\nMovesInList: {MovesInList}\nNumberOfSomethingInList: {LastIndex}\nStartOffset: {StartOffset.ToString("X")}\nCU5: {StartOfCancelInts.ToString("X")}\nEndOffset: {StartOfCancelBytes.ToString("X")}\n");

                        inFile.BaseStream.Seek(thisAddress + StartOffset, SeekOrigin.Begin);
                        Debug.WriteLine("ListAddress: " + (thisAddress + StartOffset).ToString("X"));
                        Debug.WriteLine("ListAddressEnd: " + (thisAddress + StartOfCancelBytes).ToString("X"));

                        List <Cancel> cancels = new List <Cancel>();
                        thisCancelList.Index = i;

                        for (int j = 0; j < MovesInList; j++)
                        {
                            int thisMoveInList = inFile.ReadInt16();
                            Debug.WriteLine("Move: " + thisMoveInList);

                            Move cancelMove = MoveList.Where(x => x.Index == thisMoveInList).ToList()[0];

                            Cancel thisCancel = new Cancel();
                            thisCancel.Index       = (short)thisMoveInList;
                            thisCancel.Name        = cancelMove.Name;
                            thisCancel.ScriptIndex = cancelMove.ScriptIndex;

                            cancels.Add(thisCancel);
                        }

                        thisCancelList.Cancels = cancels.ToArray();

                        //All lists should have Moves divisible by 2. If it doesn't, simply add an empty one (0x00, 0x00)
                        if (MovesInList % 2 != 0)
                        {
                            Debug.WriteLine("READING EMPTY MOVE");
                            inFile.ReadInt16();
                        }

                        if (StartOfCancelInts != 0)
                        {
                            Debug.WriteLine("We got something!!!" + inFile.BaseStream.Position.ToString("X") + " - Should be: " + (thisAddress + StartOfCancelInts).ToString("X"));
                            Debug.WriteLine(((thisAddress + StartOfCancelBytes) - (thisAddress + StartOfCancelInts)) / MovesInList);

                            for (int j = 0; j < MovesInList; j++)
                            {
                                int value1 = inFile.ReadInt32();
                                int value2 = inFile.ReadInt32();

                                thisCancelList.Cancels[j].CancelInts = new CancelInts()
                                {
                                    Unknown1 = value1,
                                    Unknown2 = value2
                                };
                            }
                        }

                        Debug.WriteLine("Position is " + inFile.BaseStream.Position.ToString("X") + " - Should be: " + (thisAddress + StartOfCancelBytes).ToString("X"));

                        if (inFile.BaseStream.Position != thisAddress + StartOfCancelBytes) //NOT a good idea
                        {
                            Debug.WriteLine("We are not where we're supposed to be, reading bytes until we are...");

                            while (inFile.BaseStream.Position != thisAddress + StartOfCancelBytes)
                            {
                                Debug.WriteLine(inFile.ReadByte());
                            }

                            Debug.WriteLine("Position is " + inFile.BaseStream.Position.ToString("X") + " - Should be: " + (thisAddress + StartOfCancelBytes).ToString("X"));
                        }

                        for (int j = 0; j < LastIndex; j++)
                        {
                            inFile.BaseStream.Seek((thisAddress + StartOfCancelBytes) + (j * 4), SeekOrigin.Begin);

                            var offset = inFile.ReadInt32();

                            if (offset == 0)
                            {
                                continue;
                            }

                            Debug.WriteLine("SomethingElseInCancelList(offsets?): " + offset.ToString("X") + " Pos: " + (inFile.BaseStream.Position - 4).ToString("X") + " - Index: " + j + "  added offset:" + (offset + thisAddress).ToString("X"));

                            var address = offset + thisAddress;

                            inFile.BaseStream.Seek(address, SeekOrigin.Begin);

                            var cancelBytesBelongsTo = thisCancelList.Cancels.First(x => x.Index == j);

                            var unkBytes = inFile.ReadBytes(0x24);

                            cancelBytesBelongsTo.UnknownBytes = unkBytes;
                        }

                        CancelLists.Add(thisCancelList);
                        Debug.WriteLine("\n");
                    }

                    try
                    {
                        foreach (var cancelList in CancelLists)
                        {
                            if (cancelList?.Cancels == null)
                            {
                                continue;
                            }

                            Debug.WriteLine($"\nCancelList Index: {cancelList.Index}\n");

                            foreach (var cancel in cancelList.Cancels)
                            {
                                if (cancel == null)
                                {
                                    continue;
                                }

                                Debug.WriteLine("Cancel: " + cancel.Index + " ScriptIndex:" + cancel.ScriptIndex);

                                foreach (var unknownByte in cancel.UnknownBytes)
                                {
                                    Debug.Write(unknownByte.ToString("X") + " ");
                                }

                                Debug.WriteLine("");
                            }
                        }
                    }
                    catch (Exception)
                    {
                        Debug.WriteLine("Are the Cancel indices of the CancelList in order?");
                    }

                    Debug.WriteLine("\nCharges\n");

                    foreach (var charge in ChargeList)
                    {
                        Debug.WriteLine("CHARGE: " + charge.Index);
                        Debug.WriteLine("Dir: " + charge.ChargeDirection);
                        Debug.WriteLine("u1: " + charge.Unknown1);
                        Debug.WriteLine("u2: " + charge.Unknown2);
                        Debug.WriteLine("u3: " + charge.Unknown3);
                        Debug.WriteLine("ChargeFrames: " + charge.ChargeFrames);
                        Debug.WriteLine("Flags: " + charge.Flags);
                        Debug.WriteLine("CINDEX: " + charge.ChargeIndex);
                        Debug.WriteLine("u4: " + charge.Unknown4);
                        Debug.WriteLine("\n");
                    }

                    foreach (var input in InputList)
                    {
                        Debug.WriteLine("Input: " + input.Index);
                        Debug.WriteLine("Name: " + input.Name);
                        Debug.WriteLine("Entries: " + input.InputEntries.Length);

                        WriteInputToDebug(input);

                        Debug.WriteLine("\n");
                    }
                }

            Debug.WriteLine("Done");

            BCMFile bcm = new BCMFile()
            {
                Inputs      = InputList.ToArray(),
                CancelLists = CancelLists.ToArray(),
                Charges     = ChargeList.ToArray(),
                Moves       = MoveList.ToArray(),
                RawUassetHeaderDontTouch = UassetHeaderBytes
            };

            return(bcm);
        }
Exemplo n.º 2
0
        public static BCMFile FromUassetFile(string fileName)
        {
            byte[] fileBytes = File.ReadAllBytes(fileName);

            byte[] UassetHeaderBytes = GetUassetHeader(fileBytes);
            fileBytes = CreateGameBCMFromFile(fileBytes);

               List<Move> MoveList = new List<Move>();
               List<CancelList> CancelLists = new List<CancelList>();
               List<Input> InputList = new List<Input>();
               List<Charge> ChargeList = new List<Charge>();

            Debug.WriteLine("READING");
            using (var ms = new MemoryStream(fileBytes))
            using (var inFile = new BinaryReader(ms))
            {
                string bcmString = new string(inFile.ReadChars(4));

                if (bcmString != "#BCM")
                {
                    throw new Exception("Error: Not a valid KWBCM file!");
                }

                Debug.WriteLine(bcmString);

                inFile.BaseStream.Seek(0xC, SeekOrigin.Begin);

                short ChargeCount = inFile.ReadInt16();
                Debug.WriteLine("ChargeCount: " + ChargeCount);
                short InputCount = inFile.ReadInt16();
                Debug.WriteLine("InputCount: " + InputCount);
                short MoveCount = inFile.ReadInt16();
                Debug.WriteLine("Movecount: " + MoveCount);
                short CancelCount = inFile.ReadInt16(); //last cancel index
                Debug.WriteLine("Cancelcount: " + CancelCount);

                int startOfCharges = inFile.ReadInt32();
                int startOfInputs = inFile.ReadInt32();
                int startOfMoves = inFile.ReadInt32();
                int startOfNames = inFile.ReadInt32();
                int startOfCancelLists = inFile.ReadInt32();
                Debug.WriteLine("StartOfCharges: " + startOfCharges);
                Debug.WriteLine("StartOfInputs: " + startOfInputs);

                Debug.WriteLine("StartOfMoves: " + startOfMoves);
                Debug.WriteLine("StartOfNames: " + startOfNames);

                Debug.WriteLine("StartOfCancelLists: " + startOfCancelLists);

                Debug.WriteLine("Current pos: " + inFile.BaseStream.Position.ToString("X"));
                Debug.WriteLine("\n\n");

                inFile.BaseStream.Seek(startOfCharges, SeekOrigin.Begin);

                List<int> ChargeAddresses = new List<int>();

                for (int i = 0; i < ChargeCount; i++)
                {
                    ChargeAddresses.Add(inFile.ReadInt32());
                }

                for (int i = 0; i < ChargeAddresses.Count; i++)
                {
                    Charge thisCharge = new Charge();
                    int thisChargeAddress = ChargeAddresses[i];
                    inFile.BaseStream.Seek(thisChargeAddress, SeekOrigin.Begin);
                    Debug.WriteLine("ChargeAddress: " + thisChargeAddress.ToString("X"));

                    thisCharge.ChargeDirection = inFile.ReadInt16();
                    thisCharge.Unknown1 = inFile.ReadInt16();
                    thisCharge.Unknown2 = inFile.ReadInt16();
                    thisCharge.Unknown3 = inFile.ReadInt16();
                    thisCharge.ChargeFrames = inFile.ReadInt16();
                    thisCharge.Flags = inFile.ReadInt16();
                    thisCharge.ChargeIndex = inFile.ReadInt16();
                    thisCharge.Unknown4 = inFile.ReadInt16();

                    thisCharge.Index = i;
                    ChargeList.Add(thisCharge);
                }

                inFile.BaseStream.Seek(startOfInputs, SeekOrigin.Begin);

                List<int> InputAddresses = new List<int>();

                for (int i = 0; i < InputCount; i++)
                {
                    InputAddresses.Add(inFile.ReadInt32());
                }

                for (int i = 0; i < InputAddresses.Count; i++)
                {
                    Input thisInput = new Input();
                    int thisInputAddress = InputAddresses[i];
                    inFile.BaseStream.Seek(thisInputAddress, SeekOrigin.Begin);
                    Debug.WriteLine("InputAddress: " + thisInputAddress.ToString("X"));

                    List<int> moveEntryOffsets = new List<int>();

                    moveEntryOffsets.Add(inFile.ReadInt32());
                    moveEntryOffsets.Add(inFile.ReadInt32());
                    moveEntryOffsets.Add(inFile.ReadInt32());
                    moveEntryOffsets.Add(inFile.ReadInt32());

                    var entries = new List<InputEntry>();

                    foreach (var entryOffset in moveEntryOffsets)
                    {
                        if (entryOffset == 0)
                        {
                            entries.Add(new InputEntry());
                            continue;
                        }

                        inFile.BaseStream.Seek(entryOffset + thisInputAddress, SeekOrigin.Begin);
                        var partCount = inFile.ReadInt32();

                        InputEntry thisInputEntry = new InputEntry();
                        List<InputPart> parts = new List<InputPart>();

                        for (int j = 0; j < partCount; j++)
                        {
                            InputPart thisPart = new InputPart()
                            {
                                InputType = (InputType)inFile.ReadInt16(),
                                Buffer = inFile.ReadInt16(),
                                InputDirection = (InputDirection)inFile.ReadInt16(),
                                Unknown1 = inFile.ReadInt16(),
                                Unknown2 = inFile.ReadInt16(),
                                Unknown3 = inFile.ReadInt16(),
                                Unknown4 = inFile.ReadInt16(),
                                Unknown5 = inFile.ReadInt16(),
                            };

                            parts.Add(thisPart);
                        }

                        for (int j = 0; j < 16-partCount; j++) //There can be up to 16 parts, but even if they are empty they are still there, only filled with 0x00
                        {
                            var unused = inFile.ReadBytes(16);
                            foreach (var b in unused)
                            {
                                if (b != 0)
                                {
                                    Debug.WriteLine("Read unexpected byte in what was thought to be an empty part of an input.");
                                }
                            }
                        }

                        thisInputEntry.InputParts = parts.ToArray();
                        entries.Add(thisInputEntry);
                    }

                    thisInput.InputEntries = entries.ToArray();

                    thisInput.Index = i;
                    InputList.Add(thisInput);
                    Debug.WriteLine("Created input with index: " + i);
                }

                for (int i = 0; i < MoveCount*4; i+=0x4)
                {
                    long thisMovePosition = startOfMoves + i;
                    long thisNamePosition = startOfNames + i;

                    inFile.BaseStream.Seek(thisNamePosition, SeekOrigin.Begin);
                    int NameAddress = inFile.ReadInt32();
                    string Name = GetName(NameAddress, inFile);

                    inFile.BaseStream.Seek(thisMovePosition, SeekOrigin.Begin);
                    int offset = inFile.ReadInt32();
                    Debug.WriteLine("Adding move at: " + offset.ToString("X"));

                    inFile.BaseStream.Seek(offset, SeekOrigin.Begin);

                    short input = inFile.ReadInt16();
                    short inputFlags = inFile.ReadInt16();
                    int restrict = inFile.ReadInt32();
                    int restrict2 = inFile.ReadInt32();
                    float restrictDistance = inFile.ReadSingle();
                    int projectileRestrict = inFile.ReadInt32();
                    int unknown6 = inFile.ReadInt16();
                    int unknown7 = inFile.ReadInt16();
                    short unknown8 = inFile.ReadInt16();
                    short unknown9 = inFile.ReadInt16();

                    short MeterRequirement = inFile.ReadInt16();
                    short MeterUsed = inFile.ReadInt16();
                    short unknown10 = inFile.ReadInt16();
                    short unknown11 = inFile.ReadInt16();
                    int VtriggerRequirement = inFile.ReadInt16();
                    int VtriggerUsed = inFile.ReadInt16();
                    int Unknown16 = inFile.ReadInt32();
                    int InputMotionIndex = inFile.ReadInt16();
                    int ScriptIndex = inFile.ReadInt16();

                    Move thisMove = new Move()
                    {
                        Name = Name,
                        Index = (short)(i == 0 ? 0 : (i / 4)),
                        Input = input,
                        InputFlags = inputFlags,
                        PositionRestriction = restrict,
                        Unknown3 = restrict2,
                        RestrictionDistance = restrictDistance,
                        ProjectileLimit = projectileRestrict,
                        Unknown6 = (short)unknown6,
                        Unknown7 = (short)unknown7,
                        Unknown8 = unknown8,
                        Unknown9 = unknown9,
                        Unknown10 = unknown10,
                        Unknown11 = unknown11,
                        MeterRequirement =  (short)MeterRequirement,
                        MeterUsed = (short)MeterUsed,
                        VtriggerRequirement = (short)VtriggerRequirement,
                        VtriggerUsed = (short)VtriggerUsed,
                        Unknown16 = Unknown16,
                        InputMotionIndex = (short)InputMotionIndex,
                        ScriptIndex = (short)ScriptIndex,
                        Unknown17 = inFile.ReadInt32(),
                        Unknown18 = inFile.ReadInt32(),
                        Unknown19 = inFile.ReadInt32(),
                        Unknown20 = inFile.ReadSingle(),
                        Unknown21 = inFile.ReadSingle(),
                        Unknown22 = inFile.ReadInt32(),
                        Unknown23 = inFile.ReadInt32(),
                        Unknown24 = inFile.ReadInt32(),
                        Unknown25 = inFile.ReadInt32(),
                        Unknown26 = inFile.ReadInt16(),
                        Unknown27 = inFile.ReadInt16(),
                        Unknown28 = inFile.ReadInt32()
                    };

                    if (thisMove.InputMotionIndex != -1) //Just for debugging...
                    {
                        InputList.Where(x => x.Index == thisMove.InputMotionIndex).ToList()[0].Name += thisMove.Name + ", ";
                    }

                    MoveList.Add(thisMove);

                    Debug.WriteLine("MOVE: " + "Index: " + (i == 0 ? 0 : (i/4)) +
                                    "\nName: " + Name +
                                    "\nOffset: " + offset.ToString("X") +
                                    "\nNameOffet: " + NameAddress.ToString("X") +
                                    "\nInput: " + input +
                                    "\nflags: " + inputFlags
                                    + "\nRestrict: " + restrict
                                    + "\nRestrict2: " + restrict2
                                    + "\nRestrictDistance: " + restrictDistance
                                    + "\nProjectileRestrict: " + projectileRestrict
                                    + "\nUnknown6: " + unknown6
                                    + "\nUnknown7: " + unknown7
                                    + "\nUnknown8: " + unknown8
                                    + "\nUnknown9: " + unknown9
                                    + "\nUnknown10: " + unknown10
                                    + "\nUnknown11: " + unknown11
                                    + "\nMeterReq: " + MeterRequirement
                                    + "\nMeterUsed: " + MeterUsed
                                    + "\nVtriggerReq: " + VtriggerRequirement
                                    + "\nVtriggerUsed: " + VtriggerUsed
                                    + "\nUnknown16: " + Unknown16
                                    + "\nInputMotionIndex: " + InputMotionIndex
                                    + "\nScriptIndex: " + ScriptIndex
                                    +"\nUnknown17: " + thisMove.Unknown17
                                    + "\nUnknown18: " + thisMove.Unknown18
                                    + "\nUnknown19: " + thisMove.Unknown19
                                    + "\nUnknown20: " + thisMove.Unknown20
                                    + "\nUnknown21: " + thisMove.Unknown21
                                    + "\nUnknown22: " + thisMove.Unknown22
                                    + "\nUnknown23: " + thisMove.Unknown23
                                    + "\nUnknown24: " + thisMove.Unknown24
                                    + "\nUnknown25: " + thisMove.Unknown25
                                    + "\nUnknown26: " + thisMove.Unknown26
                                    + "\nUnknown27: " + thisMove.Unknown27
                                    + "\nUnknown28: " + thisMove.Unknown28
                                    + "\n\n");
                }

                inFile.BaseStream.Seek(startOfCancelLists, SeekOrigin.Begin);
                List<int> CancelAddresses = new List<int>();
                for (int i = 0; i < CancelCount; i++)
                {
                    int thisCancelAddress = inFile.ReadInt32();
                    Debug.WriteLine("Cancel " + (i) + ": " + thisCancelAddress.ToString("X"));
                    CancelAddresses.Add(thisCancelAddress);
                }

                for (int i = 0; i < CancelAddresses.Count; i++)
                {
                    CancelList thisCancelList = new CancelList();
                    int thisAddress = CancelAddresses[i];

                    if (thisAddress == 0)
                    {
                        CancelLists.Add(new CancelList());
                        continue;
                    }

                    inFile.BaseStream.Seek(thisAddress, SeekOrigin.Begin);

                    thisCancelList.Unknown1 = inFile.ReadInt32();
                    int MovesInList = inFile.ReadInt32();
                    int LastIndex = inFile.ReadInt32(); //last move index in list -1...
                    int StartOffset = inFile.ReadInt32(); //offset until real list FROM START OF CANCEL!!!
                    int StartOfCancelInts = inFile.ReadInt32();
                    int StartOfCancelBytes = inFile.ReadInt32();

                    Debug.WriteLine("ThisCancelAddress: " + thisAddress.ToString("X"));
                    Debug.WriteLine("Cancel {6}:\nCU1: {0}\nMovesInList: {1}\nNumberOfSomethingInList: {2}\nStartOffset: {3}\nCU5: {4}\nEndOffset: {5}\n", thisCancelList.Unknown1, MovesInList, LastIndex, StartOffset.ToString("X"), StartOfCancelInts.ToString("X"), StartOfCancelBytes.ToString("X"), i);

                    inFile.BaseStream.Seek(thisAddress + StartOffset, SeekOrigin.Begin);
                    Debug.WriteLine("ListAddress: " + (thisAddress + StartOffset).ToString("X"));
                    Debug.WriteLine("ListAddressEnd: " + (thisAddress + StartOfCancelBytes).ToString("X"));

                    List<Cancel> cancels = new List<Cancel>();
                    thisCancelList.Index = i;

                    for (int j = 0; j < MovesInList; j++)
                    {
                        int thisMoveInList = inFile.ReadInt16();
                        Debug.WriteLine("Move: " + thisMoveInList);

                        Move cancelMove = MoveList.Where(x => x.Index == thisMoveInList).ToList()[0];

                        Cancel thisCancel = new Cancel();
                        thisCancel.Index = (short)thisMoveInList;
                        thisCancel.Name = cancelMove.Name;
                        thisCancel.ScriptIndex = cancelMove.ScriptIndex;

                        cancels.Add(thisCancel);
                    }

                    thisCancelList.Cancels = cancels.ToArray();

                    //All lists should have Moves divisible by 2. If it doesn't, simply add an empty one (0x00, 0x00)
                    if (MovesInList % 2 != 0)
                    {
                        Debug.WriteLine("READING EMPTY MOVE");
                        inFile.ReadInt16();
                    }

                    if (StartOfCancelInts != 0)
                    {
                        Debug.WriteLine("We got something!!!" + inFile.BaseStream.Position.ToString("X") + " - Should be: " + (thisAddress + StartOfCancelInts).ToString("X"));
                        Debug.WriteLine(((thisAddress + StartOfCancelBytes) - (thisAddress + StartOfCancelInts)) / MovesInList);

                        for (int j = 0; j < MovesInList; j++)
                        {
                            int value1 = inFile.ReadInt32();
                            int value2 = inFile.ReadInt32();

                            thisCancelList.Cancels[j].CancelInts = new CancelInts()
                            {
                                Unknown1 = value1,
                                Unknown2 = value2
                            };
                        }
                    }

                    Debug.WriteLine("Position is " + inFile.BaseStream.Position.ToString("X") + " - Should be: " + (thisAddress + StartOfCancelBytes).ToString("X"));

                    if (inFile.BaseStream.Position != thisAddress + StartOfCancelBytes) //NOT a good idea
                    {
                        Debug.WriteLine("We are not where we're supposed to be, reading bytes until we are...");

                        while (inFile.BaseStream.Position != thisAddress + StartOfCancelBytes)
                        {
                            Debug.WriteLine(inFile.ReadByte());
                        }

                        Debug.WriteLine("Position is " + inFile.BaseStream.Position.ToString("X") + " - Should be: " + (thisAddress + StartOfCancelBytes).ToString("X"));
                    }

                    for (int j = 0; j < LastIndex; j++)
                    {
                        inFile.BaseStream.Seek((thisAddress + StartOfCancelBytes) + (j * 4), SeekOrigin.Begin);

                        var offset = inFile.ReadInt32();

                        if (offset == 0)
                        {
                            continue;
                        }

                        Debug.WriteLine("SomethingElseInCancelList(offsets?): " + offset.ToString("X") + " Pos: " + (inFile.BaseStream.Position - 4).ToString("X") + " - Index: " + j + "  added offset:" + (offset+thisAddress).ToString("X"));

                        var address = offset + thisAddress;

                        inFile.BaseStream.Seek(address, SeekOrigin.Begin);

                        var cancelBytesBelongsTo = thisCancelList.Cancels.First(x => x.Index == j);

                        cancelBytesBelongsTo.UnknownBytes = inFile.ReadBytes(0x24);
                    }

                    CancelLists.Add(thisCancelList);
                    Debug.WriteLine("\n");
                }

                foreach (var cancelList in CancelLists)
                {
                    if (cancelList.Cancels == null)
                    {
                        continue;
                    }

                    foreach (var cancel in cancelList.Cancels)
                    {
                        if (cancel == null)
                        {
                            continue;
                        }
                        Debug.WriteLine("Cancel: " + cancel.Index + " ScriptIndex:" + cancel.ScriptIndex);
                        foreach (var unknownByte in cancel.UnknownBytes)
                        {
                            Debug.Write(unknownByte.ToString("X") + " ");
                        }
                        Debug.WriteLine("");
                    }
                }

                Debug.WriteLine("\nCharges\n");

                foreach (var charge in ChargeList)
                {
                    Debug.WriteLine("CHARGE: " + charge.Index);
                    Debug.WriteLine("Dir: " + charge.ChargeDirection);
                    Debug.WriteLine("u1: " + charge.Unknown1);
                    Debug.WriteLine("u2: " + charge.Unknown2);
                    Debug.WriteLine("u3: " + charge.Unknown3);
                    Debug.WriteLine("ChargeFrames: " + charge.ChargeFrames);
                    Debug.WriteLine("Flags: " + charge.Flags);
                    Debug.WriteLine("CINDEX: " + charge.ChargeIndex);
                    Debug.WriteLine("u4: " + charge.Unknown4);
                    Debug.WriteLine("\n");
                }

                foreach (var input in InputList)
                {
                    Debug.WriteLine("Input: " + input.Index);
                    Debug.WriteLine("Name: " + input.Name);
                    Debug.WriteLine("Entries: " + input.InputEntries.Length);

                    WriteInputToDebug(input);

                    Debug.WriteLine("\n");
                }
            }

            Debug.WriteLine("Done");

            BCMFile bcm = new BCMFile()
            {
                Inputs = InputList.ToArray(),
                CancelLists = CancelLists.ToArray(),
                Charges = ChargeList.ToArray(),
                Moves = MoveList.ToArray(),
                RawUassetHeaderDontTouch = UassetHeaderBytes
            };

            return bcm;
        }
Exemplo n.º 3
0
        public static void ToUassetFile(BCMFile file, string fileName)
        {
            byte[] outPutFileBytes;

            using (var ms = new MemoryStream())
            {
                using (var outFile = new BinaryWriter(ms))
                {
                    byte[] headerBytes =
                    {
                        0x23, 0x42, 0x43, 0x4D, 0xFE, 0xFF, 0x2c, 0x00, 0x00, 0x00, 0x01, 0x00
                    };

                    outFile.Write(headerBytes);

                    outFile.Write((short)file.Charges.Length);
                    outFile.Write((short)file.Inputs.Length);
                    outFile.Write((short)file.Moves.Length);
                    outFile.Write((short)file.CancelLists.Length);

                    var StartOfStartOfChargeOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfInputOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfMoveOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfNameOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfCancelListOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    outFile.Write(0); //Unused?

                    var StartOfChargeOffsets = outFile.BaseStream.Position;
                    if (file.Charges.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfChargeOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Charges.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfInputOffsets = outFile.BaseStream.Position;
                    if (file.Inputs.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfInputOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Inputs.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfMoveOffsets = outFile.BaseStream.Position;
                    if (file.Moves.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfMoveOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfNameOffsets = outFile.BaseStream.Position;
                    if (file.Moves.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfNameOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfCancelListOffsets = outFile.BaseStream.Position;
                    if (file.CancelLists.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfCancelListOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.CancelLists.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    Debug.WriteLine("Done writing temp offsets, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Charges.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfChargeOffsets + (i * 4), (int)outFile.BaseStream.Position);

                        outFile.Write(file.Charges[i].ChargeDirection);
                        outFile.Write(file.Charges[i].Unknown1);
                        outFile.Write(file.Charges[i].Unknown2);
                        outFile.Write(file.Charges[i].Unknown3);
                        outFile.Write(file.Charges[i].ChargeFrames);
                        outFile.Write(file.Charges[i].Flags);
                        outFile.Write(file.Charges[i].ChargeIndex);
                        outFile.Write(file.Charges[i].Unknown4);
                    }

                    Debug.WriteLine("Done writing charges, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Inputs.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfInputOffsets + (i * 4), (int)outFile.BaseStream.Position);
                        var entryOffsetPosition = outFile.BaseStream.Position;

                        outFile.Write(0);
                        outFile.Write(0);
                        outFile.Write(0);
                        outFile.Write(0);

                        for (int j = 0; j < file.Inputs[i].InputEntries.Length; j++)
                        {
                            if (file.Inputs[i].InputEntries[j].InputParts == null)
                            {
                                continue;
                            }

                            WriteInt32ToPosition(outFile, entryOffsetPosition + (j * 4), (int)(outFile.BaseStream.Position - entryOffsetPosition));

                            outFile.Write(file.Inputs[i].InputEntries[j].InputParts.Length);

                            for (int k = 0; k < file.Inputs[i].InputEntries[j].InputParts.Length; k++)
                            {
                                outFile.Write((short)file.Inputs[i].InputEntries[j].InputParts[k].InputType);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Buffer);
                                outFile.Write((short)file.Inputs[i].InputEntries[j].InputParts[k].InputDirection);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown1);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown2);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown3);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown4);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown5);
                            }

                            for (int k = 0; k < 16 - file.Inputs[i].InputEntries[j].InputParts.Length; k++)
                            {
                                for (int l = 0; l < 16; l++)
                                {
                                    outFile.Write((byte)0x00);
                                }
                            }
                        }
                    }

                    Debug.WriteLine("Done writing Inputs, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfMoveOffsets + (i * 4), (int)outFile.BaseStream.Position);

                        outFile.Write(file.Moves[i].Input);
                        outFile.Write(file.Moves[i].InputFlags);
                        outFile.Write(file.Moves[i].PositionRestriction);
                        outFile.Write(file.Moves[i].Unknown3);
                        outFile.Write(file.Moves[i].RestrictionDistance);
                        outFile.Write(file.Moves[i].Unknown4);
                        outFile.Write(file.Moves[i].ProjectileGroup);
                        outFile.Write(file.Moves[i].ProjectileMaxCount);
                        outFile.Write(file.Moves[i].Unknown6);
                        outFile.Write(file.Moves[i].Unknown7);
                        outFile.Write(file.Moves[i].Unknown8);
                        outFile.Write(file.Moves[i].Unknown9);

                        outFile.Write(file.Moves[i].MeterRequirement);
                        outFile.Write(file.Moves[i].MeterUsed);

                        outFile.Write(file.Moves[i].Unknown10);
                        outFile.Write(file.Moves[i].Unknown11);

                        outFile.Write(file.Moves[i].VtriggerRequirement);
                        outFile.Write(file.Moves[i].VtriggerUsed);

                        outFile.Write(file.Moves[i].Unknown16);
                        outFile.Write(file.Moves[i].InputMotionIndex);
                        outFile.Write(file.Moves[i].ScriptIndex);

                        outFile.Write(file.Moves[i].Unknown17);
                        outFile.Write(file.Moves[i].Unknown18);
                        outFile.Write(file.Moves[i].Unknown19); // TODO: Why is this omitted?
                        outFile.Write(file.Moves[i].Unknown20);
                        outFile.Write(file.Moves[i].Unknown21);
                        outFile.Write(file.Moves[i].Unknown22);
                        outFile.Write(file.Moves[i].Unknown23);
                        outFile.Write(file.Moves[i].Unknown24);
                        outFile.Write(file.Moves[i].Unknown25);
                        outFile.Write(file.Moves[i].Unknown26);
                        outFile.Write(file.Moves[i].NormalOrVtrigger);
                        outFile.Write(file.Moves[i].Unknown28);
                    }

                    Debug.WriteLine("Done writing Moves, now at: " + outFile.BaseStream.Position.ToString("X"));

                    List <long> CancelListOffsets      = new List <long>();
                    List <long> StartOfCancelListsList = new List <long>();

                    for (int i = 0; i < file.CancelLists.Length; i++)
                    {
                        StartOfCancelListsList.Add(outFile.BaseStream.Position);
                        if (file.CancelLists[i].Cancels == null)
                        {
                            WriteInt32ToPosition(outFile, StartOfCancelListOffsets + (i * 4), 0);
                            CancelListOffsets.Add(-1);
                            continue;
                        }

                        WriteInt32ToPosition(outFile, StartOfCancelListOffsets + (i * 4),
                                             (int)outFile.BaseStream.Position);

                        outFile.Write(file.CancelLists[i].Unknown1);
                        outFile.Write(file.CancelLists[i].Cancels.Length);
                        outFile.Write(file.CancelLists[i].Cancels[file.CancelLists[i].Cancels.Length - 1].Index + 1);

                        CancelListOffsets.Add(outFile.BaseStream.Position);

                        outFile.Write(0);
                        outFile.Write(0);
                        outFile.Write(0);
                    }

                    for (int i = 0; i < file.CancelLists.Length; i++)
                    {
                        if (file.CancelLists[i].Cancels == null)
                        {
                            continue;
                        }

                        Debug.WriteLine("CancelListAtAddress: " + outFile.BaseStream.Position.ToString("X"));
                        if (CancelListOffsets[i] != -1)
                        {
                            WriteInt32ToPosition(outFile, CancelListOffsets[i], (int)(outFile.BaseStream.Position - StartOfCancelListsList[i]));
                        }

                        for (int j = 0; j < file.CancelLists[i].Cancels.Length; j++)
                        {
                            outFile.Write(file.CancelLists[i].Cancels[j].Index);
                        }

                        if (file.CancelLists[i].Cancels.Length % 2 != 0)
                        {
                            Debug.WriteLine("Writing empty move: " + outFile.BaseStream.Position.ToString("X"));
                            outFile.Write((short)0);
                        }

                        bool shouldWrite        = false;
                        var  CancelIntsPosition = outFile.BaseStream.Position;

                        foreach (var cancel in file.CancelLists[i].Cancels)
                        {
                            if (cancel.CancelInts != null)
                            {
                                outFile.Write(cancel.CancelInts.Unknown1);
                                outFile.Write(cancel.CancelInts.Unknown2);
                                shouldWrite = true;
                            }
                        }

                        if (shouldWrite)
                        {
                            if (CancelListOffsets[i] != -1)
                            {
                                WriteInt32ToPosition(outFile, CancelListOffsets[i] + 4,
                                                     (int)(CancelIntsPosition - StartOfCancelListsList[i]));
                            }
                        }

                        Debug.WriteLine("Startofunknownbytes: " + outFile.BaseStream.Position.ToString("X"));

                        if (CancelListOffsets[i] != -1)
                        {
                            WriteInt32ToPosition(outFile, CancelListOffsets[i] + 8, (int)(outFile.BaseStream.Position - StartOfCancelListsList[i]));
                        }

                        var numberOfOffsets =
                            file.CancelLists[i].Cancels[file.CancelLists[i].Cancels.Length - 1].Index + 1; //???? +1 only when not dividable by 2??

                        var UnknownBytesOffsetPosition = outFile.BaseStream.Position;

                        for (int j = 0; j < numberOfOffsets; j++)
                        {
                            outFile.Write(0);
                        }

                        for (int j = 0; j < file.CancelLists[i].Cancels.Length; j++)
                        {
                            if (file.CancelLists[i].Cancels[j].UnknownBytes != null)
                            {
                                WriteInt32ToPosition(outFile, UnknownBytesOffsetPosition + (file.CancelLists[i].Cancels[j].Index * 4), (int)(outFile.BaseStream.Position - StartOfCancelListsList[i]));
                                outFile.Write(file.CancelLists[i].Cancels[j].UnknownBytes);
                            }
                        }
                    }

                    Debug.WriteLine("Done writing Cancels, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfNameOffsets + (i * 4), (int)outFile.BaseStream.Position);

                        outFile.Write(file.Moves[i].Name.ToCharArray());
                        outFile.Write((byte)0x00);
                    }

                    Debug.WriteLine("Done writing names, now at: " + outFile.BaseStream.Position.ToString("X"));

                    outPutFileBytes = ms.ToArray();

                    Debug.WriteLine("Done.");
                }
            }

            var outPut = outPutFileBytes.ToList();

            outPut.InsertRange(0, BitConverter.GetBytes(outPutFileBytes.Length));

            outPut.InsertRange(0, new byte[]
            {
                0x00, 0x00, 0x00, 0x00,
                0x05, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00
            });

            outPut.InsertRange(0, BitConverter.GetBytes(outPutFileBytes.Length + 4));

            outPut.InsertRange(0, new byte[]
            {
                0x07, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00,
                0x03, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00
            });

            outPut = Common.CreateUassetFile(outPut, file.RawUassetHeaderDontTouch);

            Debug.WriteLine("Done.");

            File.WriteAllBytes(fileName, outPut.ToArray());
        }
Exemplo n.º 4
0
        public static void ToUassetFile(BCMFile file, string fileName)
        {
            byte[] outPutFileBytes;

            using (var ms = new MemoryStream())
            {
                using (var outFile = new BinaryWriter(ms))
                {
                    byte[] headerBytes =
                    {
                        0x23, 0x42, 0x43, 0x4D, 0xFE, 0xFF, 0x2c, 0x00, 0x00, 0x00, 0x00, 0x00
                    };

                    outFile.Write(headerBytes);

                    outFile.Write((short) file.Charges.Length);
                    outFile.Write((short) file.Inputs.Length);
                    outFile.Write((short) file.Moves.Length);
                    outFile.Write((short) file.CancelLists.Length);

                    var StartOfStartOfChargeOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfInputOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfMoveOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfNameOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    var StartOfStartOfCancelListOffsets = outFile.BaseStream.Position;
                    outFile.Write(0);

                    outFile.Write(0); //Unused?

                    var StartOfChargeOffsets = outFile.BaseStream.Position;
                    if (file.Charges.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfChargeOffsets, (int) outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Charges.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfInputOffsets = outFile.BaseStream.Position;
                    if (file.Inputs.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfInputOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Inputs.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfMoveOffsets = outFile.BaseStream.Position;
                    if (file.Moves.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfMoveOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfNameOffsets = outFile.BaseStream.Position;
                    if (file.Moves.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfNameOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    var StartOfCancelListOffsets = outFile.BaseStream.Position;
                    if (file.CancelLists.Length > 0)
                    {
                        WriteInt32ToPosition(outFile, StartOfStartOfCancelListOffsets, (int)outFile.BaseStream.Position);
                    }
                    for (int i = 0; i < file.CancelLists.Length; i++)
                    {
                        outFile.Write(0);
                    }

                    Debug.WriteLine("Done writing temp offsets, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Charges.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfChargeOffsets + (i*4), (int)outFile.BaseStream.Position);

                        outFile.Write(file.Charges[i].ChargeDirection);
                        outFile.Write(file.Charges[i].Unknown1);
                        outFile.Write(file.Charges[i].Unknown2);
                        outFile.Write(file.Charges[i].Unknown3);
                        outFile.Write(file.Charges[i].ChargeFrames);
                        outFile.Write(file.Charges[i].Flags);
                        outFile.Write(file.Charges[i].ChargeIndex);
                        outFile.Write(file.Charges[i].Unknown4);
                    }

                    Debug.WriteLine("Done writing charges, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Inputs.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfInputOffsets + (i * 4), (int)outFile.BaseStream.Position);
                        var entryOffsetPosition = outFile.BaseStream.Position;

                        outFile.Write(0);
                        outFile.Write(0);
                        outFile.Write(0);
                        outFile.Write(0);

                        for (int j = 0; j < file.Inputs[i].InputEntries.Length; j++)
                        {
                            if (file.Inputs[i].InputEntries[j].InputParts == null)
                            {
                                continue;
                            }

                            WriteInt32ToPosition(outFile, entryOffsetPosition + (j*4), (int)(outFile.BaseStream.Position- entryOffsetPosition));

                            outFile.Write(file.Inputs[i].InputEntries[j].InputParts.Length);

                            for (int k = 0; k < file.Inputs[i].InputEntries[j].InputParts.Length; k++)
                            {
                                outFile.Write((short)file.Inputs[i].InputEntries[j].InputParts[k].InputType);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Buffer);
                                outFile.Write((short)file.Inputs[i].InputEntries[j].InputParts[k].InputDirection);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown1);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown2);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown3);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown4);
                                outFile.Write(file.Inputs[i].InputEntries[j].InputParts[k].Unknown5);
                            }

                            for (int k = 0; k < 16 - file.Inputs[i].InputEntries[j].InputParts.Length; k++)
                            {
                                for (int l = 0; l < 16; l++)
                                {
                                    outFile.Write((byte)0x00);
                                }
                            }
                        }
                    }

                    Debug.WriteLine("Done writing Inputs, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        WriteInt32ToPosition(outFile,StartOfMoveOffsets + (i*4), (int)outFile.BaseStream.Position);

                        outFile.Write(file.Moves[i].Input);
                        outFile.Write(file.Moves[i].InputFlags);
                        outFile.Write(file.Moves[i].PositionRestriction);
                        outFile.Write(file.Moves[i].Unknown3);
                        outFile.Write(file.Moves[i].RestrictionDistance);
                        outFile.Write(file.Moves[i].ProjectileLimit);
                        outFile.Write(file.Moves[i].Unknown6);
                        outFile.Write(file.Moves[i].Unknown7);
                        outFile.Write(file.Moves[i].Unknown8);
                        outFile.Write(file.Moves[i].Unknown9);

                        outFile.Write(file.Moves[i].MeterRequirement);
                        outFile.Write(file.Moves[i].MeterUsed);

                        outFile.Write(file.Moves[i].Unknown10);
                        outFile.Write(file.Moves[i].Unknown11);

                        outFile.Write(file.Moves[i].VtriggerRequirement);
                        outFile.Write(file.Moves[i].VtriggerUsed);

                        outFile.Write(file.Moves[i].Unknown16);
                        outFile.Write(file.Moves[i].InputMotionIndex);
                        outFile.Write(file.Moves[i].ScriptIndex);

                        outFile.Write(file.Moves[i].Unknown17);
                        outFile.Write(file.Moves[i].Unknown18);
                        outFile.Write(file.Moves[i].Unknown19);
                        outFile.Write(file.Moves[i].Unknown20);
                        outFile.Write(file.Moves[i].Unknown21);
                        outFile.Write(file.Moves[i].Unknown22);
                        outFile.Write(file.Moves[i].Unknown23);
                        outFile.Write(file.Moves[i].Unknown24);
                        outFile.Write(file.Moves[i].Unknown25);
                        outFile.Write(file.Moves[i].Unknown26);
                        outFile.Write(file.Moves[i].Unknown27);
                        outFile.Write(file.Moves[i].Unknown28);
                    }

                    Debug.WriteLine("Done writing Moves, now at: " + outFile.BaseStream.Position.ToString("X"));

                    List<long> CancelListOffsets = new List<long>();
                    List<long> StartOfCancelListsList = new List<long>();

                    for (int i = 0; i < file.CancelLists.Length; i++)
                    {
                        StartOfCancelListsList.Add(outFile.BaseStream.Position);
                        if (file.CancelLists[i].Cancels == null)
                        {
                            WriteInt32ToPosition(outFile, StartOfCancelListOffsets + (i*4), 0);
                            CancelListOffsets.Add(-1);
                            continue;
                        }

                        WriteInt32ToPosition(outFile, StartOfCancelListOffsets + (i*4),
                            (int) outFile.BaseStream.Position);

                        outFile.Write(file.CancelLists[i].Unknown1);
                        outFile.Write(file.CancelLists[i].Cancels.Length);
                        outFile.Write(file.CancelLists[i].Cancels[file.CancelLists[i].Cancels.Length - 1].Index + 1);

                        CancelListOffsets.Add(outFile.BaseStream.Position);

                        outFile.Write(0);
                        outFile.Write(0);
                        outFile.Write(0);
                    }

                    for (int i = 0; i < file.CancelLists.Length; i++)
                    {
                        if (file.CancelLists[i].Cancels == null)
                        {
                            continue;
                        }

                        Debug.WriteLine("CancelListAtAddress: " + outFile.BaseStream.Position.ToString("X"));
                        if (CancelListOffsets[i] != -1)
                        {
                            WriteInt32ToPosition(outFile, CancelListOffsets[i], (int)(outFile.BaseStream.Position - StartOfCancelListsList[i]));
                        }

                        for (int j = 0; j < file.CancelLists[i].Cancels.Length; j++)
                        {
                            outFile.Write(file.CancelLists[i].Cancels[j].Index);
                        }

                        if (file.CancelLists[i].Cancels.Length%2 != 0)
                        {
                            Debug.WriteLine("Writing empty move: " + outFile.BaseStream.Position.ToString("X"));
                            outFile.Write((short)0);
                        }

                        bool shouldWrite = false;
                        var CancelIntsPosition = outFile.BaseStream.Position;

                        foreach (var cancel in file.CancelLists[i].Cancels)
                        {
                            if (cancel.CancelInts != null)
                            {
                                outFile.Write(cancel.CancelInts.Unknown1);
                                outFile.Write(cancel.CancelInts.Unknown2);
                                shouldWrite = true;
                            }
                        }

                        if (shouldWrite)
                        {
                            if (CancelListOffsets[i] != -1)
                            {
                                WriteInt32ToPosition(outFile, CancelListOffsets[i] + 4,
                                    (int) (CancelIntsPosition - StartOfCancelListsList[i]));
                            }
                        }

                        Debug.WriteLine("Startofunknownbytes: " + outFile.BaseStream.Position.ToString("X"));

                        if (CancelListOffsets[i] != -1)
                        {
                            WriteInt32ToPosition(outFile, CancelListOffsets[i]+8, (int)(outFile.BaseStream.Position - StartOfCancelListsList[i]));
                        }

                        var numberOfOffsets =
                            file.CancelLists[i].Cancels[file.CancelLists[i].Cancels.Length - 1].Index + 1; //???? +1 only when not dividable by 2??

                        var UnknownBytesOffsetPosition = outFile.BaseStream.Position;

                        for (int j = 0; j < numberOfOffsets; j++)
                        {
                            outFile.Write(0);
                        }

                        for (int j = 0; j < file.CancelLists[i].Cancels.Length; j++)
                        {
                            if (file.CancelLists[i].Cancels[j].UnknownBytes != null)
                            {
                                WriteInt32ToPosition(outFile, UnknownBytesOffsetPosition  + (file.CancelLists[i].Cancels[j].Index*4), (int)(outFile.BaseStream.Position- StartOfCancelListsList[i]));
                                outFile.Write(file.CancelLists[i].Cancels[j].UnknownBytes);
                            }
                        }
                    }

                    Debug.WriteLine("Done writing Cancels, now at: " + outFile.BaseStream.Position.ToString("X"));

                    for (int i = 0; i < file.Moves.Length; i++)
                    {
                        WriteInt32ToPosition(outFile, StartOfNameOffsets + (i*4), (int)outFile.BaseStream.Position);

                        outFile.Write(file.Moves[i].Name.ToCharArray());
                        outFile.Write((byte)0x00);
                    }

                    Debug.WriteLine("Done writing names, now at: " + outFile.BaseStream.Position.ToString("X"));

                    outPutFileBytes = ms.ToArray();

                    Debug.WriteLine("Done.");
                }
            }

            var outPut = outPutFileBytes.ToList();
            outPut.InsertRange(0, BitConverter.GetBytes(outPutFileBytes.Length));

            outPut.InsertRange(0, new byte[]
            {
                0x00, 0x00, 0x00, 0x00,
                0x05, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00
            });

            outPut.InsertRange(0, BitConverter.GetBytes(outPutFileBytes.Length + 4));

            outPut.InsertRange(0, new byte[]
            {
                0x07, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00,
                0x03, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00
            });

            outPut.AddRange(new byte[]
            {
                0x09, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00,
                0x00, 0x00, 0x00, 0x00
            });

            var tempLengthBytes = BitConverter.GetBytes(outPut.Count);
            byte[] UassetHeader = file.RawUassetHeaderDontTouch;
            UassetHeader[0x1b0] = tempLengthBytes[0];
            UassetHeader[0x1b1] = tempLengthBytes[1];
            UassetHeader[0x1b2] = tempLengthBytes[2];
            UassetHeader[0x1b3] = tempLengthBytes[3];

            outPut.InsertRange(0, UassetHeader);

            byte[] UassetEnd = new byte[4];
            UassetHeader.ToList().CopyTo(0, UassetEnd, 0, 4);

            outPut.AddRange(UassetEnd);

            Debug.WriteLine("Done.");

            File.WriteAllBytes(fileName, outPut.ToArray());
        }