diff --git a/stepmania/src/RageUtil.cpp b/stepmania/src/RageUtil.cpp index 97ce3a25fa..a6e9fa4aaa 100644 --- a/stepmania/src/RageUtil.cpp +++ b/stepmania/src/RageUtil.cpp @@ -258,6 +258,74 @@ void split( const wstring &Source, const wstring &Deliminator, vector & do_split(Source, Deliminator, AddIt, bIgnoreEmpty ); } +/* Use: + +CString str="a,b,c"; +int start = 0, size = -1; +while( 1 ) +{ + do_split( str, ",", begin, size ); + if( begin == str.end() ) + break; + str[begin] = 'Q'; +} + + */ + +template +void do_split( const S &Source, const S &Delimitor, int &begin, int &size, int len, const bool bIgnoreEmpty ) +{ + if( size != -1 ) + { + /* Start points to the beginning of the last delimiter. Move it up. */ + begin += size+Delimitor.size(); + begin = min( begin, len ); + } + + size = 0; + + if( bIgnoreEmpty ) + { + /* Skip delims. */ + while( begin + Delimitor.size() < Source.size() && + !Source.compare( begin, Delimitor.size(), Delimitor ) ) + ++begin; + } + + /* Where's the string function to find within a substring? C++ strings apparently + * are missing that ... */ + unsigned pos; + if( Delimitor.size() == 1 ) + pos = Source.find( Delimitor[0], begin ); + else + pos = Source.find( Delimitor, begin ); + if( pos == Source.npos || (int) pos > len ) + pos = len; + size = pos - begin; +} + +void split( const CString &Source, const CString &Delimitor, int &begin, int &size, int len, const bool bIgnoreEmpty ) +{ + do_split( Source, Delimitor, begin, size, len, bIgnoreEmpty ); + +} + +void split( const wstring &Source, const wstring &Delimitor, int &begin, int &size, int len, const bool bIgnoreEmpty ) +{ + do_split( Source, Delimitor, begin, size, len, bIgnoreEmpty ); +} + +void split( const CString &Source, const CString &Delimitor, int &begin, int &size, const bool bIgnoreEmpty ) +{ + do_split( Source, Delimitor, begin, size, Source.size(), bIgnoreEmpty ); +} + +void split( const wstring &Source, const wstring &Delimitor, int &begin, int &size, const bool bIgnoreEmpty ) +{ + do_split( Source, Delimitor, begin, size, Source.size(), bIgnoreEmpty ); +} + + /* * foo\fum\ -> "foo\fum\", "", "" diff --git a/stepmania/src/RageUtil.h b/stepmania/src/RageUtil.h index add817d280..69528e8640 100644 --- a/stepmania/src/RageUtil.h +++ b/stepmania/src/RageUtil.h @@ -162,9 +162,17 @@ wchar_t utf8_get_char (const char *p); int utf8_get_char_len (const char *p); bool utf8_is_valid(const CString &str); -// Splits a CString into an CStringArray according the Deliminator. +// Splits a CString into an CStringArray according the Delimitor. void split( const CString &Source, const CString &Delimitor, CStringArray& AddIt, const bool bIgnoreEmpty = true ); -void split( const wstring &Source, const wstring &Deliminator, vector &AddIt, const bool bIgnoreEmpty = true ); +void split( const wstring &Source, const wstring &Delimitor, vector &AddIt, const bool bIgnoreEmpty = true ); + +/* In-place split. */ +void split( const CString &Source, const CString &Delimitor, int &begin, int &size, const bool bIgnoreEmpty = true ); +void split( const wstring &Source, const wstring &Delimitor, int &begin, int &size, const bool bIgnoreEmpty = true ); + +/* In-place split of partial string. */ +void split( const CString &Source, const CString &Delimitor, int &begin, int &size, int len, const bool bIgnoreEmpty ); /* no default to avoid ambiguity */ +void split( const wstring &Source, const wstring &Delimitor, int &begin, int &size, int len, const bool bIgnoreEmpty ); // Joins a CStringArray to create a CString according the Deliminator. CString join( const CString &Delimitor, const CStringArray& Source );