LCOV - code coverage report
Current view: top level - muse/framework/mpe/qml/Muse/Mpe - articulationsprofileeditormodel.cpp Coverage Total Hit
Test: filtered_coverage.info Lines: 0.0 % 118 0
Test Date: 2026-11-05 04:07:02

            Line data    Source code
       1              : /*
       2              :  * SPDX-License-Identifier: GPL-3.0-only
       3              :  * MuseScore-CLA-applies
       4              :  *
       5              :  * MuseScore Studio
       6              :  * Music Composition & Notation
       7              :  *
       8              :  * Copyright (C) 2021 MuseScore Limited and others
       9              :  *
      10              :  * This program is free software: you can redistribute it and/or modify
      11              :  * it under the terms of the GNU General Public License version 3 as
      12              :  * published by the Free Software Foundation.
      13              :  *
      14              :  * This program is distributed in the hope that it will be useful,
      15              :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      16              :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      17              :  * GNU General Public License for more details.
      18              :  *
      19              :  * You should have received a copy of the GNU General Public License
      20              :  * along with this program.  If not, see <https://www.gnu.org/licenses/>.
      21              :  */
      22              : 
      23              : #include "articulationsprofileeditormodel.h"
      24              : 
      25              : using namespace muse;
      26              : using namespace muse::mpe;
      27              : 
      28              : static const std::string PROFILE_EXTENSION = "(*.json)";
      29              : 
      30            0 : ArticulationsProfileEditorModel::ArticulationsProfileEditorModel(QObject* parent)
      31            0 :     : QObject(parent), Contextable(muse::iocCtxForQmlObject(this))
      32              : {
      33            0 : }
      34              : 
      35            0 : void ArticulationsProfileEditorModel::init()
      36              : {
      37            0 :     loadItems();
      38              : 
      39            0 :     setProfile(profilesRepository()->createNew());
      40            0 : }
      41              : 
      42            0 : void ArticulationsProfileEditorModel::requestToOpenProfile()
      43              : {
      44              :     //! Make these strings translatable when we expose this tool to users
      45            0 :     std::vector<std::string> filter = { /*qtrc*/ std::string("MPE articulations profile") + " " + PROFILE_EXTENSION };
      46            0 :     io::path_t path = interactive()->selectOpeningFileSync(/*trc*/ "Open MPE articulations profile", "", filter);
      47              : 
      48            0 :     if (path.empty()) {
      49            0 :         return;
      50              :     }
      51              : 
      52            0 :     setCurrentPath(path.toQString());
      53              : 
      54            0 :     setProfile(profilesRepository()->loadProfile(m_profilePath));
      55            0 : }
      56              : 
      57            0 : bool ArticulationsProfileEditorModel::requestToCreateProfile()
      58              : {
      59            0 :     std::vector<std::string> filter = { /*qtrc*/ std::string("MPE articulations profile") + " " + PROFILE_EXTENSION };
      60            0 :     io::path_t path = interactive()->selectSavingFileSync(/*trc*/ "Save MPE articulations profile", "", filter);
      61              : 
      62            0 :     if (path.empty()) {
      63            0 :         return false;
      64              :     }
      65              : 
      66            0 :     setCurrentPath(path.toQString());
      67            0 :     return true;
      68            0 : }
      69              : 
      70            0 : void ArticulationsProfileEditorModel::requestToSaveProfile()
      71              : {
      72            0 :     if (m_profilePath.empty()) {
      73            0 :         if (!requestToCreateProfile()) {
      74            0 :             return;
      75              :         }
      76              :     }
      77              : 
      78            0 :     for (const auto& item : m_singleNoteItems) {
      79            0 :         if (item->isActive()) {
      80            0 :             m_profile->setPattern(item->type(), item->patternData());
      81              :         } else {
      82            0 :             m_profile->removePattern(item->type());
      83              :         }
      84              :     }
      85              : 
      86            0 :     for (const auto& item : m_multiNoteItems) {
      87            0 :         if (item->isActive()) {
      88            0 :             m_profile->setPattern(item->type(), item->patternData());
      89              :         } else {
      90            0 :             m_profile->removePattern(item->type());
      91              :         }
      92              :     }
      93              : 
      94            0 :     profilesRepository()->saveProfile(m_profilePath, m_profile);
      95              : }
      96              : 
      97            0 : void ArticulationsProfileEditorModel::copyPatternDataFromItem(ArticulationPatternItem* item)
      98              : {
      99            0 :     if (!item || !selectedItem()) {
     100            0 :         return;
     101              :     }
     102              : 
     103            0 :     m_selectedItem->load(item->patternData());
     104              : }
     105              : 
     106            0 : void ArticulationsProfileEditorModel::setProfile(ArticulationsProfilePtr ptr)
     107              : {
     108            0 :     m_profile = std::move(ptr);
     109              : 
     110            0 :     auto load = [this](const QMap<ArticulationType, ArticulationPatternItem*>& items) {
     111            0 :         for (auto& item : items) {
     112            0 :             item->setIsActive(m_profile->contains(item->type()));
     113            0 :             item->load(m_profile->pattern(item->type()));
     114              :         }
     115            0 :     };
     116              : 
     117            0 :     load(m_singleNoteItems);
     118            0 :     load(m_multiNoteItems);
     119              : 
     120            0 :     setSelectedItem(m_singleNoteItems.first());
     121            0 : }
     122              : 
     123            0 : void ArticulationsProfileEditorModel::loadItems()
     124              : {
     125            0 :     int firstIdx = static_cast<int>(ArticulationType::Standard);
     126            0 :     int lastIdx = static_cast<int>(ArticulationType::Last);
     127              : 
     128            0 :     for (int i = firstIdx; i < lastIdx; ++i) {
     129            0 :         ArticulationType type = static_cast<ArticulationType>(i);
     130              : 
     131            0 :         if (isSingleNoteArticulation(type)) {
     132            0 :             m_singleNoteItems.insert(type, buildItem(type, true /*isSingleNoteType*/));
     133              :         } else {
     134            0 :             m_multiNoteItems.insert(type, buildItem(type, false /*isSingleNoteType*/));
     135              :         }
     136              :     }
     137            0 : }
     138              : 
     139            0 : ArticulationPatternItem* ArticulationsProfileEditorModel::buildItem(const ArticulationType type, const bool isSingleNoteType)
     140              : {
     141            0 :     ArticulationPatternItem* item = new ArticulationPatternItem(this, type, isSingleNoteType);
     142              : 
     143            0 :     connect(item, &ArticulationPatternItem::isSelectedChanged, this, [this, item]() {
     144            0 :         setSelectedItem(item);
     145            0 :     });
     146              : 
     147            0 :     return item;
     148              : }
     149              : 
     150            0 : QString ArticulationsProfileEditorModel::currentPath() const
     151              : {
     152            0 :     return m_profilePath.toQString();
     153              : }
     154              : 
     155            0 : void ArticulationsProfileEditorModel::setCurrentPath(const QString& newCurrentPath)
     156              : {
     157            0 :     io::path_t newPath(newCurrentPath);
     158              : 
     159            0 :     if (m_profilePath == newPath) {
     160            0 :         return;
     161              :     }
     162            0 :     m_profilePath = newPath;
     163            0 :     emit currentPathChanged();
     164            0 : }
     165              : 
     166            0 : ArticulationPatternItem* ArticulationsProfileEditorModel::selectedItem() const
     167              : {
     168            0 :     return m_selectedItem;
     169              : }
     170              : 
     171            0 : void ArticulationsProfileEditorModel::setSelectedItem(ArticulationPatternItem* newSelectedItem)
     172              : {
     173            0 :     if (m_selectedItem == newSelectedItem) {
     174            0 :         return;
     175              :     }
     176              : 
     177            0 :     if (m_selectedItem) {
     178            0 :         m_selectedItem->setIsSelected(false);
     179              :     }
     180              : 
     181            0 :     newSelectedItem->setIsSelected(true);
     182            0 :     m_selectedItem = newSelectedItem;
     183            0 :     emit selectedItemChanged();
     184              : }
     185              : 
     186            0 : QList<ArticulationPatternItem*> ArticulationsProfileEditorModel::singleNoteItems() const
     187              : {
     188            0 :     QList<ArticulationPatternItem*> result;
     189              : 
     190            0 :     for (const auto& item : m_singleNoteItems) {
     191            0 :         result << item;
     192              :     }
     193              : 
     194            0 :     return result;
     195            0 : }
     196              : 
     197            0 : QList<ArticulationPatternItem*> ArticulationsProfileEditorModel::multiNoteItems() const
     198              : {
     199            0 :     QList<ArticulationPatternItem*> result;
     200              : 
     201            0 :     for (const auto& item : m_multiNoteItems) {
     202            0 :         result << item;
     203              :     }
     204              : 
     205            0 :     return result;
     206            0 : }
     207              : 
     208            0 : bool ArticulationsProfileEditorModel::isArrangementVisible() const
     209              : {
     210            0 :     return m_isArrangementVisible;
     211              : }
     212              : 
     213            0 : void ArticulationsProfileEditorModel::setIsArrangementVisible(bool newIsArrangementVisible)
     214              : {
     215            0 :     if (m_isArrangementVisible == newIsArrangementVisible) {
     216            0 :         return;
     217              :     }
     218            0 :     m_isArrangementVisible = newIsArrangementVisible;
     219            0 :     emit isArrangementVisibleChanged();
     220              : }
     221              : 
     222            0 : bool ArticulationsProfileEditorModel::isPitchVisible() const
     223              : {
     224            0 :     return m_isPitchVisible;
     225              : }
     226              : 
     227            0 : void ArticulationsProfileEditorModel::setIsPitchVisible(bool newIsPitchVisible)
     228              : {
     229            0 :     if (m_isPitchVisible == newIsPitchVisible) {
     230            0 :         return;
     231              :     }
     232            0 :     m_isPitchVisible = newIsPitchVisible;
     233            0 :     emit isPitchVisibleChanged();
     234              : }
     235              : 
     236            0 : bool ArticulationsProfileEditorModel::isExpressionVisible() const
     237              : {
     238            0 :     return m_isExpressionVisible;
     239              : }
     240              : 
     241            0 : void ArticulationsProfileEditorModel::setIsExpressionVisible(bool newIsExpressionVisible)
     242              : {
     243            0 :     if (m_isExpressionVisible == newIsExpressionVisible) {
     244            0 :         return;
     245              :     }
     246            0 :     m_isExpressionVisible = newIsExpressionVisible;
     247            0 :     emit isExpressionVisibleChanged();
     248              : }
        

Generated by: LCOV version 2.0-1