diff --git a/.gitignore b/.gitignore index f2ba980..7fa6ffc 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,3 @@ /build*/ /debug*/ - +CMakeLists.txt.user diff --git a/Changelog.txt b/Changelog.txt index c9848af..444c2a6 100644 --- a/Changelog.txt +++ b/Changelog.txt @@ -1,3 +1,8 @@ +v0.7.3 (25 Feb 2020) +- Integrated fluidsynth as an build option. +- Changes necessary for AppImage. +- Added to the manual langage selection. + v0.7.2b (25 Feb 2020) - Fixed a problem that prevented a connected MIDI piano keyboard from working. - cmake with no options now works correctly (cmake .. && make). diff --git a/src/Bar.cpp b/src/Bar.cpp index 5216fdd..8b47d1f 100644 --- a/src/Bar.cpp +++ b/src/Bar.cpp @@ -35,7 +35,6 @@ #define ppDEBUG_BAR(args) #endif - void CBar::setTimeSig(int top, int bottom) { m_currentTimeSigTop = top; @@ -111,7 +110,6 @@ void CBar::checkGotoBar() } } - void CBar::setPlayFromBar(double bar) { m_playFromBar = bar; diff --git a/src/Bar.h b/src/Bar.h index bfd2d82..aa16705 100644 --- a/src/Bar.h +++ b/src/Bar.h @@ -29,10 +29,8 @@ #ifndef __BAR_H__ #define __BAR_H__ - #include "MidiFile.h" - // The event bits can be ORed together #define EVENT_BITS_playingStopped 0x0001 // set when we reach the end of piece #define EVENT_BITS_forceFullRedraw 0x0002 // force the whole screen to be redrawn @@ -43,8 +41,6 @@ typedef unsigned long eventBits_t; - - // controls the bar numbers class CBar { @@ -97,9 +93,11 @@ public: // int getBarNumber(){ return m_barCounter;} - double getCurrentBarPos() { return m_barCounter + static_cast(m_beatCounter)/m_currentTimeSigBottom + - static_cast(m_deltaTime)/(m_beatLength * m_currentTimeSigBottom * SPEED_ADJUST_FACTOR); } - + double getCurrentBarPos() + { + return m_barCounter + static_cast(m_beatCounter)/m_currentTimeSigBottom + + static_cast(m_deltaTime)/(m_beatLength * m_currentTimeSigBottom * SPEED_ADJUST_FACTOR); + } bool seekingBarNumber() { return m_seekingBarNumber;} @@ -120,8 +118,6 @@ private: m_enablePlayFromBar = (m_enableLooping || m_playFromBar > 0.0)?true:false; } - - int m_deltaTime; int m_beatLength; //in ppqn ticks int m_barLength; // m_beatLength * getTimeSigTop() (also in ppqn ticks) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt old mode 100644 new mode 100755 index 4fb5cc1..de35293 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,9 +1,13 @@ # Cmake File for Piano Booster option(USE_FTGL "build with ftgl" ON) -option(USE_JACK "build with Jack (Only required of BSD Unix)" OFF) -option(USE_BUNDLED_RTMIDI "build with bundled rtmidi (for older distributions only)" OFF) +option(USE_JACK "build with Jack (Only required for BSD Unix)" OFF) option(USE_SYSTEM_FONT "build with system font" OFF) +if(${CMAKE_SYSTEM} MATCHES "Linux") + option(USE_BUNDLED_RTMIDI "build with bundled rtmidi (for older distributions only)" OFF) +else() + option(USE_BUNDLED_RTMIDI "build with bundled rtmidi" ON) +endif() cmake_minimum_required(VERSION 2.4) if(COMMAND cmake_policy) @@ -12,7 +16,6 @@ endif(COMMAND cmake_policy) if(WIN32) MESSAGE("GUI system is WIN32 ${CMAKE_GENERATOR}") - SET(CMAKE_COLOR_MAKEFILE OFF) endif(WIN32) # set project's name @@ -45,8 +48,10 @@ MESSAGE("CMAKE_INSTALL_BINDIR: " ${CMAKE_INSTALL_BINDIR}) FIND_PACKAGE( OpenGL REQUIRED ) -include(FindPkgConfig) -FIND_PACKAGE( PkgConfig REQUIRED ) +if(NOT WIN32) + include(FindPkgConfig) + FIND_PACKAGE( PkgConfig REQUIRED ) +endif() if(USE_FTGL) pkg_check_modules(FTGL ftgl) @@ -92,21 +97,19 @@ if(EXPERIMENTAL_USE_FLUIDSYNTH) MESSAGE("Building using fluidsynth") SET( PB_BASE_SRCS MidiDeviceFluidSynth.cpp ) - if(FLUIDSYNTH_INPLACE_DIR) + if(DEFINED ENV{FLUIDSYNTH_INPLACE_DIR}) + SET (FLUIDSYNTH_INPLACE_DIR = $ENV{FLUIDSYNTH_INPLACE_DIR}) INCLUDE_DIRECTORIES(${FLUIDSYNTH_INPLACE_DIR}/include/) if(WIN32) - LINK_LIBRARIES( ${FLUIDSYNTH_INPLACE_DIR}/src/.libs/libfluidsynth.dll.a) + LINK_LIBRARIES( $ENV{FLUIDSYNTH_INPLACE_DIR}/lib/libfluidsynth.dll.a) endif(WIN32) - if(UNIX) - LINK_LIBRARIES(${FLUIDSYNTH_INPLACE_DIR}/src/.libs/libfluidsynth.so) - endif(UNIX) - else(FLUIDSYNTH_INPLACE_DIR) + else() pkg_check_modules(FLUIDSYNTH fluidsynth) if(NOT FLUIDSYNTH_FOUND) MESSAGE(FATAL_ERROR "FLUIDSYNTH was not found") endif(NOT FLUIDSYNTH_FOUND) - LINK_LIBRARIES( fluidsynth) - endif(FLUIDSYNTH_INPLACE_DIR) + LINK_LIBRARIES(fluidsynth) + endif() endif(EXPERIMENTAL_USE_FLUIDSYNTH) # we need this to be able to include headers produced by uic in our code @@ -141,7 +144,10 @@ if(USE_BUNDLED_RTMIDI) set(PB_BASE_SRCS ${PB_BASE_SRCS} 3rdparty/rtmidi/RtMidi.cpp) set(PB_BASE_HDR ${PB_BASE_HDR} 3rdparty/rtmidi/RtMidi.h) else() - pkg_check_modules(RTMIDI REQUIRED rtmidi) + pkg_check_modules(RTMIDI rtmidi) + if(NOT RTMIDI_FOUND) + MESSAGE(FATAL_ERROR "rtmidi not found (Try building with option USE_BUNDLED_RTMIDI=ON)") + endif(NOT RTMIDI_FOUND) include_directories(${RTMIDI_INCLUDE_DIRS}) link_directories(${RTMIDI_LIBRARY_DIRS}) endif() diff --git a/src/Cfg.cpp b/src/Cfg.cpp index 96680b6..5fd891d 100644 --- a/src/Cfg.cpp +++ b/src/Cfg.cpp @@ -26,9 +26,6 @@ */ /*********************************************************************************/ - - - #include "Cfg.h" float Cfg::m_staveEndX; @@ -49,8 +46,3 @@ int Cfg::tickRate; const int Cfg::m_playZoneEarly = 25; // Was 25 const int Cfg::m_playZoneLate = 25; - - - - - diff --git a/src/Cfg.h b/src/Cfg.h index 3b65552..0787d22 100644 --- a/src/Cfg.h +++ b/src/Cfg.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -40,13 +40,11 @@ #define BENCHMARK_RESULTS() #endif - class CColor { public: CColor() { red = green = blue = 0; } - CColor(double r, double g, double b) { red = static_cast(r); @@ -86,11 +84,9 @@ public: static int chordNoteGap() {return 10;} // all notes in a cord must be spaced less than this a gap static int chordMaxLength() {return 20;} // the max time between the start and end of a cord - static CColor menuColor() {return CColor(0.1, 0.6, 0.6);} static CColor menuSelectedColor(){return CColor(0.7, 0.7, 0.1);} - static CColor staveColor() {return CColor(0.1, 0.7, 0.1);} // green static CColor staveColorDim() {return CColor(0.15, 0.40, 0.15);} // grey static CColor noteColor() {return CColor(0.1, 0.9, 0.1);} // green @@ -114,8 +110,6 @@ public: #endif } - - static void setStaveEndX(float x) { m_staveEndX = x; @@ -132,8 +126,6 @@ public: m_appHeight = height; } - - static int defaultWrongPatch() {return 7;} // Starts at 1 static int defaultRightPatch() {return 1;} // Starts at 1 diff --git a/src/Chord.cpp b/src/Chord.cpp index d06ad1f..570614f 100644 --- a/src/Chord.cpp +++ b/src/Chord.cpp @@ -68,7 +68,6 @@ whichPart_t CNote::findHand(int midiNote, int midiChannel, int whichChannel, whi return hand; } - void CChord::addNote(whichPart_t part, int note, int duration) { if (m_length >= MAX_CHORD_NOTES) @@ -166,7 +165,6 @@ bool CFindChord::findChord(CMidiEvent midi, int channel, whichPart_t part) m_noteGapTime += midi.deltaTime(); - if ((m_noteGapTime >= m_cfg_ChordNoteGap || m_cordSpanGapTime > m_cfg_ChordMaxLength) && m_currentChord.length() > 0 ) { diff --git a/src/Chord.h b/src/Chord.h index c3e6c5b..edc7787 100644 --- a/src/Chord.h +++ b/src/Chord.h @@ -47,7 +47,6 @@ typedef enum PB_PART_none, } whichPart_t; - #define MAX_CHORD_NOTES 20 // The maximum notes in a chord well we only have 10 fingers class CNote @@ -127,7 +126,6 @@ public: bool searchChord(int note, int transpose = 0); int trimOutOfRangeNotes(int transpose); - void transpose(int amount) { for (int i = 0; i < m_length; i++) @@ -165,10 +163,8 @@ private: int m_length; static int m_cfg_highestPianoNote; // The highest note on the users piano keyboard; static int m_cfg_lowestPianoNote; - }; - // Define a chord class CFindChord { @@ -188,7 +184,6 @@ public: m_cfg_ChordMaxLength = CMidiFile::ppqnAdjust(Cfg::chordMaxLength()); } - CChord getChord() { CChord chord; diff --git a/src/Conductor.cpp b/src/Conductor.cpp index f311d88..4c20d52 100644 --- a/src/Conductor.cpp +++ b/src/Conductor.cpp @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman, all rights reserved This file is part of the PianoBooster application @@ -33,7 +33,6 @@ #define ppDEBUG_CONDUCTOR(args) #endif - #include "Conductor.h" #include "Score.h" #include "Piano.h" @@ -45,9 +44,9 @@ CConductor::CConductor() { int i; - m_scoreWin = 0; - m_settings = 0; - m_piano = 0; + m_scoreWin = nullptr; + m_settings = nullptr; + m_piano = nullptr; m_songEventQueue = new CQueue(1000); m_wantedChordQueue = new CQueue(1000); @@ -104,7 +103,6 @@ void CConductor::reset() } } - //! add a midi event to be analysed and displayed on the score void CConductor::midiEventInsert(CMidiEvent event) { @@ -182,7 +180,6 @@ void CConductor::mutePart(int part, bool state) return; } - for ( channel = 0; channel < MAX_MIDI_CHANNELS; channel++) { muteChannel( channel, state); @@ -346,7 +343,6 @@ void CConductor::setPlayMode(playMode_t mode) m_piano->setRhythmTapping(m_playMode == PB_PLAY_MODE_rhythmTapping); } - void CConductor::setActiveChannel(int channel) { m_activeChannel = channel; @@ -356,7 +352,6 @@ void CConductor::setActiveChannel(int channel) activatePianistMutePart(); } - void CConductor::outputPianoVolume() { CMidiEvent event; @@ -485,7 +480,7 @@ void CConductor::resetWantedChord() // switch modes if we are playing well enough (i.e. don't slow down if we are playing late) void CConductor::setFollowSkillAdvanced(bool enable) { - if (m_settings==0 || m_scoreWin == 0) + if (m_settings==nullptr || m_scoreWin == nullptr) return; m_settings-> setAdvancedMode(enable); @@ -507,7 +502,6 @@ void CConductor::setFollowSkillAdvanced(bool enable) m_stopPoint = (enable) ? m_cfg_stopPointAdvanced: m_cfg_stopPointBeginner ; } - void CConductor::findSplitPoint() { // find the split point @@ -637,7 +631,6 @@ void CConductor::expandPianistInput(CMidiEvent inputNote) CChord chordForOneHand; int notesFound = 0; - if (inputNote.type() == MIDI_NOTE_OFF) { chord = m_piano->removeSavedChord(inputNote.note()); @@ -691,7 +684,6 @@ void CConductor::pianistInput(CMidiEvent inputNote) // inputNote.transpose(+12); fixme - if (m_testWrongNoteSound) goodSound = false; @@ -702,7 +694,6 @@ void CConductor::pianistInput(CMidiEvent inputNote) if ( inputNote.channel() == MIDI_DRUM_CHANNEL) hand = (inputNote.note() >= MIDDLE_C) ? PB_PART_right : PB_PART_left; - if (inputNote.type() == MIDI_NOTE_ON) { @@ -867,7 +858,6 @@ void CConductor::pianistInput(CMidiEvent inputNote) playTrackEvent( inputNote ); } - /* // use the same channel for the right and wrong note int pianoSound = (goodSound == true) ? m_cfg_rightNoteSound : m_cfg_wrongNoteSound; @@ -1001,7 +991,6 @@ void CConductor::realTimeEngine(int mSecTicks) m_tempo.insertPlayingTicks(ticks); - if (m_pianistTiming > m_cfg_playZoneLate) { if (m_followPlayingTimeOut == false) @@ -1032,7 +1021,6 @@ void CConductor::realTimeEngine(int mSecTicks) m_tempo.adjustTempo(&ticks); - ticks = m_bar.addDeltaTime(ticks); if (seekingBarNumber()) @@ -1164,6 +1152,7 @@ void CConductor::init2(CScore * scoreWin, CSettings* settings) m_scoreWin = scoreWin; m_settings = settings; + setQSettings(settings); setFollowSkillAdvanced(false); @@ -1179,6 +1168,5 @@ void CConductor::init2(CScore * scoreWin, CSettings* settings) m_piano = m_scoreWin->getPianoObject(); } - rewind(); } diff --git a/src/Conductor.h b/src/Conductor.h index 62dccec..aa46d1c 100644 --- a/src/Conductor.h +++ b/src/Conductor.h @@ -63,14 +63,12 @@ typedef enum { PB_RHYTHM_TAP_drumsAndMellody } rhythmTapping_t; - typedef enum { PB_STOP_POINT_MODE_automatic, PB_STOP_POINT_MODE_onTheBeat, PB_STOP_POINT_MODE_afterTheBeat } stopPointMode_t; - /*! * @brief xxxxx. */ @@ -82,7 +80,6 @@ public: void init2(CScore * scoreWin, CSettings* settings); - //! add a midi event to be analysed and played void midiEventInsert(CMidiEvent event); @@ -207,7 +204,6 @@ public: stopPointMode_t cfg_stopPointMode; rhythmTapping_t cfg_rhythmTapping; - protected: CScore* m_scoreWin; CSettings* m_settings; @@ -223,7 +219,6 @@ protected: void resetWantedChord(); void playWantedChord (CChord chord, CMidiEvent inputNote); - bool validatePianistNote( const CMidiEvent& inputNote); bool validatePianistChord(); @@ -231,10 +226,6 @@ protected: int track2Channel(int track) {return m_track2ChannelLookUp[track];} - - - - private: void allSoundOff(); void resetAllChannels(); @@ -298,7 +289,6 @@ private: CTempo m_tempo; bool m_KeyboardLightsOn; - int m_pianistSplitPoint; // Defines which notes go in the base and treble clef bool m_followSkillAdvanced; int m_lastSound; diff --git a/src/Draw.cpp b/src/Draw.cpp index 53fbc28..5d1a583 100644 --- a/src/Draw.cpp +++ b/src/Draw.cpp @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -37,6 +37,45 @@ typedef unsigned char guint8; whichPart_t CDraw::m_displayHand; int CDraw::m_forceCompileRedraw; +CDraw::CDraw(CSettings* settings) +#ifndef NO_USE_FTGL + :font(nullptr) +#endif +{ +#ifndef NO_USE_FTGL + QStringList listPathFonts; + +#if defined(USE_FONT) + listPathFonts.push_back(USE_FONT); +#endif + listPathFonts.push_back(Util::dataDir()+"/fonts/DejaVuSans.ttf"); + listPathFonts.push_back(QApplication::applicationDirPath() + "/fonts/DejaVuSans.ttf"); + listPathFonts.push_back("/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf"); + listPathFonts.push_back("/usr/share/fonts/dejavu/DejaVuSans.ttf"); + listPathFonts.push_back("/usr/share/fonts/TTF/dejavu/DejaVuSans.ttf"); + listPathFonts.push_back("/usr/share/fonts/TTF/DejaVuSans.ttf"); + listPathFonts.push_back("/usr/share/fonts/truetype/DejaVuSans.ttf"); + listPathFonts.push_back("/usr/local/share/fonts/dejavu/DejaVuSans.ttf"); + + for (int i=0;iFaceSize(FONT_SIZE, FONT_SIZE); +#endif + m_settings = settings; + m_displayHand = PB_PART_both; + m_forceCompileRedraw = 1; + m_scrollProperties = &m_scrollPropertiesHorizontal; +} + void CDraw::oneLine(float x1, float y1, float x2, float y2) { glBegin(GL_LINES); @@ -245,7 +284,6 @@ void CDraw::drawNoteName(int midiNote, float x, float y, int type) glEnd(); break; - default: glBegin(GL_LINES); glVertex2f( 3 + x, -15 + y); // 1 @@ -315,7 +353,6 @@ void CDraw::checkAccidental(CSymbol symbol, float x, float y) accidental = symbol.getStavePos().getAccidental(); - if (symbol.getAccidentalModifer() == PB_ACCIDENTAL_MODIFER_suppress) accidental = 0; // Suppress the accidental if it is the same bar @@ -339,7 +376,6 @@ void CDraw::checkAccidental(CSymbol symbol, float x, float y) } } - bool CDraw::drawNote(CSymbol* symbol, float x, float y, CSlot* slot, CColor color, bool playable) { const float stemLength = 34.0; @@ -362,7 +398,6 @@ bool CDraw::drawNote(CSymbol* symbol, float x, float y, CSlot* slot, CColor colo else if (symbol->getType() <= PB_SYMBOL_quaver) stemFlagCount = 1; - if (symbol->getType() <= PB_SYMBOL_crotchet) solidNoteHead = true; @@ -784,8 +819,6 @@ void CDraw::drawSymbol(CSymbol symbol, float x) drawSymbol(symbol, x, symbol.getStavePos().getPosY()); } - - void CDraw::drawSlot(CSlot* slot) { CStavePos stavePos; @@ -800,7 +833,6 @@ void CDraw::drawSlot(CSlot* slot) } } - void CDraw::drawStaves(float startX, float endX) { int i; @@ -827,7 +859,6 @@ void CDraw::drawStaves(float startX, float endX) glEnd(); } - void CDraw::drawKeySignature(int key) { const int sharpLookUpRight[] = { 4, 1, 5, 2,-1, 3, 0}; diff --git a/src/Draw.h b/src/Draw.h index 3d9732f..d3eb05c 100644 --- a/src/Draw.h +++ b/src/Draw.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -49,7 +49,6 @@ #include "Symbol.h" - class CSettings; class CSlot; @@ -69,43 +68,8 @@ private: class CDraw : public QObject { public: - CDraw(CSettings* settings) -#ifndef NO_USE_FTGL - :font(nullptr) -#endif - { -#ifndef NO_USE_FTGL - QStringList listPathFonts; - #if defined(USE_FONT) - listPathFonts.push_back(USE_FONT); - #endif - listPathFonts.push_back(QString(PREFIX)+"/"+QString(DATA_DIR)+"/fonts/DejaVuSans.ttf"); - listPathFonts.push_back(QApplication::applicationDirPath() + "/fonts/DejaVuSans.ttf"); - listPathFonts.push_back("/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf"); - listPathFonts.push_back("/usr/share/fonts/dejavu/DejaVuSans.ttf"); - listPathFonts.push_back("/usr/share/fonts/TTF/dejavu/DejaVuSans.ttf"); - listPathFonts.push_back("/usr/share/fonts/TTF/DejaVuSans.ttf"); - listPathFonts.push_back("/usr/share/fonts/truetype/DejaVuSans.ttf"); - listPathFonts.push_back("/usr/local/share/fonts/dejavu/DejaVuSans.ttf"); - for (int i=0;iFaceSize(FONT_SIZE, FONT_SIZE); -#endif - m_settings = settings; - m_displayHand = PB_PART_both; - m_forceCompileRedraw = 1; - m_scrollProperties = &m_scrollPropertiesHorizontal; - } + CDraw(CSettings* settings); ~CDraw(){ #ifndef NO_USE_FTGL diff --git a/src/GlView.cpp b/src/GlView.cpp index f275c84..189606a 100644 --- a/src/GlView.cpp +++ b/src/GlView.cpp @@ -42,13 +42,12 @@ #define REDRAW_COUNT ((m_cfg_openGlOptimise >= 2) ? 1 : 2) // there are two gl buffers but redrawing once is best (set 2 with buggy gl drivers) - CGLView::CGLView(QtWindow* parent, CSettings* settings) : QGLWidget(parent) { m_qtWindow = parent; m_settings = settings; - m_rating = 0; + m_rating = nullptr; m_fullRedrawFlag = true; m_forcefullRedraw = 0; m_forceRatingRedraw = 0; @@ -127,7 +126,6 @@ void CGLView::paintGL() m_score->drawScroll(m_forcefullRedraw); BENCHMARK(10, "drawScroll"); - if (m_forcefullRedraw) m_forcefullRedraw--; BENCHMARK(11, "exit"); BENCHMARK_RESULTS(); @@ -144,7 +142,7 @@ void CGLView::drawTimeSignature() float x,y; int topNumber, bottomNumber; - if (m_song == 0) return; + if (m_song == nullptr) return; m_song->getTimeSig(&topNumber, &bottomNumber); if (topNumber == 0 ) return; @@ -179,7 +177,6 @@ void CGLView::drawAccurracyBar() return; m_forceRatingRedraw--; - float accuracy; CColor color; @@ -197,7 +194,6 @@ void CGLView::drawAccurracyBar() CDraw::drColor (Cfg::backgroundColor()); glRectf(x + width * accuracy, y - lineWidth, x + width, y + lineWidth); - glLineWidth (1); CDraw::drColor (CColor(1.0, 1.0, 1.0)); glBegin(GL_LINE_LOOP); @@ -210,7 +206,7 @@ void CGLView::drawAccurracyBar() void CGLView::drawDisplayText() { - if (m_rating == 0) + if (m_rating == nullptr) { m_rating = m_song->getRating(); return; // don't run this func the first time it is called @@ -328,7 +324,6 @@ void CGLView::initializeGL() glShadeModel (GL_FLAT); //glEnable(GL_TEXTURE_2D); // Enable Texture Mapping - //from initCheck(); glShadeModel(GL_FLAT); //glEnable(GL_DEPTH_TEST); @@ -364,7 +359,6 @@ void CGLView::initializeGL() m_song->regenerateChordQueue(); - // increased the tick time for Midi handling m_timer.start(Cfg::tickRate, this ); @@ -393,7 +387,6 @@ void CGLView::timerEvent(QTimerEvent *event) return; } - updateMidiTask(); BENCHMARK(1, "m_song task"); diff --git a/src/GlView.h b/src/GlView.h index 4318060..31890d2 100644 --- a/src/GlView.h +++ b/src/GlView.h @@ -71,7 +71,6 @@ private: void drawBarNumber(); void updateMidiTask(); - QColor m_backgroundColor; QtWindow* m_qtWindow; // The parent Window CSettings* m_settings; diff --git a/src/GuiKeyboardSetupDialog.cpp b/src/GuiKeyboardSetupDialog.cpp index 2c4b3eb..0928ae5 100644 --- a/src/GuiKeyboardSetupDialog.cpp +++ b/src/GuiKeyboardSetupDialog.cpp @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -36,7 +36,7 @@ GuiKeyboardSetupDialog::GuiKeyboardSetupDialog(QWidget *parent) : QDialog(parent) { - m_song = 0; + m_song = nullptr; setupUi(this); setWindowTitle(tr("Piano Keyboard Settings")); } diff --git a/src/GuiKeyboardSetupDialog.h b/src/GuiKeyboardSetupDialog.h index ac84b60..9369b87 100644 --- a/src/GuiKeyboardSetupDialog.h +++ b/src/GuiKeyboardSetupDialog.h @@ -34,7 +34,6 @@ #include "Song.h" #include "Settings.h" - #include "ui_GuiKeyboardSetupDialog.h" class GuiKeyboardSetupDialog : public QDialog, private Ui::GuiKeyboardSetupDialog @@ -50,7 +49,6 @@ private slots: void accept(); void reject(); - void on_rightTestButton_pressed() { m_song->testWrongNoteSound(false); m_song->pcKeyPress( 'x', true); diff --git a/src/GuiLoopingPopup.cpp b/src/GuiLoopingPopup.cpp index 8548e05..94f03ed 100644 --- a/src/GuiLoopingPopup.cpp +++ b/src/GuiLoopingPopup.cpp @@ -33,12 +33,11 @@ GuiLoopingPopup::GuiLoopingPopup(QWidget *parent) : QWidget(parent) { setupUi(this); - m_song = 0; + m_song = nullptr; setWindowTitle(tr("Continuous Looping")); setWindowFlags(Qt::Popup); } - void GuiLoopingPopup::init(CSong* song) { m_song = song; @@ -54,7 +53,6 @@ void GuiLoopingPopup::updateInfo() loopingText->setText(tr("Repeat Bar is disabled")); } - void GuiLoopingPopup::on_loopBarsSpin_valueChanged(double bars) { if (!m_song) return; diff --git a/src/GuiLoopingPopup.h b/src/GuiLoopingPopup.h index 4678dc2..525adf0 100644 --- a/src/GuiLoopingPopup.h +++ b/src/GuiLoopingPopup.h @@ -29,12 +29,10 @@ #ifndef __GUILOOPINGPOPUP_H__ #define __GUILOOPINGPOPUP_H__ - #include #include "Song.h" - #include "ui_GuiLoopingPopup.h" class CGLView; diff --git a/src/GuiMidiSetupDialog.cpp b/src/GuiMidiSetupDialog.cpp old mode 100644 new mode 100755 index 8a34548..8f061ea --- a/src/GuiMidiSetupDialog.cpp +++ b/src/GuiMidiSetupDialog.cpp @@ -5,7 +5,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -28,12 +28,15 @@ #include "GuiMidiSetupDialog.h" +#if EXPERIMENTAL_USE_FLUIDSYNTH +#include "MidiDeviceFluidSynth.h" +#endif GuiMidiSetupDialog::GuiMidiSetupDialog(QWidget *parent) : QDialog(parent) { - m_song = 0; - m_settings = 0; + m_song = nullptr; + m_settings = nullptr; setupUi(this); m_latencyFix = 0; m_latencyChanged = false; @@ -53,67 +56,84 @@ void GuiMidiSetupDialog::init(CSong* song, CSettings* settings) // Check inputs. QString portName; - int i = 0; m_latencyFix = m_song->getLatencyFix(); - midiInputCombo->addItem(tr("None (PC Keyboard)")); + refreshMidiInputCombo(); + refreshMidiOutputCombo(); + masterGainSpin->setValue(40); + reverbCheck->setChecked(false); + chorusCheck->setChecked(false); - midiInputCombo->addItems(song->getMidiPortList(CMidiDevice::MIDI_INPUT)); - - - // Check outputs. - midiOutputCombo->addItem(tr("None")); - midiOutputCombo->addItems(song->getMidiPortList(CMidiDevice::MIDI_OUTPUT)); - i = midiInputCombo->findText(m_settings->value("Midi/Input").toString()); - if (i!=-1) - midiInputCombo->setCurrentIndex(i); - i = midiOutputCombo->findText(m_settings->value("Midi/Output").toString()); - if (i!=-1) - midiOutputCombo->setCurrentIndex(i); - - sampleRateCombo->addItem("44100"); - sampleRateCombo->addItem("22050"); - sampleRateCombo->setValidator(new QIntValidator(0, 999999, this)); + sampleRateCombo->addItems({"22050", "44100","48000", "88200","96000"}); + sampleRateCombo->setValidator(new QIntValidator(22050, 96000, this)); + bufferSizeCombo->addItems({"64", "128", "512", "1024", "2024", "4096","8192"}); + bufferSizeCombo->setValidator(new QIntValidator(64, 8192, this)); + bufferSizeCombo->setCurrentIndex(1); + bufferCountCombo->addItems({"2","4", "8","16", "32", "64"}); + bufferCountCombo->setValidator(new QIntValidator(2, 64, this)); + bufferCountCombo->setCurrentIndex(1); updateMidiInfoText(); audioDriverCombo->clear(); - audioDriverCombo->addItem(""); - audioDriverCombo->addItem("alsa"); - audioDriverCombo->addItem("file"); - audioDriverCombo->addItem("jack"); - audioDriverCombo->addItem("oss"); - audioDriverCombo->addItem("portaudio"); - audioDriverCombo->addItem("pulseaudio"); - setDefaultFluidSynth(); +#if defined (Q_OS_LINUX) + audioDriverCombo->addItems({"alsa","pulseaudio"}); +#elif defined (Q_OS_UNIX) || defined (Q_OS_DARWIN) + audioDriverCombo->addItems({"pulseaudio"}); +#endif - connect(audioDriverCombo,SIGNAL(currentIndexChanged(int)),this,SLOT(on_audioDriverCombo_currentIndexChanged(int))); - - if (m_settings->getFluidSoundFontNames().size()!=0){ - masterGainSpin->setValue(m_settings->value("FluidSynth/masterGainSpin","0.2").toDouble()); - bufferSizeSpin->setValue(m_settings->value("FluidSynth/bufferSizeSpin","").toInt()); - bufferCountsSpin->setValue(m_settings->value("FluidSynth/bufferCountsSpin","").toInt()); + if (m_settings->getFluidSoundFontNames().size()>0){ + masterGainSpin->setValue(m_settings->value("FluidSynth/masterGainSpin","40").toInt()); reverbCheck->setChecked(m_settings->value("FluidSynth/reverbCheck","false").toBool()); chorusCheck->setChecked(m_settings->value("FluidSynth/chorusCheck","false").toBool()); + setComboFromSetting(audioDriverCombo, "FluidSynth/audioDriverCombo","alsa"); + setComboFromSetting(sampleRateCombo, "FluidSynth/sampleRateCombo","22050"); + setComboFromSetting(bufferSizeCombo, "FluidSynth/bufferSizeCombo","128"); + setComboFromSetting(bufferCountCombo, "FluidSynth/bufferCountCombo","4"); + } - audioDeviceLineEdit->setText(m_settings->value("FluidSynth/audioDeviceLineEdit","").toString()); - for (int i=0;icount();i++){ - if (audioDriverCombo->itemText(i)==m_settings->value("FluidSynth/audioDriverCombo","").toString()){ - audioDriverCombo->setCurrentIndex(i); - break; - } - } - sampleRateCombo->setCurrentText(m_settings->value("FluidSynth/sampleRateCombo").toString()); + updateFluidInfoStatus(); +} + +void GuiMidiSetupDialog::setComboFromSetting(QComboBox *combo, const QString &key, const QVariant &defaultValue) { + QString value = m_settings->value(key, defaultValue).toString(); + int index = combo->findText(value); + + if ( index != -1 ) { // -1 for not found + combo->setCurrentIndex(index); + } else { + combo->setCurrentText(value); } +} - updateFluidInfoText(); +void GuiMidiSetupDialog::refreshMidiInputCombo() +{ + int i = 0; + midiInputCombo->clear(); + midiInputCombo->addItem(tr("None (PC Keyboard)")); + midiInputCombo->addItems(m_song->getMidiPortList(CMidiDevice::MIDI_INPUT)); + i = midiInputCombo->findText(m_settings->value("Midi/Input").toString()); + if (i!=-1) + midiInputCombo->setCurrentIndex(i); +} + +void GuiMidiSetupDialog::refreshMidiOutputCombo() +{ + int i = 0; + + // Check outputs. + midiOutputCombo->clear(); + midiOutputCombo->addItem(tr("None")); + midiOutputCombo->addItems(m_song->getMidiPortList(CMidiDevice::MIDI_OUTPUT)); + i = midiOutputCombo->findText(m_settings->value("Midi/Output").toString()); + if (i!=-1) + midiOutputCombo->setCurrentIndex(i); } void GuiMidiSetupDialog::updateMidiInfoText() { - midiInfoText->clear(); if (midiInputCombo->currentIndex() == 0) @@ -135,7 +155,7 @@ void GuiMidiSetupDialog::updateMidiInfoText() latencyFixLabel->setText(tr("%1 mSec").arg(m_latencyFix)); - updateFluidInfoText(); + updateFluidInfoStatus(); } void GuiMidiSetupDialog::on_midiInputCombo_activated (int index) @@ -168,9 +188,23 @@ void GuiMidiSetupDialog::on_latencyFixButton_clicked ( bool checked ) } } - void GuiMidiSetupDialog::accept() { + // save FluidSynth settings + if (m_settings->getFluidSoundFontNames().size()==0){ + m_settings->remove("FluidSynth"); + }else{ + m_settings->setValue("FluidSynth/masterGainSpin",masterGainSpin->value()); + m_settings->setValue("FluidSynth/bufferSizeCombo", bufferSizeCombo->currentText()); + m_settings->setValue("FluidSynth/bufferCountCombo", bufferCountCombo->currentText()); + m_settings->setValue("FluidSynth/reverbCheck",reverbCheck->isChecked()); + m_settings->setValue("FluidSynth/chorusCheck",chorusCheck->isChecked()); + m_settings->setValue("FluidSynth/audioDriverCombo",audioDriverCombo->currentText()); + m_settings->setValue("FluidSynth/sampleRateCombo",sampleRateCombo->currentText()); + } + + m_settings->saveSoundFontSettings(); + m_settings->setValue("Midi/Input", midiInputCombo->currentText()); m_song->openMidiPort(CMidiDevice::MIDI_INPUT, midiInputCombo->currentText() ); if (midiInputCombo->currentText().startsWith(tr("None"))) @@ -210,132 +244,83 @@ void GuiMidiSetupDialog::accept() m_latencyChanged = false; } - - - // save FluidSynth settings - if (m_settings->getFluidSoundFontNames().size()==0){ - m_settings->remove("FluidSynth"); - }else{ - m_settings->setValue("FluidSynth/masterGainSpin",QString::number(masterGainSpin->value(),'f',2)); - m_settings->setValue("FluidSynth/bufferSizeSpin",bufferSizeSpin->value()); - m_settings->setValue("FluidSynth/bufferCountsSpin",bufferCountsSpin->value()); - m_settings->setValue("FluidSynth/reverbCheck",reverbCheck->isChecked()); - m_settings->setValue("FluidSynth/chorusCheck",chorusCheck->isChecked()); - m_settings->setValue("FluidSynth/audioDriverCombo",audioDriverCombo->currentText()); - if (audioDriverCombo->currentText()=="alsa"){ - m_settings->setValue("FluidSynth/audioDeviceLineEdit",audioDeviceLineEdit->text()); - }else{ - m_settings->setValue("FluidSynth/audioDeviceLineEdit",""); - } - m_settings->setValue("FluidSynth/sampleRateCombo",sampleRateCombo->currentText()); - } - this->QDialog::accept(); } - -void GuiMidiSetupDialog::updateFluidInfoText() +void GuiMidiSetupDialog::updateFluidInfoStatus() { QStringList soundFontNames = m_settings->getFluidSoundFontNames(); soundFontList->clear(); - for (int i=0; i < soundFontNames.count(); i++) + if (!m_settings->getFluidSoundFontNames().isEmpty()) { - int n = soundFontNames.at(i).lastIndexOf("/"); - soundFontList->addItem(soundFontNames.at(i).mid(n+1)); + QFileInfo fileInfo = QFileInfo(m_settings->getFluidSoundFontNames().at(0)); + if (fileInfo.exists()) + { + soundFontList->addItem(fileInfo.fileName()); + } } - bool fontLoaded = (soundFontList->count() > 0) ? true : false; - fluidRemoveButton->setEnabled(fontLoaded); + fluidClearButton->setEnabled(fontLoaded); - fluidAddButton->setEnabled(soundFontList->count() < 2 ? true : false); + fluidLoadButton->setEnabled(soundFontList->count() < 2 ? true : false); fluidSettingsGroupBox->setEnabled(fontLoaded); } -void GuiMidiSetupDialog::setDefaultFluidSynth(){ - masterGainSpin->setValue(0.4); - bufferSizeSpin->setValue(128); - bufferCountsSpin->setValue(6); - reverbCheck->setChecked(false); - chorusCheck->setChecked(false); - #if defined (Q_OS_UNIX) || defined (Q_OS_DARWIN) - audioDriverCombo->setCurrentIndex(3); - audioDeviceLineEdit->setText(""); - #endif - #if defined (Q_OS_LINUX) - audioDriverCombo->setCurrentIndex(1); - audioDeviceLineEdit->setText("plughw:0"); - #endif - sampleRateCombo->setCurrentIndex(0); - -} - - -void GuiMidiSetupDialog::on_fluidAddButton_clicked ( bool checked ) +void GuiMidiSetupDialog::on_fluidLoadButton_clicked ( bool checked ) { - QStringList possibleSoundFontFolders; +#if EXPERIMENTAL_USE_FLUIDSYNTH + QString lastSoundFont = m_settings->value("LastSoundFontDir","").toString(); + + if (lastSoundFont.isEmpty()) { + + lastSoundFont = QDir::homePath(); + + QStringList possibleSoundFontFolders; #if defined (Q_OS_LINUX) || defined (Q_OS_UNIX) - possibleSoundFontFolders.push_back("/usr/share/soundfonts"); - possibleSoundFontFolders.push_back("/usr/share/sounds/sf2"); + possibleSoundFontFolders.push_back("/usr/share/soundfonts"); + possibleSoundFontFolders.push_back("/usr/share/sounds/sf2"); #endif - - QString lastSoundFont = QDir::homePath(); - - for (QString soundFontFolder:possibleSoundFontFolders){ - QDir dir(soundFontFolder); - if (dir.exists()){ - lastSoundFont=soundFontFolder; - break; + for (QString soundFontFolder:possibleSoundFontFolders){ + QDir dir(soundFontFolder); + if (dir.exists()){ + lastSoundFont=soundFontFolder; + break; + } } } + QFileInfo soundFontInfo = QFileDialog::getOpenFileName(this,tr("Open SoundFont File for fluidsynth"), + lastSoundFont, tr("SoundFont Files (*.sf2 *.sf3)")); + if (!soundFontInfo.isFile()) return; - QString soundFontName = QFileDialog::getOpenFileName(this,tr("Open SoundFont2 File for fluidsynth"), - lastSoundFont, tr("SoundFont2 Files (*.sf2)")); - if (soundFontName.isEmpty()) return; + m_settings->setFluidSoundFontNames(soundFontInfo.filePath()); + m_settings->setValue("LastSoundFontDir", soundFontInfo.path()); - m_settings->addFluidSoundFontName(soundFontName); - - updateFluidInfoText(); - - m_settings->setValue("FluidSynth/SoundFont2_1",""); - m_settings->setValue("FluidSynth/SoundFont2_2",""); - for (int i=0;igetFluidSoundFontNames().size();i++){ - m_settings->setValue("FluidSynth/SoundFont2_"+QString::number(1+i),m_settings->getFluidSoundFontNames().at(i)); - }} - -void GuiMidiSetupDialog::on_fluidRemoveButton_clicked ( bool checked ){ - if (soundFontList->currentRow()==-1) return; - - QStringList soundFontNames = m_settings->getFluidSoundFontNames(); - - m_settings->removeFluidSoundFontName(soundFontNames.at(soundFontList->currentRow())); - soundFontList->removeItemWidget(soundFontList->currentItem()); - - updateFluidInfoText(); - - m_settings->setValue("FluidSynth/SoundFont2_1",""); - m_settings->setValue("FluidSynth/SoundFont2_2",""); - for (int i=0;igetFluidSoundFontNames().size();i++){ - m_settings->setValue("FluidSynth/SoundFont2_"+QString::number(1+i),m_settings->getFluidSoundFontNames().at(i)); + if (m_settings->isNewSoundFontEntered()) + { + int i = midiOutputCombo->findText(CMidiDeviceFluidSynth::getFluidInternalName()); + if (i==-1) + midiOutputCombo->addItem(CMidiDeviceFluidSynth::getFluidInternalName()); + i = midiOutputCombo->findText(CMidiDeviceFluidSynth::getFluidInternalName()); + if (i!=-1) + midiOutputCombo->setCurrentIndex(i); } - - if (m_settings->getFluidSoundFontNames().size()==0){ - setDefaultFluidSynth(); - m_settings->remove("Fluid"); - } - + updateFluidInfoStatus(); + updateMidiInfoText(); +#endif } -void GuiMidiSetupDialog::on_audioDriverCombo_currentIndexChanged(int index){ - if (audioDriverCombo->currentText()=="alsa"){ - audioDeviceLineEdit->setEnabled(true); - if (audioDeviceLineEdit->text().isEmpty()){ - audioDeviceLineEdit->setText("plughw:0"); - } - }else{ - audioDeviceLineEdit->setEnabled(false); - audioDeviceLineEdit->setText(""); +void GuiMidiSetupDialog::on_fluidClearButton_clicked( bool checked ){ +#if EXPERIMENTAL_USE_FLUIDSYNTH + m_settings->clearFluidSoundFontNames(); + int i = midiOutputCombo->findText(CMidiDeviceFluidSynth::getFluidInternalName()); + if (i>=0) + { + midiOutputCombo->removeItem(i); + midiOutputCombo->setCurrentIndex(0); } + updateFluidInfoStatus(); +#endif } diff --git a/src/GuiMidiSetupDialog.h b/src/GuiMidiSetupDialog.h index 654a6c2..4f848a5 100644 --- a/src/GuiMidiSetupDialog.h +++ b/src/GuiMidiSetupDialog.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -50,15 +50,15 @@ private slots: void on_midiInputCombo_activated (int index); void on_midiOutputCombo_activated (int index); void on_latencyFixButton_clicked ( bool checked ); - void on_fluidAddButton_clicked ( bool checked ); - void on_fluidRemoveButton_clicked ( bool checked ); - void on_audioDriverCombo_currentIndexChanged ( int index ); + void on_fluidLoadButton_clicked ( bool checked ); + void on_fluidClearButton_clicked ( bool checked ); private: - + void setComboFromSetting(QComboBox *combo, const QString &key, const QVariant &defaultValue = QVariant()); void updateMidiInfoText(); - void updateFluidInfoText(); - void setDefaultFluidSynth(); + void refreshMidiInputCombo(); + void refreshMidiOutputCombo(); + void updateFluidInfoStatus(); CSettings* m_settings; CSong* m_song; int m_latencyFix; diff --git a/src/GuiMidiSetupDialog.ui b/src/GuiMidiSetupDialog.ui index bbed1d2..9c1c364 100644 --- a/src/GuiMidiSetupDialog.ui +++ b/src/GuiMidiSetupDialog.ui @@ -6,8 +6,8 @@ 0 0 - 535 - 439 + 562 + 408 @@ -20,7 +20,7 @@ QTabWidget::Rounded - 2 + 1 @@ -130,30 +130,50 @@ FluidSynth + + + + Qt::Vertical + + + + 20 + 40 + + + + - Sound Fonts + Sound Font - + + + + 0 + 0 + + + - + - Add + Load - + - Remove + Clear @@ -182,132 +202,124 @@ Settings - - - - - - - Chorus - - - - - - - Sample Rate: - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - Audio Driver: - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - Audio Device: - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - true - - - - - - - Buffer Counts: - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - - 150 - 0 - - - - - - - - Master Gain: - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - 999999999 - - - - - - - Reverb - - - - - - - Buffer Size: - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - - - - 999999999 - - - - - - - 10.000000000000000 - - - 0.200000000000000 - - - - + + + + + Reverb + + + + + + + Chorus + + + + + + + true + + + + + + + 200 + + + 5 + + + 100 + + + + + + + Sample Rate: + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + + + + Buffer Count: + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + Master Gain: + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + Buffer Size: + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + Audio Driver: + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + true + + + + + + + true + + + + + + Qt::Vertical + + + + 20 + 40 + + + + @@ -369,8 +381,8 @@ accept() - 248 - 254 + 257 + 429 157 @@ -385,8 +397,8 @@ reject() - 316 - 260 + 325 + 429 286 diff --git a/src/GuiPreferencesDialog.cpp b/src/GuiPreferencesDialog.cpp index 5d66ad4..4d12a71 100644 --- a/src/GuiPreferencesDialog.cpp +++ b/src/GuiPreferencesDialog.cpp @@ -5,7 +5,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -36,9 +36,9 @@ GuiPreferencesDialog::GuiPreferencesDialog(QWidget *parent) : QDialog(parent) { setupUi(this); - m_song = 0; - m_settings = 0; - m_glView = 0; + m_song = nullptr; + m_settings = nullptr; + m_glView = nullptr; setWindowTitle(tr("Preferences")); followStopPointCombo->addItem(tr("Automatic (Recommended)")); followStopPointCombo->addItem(tr("On the Beat")); @@ -52,7 +52,7 @@ void GuiPreferencesDialog::initLanguageCombo(){ QFile fileTestLocale(localeDirectory); if (!fileTestLocale.exists()){ - localeDirectory=QString(PREFIX)+"/"+QString(DATA_DIR)+"/translations/"; + localeDirectory=Util::dataDir()+"/translations/"; #ifdef Q_OS_DARWIN localeDirectory=QApplication::applicationDirPath() + "/../Resources/translations/"; #endif @@ -80,13 +80,17 @@ void GuiPreferencesDialog::initLanguageCombo(){ // loading languages languageCombo->clear(); + languageCombo->addItem("<"+tr("System Language")+">",""); languageCombo->addItem("English","en"); + if (m_settings->value("General/lang","").toString()=="en"){ + languageCombo->setCurrentIndex(languageCombo->count()-1); + } QDir dirLang(localeDirectory); dirLang.setFilter(QDir::Files | QDir::Hidden | QDir::NoDotAndDotDot); QFileInfoList listLang = dirLang.entryInfoList(); - for (int i = 0; i < listLang.size(); ++i) { - QFileInfo fileInfo = listLang.at(i); + for (QFileInfo fileInfo : listLang) { + QRegExp rx("(pianobooster_)(.*)(.qm)"); if (rx.indexIn(fileInfo.fileName())!=-1){ QString lang_code = rx.cap(2); @@ -119,7 +123,7 @@ void GuiPreferencesDialog::initLanguageCombo(){ } languageCombo->addItem(languageName,lang_code); - if (m_settings->value("General/lang",QLocale::system().bcp47Name()).toString()==lang_code){ + if (m_settings->value("General/lang","").toString()==lang_code){ languageCombo->setCurrentIndex(languageCombo->count()-1); } } @@ -163,7 +167,7 @@ void GuiPreferencesDialog::accept() m_song->cfg_stopPointMode = static_cast (followStopPointCombo->currentIndex()); m_settings->setValue("Score/StopPointMode", m_song->cfg_stopPointMode ); - m_settings->setValue("General/lang",languageCombo->currentData().toString()); + m_settings->setValue("General/lang", languageCombo->currentData().toString()); m_song->refreshScroll(); diff --git a/src/GuiPreferencesDialog.h b/src/GuiPreferencesDialog.h index 0967e3a..f474611 100644 --- a/src/GuiPreferencesDialog.h +++ b/src/GuiPreferencesDialog.h @@ -29,13 +29,11 @@ #ifndef __GUIPREFERENCESDIALOG_H__ #define __GUIPREFERENCESDIALOG_H__ - #include #include "Song.h" #include "Settings.h" - #include "ui_GuiPreferencesDialog.h" class CGLView; diff --git a/src/GuiSidePanel.cpp b/src/GuiSidePanel.cpp index efc98f1..4a7275e 100644 --- a/src/GuiSidePanel.cpp +++ b/src/GuiSidePanel.cpp @@ -33,21 +33,17 @@ #include "TrackList.h" #include "Conductor.h" - GuiSidePanel::GuiSidePanel(QWidget *parent, CSettings* settings) : QWidget(parent), m_parent(parent) { - m_song = 0; - m_score = 0; - m_trackList = 0; - m_topBar = 0; + m_song = nullptr; + m_score = nullptr; + m_trackList = nullptr; + m_topBar = nullptr; m_settings = settings; setupUi(this); - - } - void GuiSidePanel::init(CSong* songObj, CTrackList* trackList, GuiTopBar* topBar) { m_song = songObj; @@ -87,7 +83,6 @@ void GuiSidePanel::init(CSong* songObj, CTrackList* trackList, GuiTopBar* topBar on_rhythmTappingCombo_activated(m_settings->value("SidePanel/rhythmTapping",0).toInt()); rhythmTappingCombo->setCurrentIndex(m_song->cfg_rhythmTapping); - repeatSong->setChecked(m_settings->value("SidePanel/repeatSong",false).toBool()); connect(repeatSong,SIGNAL(stateChanged(int)),this,SLOT(on_repeatSong_released())); @@ -110,9 +105,6 @@ void GuiSidePanel::init(CSong* songObj, CTrackList* trackList, GuiTopBar* topBar connect(act, SIGNAL(triggered()), this, SLOT(clearTrackPart())); trackListWidget->setContextMenuPolicy(Qt::ActionsContextMenu); - - - } void GuiSidePanel::refresh() { @@ -124,7 +116,6 @@ void GuiSidePanel::refresh() { trackListWidget->addItems(m_trackList->getAllChannelProgramNames()); - trackListWidget->setCurrentRow(m_trackList->getActiveItemIndex()); for (int i = 0; i < trackListWidget->count(); i++) @@ -264,7 +255,6 @@ void GuiSidePanel::updateTranslate(){ listActionsRetranslateUi[w]=m; } - } // retranslate UI @@ -289,7 +279,6 @@ void GuiSidePanel::updateTranslate(){ retranslateUi(this); - // --- smart resize panel --- // int maxDeltaWidth=0; this->setMaximumWidth(300); // default @@ -310,7 +299,6 @@ void GuiSidePanel::updateTranslate(){ this->setMaximumWidth(300+maxDeltaWidth); } - void GuiSidePanel::on_rhythmTappingCombo_activated (int index) { m_settings->setValue("SidePanel/rhythmTapping",index); diff --git a/src/GuiSidePanel.h b/src/GuiSidePanel.h index f0761d5..6a3cf9e 100644 --- a/src/GuiSidePanel.h +++ b/src/GuiSidePanel.h @@ -143,7 +143,6 @@ private slots: autoSetMuteYourPart(); } - void on_rhythmTappingCombo_activated (int index); void on_muteYourPartCheck_toggled (bool checked) @@ -169,7 +168,6 @@ private slots: m_song->refreshScroll(); } - void clearTrackPart() { int row = trackListWidget->currentRow(); m_trackList->setActiveHandsIndex( -1, -1); @@ -177,7 +175,6 @@ private slots: m_song->refreshScroll(); } - private: void autoSetMuteYourPart(); diff --git a/src/GuiSongDetailsDialog.cpp b/src/GuiSongDetailsDialog.cpp index a04c9e1..8c84e76 100644 --- a/src/GuiSongDetailsDialog.cpp +++ b/src/GuiSongDetailsDialog.cpp @@ -33,13 +33,12 @@ GuiSongDetailsDialog::GuiSongDetailsDialog(QWidget *parent) : QDialog(parent) { setupUi(this); - m_song = 0; - m_settings = 0; - m_trackList = 0; + m_song = nullptr; + m_settings = nullptr; + m_trackList = nullptr; setWindowTitle(tr("Song Details")); } - void GuiSongDetailsDialog::init(CSong* song, CSettings* settings) { m_song = song; @@ -56,7 +55,6 @@ void GuiSongDetailsDialog::init(CSong* song, CSettings* settings) } - void GuiSongDetailsDialog::updateSongInfoText() { QString str; @@ -79,7 +77,6 @@ void GuiSongDetailsDialog::updateSongInfoText() buttonBox->button(QDialogButtonBox::Ok)->setEnabled(activateOkButton); } - void GuiSongDetailsDialog::on_leftHandChannelCombo_activated (int index) { updateSongInfoText(); diff --git a/src/GuiSongDetailsDialog.h b/src/GuiSongDetailsDialog.h index a948c6c..e7c1554 100644 --- a/src/GuiSongDetailsDialog.h +++ b/src/GuiSongDetailsDialog.h @@ -29,13 +29,11 @@ #ifndef __GUISONGDETAILSDIALOG_H__ #define __GUISONGDETAILSDIALOG_H__ - #include #include "Song.h" #include "Settings.h" - #include "ui_GuiSongDetailsDialog.h" class CGLView; diff --git a/src/GuiTopBar.cpp b/src/GuiTopBar.cpp index e886807..4ac8b09 100644 --- a/src/GuiTopBar.cpp +++ b/src/GuiTopBar.cpp @@ -32,13 +32,12 @@ #include "TrackList.h" #include "GuiLoopingPopup.h" - GuiTopBar::GuiTopBar(QWidget *parent, CSettings* settings) : QWidget(parent), m_settings(settings) { m_atTheEndOfTheSong = false; - m_song = 0; + m_song = nullptr; setupUi(this); parent->installEventFilter(this); @@ -206,7 +205,6 @@ void GuiTopBar::updateTranslate(){ retranslateUi(this); } - void GuiTopBar::on_playButton_clicked(bool clicked) { if (!m_song) return; @@ -246,8 +244,6 @@ void GuiTopBar::on_startBarSpin_valueChanged(double bar) m_song->setPlayFromBar( bar); } - - void GuiTopBar::on_saveBarButton_clicked(bool clicked) { if (!m_song) return; @@ -255,7 +251,6 @@ void GuiTopBar::on_saveBarButton_clicked(bool clicked) startBarSpin->setValue(barNumber); } - void GuiTopBar::on_loopingBarsPopupButton_clicked(bool clicked) { if (!m_song) return; diff --git a/src/GuiTopBar.h b/src/GuiTopBar.h index b009475..25fef58 100644 --- a/src/GuiTopBar.h +++ b/src/GuiTopBar.h @@ -74,7 +74,6 @@ private slots: void on_saveBarButton_clicked(bool clicked); void on_loopingBarsPopupButton_clicked(bool clicked); - private: bool eventFilter(QObject *obj, QEvent *event); void reloadKeyCombo(bool major); diff --git a/src/Merge.cpp b/src/Merge.cpp index f2dfacc..c6e9276 100644 --- a/src/Merge.cpp +++ b/src/Merge.cpp @@ -28,9 +28,6 @@ #include "Merge.h" - - - void CMerge::initMergedEvents() { int i; @@ -42,16 +39,15 @@ void CMerge::initMergedEvents() } } - int CMerge::nextMergedEvent() { int nearestIndex = 0; - + int i; CMidiEvent* nearestEvent; int deltaTime; - nearestEvent = 0; + nearestEvent = nullptr; // find the first active slot for( i = 0; i < m_mergeEvents.size(); i++) { @@ -62,7 +58,7 @@ int CMerge::nextMergedEvent() break; } } - if (nearestEvent == 0) + if (nearestEvent == nullptr) return 0; // now search the remaining active slots @@ -89,11 +85,10 @@ int CMerge::nextMergedEvent() if (m_mergeEvents[i].type() != MIDI_NONE) m_mergeEvents[i].addDeltaTime( deltaTime ); } - + return nearestIndex; } - CMidiEvent CMerge::readMidiEvent() { int mergeIdx; diff --git a/src/MidiDevice.cpp b/src/MidiDevice.cpp index 0d597b8..779965b 100644 --- a/src/MidiDevice.cpp +++ b/src/MidiDevice.cpp @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman, all rights reserved This file is part of the PianoBooster application @@ -32,9 +32,6 @@ #include "MidiDeviceFluidSynth.h" #endif - - - CMidiDevice::CMidiDevice() { m_rtMidiDevice = new CMidiDeviceRt(); @@ -54,10 +51,12 @@ CMidiDevice::~CMidiDevice() #endif } - - void CMidiDevice::init() { +#if EXPERIMENTAL_USE_FLUIDSYNTH + m_fluidSynthMidiDevice->setQSettings(qsettings); +#endif + } QStringList CMidiDevice::getMidiPortList(midiType_t type) @@ -108,29 +107,27 @@ bool CMidiDevice::openMidiPort(midiType_t type, QString portName) void CMidiDevice::closeMidiPort(midiType_t type, int index) { - if (m_selectedMidiOutputDevice == 0) + if (m_selectedMidiOutputDevice == nullptr) return; m_selectedMidiOutputDevice->closeMidiPort(type, index); - - m_selectedMidiOutputDevice = 0; + m_selectedMidiOutputDevice = nullptr; } //! add a midi event to be played immediately void CMidiDevice::playMidiEvent(const CMidiEvent & event) { - if (m_selectedMidiOutputDevice == 0) + if (m_selectedMidiOutputDevice == nullptr) return; m_selectedMidiOutputDevice->playMidiEvent(event); //event.printDetails(); // useful for debugging } - // Return the number of events waiting to be read from the midi device int CMidiDevice::checkMidiInput() { - if (m_selectedMidiInputDevice == 0) + if (m_selectedMidiInputDevice == nullptr) return 0; return m_selectedMidiInputDevice->checkMidiInput(); @@ -142,7 +139,6 @@ CMidiEvent CMidiDevice::readMidiInput() return m_selectedMidiInputDevice->readMidiInput(); } - int CMidiDevice::midiSettingsSetStr(QString name, QString str) { if (m_selectedMidiOutputDevice) diff --git a/src/MidiDevice.h b/src/MidiDevice.h index e043381..9ce5bc7 100644 --- a/src/MidiDevice.h +++ b/src/MidiDevice.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -63,7 +63,6 @@ public: virtual int midiSettingsGetInt(QString name); private: - CMidiDeviceBase* m_rtMidiDevice; #if EXPERIMENTAL_USE_FLUIDSYNTH CMidiDeviceBase* m_fluidSynthMidiDevice; diff --git a/src/MidiDeviceBase.h b/src/MidiDeviceBase.h index 413ea64..7b3404d 100644 --- a/src/MidiDeviceBase.h +++ b/src/MidiDeviceBase.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -28,19 +28,16 @@ #ifndef __MIDI_DEVICE_BASE_H__ #define __MIDI_DEVICE_BASE_H__ +#include #include +#include #include "Util.h" #include "Cfg.h" -/*! - * @brief xxxxx. - */ - #include "MidiEvent.h" - -class CMidiDeviceBase +class CMidiDeviceBase : public QObject { public: virtual void init() = 0; @@ -62,12 +59,15 @@ public: virtual QString midiSettingsGetStr(QString name) = 0; virtual double midiSettingsGetNum(QString name) = 0; virtual int midiSettingsGetInt(QString name) = 0; + void setQSettings(QSettings* settings) {qsettings = settings;} //you should always have a virtual destructor when using virtual functions virtual ~CMidiDeviceBase() {}; - +protected: + QSettings* qsettings = nullptr; private: + }; #endif //__MIDI_DEVICE_H__ diff --git a/src/MidiDeviceFluidSynth.cpp b/src/MidiDeviceFluidSynth.cpp old mode 100644 new mode 100755 index c945fd2..6eaaa90 --- a/src/MidiDeviceFluidSynth.cpp +++ b/src/MidiDeviceFluidSynth.cpp @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman, all rights reserved This file is part of the PianoBooster application @@ -28,15 +28,11 @@ #include "MidiDeviceFluidSynth.h" -#include -#include -#include - CMidiDeviceFluidSynth::CMidiDeviceFluidSynth() { - m_synth = 0; - m_fluidSettings = 0; - m_audioDriver = 0; + m_synth = nullptr; + m_fluidSettings = nullptr; + m_audioDriver = nullptr; m_rawDataIndex = 0; } @@ -45,35 +41,24 @@ CMidiDeviceFluidSynth::~CMidiDeviceFluidSynth() closeMidiPort(MIDI_OUTPUT, -1); } - - void CMidiDeviceFluidSynth::init() { } - QStringList CMidiDeviceFluidSynth::getMidiPortList(midiType_t type) { - if (type != MIDI_OUTPUT) // Only has an output return QStringList(); - //debugSettings(("getSongList %s + %d", qPrintable(getCurrentBookName()), qPrintable(m_bookPath))); - QDir dirSoundFont("soundfont"); - dirSoundFont.setFilter(QDir::Files); - QStringList fileNames = dirSoundFont.entryList(); + if (qsettings==nullptr) + return QStringList(); - QStringList portNames; + QStringList fontList = qsettings->value("FluidSynth/SoundFont").toStringList(); - for (int i = 0; i < fileNames.size(); i++) - { - if ( fileNames.at(i).endsWith(".sf2", Qt::CaseInsensitive ) ) - { - portNames += fileNames.at(i); - } + if (fontList.size() > 0){ + return QStringList(getFluidInternalName()); } - - return portNames; + return fontList; } bool CMidiDeviceFluidSynth::openMidiPort(midiType_t type, QString portName) @@ -85,51 +70,47 @@ bool CMidiDeviceFluidSynth::openMidiPort(midiType_t type, QString portName) if (type == MIDI_INPUT) return false; - + + if (!portName.endsWith(FLUID_NAME)) return false; + if (getMidiPortList(type).size()==0) return false; - /* Create the settings. */ + // Load a SoundFont + QStringList fontList = qsettings->value("FluidSynth/SoundFont").toStringList(); + if (fontList.size() == 0) return false; + + // Create the settings. m_fluidSettings = new_fluid_settings(); - /* Change the settings if necessary*/ + // Change the settings if necessary + fluid_settings_setnum(m_fluidSettings, "synth.sample-rate", qsettings->value("FluidSynth/sampleRateCombo",22050).toInt()); + fluid_settings_setint(m_fluidSettings, "audio.period-size", qsettings->value("FluidSynth/bufferSizeCombo", 128).toInt()); + fluid_settings_setint(m_fluidSettings, "audio.periods", qsettings->value("FluidSynth/bufferCountCombo", 4).toInt()); - fluid_settings_setnum(m_fluidSettings, (char *)"synth.sample-rate", 22050.0); - fluid_settings_setint(m_fluidSettings, "audio.periods", 5); - fluid_settings_setint(m_fluidSettings, "audio.period-size", 128); +#if defined (Q_OS_LINUX) + fluid_settings_setstr(m_fluidSettings, "audio.driver", qsettings->value("FluidSynth/audioDriverCombo", "alsa").toString().toStdString().c_str()); +#endif - fluid_settings_setstr(m_fluidSettings, "audio.alsa.device", "plughw:0"); - - - - - - /* Create the synthesizer. */ + // Create the synthesizer. m_synth = new_fluid_synth(m_fluidSettings); fluid_synth_set_reverb_on(m_synth, 0); fluid_synth_set_chorus_on(m_synth, 0); - - /* Create the audio driver. The synthesizer starts playing as soon - as the driver is created. */ + // Create the audio driver. m_audioDriver = new_fluid_audio_driver(m_fluidSettings, m_synth); - /* Load a SoundFont*/ - m_soundFontId = fluid_synth_sfload(m_synth, "FluidR3_GM.sf2", 0); - //m_soundFontId = fluid_synth_sfload(m_synth, "VintageDreamsWaves-v2.sf2", 0); - - /* Select bank 0 and preset 0 in the SoundFont we just loaded on - channel 0 */ - //fluid_synth_program_select(m_synth, 0, m_soundFontId, 0, 0); - + QString pathName = fontList.at(0); + ppLogDebug("Sound font %s", qPrintable(pathName)); + m_soundFontId = fluid_synth_sfload(m_synth, qPrintable(pathName), 0); + if (m_soundFontId == -1) + return false; for (int channel = 0; channel < MAX_MIDI_CHANNELS ; channel++) { - //fluid_synth_program_select(m_synth, channel, m_soundFontId, 0, GM_PIANO_PATCH); - fluid_synth_program_change(m_synth, channel, GM_PIANO_PATCH); + fluid_synth_program_change(m_synth, channel, GM_PIANO_PATCH); } - fluid_synth_set_gain(m_synth, 0.4); - + fluid_synth_set_gain(m_synth, qsettings->value("FluidSynth/masterGainSpin", 40).toFloat()/100.0f ); return true; } @@ -138,14 +119,14 @@ void CMidiDeviceFluidSynth::closeMidiPort(midiType_t type, int index) if (type != MIDI_OUTPUT) return; - if (m_fluidSettings == 0) + if (m_fluidSettings == nullptr) return; /* Clean up */ delete_fluid_audio_driver(m_audioDriver); delete_fluid_synth(m_synth); delete_fluid_settings(m_fluidSettings); - m_fluidSettings = 0; + m_fluidSettings = nullptr; m_rawDataIndex = 0; } @@ -153,11 +134,10 @@ void CMidiDeviceFluidSynth::closeMidiPort(midiType_t type, int index) //! add a midi event to be played immediately void CMidiDeviceFluidSynth::playMidiEvent(const CMidiEvent & event) { - - if (m_synth == 0) + if (m_synth == nullptr) return; - unsigned int channel; + int channel; channel = event.channel() & 0x0f; @@ -212,7 +192,6 @@ void CMidiDeviceFluidSynth::playMidiEvent(const CMidiEvent & event) //event.printDetails(); // useful for debugging } - // Return the number of events waiting to be read from the midi device int CMidiDeviceFluidSynth::checkMidiInput() { @@ -226,8 +205,6 @@ CMidiEvent CMidiDeviceFluidSynth::readMidiInput() return midiEvent; } - - int CMidiDeviceFluidSynth::midiSettingsSetStr(QString name, QString str) { if (!m_fluidSettings) diff --git a/src/MidiDeviceFluidSynth.h b/src/MidiDeviceFluidSynth.h index 1282279..1caf59d 100644 --- a/src/MidiDeviceFluidSynth.h +++ b/src/MidiDeviceFluidSynth.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman, all rights reserved This file is part of the PianoBooster application @@ -29,12 +29,10 @@ #ifndef __MIDI_DEVICE_FLUIDSYNTH_H__ #define __MIDI_DEVICE_FLUIDSYNTH_H__ - #include "MidiDeviceBase.h" #include - class CMidiDeviceFluidSynth : public CMidiDeviceBase { virtual void init(); @@ -59,9 +57,13 @@ public: CMidiDeviceFluidSynth(); ~CMidiDeviceFluidSynth(); + static QString getFluidInternalName() + { + return QString(tr("Internal Sound") + " " + FLUID_NAME ); + } private: - + static constexpr const char* FLUID_NAME = "(FluidSynth)"; unsigned char m_savedRawBytes[40]; // Raw data is used for used for a SYSTEM_EVENT unsigned int m_rawDataIndex; @@ -69,8 +71,6 @@ private: fluid_synth_t* m_synth; fluid_audio_driver_t* m_audioDriver; int m_soundFontId; - - }; #endif //__MIDI_DEVICE_FLUIDSYNTH_H__ diff --git a/src/MidiDeviceRt.cpp b/src/MidiDeviceRt.cpp index 8e35bef..675f373 100644 --- a/src/MidiDeviceRt.cpp +++ b/src/MidiDeviceRt.cpp @@ -28,7 +28,6 @@ #include "MidiDeviceRt.h" - CMidiDeviceRt::CMidiDeviceRt() { try { @@ -47,7 +46,6 @@ CMidiDeviceRt::CMidiDeviceRt() exit(1); } - m_midiPorts[0] = -1; m_midiPorts[1] = -1; m_rawDataIndex = 0; @@ -97,7 +95,6 @@ QStringList CMidiDeviceRt::getMidiPortList(midiType_t type) portNameList << name; } - return portNameList; } @@ -107,7 +104,6 @@ bool CMidiDeviceRt::openMidiPort(midiType_t type, QString portName) QString name; RtMidi* midiDevice; - if (portName.length() == 0) return false; @@ -152,7 +148,6 @@ void CMidiDeviceRt::closeMidiPort(midiType_t type, int index) m_midiout->closePort(); } - //! add a midi event to be played immediately void CMidiDeviceRt::playMidiEvent(const CMidiEvent & event) { @@ -218,7 +213,7 @@ void CMidiDeviceRt::playMidiEvent(const CMidiEvent & event) default: return; - break; + } m_midiout->sendMessage( &message ); @@ -226,7 +221,6 @@ void CMidiDeviceRt::playMidiEvent(const CMidiEvent & event) //event.printDetails(); // useful for debugging } - // Return the number of events waiting to be read from the midi device int CMidiDeviceRt::checkMidiInput() { @@ -242,7 +236,6 @@ CMidiEvent CMidiDeviceRt::readMidiInput() CMidiEvent midiEvent; unsigned int channel; - if (Cfg::midiInputDump) { QString str; @@ -298,7 +291,6 @@ CMidiEvent CMidiDeviceRt::readMidiInput() return midiEvent; } - int CMidiDeviceRt::midiSettingsSetStr(QString name, QString str) { return 0; diff --git a/src/MidiEvent.h b/src/MidiEvent.h index d937b2b..246a245 100644 --- a/src/MidiEvent.h +++ b/src/MidiEvent.h @@ -47,7 +47,6 @@ #define MIDI_ALL_SOUND_OFF 120 #define MIDI_ALL_NOTES_OFF 123 //0x7B channel mode message - // now define some of our own events #define MIDI_NONE 0x0ff0 #define MIDI_ERROR 0x0ff1 @@ -82,11 +81,8 @@ #define METAKEYSIG 0x59 #define METASEQEVENT 0x7F - - #define GM_PIANO_PATCH 0 // The default grand piano sound - /*! * @brief xxxxx. */ @@ -292,7 +288,6 @@ public: return r; } - void printDetails() { if (type() == MIDI_NOTE_ON) { @@ -316,5 +311,4 @@ private: int m_duration; }; - #endif //__MIDI_EVENT_H__ diff --git a/src/MidiFile.cpp b/src/MidiFile.cpp index dc93ee5..5175fcf 100644 --- a/src/MidiFile.cpp +++ b/src/MidiFile.cpp @@ -26,7 +26,6 @@ int CMidiFile::m_ppqn = DEFAULT_PPQN; - /* Read 16 bits from the Standard MIDI file */ int CMidiFile::readWord(void) { @@ -79,7 +78,6 @@ int CMidiFile::readHeader(void) return i; } - void CMidiFile::openMidiFile(string filename) { if (m_file.is_open()) @@ -89,14 +87,14 @@ void CMidiFile::openMidiFile(string filename) m_file.open(filename.c_str(), ios_base::in | ios_base::binary); if (m_file.fail() == true) { - QMessageBox::warning(0, QMessageBox::tr("Midi File Error"), + QMessageBox::warning(nullptr, QMessageBox::tr("Midi File Error"), QMessageBox::tr("Cannot open \"%1\"").arg(QString(filename.c_str()))); midiError(SMF_CANNOT_OPEN_FILE); return; } rewind(); if (getMidiError() != SMF_NO_ERROR) - QMessageBox::warning(0, QMessageBox::tr("Midi File Error"), + QMessageBox::warning(nullptr, QMessageBox::tr("Midi File Error"), QMessageBox::tr("Midi file \"%1\" is corrupted").arg(QString(filename.c_str()))); } @@ -127,10 +125,10 @@ void CMidiFile::rewind() } for (trk = 0; trk < arraySize(m_tracks); trk++) { - if (m_tracks[trk]!= 0) + if (m_tracks[trk]!= nullptr) { delete (m_tracks[trk]); - m_tracks[trk] = 0; + m_tracks[trk] = nullptr; } } filePos = m_file.tellg(); @@ -160,7 +158,7 @@ bool CMidiFile::checkMidiEventFromStream(int streamIdx) assert("streamIdx out of range"); return false; } - if (m_tracks[streamIdx] != 0 && m_tracks[streamIdx]->length() > 0) + if (m_tracks[streamIdx] != nullptr && m_tracks[streamIdx]->length() > 0) return true; return false; } diff --git a/src/MidiTrack.cpp b/src/MidiTrack.cpp index fc9759d..9c87992 100644 --- a/src/MidiTrack.cpp +++ b/src/MidiTrack.cpp @@ -42,7 +42,7 @@ int CMidiTrack::m_logLevel; CMidiTrack::CMidiTrack(fstream& file, int no) :m_file(file), m_trackNumber(no) { - m_trackEventQueue = 0; + m_trackEventQueue = nullptr; m_savedRunningStatus = 0; m_trackLengthCounter = 0; m_deltaTime = 0; @@ -51,7 +51,7 @@ CMidiTrack::CMidiTrack(fstream& file, int no) :m_file(file), m_trackNumber(no) for ( int chan = 0; chan (m_trackLength/3); // The minimum bytes per event is 3 } - - void CMidiTrack::ppDebugTrack(int level, const char *msg, ...) { va_list ap; @@ -91,7 +89,6 @@ void CMidiTrack::ppDebugTrack(int level, const char *msg, ...) fputc('\n', stdout); } - dword_t CMidiTrack::readVarLen() { dword_t value; @@ -247,8 +244,6 @@ void CMidiTrack::readKeySignatureEvent() CStavePos::setKeySignature(event.data1(), event.data2()); } - - void CMidiTrack::readMetaEvent(byte_t type) { string text; @@ -368,7 +363,6 @@ void CMidiTrack::readMetaEvent(byte_t type) } } - void CMidiTrack::decodeSystemMessage( byte_t status, byte_t data1 ) { switch ( status ) @@ -408,8 +402,7 @@ void CMidiTrack::noteOffEvent(CMidiEvent &event, int deltaTime, int channel, int { ppLogWarn("Missing note off duration Chan %d Note off %d", channel + 1, pitch); } - m_noteOnEventPtr[channel][pitch] = 0; - + m_noteOnEventPtr[channel][pitch] = nullptr; event.noteOffEvent(deltaTime, channel, pitch, velocity); diff --git a/src/MidiTrack.h b/src/MidiTrack.h index c47724a..7c0b356 100644 --- a/src/MidiTrack.h +++ b/src/MidiTrack.h @@ -36,8 +36,6 @@ using namespace std; - - typedef enum { SMF_NO_ERROR, @@ -48,8 +46,6 @@ typedef enum SMF_END_OF_FILE } midiErrors_t; - - typedef unsigned char byte_t; typedef unsigned short word_t; typedef unsigned long dword_t; @@ -91,7 +87,6 @@ public: static void setLogLevel(int level){m_logLevel = level;} - private: void errorFail(midiErrors_t error) { @@ -104,7 +99,6 @@ private: } void midiFailReset() { m_midiError = SMF_NO_ERROR;} - void ppDebugTrack(int level, const char *msg, ...); byte_t readByte(void) @@ -123,7 +117,6 @@ private: return c; } - word_t readWord(void) { word_t value; @@ -156,7 +149,6 @@ private: void decodeSystemMessage( byte_t status, byte_t data1 ); void noteOffEvent(CMidiEvent &event, int deltaTime, int channel, int pitch, int velocity); - void createNoteEventPtr(int channel) { if (m_noteOnEventPtr[channel] == 0) diff --git a/src/Notation.cpp b/src/Notation.cpp index 24051d5..5bd780f 100644 --- a/src/Notation.cpp +++ b/src/Notation.cpp @@ -26,11 +26,9 @@ */ /*********************************************************************************/ - #include "Notation.h" #include "Cfg.h" - #define OPTION_DEBUG_NOTATION 0 #if OPTION_DEBUG_NOTATION #define ppDEBUG_NOTATION(args) ppLogDebug args @@ -38,7 +36,6 @@ #define ppDEBUG_NOTATION(args) #endif - #define MERGESLOT_NOTE_INDEX 0 #define MERGESLOT_BEATMARK_INDEX 1 @@ -193,7 +190,7 @@ accidentalModifer_t CNotation::detectSuppressedNatural(int note) } if (pBackLink) { - pNoteState->setBackLink(0); + pNoteState->setBackLink(nullptr); pBackLink->setBarChange(-1); // this prevents further suppression on the original note } @@ -212,7 +209,6 @@ void CNotation::setupNotationParamaters() cfg_param[NOTATE_semibreveBoundary] = CMidiFile::ppqnAdjust(DEFAULT_PPQN*4 + 10); } - void CNotation::calculateScoreNoteLength() { if (!Cfg::experimentalNoteLength) diff --git a/src/Notation.h b/src/Notation.h index 26e8103..45cc127 100644 --- a/src/Notation.h +++ b/src/Notation.h @@ -37,7 +37,6 @@ #include "Chord.h" #include "Bar.h" - #define MAX_SYMBOLS 20 // The maximum number of symbols that can be stored in one slot class CSlot @@ -79,7 +78,6 @@ public: addSymbol(symbol); } - void transpose(int amount) { for (int i = 0; i < m_length; i++) @@ -152,7 +150,6 @@ public: void setBackLink(CNoteState * link){m_backLink = link;} CNoteState * getBackLink(){return m_backLink;} - private: int m_barChangeCounter; accidentalModifer_t m_accidentalState; @@ -191,7 +188,6 @@ public: void setChannel(int channel) {m_displayChannel = channel;} - CSlot nextSlot(); void midiEventInsert(CMidiEvent event); @@ -200,7 +196,6 @@ public: static void setCourtesyAccidentals(bool setting){m_cfg_displayCourtesyAccidentals = setting;} static bool displayCourtesyAccidentals(){return m_cfg_displayCourtesyAccidentals; } - private: CSlot nextBeatMarker(); int nextMergeSlot(); @@ -211,7 +206,6 @@ private: void calculateScoreNoteLength(); - CQueue* m_slotQueue; // Queue of symbol slots that have not been read yet CQueue* m_midiInputQueue; // A Queue of midi events CSlot m_currentSlot; diff --git a/src/Piano.cpp b/src/Piano.cpp index 10a589f..707f51b 100644 --- a/src/Piano.cpp +++ b/src/Piano.cpp @@ -38,7 +38,6 @@ static const float minNameGap = 14.0; - void CPiano::spaceNoteBunch(unsigned int bottomIndex, unsigned int topIndex) { unsigned int midPoint; @@ -110,7 +109,6 @@ void CPiano::drawPianoInputLines(CChord* chord, CColor color, int lineLength) CStavePos stavePos; - for ( i = 0; i < chord->length(); i++) { if (!m_rhythmTapping) @@ -233,7 +231,6 @@ void CPiano::addPianistNote(whichPart_t part, CMidiEvent midiNote, bool good) else m_badChord.addNote(part, note); - posY = stavePos.getPosYAccidental(); addNoteNameItem(posY, note, 0); } diff --git a/src/QtMain.cpp b/src/QtMain.cpp index 97efb37..20d445b 100644 --- a/src/QtMain.cpp +++ b/src/QtMain.cpp @@ -52,13 +52,11 @@ int main(int argc, char *argv[]){ QApplication app(argc, argv); if (!QGLFormat::hasOpenGL()) { - QMessageBox::information(0, QMessageBox::tr("OpenGL support"), + QMessageBox::information(nullptr, QMessageBox::tr("OpenGL support"), QMessageBox::tr("This system does not support OpenGL which is needed to run Piano Booster.")); return -1; } - - QtWindow window; window.show(); @@ -67,4 +65,3 @@ int main(int argc, char *argv[]){ closeLogs(); return value; } - diff --git a/src/QtWindow.cpp b/src/QtWindow.cpp index c0f626a..0c3d38a 100644 --- a/src/QtWindow.cpp +++ b/src/QtWindow.cpp @@ -5,7 +5,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -52,7 +52,6 @@ static int set_realtime_priority(int policy, int prio) } #endif - QtWindow::QtWindow() { m_settings = new CSettings(this); @@ -73,9 +72,8 @@ QtWindow::QtWindow() } for (int i = 0; i < MAX_RECENT_FILES; ++i) - m_recentFileActs[i] = 0; - m_separatorAct = 0; - + m_recentFileActs[i] = nullptr; + m_separatorAct = nullptr; #if USE_REALTIME_PRIORITY int rt_prio = sched_get_priority_max(SCHED_FIFO); @@ -88,7 +86,6 @@ QtWindow::QtWindow() m_song = m_glWidget->getSongObject(); m_score = m_glWidget->getScoreObject(); - QHBoxLayout *mainLayout = new QHBoxLayout; QVBoxLayout *columnLayout = new QVBoxLayout; @@ -133,7 +130,6 @@ QtWindow::QtWindow() m_song->cfg_stopPointMode = static_cast (m_settings->value("Score/StopPointMode", m_song->cfg_stopPointMode ).toInt()); m_song->cfg_rhythmTapping = static_cast (m_settings->value("Score/RtyhemTappingMode", m_song->cfg_rhythmTapping ).toInt()); - m_song->openMidiPort(CMidiDevice::MIDI_INPUT, midiInputName); m_song->openMidiPort(CMidiDevice::MIDI_OUTPUT,m_settings->value("Midi/Output").toString()); @@ -220,7 +216,7 @@ void QtWindow::decodeMidiFileArg(QString arg) if (!fileInfo.exists() ) { - QMessageBox::warning(0, tr("PianoBooster Midi File Error"), + QMessageBox::warning(nullptr, tr("PianoBooster Midi File Error"), tr("Cannot open \"%1\"").arg(QString(fileInfo.absoluteFilePath()))); exit(1); } @@ -228,7 +224,7 @@ void QtWindow::decodeMidiFileArg(QString arg) fileInfo.fileName().endsWith(".midi", Qt::CaseInsensitive ) || fileInfo.fileName().endsWith(".kar", Qt::CaseInsensitive )) ) { - QMessageBox::warning(0, tr("PianoBooster Midi File Error"), + QMessageBox::warning(nullptr, tr("PianoBooster Midi File Error"), tr("\"%1\" is not a Midi File").arg(QString(fileInfo.fileName()))); exit(1); } @@ -252,7 +248,7 @@ void QtWindow::decodeMidiFileArg(QString arg) m_settings->setValue("CurrentSong", fileInfo.absoluteFilePath()); else { - QMessageBox::warning(0, tr("PianoBooster Midi File Error"), + QMessageBox::warning(nullptr, tr("PianoBooster Midi File Error"), tr("\"%1\" is not a valid Midi file").arg(QString(fileInfo.absoluteFilePath()))); exit(1); } @@ -411,15 +407,12 @@ void QtWindow::createActions() addShortcutAction("ShortCuts/NextBook", SLOT(on_nextBook())); addShortcutAction("ShortCuts/PreviousBook", SLOT(on_previousBook())); - for (int i = 0; i < MAX_RECENT_FILES; ++i) { m_recentFileActs[i] = new QAction(this); m_recentFileActs[i]->setVisible(false); connect(m_recentFileActs[i], SIGNAL(triggered()), this, SLOT(openRecentFile())); } - - } void QtWindow::createMenus() @@ -467,9 +460,10 @@ void QtWindow::createMenus() m_helpMenu->addAction(m_shortcutAct); m_helpMenu->addAction(m_aboutAct); } + void QtWindow::openRecentFile() - { - QAction *action = qobject_cast(sender()); +{ + QAction *action = qobject_cast(sender()); if (action) m_settings->openSongFile(action->data().toString()); } @@ -503,7 +497,7 @@ void QtWindow::updateRecentFileActions() for (int i = 0; i < numRecentFiles; ++i) { QString text = tr("&%1 %2").arg(i + 1).arg(strippedName(files[i])); - if (m_recentFileActs[i] == 0) + if (m_recentFileActs[i] == nullptr) break; m_recentFileActs[i]->setText(text); m_recentFileActs[i]->setData(files[i]); @@ -511,7 +505,7 @@ void QtWindow::updateRecentFileActions() } for (int j = numRecentFiles; j < MAX_RECENT_FILES; ++j) { - if (m_recentFileActs[j] == 0) + if (m_recentFileActs[j] == nullptr) break; m_recentFileActs[j]->setVisible(false); } @@ -662,7 +656,6 @@ void QtWindow::keyboardShortcuts() msgBox.exec(); } - void QtWindow::open() { m_glWidget->stopTimerEvent(); @@ -710,7 +703,6 @@ void QtWindow::closeEvent(QCloseEvent *event) writeSettings(); } - void QtWindow::keyPressEvent ( QKeyEvent * event ) { if (event->text().length() == 0) @@ -771,8 +763,8 @@ void QtWindow::loadTutorHtml(const QString & name) void QtWindow::refreshTranslate(){ #ifndef NO_LANGS - - QString locale = m_settings->value("General/lang",QLocale::system().bcp47Name()).toString(); + QString appImagePath = qgetenv("APPIMAGE"); + QString locale = m_settings->selectedLangauge(); qApp->removeTranslator(&translator); qApp->removeTranslator(&translatorMusic); @@ -806,7 +798,7 @@ void QtWindow::refreshTranslate(){ QFile fileTestLocale(translationsDir); if (!fileTestLocale.exists()){ #if defined (Q_OS_LINUX) || defined (Q_OS_UNIX) - translationsDir=QString(PREFIX)+"/"+QString(DATA_DIR)+"/translations/"; + translationsDir=Util::dataDir()+"/translations/"; #endif #ifdef Q_OS_DARWIN QApplication::applicationDirPath() + "/../Resources/translations/"; @@ -825,16 +817,14 @@ void QtWindow::refreshTranslate(){ translatorMusic.load(QString("music_") + locale, QApplication::applicationDirPath()); qApp->installTranslator(&translatorMusic); - // set translator for default widget's text (for example: QMessageBox's buttons) #ifdef __WIN32 - qtTranslator.load("qt_"+locale,translationsDir); + qtTranslator.load("qt_"+locale, translationsDir); #else - qtTranslator.load("qt_"+locale,QLibraryInfo::location(QLibraryInfo::TranslationsPath)); + qtTranslator.load("qt_"+locale, QLibraryInfo::location(QLibraryInfo::TranslationsPath)); #endif qApp->installTranslator(&qtTranslator); - // retranslate UI QList l2 = this->findChildren(); for (auto &w:l2){ diff --git a/src/QtWindow.h b/src/QtWindow.h index edb0440..14261b1 100644 --- a/src/QtWindow.h +++ b/src/QtWindow.h @@ -40,8 +40,6 @@ #include "GuiLoopingPopup.h" #include "Settings.h" - - class CGLView; class QAction; class QMenu; @@ -184,7 +182,6 @@ private: QString strippedName(const QString &fullFileName); void refreshTranslate(); - void displayUsage(); void createActions(); void createMenus(); diff --git a/src/Rating.cpp b/src/Rating.cpp index 38b7f97..3835028 100644 --- a/src/Rating.cpp +++ b/src/Rating.cpp @@ -106,5 +106,3 @@ void CRating::calculateAccuracy() } } - - diff --git a/src/Rating.h b/src/Rating.h index 3fe386b..cdc2f14 100644 --- a/src/Rating.h +++ b/src/Rating.h @@ -72,8 +72,6 @@ private: float m_factor; CColor m_currentColor; bool m_goodAccuracyFlag; - }; - #endif //__RATING_H__ diff --git a/src/Score.cpp b/src/Score.cpp index 6b77e0a..69298b1 100644 --- a/src/Score.cpp +++ b/src/Score.cpp @@ -35,7 +35,7 @@ CScore::CScore(CSettings* settings) : CDraw(settings) { size_t i; m_piano = new CPiano(settings); - m_rating = 0; + m_rating = nullptr; for (i=0; i< arraySize(m_scroll); i++) { m_scroll[i] = new CScroll(i, settings); @@ -242,6 +242,3 @@ void CScore::drawScore() else glCallList(m_scoreDisplayListId); } - - - diff --git a/src/Score.h b/src/Score.h index 43fcc78..3c9e9c8 100644 --- a/src/Score.h +++ b/src/Score.h @@ -26,8 +26,6 @@ */ /*********************************************************************************/ - - #ifndef _SCORE_H_ #define _SCORE_H_ @@ -35,7 +33,6 @@ #include "Piano.h" #include "Settings.h" - class CScore : public CDraw { public: @@ -108,7 +105,6 @@ public: m_scroll[m_activeScroll]->setPlayedNoteColor(note, color, wantedDelta, pianistTimming); } - void setActiveChannel(int channel) { int newActiveSroll; @@ -132,7 +128,6 @@ public: m_scroll[m_activeScroll]->refresh(); } - void setDisplayHand(whichPart_t hand) { CDraw::setDisplayHand(hand); @@ -146,7 +141,6 @@ public: protected: CPiano* m_piano; - private: CRating* m_rating; CScroll* m_scroll[MAX_MIDI_CHANNELS]; diff --git a/src/Scroll.cpp b/src/Scroll.cpp index efcffa9..8b68493 100644 --- a/src/Scroll.cpp +++ b/src/Scroll.cpp @@ -151,7 +151,6 @@ void CScroll::removeSlots() } } - //! Draw all the symbols that we have in the list void CScroll::drawScrollingSymbols(bool show) { @@ -177,7 +176,6 @@ void CScroll::drawScrollingSymbols(bool show) glPopMatrix(); } - void CScroll::scrollDeltaTime(int ticks) { m_deltaHead -= ticks; @@ -242,7 +240,6 @@ void CScroll::setPlayedNoteColor(int note, CColor color, int wantedDelta, int pi compileSlot(m_scrollQueue->index(index)); } - void CScroll::refresh() { int i; @@ -324,7 +321,6 @@ void CScroll::showScroll(bool show) if (m_symbolID == 0) m_symbolID = glGenLists (1); - // add in the missing GL display list for ( i = 0; i < m_scrollQueue->length(); i++) { @@ -363,7 +359,6 @@ void CScroll::showScroll(bool show) } } - CScroll::CSlotDisplayList::CSlotDisplayList(const CSlot& slot, GLuint displayListId, GLuint nextDisplayListId) : CSlot(slot), m_displayListId(displayListId), m_nextDisplayListId(nextDisplayListId) { diff --git a/src/Scroll.h b/src/Scroll.h index 45e7178..6fd6f6e 100644 --- a/src/Scroll.h +++ b/src/Scroll.h @@ -29,7 +29,6 @@ #ifndef __SCROLL_H__ #define __SCROLL_H__ - #include "Draw.h" #include "Song.h" #include "Queue.h" @@ -116,5 +115,4 @@ private: float m_ppqnFactor; // if PulsesPerQuarterNote is 96 then the factor is 1.0 }; - #endif //__SCROLL_H__ diff --git a/src/Settings.cpp b/src/Settings.cpp index ddb9875..64b1d6a 100644 --- a/src/Settings.cpp +++ b/src/Settings.cpp @@ -5,7 +5,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -49,6 +49,9 @@ #include "QtWindow.h" #include "version.txt" +#if EXPERIMENTAL_USE_FLUIDSYNTH +#include "MidiDeviceFluidSynth.h" +#endif #define OPTION_DEBUG_SETTINGS 0 #if OPTION_DEBUG_SETTINGS @@ -57,7 +60,6 @@ #define debugSettings(args) #endif - CSettings::CSettings(QtWindow *mainWindow) : QSettings(CSettings::IniFormat, CSettings::UserScope, "PianoBooster", "Piano Booster"), m_mainWindow(mainWindow) { @@ -71,15 +73,8 @@ CSettings::CSettings(QtWindow *mainWindow) : QSettings(CSettings::IniFormat, CSe CNotation::setCourtesyAccidentals(value("Score/CourtesyAccidentals", false ).toBool()); m_followThroughErrorsEnabled = value("Score/FollowThroughErrors", false ).toBool(); - // load Fluid settings - - QString soundFontNames_1 = value("FluidSynth/SoundFont2_1","").toString(); - if (!soundFontNames_1.isEmpty()) addFluidSoundFontName(soundFontNames_1); - - QString soundFontNames_2 = value("FluidSynth/SoundFont2_2","").toString(); - if (!soundFontNames_2.isEmpty()) addFluidSoundFontName(soundFontNames_2); - + setFluidSoundFontNames( value("FluidSynth/SoundFont").toStringList()); } void CSettings::setDefaultValue(const QString & key, const QVariant & value ) @@ -90,7 +85,6 @@ void CSettings::setDefaultValue(const QString & key, const QVariant & value ) setValue(key, value); } - void CSettings::init(CSong* song, GuiSidePanel* sidePanel, GuiTopBar* topBar) { m_song = song; @@ -98,7 +92,6 @@ void CSettings::init(CSong* song, GuiSidePanel* sidePanel, GuiTopBar* topBar) m_guiTopBar = topBar; } - void CSettings::setNoteNamesEnabled(bool value) { m_noteNamesEnabled = value; setValue("Score/NoteNames", value ); @@ -115,7 +108,6 @@ void CSettings::setTutorPagesEnabled(bool value) { updateTutorPage(); } - void CSettings::setCourtesyAccidentals(bool value) { CNotation::setCourtesyAccidentals(value); setValue("Score/CourtesyAccidentals", value ); @@ -186,7 +178,6 @@ void CSettings::loadSongSettings() m_guiSidePanel->setCurrentHand(m_domSong.attribute("hand", "both" )); m_guiTopBar->setSpeed(m_domSong.attribute("speed", "100" ).toInt()); - // -1 means none and -2 means not set int left = m_domSong.attribute("leftHandMidiChannel", "-2").toInt(); int right = m_domSong.attribute("rightHandMidiChannel", "-2").toInt(); @@ -195,7 +186,6 @@ void CSettings::loadSongSettings() loadHandSettings(); } - void CSettings::saveSongSettings() { m_domSong.setAttribute("hand", partToHandString(m_song->getActiveHand())); @@ -213,7 +203,6 @@ void CSettings::loadBookSettings() m_currentSongName = lastSong; } - void CSettings::saveBookSettings() { if (!m_currentBookName.isEmpty()) @@ -224,7 +213,6 @@ void CSettings::saveBookSettings() saveSongSettings(); } - void CSettings::loadXmlFile() { m_domDocument.documentElement().clear(); @@ -288,7 +276,7 @@ void CSettings::updateTutorPage() QString fileBase = fileInfo.absolutePath() + "/InfoPages/" + fileInfo.completeBaseName() + "_"; - QString locale = value("General/lang",QLocale::system().bcp47Name()).toString(); + QString locale = selectedLangauge(); if (m_tutorPagesEnabled) { @@ -321,7 +309,6 @@ void CSettings::updateTutorPage() } } m_mainWindow->loadTutorHtml(QString()); - } void CSettings::openSongFile(const QString & filename) @@ -366,7 +353,6 @@ QStringList CSettings::getSongList() dirSongs.setFilter(QDir::Files); QStringList fileNames = dirSongs.entryList(); - QStringList songNames; for (int i = 0; i < fileNames.size(); i++) { @@ -388,7 +374,6 @@ QStringList CSettings::getBookList() return dirBooks.entryList(); } - void CSettings::writeSettings() { @@ -397,7 +382,6 @@ void CSettings::writeSettings() saveXmlFile(); } - void CSettings::loadSettings() { unzipBoosterMusicBooks(); @@ -418,6 +402,8 @@ void CSettings::loadSettings() // if (!songName.isEmpty()) // openSongFile( songName ); + setupDefaultSoundFont(); + updateWarningMessages(); updateTutorPage(); @@ -428,7 +414,6 @@ void CSettings::unzipBoosterMusicBooks() // Set default value const QString ZIPFILENAME("BoosterMusicBooks.zip"); - if (value("PianoBooster/MusicRelease", 0).toInt() < MUSIC_RELEASE) { QString resourceDir = QApplication::applicationDirPath() + "/../music/"; @@ -442,7 +427,7 @@ void CSettings::unzipBoosterMusicBooks() if (!QFile::exists(resourceDir + ZIPFILENAME)) { #if defined (Q_OS_LINUX) || defined (Q_OS_UNIX) - resourceDir=QString(PREFIX)+"/"+QString(DATA_DIR)+"/music/"; + resourceDir=Util::dataDir()+"/music/"; #endif #ifdef Q_OS_DARWIN resourceDir = QApplication::applicationDirPath() + "/../Resources/music/"; @@ -452,7 +437,6 @@ void CSettings::unzipBoosterMusicBooks() ppLogInfo(qPrintable("applicationDirPath=" + QApplication::applicationDirPath())); ppLogTrace("resourceDir3 %s", qPrintable(resourceDir)); - QFileInfo zipFile(resourceDir + ZIPFILENAME); ppLogTrace("xx %s", qPrintable(zipFile.filePath())); @@ -483,8 +467,6 @@ void CSettings::unzipBoosterMusicBooks() return; } - - QProcess unzip; unzip.start("unzip", QStringList() << "-o" << zipFile.filePath() << "-d" << destMusicDir.path() ); ppLogInfo(qPrintable("running unzip -o " + zipFile.filePath() + " -d " + destMusicDir.path()) ); @@ -498,7 +480,6 @@ void CSettings::unzipBoosterMusicBooks() // the line is available in buf } - if (!unzip.waitForFinished()) { ppLogError("unzip failed"); @@ -562,3 +543,33 @@ void CSettings::updateWarningMessages() m_warningMessage.clear(); } +void CSettings::setupDefaultSoundFont(){ +#if EXPERIMENTAL_USE_FLUIDSYNTH + + if (getFluidSoundFontNames().empty() && !m_song->validMidiOutput()) + { + QString appPath = qEnvironmentVariable("APPIMAGE"); + if (appPath.isEmpty()) + { + appPath = QApplication::applicationDirPath(); + } + + QDir directory(appPath); + directory.cd("SoundFont"); + QStringList dirList = directory.entryList(QStringList(),QDir::AllEntries); + foreach(QString filename, dirList) + { + // Find the first sound fount file + if ( filename.endsWith(".sf2", Qt::CaseInsensitive ) ) + { + setFluidSoundFontNames(directory.filePath(filename)); + setValue("Midi/Output",CMidiDeviceFluidSynth::getFluidInternalName() ); + setValue("LastSoundFontDir", directory.path()); + saveSoundFontSettings(); + m_song->openMidiPort(CMidiDevice::MIDI_OUTPUT, CMidiDeviceFluidSynth::getFluidInternalName()); + break; + } + } + } +#endif +} diff --git a/src/Settings.h b/src/Settings.h index a75c071..ff64a9b 100644 --- a/src/Settings.h +++ b/src/Settings.h @@ -5,7 +5,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -105,6 +105,14 @@ public: { return m_fluidSoundFontNames; } + void setFluidSoundFontNames(QStringList names) + { + m_fluidSoundFontNames = names; + } + void setFluidSoundFontNames(QString names) + { + m_fluidSoundFontNames = QStringList(names); + } void addFluidSoundFontName(QString sfName) { m_fluidSoundFontNames.append(sfName); @@ -113,6 +121,24 @@ public: { m_fluidSoundFontNames.removeAll(sfName); } + void clearFluidSoundFontNames() + { + m_fluidSoundFontNames.clear(); + } + void saveSoundFontSettings() + { + setValue("FluidSynth/SoundFont", getFluidSoundFontNames()); + } + + // has a new sound fount been entered that is not the same as the old sound font + bool isNewSoundFontEntered() + { + if (getFluidSoundFontNames().isEmpty()) + return false; + + return getFluidSoundFontNames() != value("FluidSynth/SoundFont").toStringList(); + } + void pianistActive() { m_pianistActive = true;} void setActiveHand(whichPart_t hand); @@ -122,6 +148,14 @@ public: QString getWarningMessage() {return m_warningMessage;} void updateWarningMessages(); + QString selectedLangauge() { + QString locale = value("General/lang","").toString(); + if (locale.isEmpty()) { + locale = QLocale::system().bcp47Name(); + } + return locale; + } + private: Q_OBJECT @@ -137,7 +171,7 @@ private: void loadXmlFile(); void saveXmlFile(); void setDefaultValue(const QString & key, const QVariant & value ); - + void setupDefaultSoundFont(); // returns either 'left' 'right' or 'both' const QString partToHandString(whichPart_t part) @@ -168,7 +202,7 @@ private: QString m_currentBookName; QString m_currentSongName; QString m_warningMessage; - QStringList m_fluidSoundFontNames; + QStringList m_fluidSoundFontNames = QStringList(); bool m_pianistActive; }; diff --git a/src/Song.cpp b/src/Song.cpp index 9d7de16..9f184e1 100644 --- a/src/Song.cpp +++ b/src/Song.cpp @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -29,7 +29,6 @@ #include "Song.h" #include "Score.h" - void CSong::init2(CScore * scoreWin, CSettings* settings) { @@ -72,7 +71,6 @@ void CSong::loadSong(const QString & filename) } - // read the file ahead to collect info about the song first void CSong::midiFileInfo() { @@ -118,7 +116,6 @@ void CSong::setActiveHand(whichPart_t hand) m_scoreWin->setDisplayHand(hand); } - void CSong::setActiveChannel(int chan) { this->CConductor::setActiveChannel(chan); @@ -165,7 +162,6 @@ eventBits_t CSong::task(int ticks) { realTimeEngine(ticks); - while (true) { if (m_reachedMidiEof == true) @@ -196,7 +192,6 @@ eventBits_t CSong::task(int ticks) // send the events to the other end midiEventInsert(event); - if (event.type() == MIDI_PB_EOF) { m_reachedMidiEof = true; @@ -212,7 +207,6 @@ eventBits_t CSong::task(int ticks) } else break; - } exitTask: @@ -258,7 +252,6 @@ bool CSong::pcKeyPress(int key, bool down) if (key == 't') // the tab key on the PC fakes good notes { - if (down) m_fakeChord = getWantedChord(); for (i = 0; i < m_fakeChord.length(); i++) diff --git a/src/Song.h b/src/Song.h index 90bdf2f..cac4b7d 100644 --- a/src/Song.h +++ b/src/Song.h @@ -76,8 +76,6 @@ public: playMusic(true); } - - void setActiveHand(whichPart_t hand); whichPart_t getActiveHand(){return CNote::getActiveHand();} @@ -86,13 +84,11 @@ public: CTrackList* getTrackList() {return m_trackList;} void refreshScroll(); - QString getSongTitle() {return m_songTitle;} private: void midiFileInfo(); - CMidiFile * m_midiFile; CFindChord m_findChord; bool m_reachedMidiEof; diff --git a/src/StavePosition.cpp b/src/StavePosition.cpp index 8db085f..8664cb7 100644 --- a/src/StavePosition.cpp +++ b/src/StavePosition.cpp @@ -26,7 +26,6 @@ */ /*********************************************************************************/ - #include "StavePosition.h" #include "Draw.h" diff --git a/src/StavePosition.h b/src/StavePosition.h index cb32564..db4a2b5 100644 --- a/src/StavePosition.h +++ b/src/StavePosition.h @@ -88,7 +88,6 @@ public: void notePos(whichPart_t hand, int midiNote); - //////////////////////////////////////////////////////////////////////////////// //! @brief Sets which stave the note will appear on //! return The position on the stave. @@ -125,7 +124,7 @@ public: // convert the midi note to the note name A B C D E F G static staveLookup_t midiNote2Name(int midiNote); static const staveLookup_t* getstaveLookupTable(int key); - + // do we show a sharp or a flat for this key signature // returns 0 = none, 1=sharp, -1 =flat, 2=natural (# Key) , -2=natural (b Key) static int getStaveAccidental(int midiNote) @@ -140,12 +139,11 @@ public: if (accidentalDirection == 2) // A natural so change to above accidentalDirection = 1; else if (accidentalDirection == -2) // A natural so change to below - accidentalDirection = -1; - + accidentalDirection = -1; + return accidentalDirection; } - private: // fixme TODO This could be improved as the calculations could a done in the constructor int8_t m_staveIndex; // 0 central line, 5 = top line, -5 the bottom line, @@ -153,7 +151,6 @@ private: float m_offsetY; whichPart_t m_hand; - static int m_KeySignature; static int m_KeySignatureMajorMinor; static const staveLookup_t* m_staveLookUpTable; diff --git a/src/Symbol.h b/src/Symbol.h index d510a53..5074009 100644 --- a/src/Symbol.h +++ b/src/Symbol.h @@ -33,7 +33,6 @@ #include "Cfg.h" #include "StavePosition.h" - typedef enum { PB_SYMBOL_none, @@ -49,7 +48,6 @@ typedef enum PB_SYMBOL_playingZone, PB_SYMBOL_theEndMarker, - PB_SYMBOL_noteHead, // ONLY ADD NOTES BELOW THIS MAKER PB_SYMBOL_demisemiquaver, // Demisemiquaver / Thirty-second note PB_SYMBOL_semiquaver, // Semiquaver / Sixteenth note @@ -61,7 +59,6 @@ typedef enum } musicalSymbol_t; - typedef enum { PB_ACCIDENTAL_MODIFER_noChange, PB_ACCIDENTAL_MODIFER_suppress, @@ -100,8 +97,6 @@ public: m_hand = stavePos.getHand(); } - - //////////////////////////////////////////////////////////////////////////////// //@brief Get the type of symbol musicalSymbol_t getType(){return m_symbolType;} @@ -160,11 +155,9 @@ public: return getStavePos().getAccidental(); } - void setAccidentalModifer(accidentalModifer_t value) {m_accidentalModifer = value;} accidentalModifer_t getAccidentalModifer() {return m_accidentalModifer;} - private: void init() { @@ -190,8 +183,4 @@ private: int m_total; // the number of the notes per hand; }; - - - #endif // _SYMBOL_H_ - diff --git a/src/Tempo.cpp b/src/Tempo.cpp index d02ffd9..0056ddf 100644 --- a/src/Tempo.cpp +++ b/src/Tempo.cpp @@ -26,13 +26,11 @@ */ /*********************************************************************************/ - #include "Tempo.h" int CTempo::m_cfg_followTempoAmount = 0; int CTempo::m_cfg_maxJumpAhead = 0; - void CTempo::enableFollowTempo(bool enable) { if (enable) @@ -65,7 +63,3 @@ void CTempo::adjustTempo(int * ticks) m_jumpAheadDelta = 0; } } - - - - diff --git a/src/Tempo.h b/src/Tempo.h index aaac5fb..08c1a5c 100644 --- a/src/Tempo.h +++ b/src/Tempo.h @@ -46,7 +46,6 @@ public: } void setSavedWantedChord(CChord * savedWantedChord) { m_savedWantedChord = savedWantedChord; } - void reset() { // 120 beats per minute is the default @@ -89,18 +88,16 @@ public: if (m_cfg_maxJumpAhead != 0) m_jumpAheadDelta = ticks; } + void clearPlayingTicks() { m_jumpAheadDelta = 0; } - void adjustTempo(int * ticks); - static void enableFollowTempo(bool enable); - private: float m_userSpeed; // controls the speed of the piece playing float m_midiTempo; // controls the speed of the piece playing @@ -109,7 +106,6 @@ private: static int m_cfg_followTempoAmount; CChord *m_savedWantedChord; // A copy of the wanted chord complete with both left and right parts - }; #endif // __TEMPO_H__ diff --git a/src/TrackList.h b/src/TrackList.h index 8b60acd..36bdcd2 100644 --- a/src/TrackList.h +++ b/src/TrackList.h @@ -49,7 +49,6 @@ public: int midiChannel; }; - class CTrackList : public QObject { Q_OBJECT @@ -69,7 +68,6 @@ public: // Find an unused channel int findFreeChannel(int startChannel); - void currentRowChanged(int currentRow); void examineMidiEvent(CMidiEvent event); bool pianoPartConvetionTest(); diff --git a/src/Util.cpp b/src/Util.cpp index e385d4e..aeb80a7 100644 --- a/src/Util.cpp +++ b/src/Util.cpp @@ -31,16 +31,14 @@ #include #include #include +#include #include "Util.h" #include "Cfg.h" -#include - - static QTime s_realtime; -static FILE * logInfoFile = 0; -static FILE * logErrorFile = 0; +static FILE * logInfoFile = nullptr; +static FILE * logErrorFile = nullptr; static bool logsOpened = false; @@ -52,7 +50,7 @@ static void openLogFile() { { logInfoFile = fopen ("pb.log","w"); logErrorFile = logInfoFile; - if (logErrorFile == 0) + if (logErrorFile == nullptr) { fputs("FATAL: cannot open the logfile", stderr); exit(EXIT_FAILURE); @@ -69,7 +67,6 @@ static void openLogFile() { } } - static void flushLogs() { if (logInfoFile != stdout && logsOpened) @@ -167,7 +164,6 @@ void ppLogTrace(const char *msg, ...) #endif } - void ppLogDebug( const char *msg, ...) { va_list ap; @@ -213,8 +209,6 @@ void ppTiming(const char *msg, ...) } ////////////////////// BENCH MARK ////////////////////// - - static QTime s_benchMarkTime; static int s_previousTime; static int s_previousFrameTime; @@ -244,7 +238,6 @@ void benchMarkReset(benchData_t *pBench) pBench->frameRatePrevious = pBench->frameRateCurrent; } - void benchMarkInit() { s_benchMarkTime.start(); @@ -311,3 +304,18 @@ void benchMarkResults() printResult(i, &s_benchData[i]); } } + +// Returns the location of where the data is stored +// for an AppImage the dataDir is must be relative to the applicationDirPath +QString Util::dataDir() { + QString appImagePath = qgetenv("APPIMAGE"); + + if (appImagePath.isEmpty() ) + return QString(PREFIX)+"/"+QString(DATA_DIR); + QString appImageInternalPath = QApplication::applicationDirPath(); + int i = appImageInternalPath.lastIndexOf(PREFIX); + + appImageInternalPath.truncate(i); + + return (appImageInternalPath+QString(PREFIX)+"/"+QString(DATA_DIR)); +} diff --git a/src/Util.h b/src/Util.h index 3ac552e..f537046 100644 --- a/src/Util.h +++ b/src/Util.h @@ -6,7 +6,7 @@ @author L. J. Barman - Copyright (c) 2008-2013, L. J. Barman, all rights reserved + Copyright (c) 2008-2020, L. J. Barman and others, all rights reserved This file is part of the PianoBooster application @@ -32,6 +32,7 @@ #include #include #include +#include using namespace std; @@ -51,8 +52,6 @@ typedef unsigned char byte; #define ppDEBUG(args) ppLogDebug args - - typedef enum { PB_LOG_error, @@ -71,7 +70,6 @@ void ppLogError(const char *msg, ...); void ppTiming(const char *msg, ...); void closeLogs(); - #define SPEED_ADJUST_FACTOR 1000 #define deltaAdjust(delta) ((delta)/SPEED_ADJUST_FACTOR ) @@ -79,5 +77,9 @@ void benchMarkInit(); void benchMark(unsigned int id, QString message); void benchMarkResults(); +class Util { +public: + static QString dataDir(); +}; #endif //__UTIL_H__