Beispiel #1
0
        public override bool Compile(Uri baseUri, BinaryAsset asset, XmlNode node, GameDefinition game, string trace, ref int position, out string ErrorDescription)
        {
            if (IsAttribute)
            {
                bool     isFound = false;
                string[] values  = null;
                foreach (XmlAttribute attribute in node.Attributes)
                {
                    if (attribute.Name == id)
                    {
                        isFound = true;
                        values  = attribute.Value.Split(' ');
                        break;
                    }
                }
                if (isFound)
                {
                    if (values.Length < MinLength)
                    {
                        ErrorDescription = string.Format(LessThenMinElements, trace, MinLength, id);
                        return(false);
                    }
                    if (MaxLength != 0 && values.Length > MaxLength)
                    {
                        ErrorDescription = string.Format(MoreThenMaxElements, trace, MaxLength, id);
                        return(false);
                    }
                    if (values.Length != 0)
                    {
                        FileHelper.SetInt(values.Length, position, asset.Content);
                        position += 4;
                        trace    += '.' + id;
                        BinaryAsset assetList   = null;
                        int         subPosition = 0;
                        switch (AssetType)
                        {
                        case String:
                            assetList = new BinaryAsset(values.Length * 8);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                int stringLength = value.Length;
                                FileHelper.SetInt(stringLength, subPosition, assetList.Content);
                                subPosition  += 4;
                                stringLength += 4 - (stringLength & 3);
                                BinaryAsset stringAsset = new BinaryAsset(stringLength);
                                FileHelper.SetString(value, 0, stringAsset.Content);
                                assetList.SubAssets.Add(subPosition, stringAsset);
                                subPosition += 4;
                            }
                            break;

                        case Byte:
                            int byteCount = 4 - (values.Length & 3);
                            if (byteCount == 4)
                            {
                                assetList = new BinaryAsset(values.Length);
                            }
                            else
                            {
                                assetList = new BinaryAsset(values.Length + byteCount);
                            }
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                FileHelper.SetByte(byte.Parse(value), subPosition, assetList.Content);
                                ++subPosition;
                            }
                            break;

                        case Angle:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.Angle angle = new Types.Angle(value);
                                FileHelper.SetFloat(angle.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        case Percentage:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.Percentage percentage = new Types.Percentage(value);
                                FileHelper.SetFloat(percentage.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        case SageBool:
                            int sageBoolCount = 4 - (values.Length & 3);
                            if (sageBoolCount == 4)
                            {
                                assetList = new BinaryAsset(values.Length);
                            }
                            else
                            {
                                assetList = new BinaryAsset(values.Length + sageBoolCount);
                            }
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.SageBool sageBool = new Types.SageBool(value);
                                FileHelper.SetBool(sageBool.Value, subPosition, assetList.Content);
                                ++subPosition;
                            }
                            break;

                        case SageInt:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.SageInt sageInt = new Types.SageInt(value);
                                FileHelper.SetInt(sageInt.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        case SageReal:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.SageReal sageReal = new Types.SageReal(value);
                                FileHelper.SetFloat(sageReal.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        case SageUnsignedInt:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.SageUnsignedInt sageUnsignedInt = new Types.SageUnsignedInt(value);
                                FileHelper.SetUInt(sageUnsignedInt.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        case SageUnsignedShort:
                            int sageUnsignedShortCount = 2 - (values.Length & 1);
                            if (sageUnsignedShortCount == 2)
                            {
                                assetList = new BinaryAsset(values.Length * 2);
                            }
                            else
                            {
                                assetList = new BinaryAsset((values.Length + sageUnsignedShortCount) * 2);
                            }
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.SageUnsignedShort sageUnsignedShort = new Types.SageUnsignedShort(value);
                                FileHelper.SetUShort(sageUnsignedShort.Value, subPosition, assetList.Content);
                                subPosition += 2;
                            }
                            break;

                        case Time:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.Time time = new Types.Time(value);
                                FileHelper.SetFloat(time.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        case Velocity:
                            assetList = new BinaryAsset(values.Length * 4);
                            asset.SubAssets.Add(position, assetList);
                            foreach (string value in values)
                            {
                                Types.Velocity velocity = new Types.Velocity(value);
                                FileHelper.SetFloat(velocity.Value, subPosition, assetList.Content);
                                subPosition += 4;
                            }
                            break;

                        default:
                            foreach (BaseAssetType listBaseAsset in game.Assets.AssetTypes)
                            {
                                if (listBaseAsset.id == AssetType)
                                {
                                    AssetType listAsset = listBaseAsset as AssetType;
                                    assetList = new BinaryAsset(values.Length * listAsset.GetLength(game));
                                    asset.SubAssets.Add(position, assetList);
                                    for (int idx = 0; idx < values.Length; ++idx)
                                    {
                                        XmlDocument fakeDocument  = new XmlDocument();
                                        XmlNode     fakeAttribute = fakeDocument.CreateAttribute(id);
                                        fakeAttribute.Value = values[idx];
                                        foreach (BaseEntryType listBaseEntry in listAsset.Entries)
                                        {
                                            if (!listBaseEntry.Compile(baseUri, assetList, fakeAttribute, game, trace, ref subPosition, out ErrorDescription))
                                            {
                                                return(false);
                                            }
                                        }
                                    }
                                    break;
                                }
                            }
                            break;
                        }
                        position += 4;
                    }
                    else
                    {
                        position += 8;
                    }
                }
                else
                {
                    if (IsRequired)
                    {
                        ErrorDescription = string.Format(RequiredNotFoundAttribute, id, trace);
                        return(false);
                    }
                    position += 8;
                }
            }
            else
            {
                List <XmlNode> nodes = new List <XmlNode>();
                foreach (XmlNode childNode in node.ChildNodes)
                {
                    if (childNode.Name == id)
                    {
                        nodes.Add(childNode);
                    }
                }
                if (nodes.Count < MinLength)
                {
                    ErrorDescription = string.Format(LessThenMinElements, trace, MinLength, id);
                    return(false);
                }
                if (MaxLength != 0 && nodes.Count > MaxLength)
                {
                    ErrorDescription = string.Format(MoreThenMaxElements, trace, MaxLength, id);
                    return(false);
                }
                if (nodes.Count != 0)
                {
                    FileHelper.SetInt(nodes.Count, position, asset.Content);
                    position += 4;
                    trace    += '.' + id;
                    BinaryAsset assetList   = null;
                    int         subPosition = 0;
                    switch (AssetType)
                    {
                    case String:
                        assetList = new BinaryAsset(nodes.Count * 8);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string value        = nodes[idx].InnerText;
                            int    stringLength = value.Length;
                            FileHelper.SetInt(stringLength, subPosition, assetList.Content);
                            subPosition  += 4;
                            stringLength += 4 - (stringLength & 3);
                            BinaryAsset stringAsset = new BinaryAsset(stringLength);
                            FileHelper.SetString(value, 0, stringAsset.Content);
                            assetList.SubAssets.Add(subPosition, stringAsset);
                            subPosition += 4;
                        }
                        break;

                    case Byte:
                        int byteCount = 4 - (nodes.Count & 3);
                        if (byteCount == 4)
                        {
                            assetList = new BinaryAsset(nodes.Count);
                        }
                        else
                        {
                            assetList = new BinaryAsset(nodes.Count + byteCount);
                        }
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string value = nodes[idx].InnerText;
                            FileHelper.SetByte(byte.Parse(value), subPosition, assetList.Content);
                            ++subPosition;
                        }
                        break;

                    case Angle:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string      value = nodes[idx].InnerText;
                            Types.Angle angle = new Types.Angle(value);
                            FileHelper.SetFloat(angle.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    case Percentage:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string           value      = nodes[idx].InnerText;
                            Types.Percentage percentage = new Types.Percentage(value);
                            FileHelper.SetFloat(percentage.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    case SageBool:
                        int sageBoolCount = 4 - (nodes.Count & 3);
                        if (sageBoolCount == 4)
                        {
                            assetList = new BinaryAsset(nodes.Count);
                        }
                        else
                        {
                            assetList = new BinaryAsset(nodes.Count + sageBoolCount);
                        }
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string         value    = nodes[idx].InnerText;
                            Types.SageBool sageBool = new Types.SageBool(value);
                            FileHelper.SetBool(sageBool.Value, subPosition, assetList.Content);
                            ++subPosition;
                        }
                        break;

                    case SageInt:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string        value   = nodes[idx].InnerText;
                            Types.SageInt sageInt = new Types.SageInt(value);
                            FileHelper.SetInt(sageInt.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    case SageReal:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string         value    = nodes[idx].InnerText;
                            Types.SageReal sageReal = new Types.SageReal(value);
                            FileHelper.SetFloat(sageReal.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    case SageUnsignedInt:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string value = nodes[idx].InnerText;
                            Types.SageUnsignedInt sageUnsignedInt = new Types.SageUnsignedInt(value);
                            FileHelper.SetUInt(sageUnsignedInt.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    case SageUnsignedShort:
                        int sageUnsignedShortCount = 2 - (nodes.Count & 1);
                        if (sageUnsignedShortCount == 2)
                        {
                            assetList = new BinaryAsset(nodes.Count * 2);
                        }
                        else
                        {
                            assetList = new BinaryAsset((nodes.Count + sageUnsignedShortCount) * 2);
                        }
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string value = nodes[idx].InnerText;
                            Types.SageUnsignedShort sageUnsignedShort = new Types.SageUnsignedShort(value);
                            FileHelper.SetUShort(sageUnsignedShort.Value, subPosition, assetList.Content);
                            subPosition += 2;
                        }
                        break;

                    case Time:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string     value = nodes[idx].InnerText;
                            Types.Time time  = new Types.Time(value);
                            FileHelper.SetFloat(time.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    case Velocity:
                        assetList = new BinaryAsset(nodes.Count * 4);
                        asset.SubAssets.Add(position, assetList);
                        for (int idx = 0; idx < nodes.Count; ++idx)
                        {
                            string         value    = nodes[idx].InnerText;
                            Types.Velocity velocity = new Types.Velocity(value);
                            FileHelper.SetFloat(velocity.Value, subPosition, assetList.Content);
                            subPosition += 4;
                        }
                        break;

                    default:
                        foreach (BaseAssetType listBaseAsset in game.Assets.AssetTypes)
                        {
                            if (listBaseAsset.id == AssetType)
                            {
                                AssetType listAsset = listBaseAsset as AssetType;
                                assetList = new BinaryAsset(nodes.Count * listAsset.GetLength(game));
                                asset.SubAssets.Add(position, assetList);
                                for (int idx = 0; idx < nodes.Count; ++idx)
                                {
                                    foreach (BaseEntryType listBaseEntry in listAsset.Entries)
                                    {
                                        if (!listBaseEntry.Compile(baseUri, assetList, nodes[idx], game, trace, ref subPosition, out ErrorDescription))
                                        {
                                            return(false);
                                        }
                                    }
                                }
                                break;
                            }
                        }
                        break;
                    }
                    position += 4;
                }
                else
                {
                    position += 8;
                }
            }
            ErrorDescription = string.Empty;
            return(true);
        }