Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add worex tool to add melismatic word extenders #67

Draft
wants to merge 6 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,7 @@ set(SRCS
src/tool-filter.cpp
src/tool-hproof.cpp
src/tool-imitation.cpp
src/tool-worex.cpp
src/tool-mei2hum.cpp
src/tool-metlev.cpp
src/tool-msearch.cpp
Expand Down Expand Up @@ -154,6 +155,7 @@ set(HDRS
include/tool-fb.h
include/tool-hproof.h
include/tool-imitation.h
include/tool-worex.h
include/tool-mei2hum.h
include/tool-metlev.h
include/tool-msearch.h
Expand Down
11 changes: 10 additions & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -644,7 +644,7 @@ tool-filter.o: tool-filter.cpp tool-filter.h \
tool-composite.h tool-dissonant.h \
tool-extract.h tool-fb.h tool-homorhythm.h \
tool-homorhythm2.h tool-hproof.h \
tool-humdiff.h tool-shed.h tool-imitation.h \
tool-humdiff.h tool-shed.h tool-imitation.h tool-worex.h \
tool-kern2mens.h tool-melisma.h tool-metlev.h \
tool-msearch.h tool-myank.h tool-phrase.h \
tool-recip.h tool-restfill.h tool-satb2gs.h \
Expand Down Expand Up @@ -708,6 +708,15 @@ tool-imitation.o: tool-imitation.cpp tool-imitation.h \
NoteGrid.h NoteCell.h Convert.h \
HumRegex.h

tool-worex.o: tool-worex.cpp tool-worex.h \
HumTool.h Options.h HumdrumFileSet.h \
HumdrumFile.h HumdrumFileContent.h \
HumdrumFileStructure.h HumdrumFileBase.h \
HumSignifiers.h HumSignifier.h HumdrumLine.h \
HumdrumToken.h HumNum.h HumAddress.h \
HumHash.h HumParamSet.h HumdrumFileStream.h \
HumRegex.h

tool-kern2mens.o: tool-kern2mens.cpp tool-kern2mens.h \
HumTool.h Options.h HumdrumFileSet.h \
HumdrumFile.h HumdrumFileContent.h \
Expand Down
14 changes: 14 additions & 0 deletions cli/worex.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
//
// Programmer: Wolfgang Drescher <[email protected]>
// Creation Date: Sa 4 Feb 2023 16:27:58 CET
// Filename: worex.cpp
// URL: https://github.com/craigsapp/humlib/blob/master/cli/worex.cpp
// Syntax: C++11
// vim: ts=3 noexpandtab nowrap
//
// Description: Word extender program.
//

#include "humlib.h"

STREAM_INTERFACE(Tool_worex)
27 changes: 26 additions & 1 deletion include/humlib.h
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
//
// Programmer: Craig Stuart Sapp <[email protected]>
// Creation Date: Sat Aug 8 12:24:49 PDT 2015
// Last Modified: Thu Jan 26 22:41:11 PST 2023
// Last Modified: Mi 8 Feb 2023 14:42:01 CET
// Filename: humlib.h
// URL: https://github.com/craigsapp/humlib/blob/master/include/humlib.h
// Syntax: C++11
Expand Down Expand Up @@ -10247,6 +10247,31 @@ class Tool_trillspell : public HumTool {



class Tool_worex : public HumTool {

public:
Tool_worex (void);
~Tool_worex() {};

bool run(HumdrumFileSet& infiles);
bool run(HumdrumFile& infile);
bool run(const string& indata, ostream& out);
bool run(HumdrumFile& infile, ostream& out);

protected:
void initialize (void);
void processFile (HumdrumFile& infile);
void addWordExtenders (vector<HTp> spineStartList);
void removeWordExtenders(vector<HTp> spineStartList);
HTp getParallelNote (HTp token);


private:
bool m_removeWordExtenderQ;

};


} // end of namespace hum


Expand Down
50 changes: 50 additions & 0 deletions include/tool-worex.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
//
// Programmer: Wolfgang Drescher <[email protected]>
// Creation Date: Sa 4 Feb 2023 16:27:58 CET
// Filename: tool-worex.h
// URL: https://github.com/craigsapp/humlib/blob/master/include/tool-worex.h
// Syntax: C++11; humlib
// vim: syntax=cpp ts=3 noexpandtab nowrap
//
// Description: Interface for worex tool, which adds word extenders to the lyrics.
//

#ifndef _TOOL_WOREX_H
#define _TOOL_WOREX_H

#include "HumTool.h"
#include "HumdrumFile.h"

namespace hum {

// START_MERGE

class Tool_worex : public HumTool {

public:
Tool_worex (void);
~Tool_worex() {};

bool run(HumdrumFileSet& infiles);
bool run(HumdrumFile& infile);
bool run(const string& indata, ostream& out);
bool run(HumdrumFile& infile, ostream& out);

protected:
void initialize (void);
void processFile (HumdrumFile& infile);
void addWordExtenders (vector<HTp> spineStartList);
void removeWordExtenders(vector<HTp> spineStartList);
HTp getParallelNote (HTp token);


private:
bool m_removeWordExtenderQ;

};

// END_MERGE

} // end namespace hum

#endif /* _TOOL_WOREX_H */
202 changes: 201 additions & 1 deletion src/humlib.cpp
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
//
// Programmer: Craig Stuart Sapp <[email protected]>
// Creation Date: Sat Aug 8 12:24:49 PDT 2015
// Last Modified: Thu Jan 26 22:41:11 PST 2023
// Last Modified: Mi 8 Feb 2023 14:42:01 CET
// Filename: /include/humlib.cpp
// URL: https://github.com/craigsapp/humlib/blob/master/src/humlib.cpp
// Syntax: C++11
Expand Down Expand Up @@ -79073,6 +79073,8 @@ bool Tool_filter::run(HumdrumFileSet& infiles) {
RUNTOOL(humtr, infile, commands[i].second, status);
} else if (commands[i].first == "imitation") {
RUNTOOL(imitation, infile, commands[i].second, status);
} else if (commands[i].first == "worex") {
RUNTOOL(worex, infile, commands[i].second, status);
} else if (commands[i].first == "kern2mens") {
RUNTOOL(kern2mens, infile, commands[i].second, status);
} else if (commands[i].first == "kernview") {
Expand Down Expand Up @@ -116497,4 +116499,202 @@ int Tool_trillspell::getBase40(int diatonic, int accidental) {



//////////////////////////////
//
// Tool_worex::Tool_worex -- Set the recognized options for the tool.
//

Tool_worex::Tool_worex(void) {
define("r|remove=b", "Remove melismatic underlines at ending syllables of words");
}



//////////////////////////////
//
// Tool_worex::run -- Do the main work of the tool.
//

bool Tool_worex::run(HumdrumFileSet &infiles) {
bool status = true;
for (int i = 0; i < infiles.getCount(); i++) {
status &= run(infiles[i]);
}
return status;
}

bool Tool_worex::run(const string &indata, ostream &out) {
HumdrumFile infile(indata);
bool status = run(infile);
if (hasAnyText()) {
getAllText(out);
} else {
out << infile;
}
return status;
}

bool Tool_worex::run(HumdrumFile &infile, ostream &out) {
bool status = run(infile);
if (hasAnyText()) {
getAllText(out);
} else {
out << infile;
}
return status;
}

bool Tool_worex::run(HumdrumFile &infile) {
initialize();
processFile(infile);
return true;
}



//////////////////////////////
//
// Tool_worex::initialize --
//

void Tool_worex::initialize(void) {
m_removeWordExtenderQ = getBoolean("remove");
}



//////////////////////////////
//
// Tool_worex::processFile --
//

void Tool_worex::processFile(HumdrumFile& infile) {

vector<HTp> textSpinesStartList;
infile.getSpineStartList(textSpinesStartList, "**text");

if (m_removeWordExtenderQ) {
removeWordExtenders(textSpinesStartList);
} else {
addWordExtenders(textSpinesStartList);
}

infile.createLinesFromTokens();

m_humdrum_text << infile;
}



//////////////////////////////
//
// Tool_worex::addWordExtenders --
//

void Tool_worex::addWordExtenders(vector<HTp> spineStartList) {
for (HTp token : spineStartList) {
if (!token->isDataType("**text")) {
continue;
}
HTp currentToken = token;
while (currentToken) {
HTp parallelNoteToken = getParallelNote(currentToken);
HTp nextToken = currentToken->getNextToken();
// get token of next syllable
while (nextToken != NULL && !nextToken->isNonNullData()) {
nextToken = nextToken->getNextToken();
}
if (nextToken == NULL) {
// ignore current token if there is no next
break;
}
if (parallelNoteToken != NULL) {
// if next syllable if not direclty after the duration of the current parallel note token
if (nextToken->getDurationFromStart() > (parallelNoteToken->getDurationFromStart() + parallelNoteToken->getDuration())) {
// check if parallel note of current track is not followed by a rest
HTp nextNonNullDataToken = parallelNoteToken->getNextNonNullDataToken();
if (!nextNonNullDataToken->isRest()) {
string syllableExtender = "-";
bool isWordEnd = equal(syllableExtender.rbegin(), syllableExtender.rend(), currentToken->getText().rbegin()) == false;
string wordEndExtender = "_";
bool endsWithUnderscore = equal(wordEndExtender.rbegin(), wordEndExtender.rend(), currentToken->getText().rbegin()) == true;
// if current syllable is the end end of a word
// and the token does not alredy end with a underscore
if(isWordEnd && !endsWithUnderscore) {
currentToken->setText(currentToken->getText() + "_");
}
}
}
}
currentToken = nextToken;
}
}
}



//////////////////////////////
//
// Tool_worex::removeWordExtenders --
//

void Tool_worex::removeWordExtenders(vector<HTp> spineStartList) {
for (HTp token : spineStartList) {
if (!token->isDataType("**text")) {
continue;
}
HTp currentToken = token;
while (currentToken) {
if (currentToken->isNonNullData()) {
string wordEndExtender = "_";
bool endsWithUnderscore = equal(wordEndExtender.rbegin(), wordEndExtender.rend(), currentToken->getText().rbegin()) == true;
if (endsWithUnderscore) {
string text = currentToken->getText();
text.pop_back();
currentToken->setText(text);
}
}
currentToken = currentToken->getNextToken();
}
}
}



//////////////////////////////
//
// Tool_worex::getParallelNote -- Go backwards on the line and count any note
// attack (or tied note) on the first staff-like spine (track) found to the
// left. If there is a spine split in the text and or **kern data, then this
// algorithm needs to be refined further.
//

HTp Tool_worex::getParallelNote(hum::HTp token) {
hum::HTp current = token;
int track = -1;
while (current) {
current = current->getPreviousField();
if (!current) {
break;
}
if (current->isStaff()) {
int ctrack = current->getTrack();
if (track < 0) {
track = ctrack;
}
if (track != ctrack) {
return NULL;
}
if (current->isNull()) {
continue;
}
if (current->isNote()) {
return current;
}
}
}
return NULL;
}


} // end namespace hum
3 changes: 3 additions & 0 deletions src/tool-filter.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@
#include "tool-humsheet.h"
#include "tool-humtr.h"
#include "tool-imitation.h"
#include "tool-worex.h"
#include "tool-kern2mens.h"
#include "tool-kernview.h"
#include "tool-mei2hum.h"
Expand Down Expand Up @@ -258,6 +259,8 @@ bool Tool_filter::run(HumdrumFileSet& infiles) {
RUNTOOL(humtr, infile, commands[i].second, status);
} else if (commands[i].first == "imitation") {
RUNTOOL(imitation, infile, commands[i].second, status);
} else if (commands[i].first == "worex") {
RUNTOOL(worex, infile, commands[i].second, status);
} else if (commands[i].first == "kern2mens") {
RUNTOOL(kern2mens, infile, commands[i].second, status);
} else if (commands[i].first == "kernview") {
Expand Down
Loading