ZoneBuilder/Source/Core/ZDoom/ReverbsParser.cs

128 lines
3.3 KiB
C#

using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;
namespace CodeImp.DoomBuilder.ZDoom
{
internal sealed class ReverbsParser : ZDTextParser
{
private readonly List<string> names;
private readonly List<int> firstargs;
private readonly List<int> secondargs;
private readonly List<int> combinedargs;
public ReverbsParser()
{
names = new List<string>();
firstargs = new List<int>();
secondargs = new List<int>();
combinedargs = new List<int>();
}
public override bool Parse(Stream stream, string sourcefilename, bool clearerrors)
{
if(!base.Parse(stream, sourcefilename, clearerrors)) return false;
// Continue until at the end of the stream
while(SkipWhitespace(true))
{
string token = ReadToken();
if(!string.IsNullOrEmpty(token))
{
if(token == "{")
{
// Skip inner properties
do
{
SkipWhitespace(true);
token = ReadToken();
} while(!string.IsNullOrEmpty(token) && token != "}");
}
else
{
//this should be reverb name and args
string name = StripTokenQuotes(token);
if(string.IsNullOrEmpty(name))
{
ReportError("Expected sound environment name");
break;
}
// Read first part of the ID
SkipWhitespace(true);
token = StripTokenQuotes(ReadToken());
int arg1;
if(!int.TryParse(token, NumberStyles.Integer, CultureInfo.InvariantCulture, out arg1))
{
ReportError("Expected first part of '" + name + "' sound environment ID, but got '" + token + "'");
break;
}
// Read second part of the ID
SkipWhitespace(true);
token = StripTokenQuotes(ReadToken());
int arg2;
if(!int.TryParse(token, NumberStyles.Integer, CultureInfo.InvariantCulture, out arg2))
{
ReportError("Expected second part of '" + name + "' sound environment ID, but got '" + token + "'");
break;
}
int combined = arg1 * 1000000 + arg2 * 1000;
int combinedindex = combinedargs.IndexOf(combined);
if(combinedindex != -1)
{
LogWarning("'" + names[combinedindex] + "' and '" + name + "' sound environments share the same ID (" + arg1 + " " + arg2 + ")");
}
else
{
combinedargs.Add(combined);
// Add to collections
if(names.Contains(name))
{
LogWarning("'" + name + "' sound environment is double-defined in '" + sourcefilename + "'");
int index = names.IndexOf(name);
firstargs[index] = arg1;
secondargs[index] = arg2;
}
else
{
names.Add(name);
firstargs.Add(arg1);
secondargs.Add(arg2);
}
}
}
}
}
return true;
}
internal Dictionary<string, KeyValuePair<int, int>> GetReverbs()
{
string[] sortednames = new string[names.Count];
names.CopyTo(sortednames);
Array.Sort(sortednames);
Dictionary<string, KeyValuePair<int, int>> result = new Dictionary<string, KeyValuePair<int, int>>(names.Count);
foreach(string name in sortednames)
{
int index = names.IndexOf(name);
result.Add(name, new KeyValuePair<int, int>(firstargs[index], secondargs[index]));
}
return result;
}
protected override string GetLanguageType()
{
return "REVERBS";
}
}
}