Initial
This commit is contained in:
175
music/scanner.cpp
Normal file
175
music/scanner.cpp
Normal file
@@ -0,0 +1,175 @@
|
||||
#include <music/scanner.hpp>
|
||||
#include <music/scansymbols.hpp>
|
||||
|
||||
namespace Music
|
||||
{
|
||||
|
||||
void Scanner::init(const String &chordSymbol)
|
||||
{
|
||||
remove();
|
||||
mIndex=0;
|
||||
mLength=chordSymbol.length();
|
||||
if(!mLength)return;
|
||||
mSymbol=chordSymbol;
|
||||
}
|
||||
|
||||
char Scanner::peekChar(void)
|
||||
{
|
||||
if(mIndex>=mLength)return -1;
|
||||
return mSymbol.charAt(mIndex);
|
||||
}
|
||||
|
||||
char Scanner::nextChar()
|
||||
{
|
||||
if(mIndex+1>mLength)return -1;
|
||||
return mSymbol.charAt(mIndex++);
|
||||
}
|
||||
|
||||
void Scanner::pushBack(void)
|
||||
{
|
||||
if(!mIndex)return;
|
||||
mIndex--;
|
||||
}
|
||||
|
||||
bool Scanner::scan(const String &chordSymbol)
|
||||
{
|
||||
char symbol;
|
||||
init(chordSymbol);
|
||||
while(-1!=(symbol=nextChar()))
|
||||
{
|
||||
if(isInflection(symbol))
|
||||
scanInflection(symbol);
|
||||
else if('/'==symbol)
|
||||
scanSlash();
|
||||
else if(isdigit(symbol))
|
||||
scanDegree(symbol);
|
||||
else if('^'==symbol||'-'==symbol)
|
||||
scanMnemonic(symbol);
|
||||
else if(isalpha(symbol))
|
||||
scanAlpha(symbol);
|
||||
else
|
||||
return false;
|
||||
}
|
||||
emit(ScanSymbols::Stop1);
|
||||
if(size()<=1)return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
void Scanner::scanAlpha(char symbol)
|
||||
{
|
||||
char nextChar;
|
||||
|
||||
if(isNote(symbol))
|
||||
{
|
||||
emit(ScanSymbols::Note1,Byte(symbol));
|
||||
}
|
||||
else if(isalpha(symbol)&&!isInflection(symbol)&&!isHalfDiminished(symbol)&&!isDiminished(symbol))
|
||||
{
|
||||
string verb;
|
||||
verb+=tolower(symbol);
|
||||
while(-1!=(nextChar=this->nextChar()))
|
||||
{
|
||||
if(!isalpha(nextChar)||isInflection(nextChar))
|
||||
{
|
||||
pushBack();
|
||||
break;
|
||||
}
|
||||
verb+=tolower(nextChar);
|
||||
}
|
||||
emit(ScanSymbols::Verb1,verb);
|
||||
}
|
||||
else if(isalpha(symbol)&&isInflection(symbol))
|
||||
{
|
||||
string verb;
|
||||
emit(ScanSymbols::Note1,Byte(symbol));
|
||||
symbol=this->nextChar();
|
||||
scanInflection(symbol);
|
||||
while(-1!=(nextChar=this->nextChar()))
|
||||
{
|
||||
if(!isalpha(nextChar)||isInflection(nextChar))
|
||||
{
|
||||
pushBack();
|
||||
break;
|
||||
}
|
||||
verb+=tolower(nextChar);
|
||||
}
|
||||
emit(ScanSymbols::Verb1,verb);
|
||||
}
|
||||
else if(isalpha(symbol)&&isHalfDiminished(symbol))
|
||||
{
|
||||
emit(ScanSymbols::HalfDiminished1);
|
||||
}
|
||||
else if(isalpha(symbol)&&isDiminished(symbol))
|
||||
{
|
||||
emit(ScanSymbols::Diminished1);
|
||||
}
|
||||
else emit(ScanSymbols::Note1,Byte(symbol));
|
||||
}
|
||||
|
||||
bool Scanner::isNote(char symbol)
|
||||
{
|
||||
if('A'==symbol||'B'==symbol||'C'==symbol||'D'==symbol||'E'==symbol||'F'==symbol||'G'==symbol)return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Scanner::isInflection(char symbol)
|
||||
{
|
||||
if('b'==symbol||'#'==symbol)return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Scanner::isHalfDiminished(char symbol)
|
||||
{
|
||||
if('h'==symbol)return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Scanner::isDiminished(char symbol)
|
||||
{
|
||||
if('o'==symbol)return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
void Scanner::scanDegree(char symbol)
|
||||
{
|
||||
String str;
|
||||
|
||||
str+=symbol;
|
||||
while(-1!=(symbol=peekChar())&&isdigit(symbol))
|
||||
{
|
||||
symbol=nextChar();
|
||||
str+=symbol;
|
||||
}
|
||||
emit(ScanSymbols::Degree1,Byte(str.toInt()));
|
||||
}
|
||||
|
||||
void Scanner::scanMnemonic(char symbol)
|
||||
{
|
||||
char nextSymbol;
|
||||
|
||||
nextSymbol=peekChar();
|
||||
if(symbol=='-' && nextSymbol=='^')
|
||||
{
|
||||
emit(ScanSymbols::MinorMajor71);
|
||||
nextChar();
|
||||
}
|
||||
else if(symbol=='^')emit(ScanSymbols::Major71);
|
||||
else if(symbol=='-')emit(ScanSymbols::Minor1);
|
||||
}
|
||||
|
||||
void Scanner::scanInflection(char symbol)
|
||||
{
|
||||
if('b'==symbol)emit(ScanSymbols::Alter1,Byte(ScanSymbols::Flat1));
|
||||
else if('#'==symbol)emit(ScanSymbols::Alter1,Byte(ScanSymbols::Sharp1));
|
||||
}
|
||||
|
||||
void Scanner::scanSlash()
|
||||
{
|
||||
emit(ScanSymbols::Slash1);
|
||||
}
|
||||
|
||||
String Scanner::toString(void)const
|
||||
{
|
||||
return Emitter::toString();
|
||||
}
|
||||
};
|
||||
Reference in New Issue
Block a user