/// <summary> /// セクションを書き出す /// </summary> /// <param name="section">セクションID</param> /// <param name="type">ゲームの種類</param> /// <param name="writer">ファイル書き込み用</param> private static void WriteSection(MiscSectionId section, MiscGameType type, StreamWriter writer) { writer.WriteLine(); writer.Write("{0} = {{", Misc.SectionStrings[(int) section]); // 項目のコメントと値を順に書き出す foreach (MiscItemId id in Misc.SectionItems[(int) section] .Where(id => Misc.ItemTable[(int) id, (int) type])) { writer.Write(Misc.GetComment(id)); writer.Write(Misc.GetString(id)); } // セクション末尾の空白文字/コメントを書き出す writer.Write(Misc.GetSuffix(section)); writer.WriteLine("}"); }
/// <summary> /// セクションを構文解析する /// </summary> /// <param name="section">セクションID</param> /// <param name="type">ゲームの種類</param> /// <param name="lexer">字句解析器</param> /// <returns>構文解析の成否</returns> private static bool ParseSection(MiscSectionId section, MiscGameType type, TextLexer lexer) { // 空白文字/コメントを読み飛ばす Token token; while (true) { token = lexer.GetToken(); if (token.Type != TokenType.WhiteSpace && token.Type != TokenType.Comment) { break; } } // = if (token.Type != TokenType.Equal) { Log.InvalidToken(LogCategory, token, lexer); return false; } // 空白文字/コメントを読み飛ばす while (true) { token = lexer.GetToken(); if (token.Type != TokenType.WhiteSpace && token.Type != TokenType.Comment) { break; } } // { if (token.Type != TokenType.OpenBrace) { Log.InvalidToken(LogCategory, token, lexer); return false; } StringBuilder sb; foreach (MiscItemId id in Misc.SectionItems[(int) section] .Where(id => Misc.ItemTable[(int) id, (int) type])) { // 空白文字/コメントを保存する sb = new StringBuilder(); while (true) { token = lexer.GetToken(); if (token.Type != TokenType.WhiteSpace && token.Type != TokenType.Comment) { break; } sb.Append(token.Value); } Misc.SetComment(id, sb.ToString()); // 設定値 if (token.Type != TokenType.Number) { Log.InvalidToken(LogCategory, token, lexer); return false; } switch (Misc.ItemTypes[(int) id]) { case MiscItemType.Bool: Misc.SetItem(id, (int) (double) token.Value != 0); break; case MiscItemType.Enum: case MiscItemType.Int: case MiscItemType.PosInt: case MiscItemType.NonNegInt: case MiscItemType.NonPosInt: case MiscItemType.NonNegIntMinusOne: case MiscItemType.NonNegInt1: case MiscItemType.RangedInt: case MiscItemType.RangedPosInt: case MiscItemType.RangedIntMinusOne: case MiscItemType.RangedIntMinusThree: Misc.SetItem(id, (int) (double) token.Value); break; case MiscItemType.Dbl: case MiscItemType.PosDbl: case MiscItemType.NonNegDbl: case MiscItemType.NonPosDbl: case MiscItemType.NonNegDbl0: case MiscItemType.NonNegDbl2: case MiscItemType.NonNegDbl5: case MiscItemType.NonPosDbl0: case MiscItemType.NonPosDbl2: case MiscItemType.NonNegDblMinusOne: case MiscItemType.NonNegDblMinusOne1: case MiscItemType.NonNegDbl2AoD: case MiscItemType.NonNegDbl4Dda13: case MiscItemType.NonNegDbl2Dh103Full: case MiscItemType.NonNegDbl2Dh103Full1: case MiscItemType.NonNegDbl2Dh103Full2: case MiscItemType.NonPosDbl5AoD: case MiscItemType.NonPosDbl2Dh103Full: case MiscItemType.RangedDbl: case MiscItemType.RangedDblMinusOne: case MiscItemType.RangedDblMinusOne1: case MiscItemType.RangedDbl0: case MiscItemType.NonNegIntNegDbl: Misc.SetItem(id, (double) token.Value); break; } } // セクション末尾の空白文字/コメントを保存する sb = new StringBuilder(); while (true) { token = lexer.GetToken(); if (token.Type != TokenType.WhiteSpace && token.Type != TokenType.Comment) { break; } sb.Append(token.Value); } Misc.SetSuffix(section, sb.ToString()); // } (セクション終端) if (token.Type != TokenType.CloseBrace) { Log.InvalidToken(LogCategory, token, lexer); return false; } return true; }