#region CmdMessenger - MIT - (c) 2013 Thijs Elenbaas.
/*
CmdMessenger - library that provides command based messaging
Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.
Copyright 2013 - Thijs Elenbaas
*/
#endregion
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
namespace CommandMessenger
{
/// Class for bookkeeping which characters in the stream are escaped.
public class IsEscaped
{
private char _lastChar = '\0'; // The last character
// Returns if the character is escaped
// Note create new instance for every independent string
/// Returns if the character is escaped.
/// Note create new instance for every independent string
/// The currebt character.
/// true if the character is escaped, false if not.
public bool EscapedChar(char currChar)
{
bool escaped = (_lastChar == Escaping.EscapeCharacter);
_lastChar = currChar;
// special case: the escape char has been escaped:
if (_lastChar == Escaping.EscapeCharacter && escaped)
{
_lastChar = '\0';
}
return escaped;
}
}
/// Utility class providing escaping functions
public static class Escaping
{
// Remove all occurrences of removeChar unless it is escaped by escapeChar
private static char _fieldSeparator = ','; // The field separator
private static char _commandSeparator = ';'; // The command separator
private static char _escapeCharacter = '/'; // The escape character
/// Gets the escape character.
/// The escape character.
public static char EscapeCharacter
{
get { return _escapeCharacter; }
}
/// Sets custom escape characters.
/// The field separator.
/// The command separator.
/// The escape character.
public static void EscapeChars(char fieldSeparator, char commandSeparator, char escapeCharacter)
{
_fieldSeparator = fieldSeparator;
_commandSeparator = commandSeparator;
_escapeCharacter = escapeCharacter;
}
/// Removes all occurences of a specific character unless escaped.
/// The input.
/// The character to remove.
/// The escape character.
/// The string with all removeChars removed.
public static string Remove(string input, char removeChar, char escapeChar)
{
var output = string.Empty;
var escaped = new IsEscaped();
for (var i = 0; i < input.Length; i++)
{
char inputChar = input[i];
bool isEscaped = escaped.EscapedChar(inputChar);
if (inputChar != removeChar || isEscaped)
{
output += inputChar;
}
}
return output;
}
// Split String on separator character unless it is escaped by escapeChar
/// Splits.
/// The input.
/// The separator.
/// The escape character.
/// Options for controlling the string split.
/// The split string.
public static String[] Split(string input, char separator, char escapeCharacter,
StringSplitOptions stringSplitOptions)
{
var word = string.Empty;
var result = new List();
for (var i = 0; i < input.Length; i++)
{
var t = input[i];
if (t == separator)
{
result.Add(word);
word = string.Empty;
}
else
{
if (t == escapeCharacter)
{
word += t;
if (i < input.Length - 1) t = input[++i];
}
word += t;
}
}
result.Add(word);
if (stringSplitOptions == StringSplitOptions.RemoveEmptyEntries) result.RemoveAll(item => item == string.Empty);
return result.ToArray();
}
/// Escapes the input string.
/// The unescaped input string.
/// Escaped output string.
public static string Escape(string input)
{
var escapeChars = new[]
{
_escapeCharacter.ToString(CultureInfo.InvariantCulture),
_fieldSeparator.ToString(CultureInfo.InvariantCulture),
_commandSeparator.ToString(CultureInfo.InvariantCulture),
"\0"
};
input = escapeChars.Aggregate(input,
(current, escapeChar) =>
current.Replace(escapeChar, _escapeCharacter + escapeChar));
return input;
}
/// Unescapes the input string.
/// The escaped input string.
/// The unescaped output string.
public static string Unescape(string input)
{
string output = string.Empty;
// Move unescaped characters right
for (var fromChar = 0; fromChar < input.Length; fromChar++)
{
if (input[fromChar] == _escapeCharacter)
{
fromChar++;
}
output += input[fromChar];
}
return output;
}
}
}