Compare commits
408 Commits
Author | SHA1 | Date |
---|---|---|
RomanPudashkin | 08c1e1c911 | |
Roman Pudashkin | 42c423479d | |
Elnur Ismailzada | c163f09bc2 | |
Eism | 129532220a | |
Jerry James | 981ac5d056 | |
Eism | da03ffcd03 | |
Eism | fccabd93cc | |
Elnur Ismailzada | 4a6ebfb787 | |
Peter Jonas | 8582f3a3be | |
Elnur Ismailzada | 22861e5652 | |
Casper Jeukendrup | 5cb63af3d1 | |
Elnur Ismailzada | a45b9a5b30 | |
Eism | 8697dd52df | |
Eism | 01137bd235 | |
RomanPudashkin | dbe7c6de73 | |
Eism | 15d2c68458 | |
Eism | 0c7774e7b3 | |
Eism | 0e4e9d0b84 | |
Roman Pudashkin | 2a8a5f7999 | |
Roman Pudashkin | 31988c9ede | |
Eism | 6d615feacb | |
Eism | 6ec7e4d7a7 | |
Eism | 8b3556c0c9 | |
RomanPudashkin | 769b3af53c | |
Casper Jeukendrup | 93b4ef1b1d | |
RomanPudashkin | 48ac167c5e | |
Grzegorz Pruchniakowski | 0c43d96314 | |
Grzegorz Pruchniakowski | 59f839cc1e | |
Grzegorz Pruchniakowski | d10ba047fd | |
Grzegorz Pruchniakowski | 93c8e8931b | |
Roman Pudashkin | a7ff5635f1 | |
RomanPudashkin | 3c1418f2f4 | |
Casper Jeukendrup | 376f6b902d | |
Casper Jeukendrup | d94b907e4e | |
RomanPudashkin | d23f054c58 | |
Roman Pudashkin | 1a5280e453 | |
RomanPudashkin | 530011bc8d | |
Casper Jeukendrup | 4781b1aff7 | |
RomanPudashkin | 172fa52282 | |
Michele Spagnolo | b59aaaeb5b | |
Michele Spagnolo | 60e5441858 | |
Michele Spagnolo | d8b1b6433c | |
Michele Spagnolo | 5c8b529870 | |
Casper Jeukendrup | 0a9eacb461 | |
Casper Jeukendrup | 92c611bb94 | |
Casper Jeukendrup | dc655e146c | |
Casper Jeukendrup | 63dae6cea3 | |
RomanPudashkin | 792e7d2383 | |
RomanPudashkin | 62b2edd717 | |
Michele Spagnolo | ce15209cea | |
Michele Spagnolo | c9dfa559d5 | |
RomanPudashkin | 28da3b1617 | |
Roman Pudashkin | 6895140416 | |
Eism | 85c62be17a | |
Michele Spagnolo | 29540b8fbf | |
Matthew Tesch | 6027eb35f4 | |
Aaron Sattely | 81486860c0 | |
Aaron Sattely | 78c459cda9 | |
Aaron Sattely | 1667eb079f | |
Aaron Sattely | 3b0ba1daf7 | |
Aaron Sattely | 050d913758 | |
RomanPudashkin | 78ab24f6fb | |
Eism | f7cc15a55b | |
Eism | 19bea344b8 | |
Eism | b905ff6498 | |
Roman Pudashkin | f40f68a902 | |
RomanPudashkin | e2412a09ea | |
Igor Korsukov | 98f6c2fa84 | |
Roman Pudashkin | d42b7ca639 | |
Marc Sabatella | fd9d2a8672 | |
Eism | 3dee9987fd | |
Eism | 055a0c2727 | |
Casper Jeukendrup | a26240527a | |
Casper Jeukendrup | 86cf9225fa | |
Michele Spagnolo | 47bbb39826 | |
Michele Spagnolo | b5be30e94f | |
Roman Pudashkin | 9ea29a65ef | |
Roman Pudashkin | 12ea5716c2 | |
Roman Pudashkin | 209f5b5f98 | |
Roman Pudashkin | af30f64044 | |
Elnur Ismailzada | fa46d7fa90 | |
Eism | 38c800b780 | |
RomanPudashkin | 8c85e6cdd7 | |
Casper Jeukendrup | 80450a55c0 | |
Casper Jeukendrup | e0c6a37c40 | |
Matthew Tesch | 811bced015 | |
Matthew Tesch | accffcf84e | |
hirnaymay | cbb2530824 | |
Eism | 2a00fed52b | |
Casper Jeukendrup | 2b80d36a7c | |
Michele Spagnolo | 6d0c41ee3d | |
Michele Spagnolo | 1467387776 | |
Casper Jeukendrup | c3095b1f23 | |
Casper Jeukendrup | 9d98e3a489 | |
Casper Jeukendrup | 14add38bef | |
Roman Pudashkin | 5f6f693790 | |
Roman Pudashkin | 6b44aa9969 | |
Roman Pudashkin | e5c7b4e2a3 | |
Roman Pudashkin | 741ea815d0 | |
Casper Jeukendrup | d680590986 | |
Casper Jeukendrup | 2a6d94c71c | |
Casper Jeukendrup | 0cb32468f6 | |
Casper Jeukendrup | 561d7a855e | |
Casper Jeukendrup | 706617a109 | |
Eism | a408c1ae42 | |
Eism | fdb939d0f3 | |
RomanPudashkin | a36e59872d | |
Eism | 630261fa7a | |
softcat477 | 1762fdadfd | |
Eism | 55872600b5 | |
Michele Spagnolo | 2f95fa44bc | |
Michele Spagnolo | 04575ff1aa | |
Sam Lavin | d6000daa18 | |
Sam Lavin | 9c1c3985cb | |
Eism | df5ba009a1 | |
Casper Jeukendrup | fdd7905a0a | |
Casper Jeukendrup | 6abfd1bd76 | |
Elnur Ismailzada | c1d50876fb | |
Eism | 59a602c3b2 | |
Eism | 4be363958a | |
Elnur Ismailzada | 554286fae9 | |
Eism | 6d5f691af0 | |
Eism | 39acb33618 | |
RomanPudashkin | aabbec1406 | |
Roman Pudashkin | e18c9c0c5a | |
Hemant Antony | 2e9b876de7 | |
Peter Jonas | 90847f0c9b | |
Michele Spagnolo | b2ee297f24 | |
Michele Spagnolo | 2650e3845e | |
Michele Spagnolo | cabf2f31f3 | |
Michele Spagnolo | b0d9a84029 | |
Michele Spagnolo | de39c21f94 | |
Michele Spagnolo | 26b6957f5e | |
Michele Spagnolo | d5ef2c2750 | |
Michele Spagnolo | b07a68385b | |
Michele Spagnolo | 426431a2cc | |
Casper Jeukendrup | 05fed26186 | |
Roman Pudashkin | a8f143ff81 | |
Casper Jeukendrup | fb1cb12ebd | |
Eism | 1c97adc3bd | |
Casper Jeukendrup | 944ec79b0d | |
Roman Pudashkin | 50c0037447 | |
Roman Pudashkin | dcb6436eab | |
RomanPudashkin | c229b14124 | |
Casper Jeukendrup | cfffaa12d7 | |
Casper Jeukendrup | 65bf44aa87 | |
Joachim Schmitz | 5db9f19373 | |
Joachim Schmitz | d729b3ead6 | |
Rishav Raj | 6f1b511af4 | |
Michele Spagnolo | 2de2771ce1 | |
Casper Jeukendrup | 18b9e176c9 | |
Grzegorz Pruchniakowski | c938e80b73 | |
Roman Pudashkin | a47ab1a922 | |
Roman Pudashkin | c8239fdd80 | |
Roman Pudashkin | bd7579953f | |
Roman Pudashkin | 3f6244d0f6 | |
Elnur Ismailzada | 0b18c4bd27 | |
Eism | e47d522cef | |
Eism | d21770095e | |
RomanPudashkin | 3e9f13112f | |
Eism | af3e4ae263 | |
Casper Jeukendrup | a0165fd588 | |
RomanPudashkin | 68b18e4948 | |
hirnaymay | 54eefe4c17 | |
Casper Jeukendrup | 7aac2afe33 | |
Michele Spagnolo | 7d39d6cbd3 | |
Michele Spagnolo | 3894da1e54 | |
Michele Spagnolo | 6ac0ba9f63 | |
Eism | 91911ef8b9 | |
Eism | e195205315 | |
RomanPudashkin | a6922a60eb | |
Roman Pudashkin | 9e6fb14688 | |
Roman Pudashkin | 96ca173b64 | |
Roman Pudashkin | ed50308cba | |
Roman Pudashkin | 8b77ec8359 | |
Roman Pudashkin | 93f3a2b505 | |
Roman Pudashkin | daf685c53f | |
Casper Jeukendrup | 47af42e78c | |
Elnur Ismailzada | 93cb29e6f8 | |
Eism | c2df6c36b8 | |
Eism | b6d8004eaa | |
Eism | e5504a2df0 | |
RomanPudashkin | 13f9eaed92 | |
RomanPudashkin | db7d92b6ae | |
Eism | db2b727ccf | |
Eism | 236d5e1e7e | |
RomanPudashkin | dfe108e760 | |
RomanPudashkin | a71a7898a9 | |
Roman Pudashkin | f303161885 | |
Roman Pudashkin | 073d447c03 | |
Roman Pudashkin | 8a5e2de409 | |
Roman Pudashkin | c52bdada23 | |
Roman Pudashkin | 0ef68c16a3 | |
Roman Pudashkin | 61d1938428 | |
Roman Pudashkin | 71c6516ef1 | |
Roman Pudashkin | 45a46e8410 | |
Roman Pudashkin | a01788311d | |
Roman Pudashkin | b3e707585a | |
Roman Pudashkin | 110a9b0358 | |
Roman Pudashkin | 390abd2340 | |
Casper Jeukendrup | f305628d2b | |
Hemant Antony | dfe00f0976 | |
Michele Spagnolo | f8765f200c | |
Michele Spagnolo | 6050bac502 | |
Casper Jeukendrup | db41db57f7 | |
Casper Jeukendrup | ef4783f6ac | |
Roman Pudashkin | 668470c425 | |
Roman Pudashkin | d6c8f5775f | |
Roman Pudashkin | ef2261ddbc | |
Marc Sabatella | b57fe728bb | |
Michele Spagnolo | 9ba8bd21b1 | |
Michele Spagnolo | 5155828f22 | |
FigmentBoy | 335ae6185c | |
RomanPudashkin | b807808d65 | |
Roman Pudashkin | cc9ced1711 | |
pereverzev_v | 50d46dd997 | |
RomanPudashkin | 9b70a8cb28 | |
Michele Spagnolo | 7273044709 | |
Roman Pudashkin | 23415d5fb4 | |
Roman Pudashkin | b119ee7e8c | |
Roman Pudashkin | 6b06c81cc7 | |
Roman Pudashkin | d50a9bd5bf | |
RomanPudashkin | 76500c3b6e | |
Roman Pudashkin | 3f24594504 | |
Aaron Sattely | f2640a05a8 | |
Eism | 3caa460cb2 | |
Eism | 1285ea2346 | |
Eism | 0f0d85c4f1 | |
Eism | 9104cd92ca | |
Casper Jeukendrup | f5af414890 | |
Michele Spagnolo | 715509ef33 | |
Roman Pudashkin | ded3520942 | |
Michele Spagnolo | e5b889b88a | |
RomanPudashkin | 5a86fc660b | |
Eism | ade35b4ed0 | |
Elnur Ismailzada | f23ceb1e18 | |
Eism | 7bd7155d78 | |
pereverzev_v | b6d3bfc1b6 | |
RomanPudashkin | 98d89adfc7 | |
Eism | f52a296ad0 | |
Eism | cdd745e715 | |
Eism | acda813659 | |
Casper Jeukendrup | 5c2cffa4ef | |
Casper Jeukendrup | 29aaccba57 | |
Casper Jeukendrup | 3cc17fec3c | |
Casper Jeukendrup | ab26fbded3 | |
Casper Jeukendrup | 73a5a305a6 | |
Casper Jeukendrup | 340faf5a68 | |
Roman Pudashkin | 246dffd51c | |
RomanPudashkin | 4acdad8b7b | |
Roman Pudashkin | 0a30b529c9 | |
Eism | 542a3034ae | |
Eism | 548562132f | |
pereverzev_v | e9869aa88d | |
pereverzev_v | 9dcd13144a | |
Michele Spagnolo | 24b8e34858 | |
DmitryArefiev | 2ada4e779d | |
pereverzev+v | 1d3a5a8771 | |
pereverzev+v | 4da8e5ed18 | |
Aaron Sattely | 25266e98a5 | |
pereverzev+v | 2e2085eb5d | |
pereverzev+v | bab78a6f81 | |
pereverzev+v | 12ec72a7fe | |
Elnur Ismailzada | dbbf2ad8e7 | |
Michele Spagnolo | dc67d6429f | |
RomanPudashkin | c9b9717951 | |
RomanPudashkin | 65f14814b9 | |
Elnur Ismailzada | 5654eb1da0 | |
Eism | 701184d894 | |
pereverzev_v | f23002aedf | |
RomanPudashkin | 92b3462113 | |
DmitryArefiev | 8e17b96de8 | |
DmitryArefiev | 95179da691 | |
pereverzev_v | 1c5e4eb077 | |
pereverzev_v | 3820cd5411 | |
RomanPudashkin | cb5a7a8475 | |
Roman Pudashkin | a43001b591 | |
DmitryArefiev | 02e6f1fdcf | |
DmitryArefiev | 2df795a9d7 | |
RomanPudashkin | ebf26c28e7 | |
RomanPudashkin | 7cd27b0805 | |
Elnur Ismailzada | cd7f437b6e | |
Eism | cc1853ea39 | |
Eism | 32570c870e | |
pereverzev+v | 19abc468ad | |
Elnur Ismailzada | 40c5b42bbd | |
RomanPudashkin | d791118d7b | |
Eism | 57e5f382e0 | |
Eism | 5a8d6ea733 | |
pereverzev_v | d050fb0a2d | |
pereverzev+v | 85598a7881 | |
pereverzev+v | 9de702260e | |
pereverzev+v | 7f989ff0ce | |
pereverzev+v | 28ff70f8fb | |
Casper Jeukendrup | 2fa6ad8bcd | |
Casper Jeukendrup | 95a9ac3ff1 | |
RomanPudashkin | 890dfd80ec | |
RomanPudashkin | 98a738855c | |
Elnur Ismailzada | 9f5e9f34d0 | |
RomanPudashkin | 34b69c9a2f | |
Michele Spagnolo | 973a9a47ec | |
pereverzev_v | b5a1133c6e | |
RomanPudashkin | a1bbe6487a | |
pereverzev_v | a988b5c549 | |
pereverzev_v | d7782c2413 | |
RomanPudashkin | d63f0cc1b3 | |
RomanPudashkin | f9d4900da0 | |
Michele Spagnolo | 551fc83c6b | |
Michele Spagnolo | 0fbf0281ab | |
Michele Spagnolo | e8cea477ab | |
Elnur Ismailzada | 78350f8d80 | |
Roman Pudashkin | 40dee9a240 | |
Roman Pudashkin | b83262b669 | |
Roman Pudashkin | c938c281c9 | |
Roman Pudashkin | 02fa60e839 | |
Roman Pudashkin | 262ccb2028 | |
Roman Pudashkin | cea5f9b6c6 | |
Casper Jeukendrup | bcc69e95f8 | |
Casper Jeukendrup | d2635ec790 | |
Roman Pudashkin | df5498313a | |
RomanPudashkin | 2ec580f288 | |
DmitryArefiev | fe562d71b8 | |
pereverzev_v | 805f1c1087 | |
Casper Jeukendrup | acc57e2d5b | |
jeetee | cbba750a10 | |
Marc Sabatella | a1874b3a29 | |
Marc Sabatella | 3b71ff3b16 | |
Elnur Ismailzada | 239f96a643 | |
Eism | 3d9d3d4d41 | |
RomanPudashkin | 4e334b10dd | |
RomanPudashkin | 88a494cfb4 | |
Michele Spagnolo | 7836c0f5d0 | |
Aaron Sattely | eee1c1cd84 | |
Roman Pudashkin | 707e5852c7 | |
Roman Pudashkin | 02945cbf12 | |
Hemant Antony | 1a023ff2d5 | |
Casper Jeukendrup | 1209e0b0ec | |
Casper Jeukendrup | 67cfccc028 | |
Casper Jeukendrup | 458dca54fb | |
pereverzev_v | 04c04001d7 | |
RomanPudashkin | 1431b58233 | |
RomanPudashkin | f57122f224 | |
Elnur Ismailzada | 9cfe34a1d5 | |
Eism | 9f8c23b254 | |
pereverzev_v | fe8a2de4c8 | |
RomanPudashkin | c4977d4381 | |
RomanPudashkin | a4b5fed825 | |
Casper Jeukendrup | 6014da2192 | |
Casper Jeukendrup | f745355e94 | |
pereverzev_v | 7abe56a213 | |
pereverzev_v | 9e37717e15 | |
RomanPudashkin | 6e5c4dc8e3 | |
RomanPudashkin | e74b6f308f | |
pereverzev_v | dadc7d92cf | |
RomanPudashkin | 06b8692dec | |
RomanPudashkin | fdbd087461 | |
Peter Jonas | 365446e370 | |
Grzegorz Pruchniakowski | 1ddc154484 | |
RomanPudashkin | b43a6ec5a0 | |
pereverzev_v | e17bc32e88 | |
Roman Pudashkin | 5f171c5f6d | |
Roman Pudashkin | 54976734b4 | |
Roman Pudashkin | ff1999223a | |
Roman Pudashkin | 149ea72df8 | |
Casper Jeukendrup | 427f872221 | |
Roman Pudashkin | f3168db80b | |
Roman Pudashkin | 84b26667a3 | |
Michele Spagnolo | 6596497e7d | |
Eism | b942cc8ed0 | |
Igor Korsukov | a0de6dc41b | |
Michele Spagnolo | 5e8eb895c2 | |
Michele Spagnolo | c241032b8b | |
RomanPudashkin | 2409b8a330 | |
Peter Jonas | 818bd2a763 | |
Peter Jonas | 64e5086467 | |
pereverzev_v | 3eb411716f | |
pereverzev_v | 0ed7932801 | |
RomanPudashkin | a4675ee803 | |
Roman Pudashkin | 33498f043c | |
Roman Pudashkin | 69e21a5ee6 | |
Roman Pudashkin | f5a95dd0e1 | |
pereverzev_v | 0fe713fe5a | |
pereverzev_v | cd0626cce6 | |
pereverzev_v | 14d66858ea | |
pereverzev_v | 4ec9de79bc | |
pereverzev_v | 82240d807b | |
pereverzev_v | cb75da2b3b | |
pereverzev_v | 580307d973 | |
pereverzev_v | 5ec90f8827 | |
pereverzev_v | 74fb76bae0 | |
pereverzev_v | b65574ea33 | |
pereverzev_v | aba024eda0 | |
RomanPudashkin | f0aa06f3ad | |
Roman Pudashkin | 4474b20d99 | |
RomanPudashkin | d21ebb58fb | |
RomanPudashkin | 2c14fae122 | |
Casper Jeukendrup | d4c4e6f6dc | |
Casper Jeukendrup | 02354e514a | |
Casper Jeukendrup | ff380a0958 | |
Casper Jeukendrup | 737f3d3b4b | |
RomanPudashkin | 1279972e0b | |
RomanPudashkin | 172169ea80 | |
Roman Pudashkin | 40c7901b41 | |
Roman Pudashkin | 0ca2295793 | |
Roman Pudashkin | c76f4e72ab | |
RomanPudashkin | 1e44ca6969 | |
Roman Pudashkin | d2afb72dab | |
Aaron Sattely | f217faaf1d |
|
@ -14,7 +14,7 @@ on:
|
|||
|
||||
jobs:
|
||||
build_mu4:
|
||||
runs-on: ubuntu-18.04
|
||||
runs-on: ubuntu-20.04
|
||||
steps:
|
||||
- name: Cancel Previous Runs
|
||||
uses: styfle/cancel-workflow-action@0.9.1
|
||||
|
|
|
@ -4,6 +4,7 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
- 4.0.2
|
||||
|
||||
jobs:
|
||||
codestyle:
|
||||
|
|
|
@ -4,9 +4,11 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
- 4.0.2
|
||||
|
||||
schedule:
|
||||
- cron: '0 4 */1 */1 *' # At 04:00 on every day-of-month
|
||||
schedule:
|
||||
- cron: '0 3 */1 */1 *' # At 03:00 on every day-of-month for master
|
||||
- cron: '0 5 */1 */1 *' # At 05:00 on every day-of-month for 4.0_rc
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
build_mode:
|
||||
|
@ -30,8 +32,14 @@ jobs:
|
|||
uses: styfle/cancel-workflow-action@0.9.1
|
||||
with:
|
||||
access_token: ${{ github.token }}
|
||||
- name: Clone repository
|
||||
- name: Clone repository (default)
|
||||
uses: actions/checkout@v2
|
||||
if: ${{ github.event_name != 'schedule' || github.event.schedule == '0 3 */1 */1 *' }}
|
||||
- name: Clone repository (4.0_rc)
|
||||
uses: actions/checkout@v2
|
||||
if: ${{ github.event_name == 'schedule' && github.event.schedule == '0 5 */1 */1 *' }}
|
||||
with:
|
||||
ref: 4.0_rc
|
||||
- name: Ccache cache files
|
||||
uses: actions/cache@v2
|
||||
with:
|
||||
|
@ -101,8 +109,10 @@ jobs:
|
|||
DO_PUBLISH='false'
|
||||
fi
|
||||
|
||||
if [ "${{ github.event_name }}" == "pull_request" ]; then PR_INFO="_${{ github.event.pull_request.number }}_${pull_request_title}"; fi
|
||||
UPLOAD_ARTIFACT_NAME="$(tr '":<>|*?/\\' '_' <<<"MU4_${BUILD_NUMBER}_Lin${PR_INFO}")"
|
||||
ADD_INFO="_${GITHUB_REF#refs/heads/}"
|
||||
if [ "${{ github.event_name }}" == "schedule" && "${{ github.event.schedule }}" == "0 5 */1 */1 *" }} ]; then ADD_INFO="_4.0_rc"; fi
|
||||
if [ "${{ github.event_name }}" == "pull_request" ]; then ADD_INFO="_${{ github.event.pull_request.number }}_${pull_request_title}"; fi
|
||||
UPLOAD_ARTIFACT_NAME="$(tr '":<>|*?/\\' '_' <<<"MU4_${BUILD_NUMBER}_Lin${ADD_INFO}")"
|
||||
|
||||
echo "github.repository: ${{ github.repository }}"
|
||||
echo "BUILD_MODE=$BUILD_MODE" >> $GITHUB_ENV
|
||||
|
|
|
@ -4,9 +4,13 @@ on:
|
|||
workflow_dispatch:
|
||||
inputs:
|
||||
publish:
|
||||
description: 'Publish to Transifex: on - publish'
|
||||
description: 'Publish to Transifex (on/off)'
|
||||
required: false
|
||||
default: 'off'
|
||||
cleanup_obsolete:
|
||||
description: 'Clean up obsolete strings (on/off)'
|
||||
required: true
|
||||
|
||||
jobs:
|
||||
lupdate:
|
||||
runs-on: ubuntu-20.04
|
||||
|
@ -27,17 +31,24 @@ jobs:
|
|||
fi
|
||||
fi
|
||||
|
||||
LUPDATE_ARGS=''
|
||||
if [ "${{ github.event.inputs.cleanup_obsolete }}" == "on" ]; then
|
||||
LUPDATE_ARGS='-no-obsolete'
|
||||
fi
|
||||
|
||||
echo "DO_PUBLISH=$DO_PUBLISH" >> $GITHUB_ENV
|
||||
echo "DO_PUBLISH: $DO_PUBLISH"
|
||||
echo "BUILD_NUMBER=$BUILD_NUMBER" >> $GITHUB_ENV
|
||||
echo "BUILD_NUMBER: $BUILD_NUMBER"
|
||||
|
||||
echo "LUPDATE_ARGS=$LUPDATE_ARGS" >> $GITHUB_ENV
|
||||
echo "LUPDATE_ARGS: $LUPDATE_ARGS"
|
||||
|
||||
- name: Setup environment
|
||||
run: |
|
||||
sudo bash ./build/ci/translation/qt_install.sh
|
||||
- name: Run lupdate
|
||||
run: |
|
||||
sudo bash ./build/ci/translation/run_lupdate.sh
|
||||
sudo bash ./build/ci/translation/run_lupdate.sh ${{ env.LUPDATE_ARGS }}
|
||||
- name: Publish to Transifex
|
||||
if: env.DO_PUBLISH == 'true'
|
||||
run: |
|
||||
|
|
|
@ -4,9 +4,11 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
- 4.0.2
|
||||
|
||||
schedule:
|
||||
- cron: '0 4 */1 */1 *' # At 04:00 on every day-of-month
|
||||
schedule:
|
||||
- cron: '0 3 */1 */1 *' # At 03:00 on every day-of-month for master
|
||||
- cron: '0 5 */1 */1 *' # At 05:00 on every day-of-month for 4.0_rc
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
build_mode:
|
||||
|
@ -33,8 +35,14 @@ jobs:
|
|||
uses: styfle/cancel-workflow-action@0.9.1
|
||||
with:
|
||||
access_token: ${{ github.token }}
|
||||
- name: Clone repository
|
||||
- name: Clone repository (default)
|
||||
uses: actions/checkout@v2
|
||||
if: ${{ github.event_name != 'schedule' || github.event.schedule == '0 3 */1 */1 *' }}
|
||||
- name: Clone repository (4.0_rc)
|
||||
uses: actions/checkout@v2
|
||||
if: ${{ github.event_name == 'schedule' && github.event.schedule == '0 5 */1 */1 *' }}
|
||||
with:
|
||||
ref: 4.0_rc
|
||||
- name: Ccache cache files
|
||||
uses: actions/cache@v2
|
||||
with:
|
||||
|
@ -118,8 +126,10 @@ jobs:
|
|||
DO_PUBLISH='false'
|
||||
fi
|
||||
|
||||
if [ "${{ github.event_name }}" == "pull_request" ]; then PR_INFO="_${{ github.event.pull_request.number }}_${pull_request_title}"; fi
|
||||
UPLOAD_ARTIFACT_NAME="$(tr '":<>|*?/\\' '_' <<<"MU4_${BUILD_NUMBER}_Mac${PR_INFO}")"
|
||||
ADD_INFO="_${GITHUB_REF#refs/heads/}"
|
||||
if [ "${{ github.event_name }}" == "schedule" && "${{ github.event.schedule }}" == "0 5 */1 */1 *" }} ]; then ADD_INFO="_4.0_rc"; fi
|
||||
if [ "${{ github.event_name }}" == "pull_request" ]; then ADD_INFO="_${{ github.event.pull_request.number }}_${pull_request_title}"; fi
|
||||
UPLOAD_ARTIFACT_NAME="$(tr '":<>|*?/\\' '_' <<<"MU4_${BUILD_NUMBER}_Mac${ADD_INFO}")"
|
||||
|
||||
echo "github.repository: ${{ github.repository }}"
|
||||
echo "BUILD_MODE=$BUILD_MODE" >> $GITHUB_ENV
|
||||
|
|
|
@ -4,6 +4,7 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
- 4.0.2
|
||||
|
||||
jobs:
|
||||
run_tests:
|
||||
|
|
|
@ -4,6 +4,7 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
- 4.0.2
|
||||
|
||||
jobs:
|
||||
setup:
|
||||
|
|
|
@ -4,8 +4,11 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
schedule:
|
||||
- cron: '0 4 */1 */1 *' # At 04:00 on every day-of-month
|
||||
- 4.0.2
|
||||
|
||||
schedule:
|
||||
- cron: '0 3 */1 */1 *' # At 03:00 on every day-of-month for master
|
||||
- cron: '0 5 */1 */1 *' # At 05:00 on every day-of-month for 4.0_rc
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
build_mode:
|
||||
|
@ -29,10 +32,17 @@ jobs:
|
|||
uses: styfle/cancel-workflow-action@0.9.1
|
||||
with:
|
||||
access_token: ${{ github.token }}
|
||||
- name: Clone repository
|
||||
- name: Clone repository (default)
|
||||
uses: actions/checkout@v2
|
||||
if: ${{ github.event_name != 'schedule' || github.event.schedule == '0 3 */1 */1 *' }}
|
||||
with:
|
||||
fetch-depth: 3
|
||||
- name: Clone repository (4.0_rc)
|
||||
uses: actions/checkout@v2
|
||||
if: ${{ github.event_name == 'schedule' && github.event.schedule == '0 5 */1 */1 *' }}
|
||||
with:
|
||||
fetch-depth: 3
|
||||
ref: 4.0_rc
|
||||
- name: Fetch submodules
|
||||
run: |
|
||||
git submodule update --init --recursive
|
||||
|
@ -97,8 +107,10 @@ jobs:
|
|||
DO_PUBLISH='false'
|
||||
fi
|
||||
|
||||
if [ "${{ github.event_name }}" == "pull_request" ]; then PR_INFO="_${{ github.event.pull_request.number }}_${pull_request_title}"; fi
|
||||
UPLOAD_ARTIFACT_NAME="$(tr '":<>|*?/\\' '_' <<<"MU4_${BUILD_NUMBER}_Win${PR_INFO}")"
|
||||
ADD_INFO="_${GITHUB_REF#refs/heads/}"
|
||||
if [ "${{ github.event_name }}" == "schedule" && "${{ github.event.schedule }}" == "0 5 */1 */1 *" }} ]; then ADD_INFO="_4.0_rc"; fi
|
||||
if [ "${{ github.event_name }}" == "pull_request" ]; then ADD_INFO="_${{ github.event.pull_request.number }}_${pull_request_title}"; fi
|
||||
UPLOAD_ARTIFACT_NAME="$(tr '":<>|*?/\\' '_' <<<"MU4_${BUILD_NUMBER}_Win${ADD_INFO}")"
|
||||
|
||||
echo "github.repository: ${{ github.repository }}"
|
||||
echo "BUILD_MODE=$BUILD_MODE" >> $GITHUB_ENV
|
||||
|
|
|
@ -4,6 +4,7 @@ on:
|
|||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
- 4.0.2
|
||||
|
||||
jobs:
|
||||
run_tests:
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
MuseScore, free and open source music notation software
|
||||
Copyright (C) 1999-2022 MuseScore BVBA and others
|
||||
Copyright (C) 1999-2023 MuseScore BVBA and others
|
||||
|
||||
This program is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License version 3 as published
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
{\rtf1\ansi\ansicpg1252\deff0\nouicompat{\fonttbl{\f0\fnil\fcharset0 Courier New;}{\f1\fnil\fcharset77 Courier New;}}
|
||||
{\*\generator Riched20 6.3.9600}\viewkind4\uc1
|
||||
\pard\sa200\sl276\slmult1\f0\fs18\lang12 MuseScore, free and open source music notation software.\par
|
||||
Copyright (C) 1999-2022 MuseScore BVBA and others.\par
|
||||
Copyright (C) 1999-2023 MuseScore BVBA and others.\par
|
||||
This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License version 3 as published by the Free Software Foundation and reproduce below with the following exception:\par
|
||||
- If you create a document which uses fonts included in MuseScore, and embed this font or unaltered portions of this font into the document, then this font does not by itself cause the resulting document to be covered by the GNU General Public License. This exception does not however invalidate any other reasons why the document might be covered by the GNU General Public License. If you modify this font, you may extend this exception to your version of the font, but you are not obligated to do so. If you do not wish to do so, delete this exception statement from your version.\par
|
||||
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.\par
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
FROM library/ubuntu:18.04
|
||||
FROM library/ubuntu:20.04
|
||||
COPY setup.sh /setup.sh
|
||||
COPY install_mu.sh /install_mu.sh
|
||||
RUN bash -ex setup.sh
|
||||
RUN bash -ex setup.sh
|
||||
|
|
|
@ -52,7 +52,6 @@ apt_packages_runtime=(
|
|||
libegl1-mesa-dev
|
||||
libodbc1
|
||||
libpq-dev
|
||||
libssl1.0.0
|
||||
libxcomposite-dev
|
||||
libxcursor-dev
|
||||
libxi-dev
|
||||
|
|
|
@ -20,4 +20,4 @@
|
|||
# along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
HERE="$(cd "$(dirname "$0")" && pwd)"
|
||||
bash $HERE/../linux/setup.sh --gcc_version 7
|
||||
bash $HERE/../linux/setup.sh
|
|
@ -82,7 +82,7 @@ if [ "$PACKTYPE" == "appimage" ]; then
|
|||
# https://github.com/AppImage/AppImageSpec/blob/master/draft.md#update-information
|
||||
case "${BUILD_MODE}" in
|
||||
"stable_build") export UPDATE_INFORMATION="gh-releases-zsync|musescore|MuseScore|latest|MuseScore-*x86_64.AppImage.zsync";;
|
||||
"nightly_build") export UPDATE_INFORMATION="zsync|https://ftp.osuosl.org/pub/musescore-nightlies/linux/${MAJOR_VERSION}x/nightly/MuseScoreNightly-latest-x86_64.AppImage.zsync";;
|
||||
"nightly_build") export UPDATE_INFORMATION="zsync|https://ftp.osuosl.org/pub/musescore-nightlies/linux/${MAJOR_VERSION}x/nightly/MuseScoreNightly-latest-${BUILD_BRANCH}-x86_64.AppImage.zsync";;
|
||||
*) unset UPDATE_INFORMATION;; # disable updates for other build modes
|
||||
esac
|
||||
|
||||
|
|
|
@ -21,18 +21,10 @@
|
|||
|
||||
# For maximum AppImage compatibility, build on the oldest Linux distribution
|
||||
# that still receives security updates from its manufacturer.
|
||||
|
||||
echo "Setup Linux build environment"
|
||||
trap 'echo Setup failed; exit 1' ERR
|
||||
|
||||
GCC_VERSION="10"
|
||||
while [[ "$#" -gt 0 ]]; do
|
||||
case $1 in
|
||||
-g|--gcc_version) GCC_VERSION="$2"; shift ;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
|
||||
df -h .
|
||||
|
||||
BUILD_TOOLS=$HOME/build_tools
|
||||
|
@ -143,16 +135,17 @@ echo export QML2_IMPORT_PATH="${qt_dir}/qml" >> ${ENV_FILE}
|
|||
##########################################################################
|
||||
|
||||
# COMPILER
|
||||
sudo apt-get install -y --no-install-recommends "g++-${GCC_VERSION}"
|
||||
gcc_version="10"
|
||||
sudo apt-get install -y --no-install-recommends "g++-${gcc_version}"
|
||||
sudo update-alternatives \
|
||||
--install /usr/bin/gcc gcc "/usr/bin/gcc-${GCC_VERSION}" 40 \
|
||||
--slave /usr/bin/g++ g++ "/usr/bin/g++-${GCC_VERSION}"
|
||||
--install /usr/bin/gcc gcc "/usr/bin/gcc-${gcc_version}" 40 \
|
||||
--slave /usr/bin/g++ g++ "/usr/bin/g++-${gcc_version}"
|
||||
|
||||
echo export CC="/usr/bin/gcc-${GCC_VERSION}" >> ${ENV_FILE}
|
||||
echo export CXX="/usr/bin/g++-${GCC_VERSION}" >> ${ENV_FILE}
|
||||
echo export CC="/usr/bin/gcc-${gcc_version}" >> ${ENV_FILE}
|
||||
echo export CXX="/usr/bin/g++-${gcc_version}" >> ${ENV_FILE}
|
||||
|
||||
gcc-${GCC_VERSION} --version
|
||||
g++-${GCC_VERSION} --version
|
||||
gcc-${gcc_version} --version
|
||||
g++-${gcc_version} --version
|
||||
|
||||
# CMAKE
|
||||
# Get newer CMake (only used cached version if it is the same)
|
||||
|
|
|
@ -23,7 +23,7 @@ echo "Setup MacOS build environment"
|
|||
trap 'echo Setup failed; exit 1' ERR
|
||||
SKIP_ERR_FLAG=true
|
||||
|
||||
export MACOSX_DEPLOYMENT_TARGET=10.10
|
||||
export MACOSX_DEPLOYMENT_TARGET=10.14
|
||||
|
||||
# install dependencies
|
||||
wget -c --no-check-certificate -nv -O bottles.zip https://musescore.org/sites/musescore.org/files/2020-02/bottles-MuseScore-3.0-yosemite.zip
|
||||
|
@ -91,9 +91,9 @@ installBottleManually libsndfile
|
|||
|
||||
# fixing install python 3.9 error (it is a dependency for ninja)
|
||||
rm '/usr/local/bin/2to3'
|
||||
brew install ninja
|
||||
|
||||
brew install ninja pkg-config
|
||||
|
||||
# Qt
|
||||
export QT_SHORT_VERSION=5.15.2
|
||||
export QT_PATH=$HOME/Qt
|
||||
export QT_MACOS=$QT_PATH/$QT_SHORT_VERSION/clang_64
|
||||
|
|
|
@ -76,8 +76,11 @@ chmod 600 $SSH_KEY
|
|||
|
||||
FTP_PATH=${OS}/${MAJOR_VERSION}x/${BUILD_DIR}
|
||||
|
||||
file_extension="${ARTIFACT_NAME##*.}"
|
||||
LATEST_NAME="MuseScoreNightly-latest-x86_64.${file_extension}"
|
||||
if [ "$BUILD_MODE" == "nightly_build" ]; then
|
||||
file_extension="${ARTIFACT_NAME##*.}"
|
||||
BUILD_BRANCH=$(cat $ARTIFACTS_DIR/env/build_branch.env)
|
||||
LATEST_NAME="MuseScoreNightly-latest-${BUILD_BRANCH}-x86_64.${file_extension}"
|
||||
fi
|
||||
|
||||
echo "Copy ${ARTIFACTS_DIR}/${ARTIFACT_NAME} to $FTP_PATH"
|
||||
scp -oStrictHostKeyChecking=no -C -i $SSH_KEY $ARTIFACTS_DIR/$ARTIFACT_NAME musescore-nightlies@ftp-osl.osuosl.org:~/ftp/$FTP_PATH
|
||||
|
|
|
@ -77,7 +77,7 @@ elseif (OS_IS_WASM)
|
|||
|
||||
else()
|
||||
# Use pkg-config to get hints about paths
|
||||
find_package(PkgConfig QUIET)
|
||||
find_package(PkgConfig)
|
||||
if(PKG_CONFIG_FOUND)
|
||||
pkg_check_modules(LIBSNDFILE_PKGCONF sndfile>=1.0.25 QUIET)
|
||||
endif()
|
||||
|
|
|
@ -21,7 +21,7 @@ set(MSCORE_UNSTABLE TRUE) # Mark as unstable
|
|||
set(MSCORE_RELEASE_CHANNEL "devel")
|
||||
|
||||
if (NOT MUSESCORE_VERSION_LABEL)
|
||||
SET(MUSESCORE_VERSION_LABEL "Development")
|
||||
SET(MUSESCORE_VERSION_LABEL "dev")
|
||||
endif (NOT MUSESCORE_VERSION_LABEL)
|
||||
|
||||
SET(MUSESCORE_NAME_VERSION "${MUSESCORE_NAME} ${MUSESCORE_VERSION_MAJOR}")
|
||||
|
|
|
@ -21,7 +21,7 @@
|
|||
SET(MUSESCORE_NAME "MuseScore")
|
||||
SET(MUSESCORE_VERSION_MAJOR "4")
|
||||
SET(MUSESCORE_VERSION_MINOR "0")
|
||||
SET(MUSESCORE_VERSION_PATCH "0")
|
||||
SET(MUSESCORE_VERSION_PATCH "2")
|
||||
SET(MUSESCORE_VERSION_LABEL "")
|
||||
|
||||
message(STATUS "MUSESCORE_BUILD_CONFIG ${MUSESCORE_BUILD_CONFIG}")
|
||||
|
|
|
@ -1153,7 +1153,7 @@
|
|||
</Instrument>
|
||||
<Instrument id="g-soprano-ocarina">
|
||||
<family>ocarinas</family>
|
||||
<trackName>G Soprano Ocarina</trackName>
|
||||
<trackName>Soprano Ocarina</trackName>
|
||||
<longName>G Soprano Ocarina</longName>
|
||||
<shortName>G S. Oc.</shortName>
|
||||
<traitName type="tuning">G</traitName>
|
||||
|
@ -1171,7 +1171,7 @@
|
|||
</Instrument>
|
||||
<Instrument id="f-soprano-ocarina">
|
||||
<family>ocarinas</family>
|
||||
<trackName>F Soprano Ocarina</trackName>
|
||||
<trackName>Soprano Ocarina</trackName>
|
||||
<longName>F Soprano Ocarina</longName>
|
||||
<shortName>F S. Oc.</shortName>
|
||||
<traitName type="tuning">F</traitName>
|
||||
|
@ -4693,7 +4693,7 @@
|
|||
<trackName>Trumpet</trackName>
|
||||
<longName>Trumpet</longName>
|
||||
<shortName>Tpt.</shortName>
|
||||
<traitName type="transposition">*C</traitName>
|
||||
<traitName type="transposition">C</traitName>
|
||||
<description>Trumpet in C. Nowadays the most common orchestral trumpet.</description>
|
||||
<musicXMLid>brass.trumpet.c</musicXMLid>
|
||||
<clef>G</clef>
|
||||
|
@ -4734,8 +4734,8 @@
|
|||
<trackName>Trumpet</trackName>
|
||||
<longName>Trumpet</longName>
|
||||
<shortName>Tpt.</shortName>
|
||||
<traitName type="transposition">B♭</traitName>
|
||||
<description>Trumpet in B♭.</description>
|
||||
<traitName type="transposition">*B♭</traitName>
|
||||
<description>Trumpet in B♭. Still the most common trumpet in non-orchestral contexts.</description>
|
||||
<musicXMLid>brass.trumpet.bflat</musicXMLid>
|
||||
<clef>G</clef>
|
||||
<barlineSpan>1</barlineSpan>
|
||||
|
@ -7532,6 +7532,33 @@
|
|||
<program value="0"/> <!--Standard Kit-->
|
||||
</Channel>
|
||||
</Instrument>
|
||||
<Instrument id="bell-tree">
|
||||
<family>unpitched-metal-percussion</family>
|
||||
<trackName>Bell Tree</trackName>
|
||||
<longName>Bell Tree</longName>
|
||||
<shortName>Be. Tr.</shortName>
|
||||
<description>Inverted metal bowls nested on a vertical rod in order of pitch. The pitches are indefinite.</description>
|
||||
<musicXMLid>metal.bells.bell-tree</musicXMLid>
|
||||
<clef>PERC</clef>
|
||||
<stafftype staffTypePreset="perc1Line">percussion</stafftype>
|
||||
<barlineSpan>1</barlineSpan>
|
||||
<drumset>1</drumset>
|
||||
<singleNoteDynamics>0</singleNoteDynamics>
|
||||
<Drum pitch="84"> <!--Belltree-->
|
||||
<head>normal</head>
|
||||
<line>0</line>
|
||||
<voice>0</voice>
|
||||
<name>Glissando Down</name>
|
||||
<stem>1</stem>
|
||||
<shortcut>A</shortcut>
|
||||
</Drum>
|
||||
<Channel>
|
||||
<!--MIDI: Bank 128, Prog 0; MS General: Standard-->
|
||||
<controller ctrl="0" value="1"/> <!--Bank MSB-->
|
||||
<program value="0"/> <!--Standard Kit-->
|
||||
</Channel>
|
||||
<genre>world</genre>
|
||||
</Instrument>
|
||||
<Instrument id="bells">
|
||||
<family>unpitched-metal-percussion</family>
|
||||
<trackName>Bells</trackName>
|
||||
|
@ -7817,6 +7844,33 @@
|
|||
<program value="0"/> <!--Standard Kit-->
|
||||
</Channel>
|
||||
</Instrument>
|
||||
<Instrument id="mark-tree">
|
||||
<family>unpitched-metal-percussion</family>
|
||||
<trackName>Mark Tree</trackName>
|
||||
<longName>Mark Tree</longName>
|
||||
<shortName>Mk. Tr.</shortName>
|
||||
<description>Chimes hung from a horizontal bar in order of pitch. The pitches are indefinite.</description>
|
||||
<musicXMLid>metal.bells.mark-tree</musicXMLid>
|
||||
<clef>PERC</clef>
|
||||
<stafftype staffTypePreset="perc1Line">percussion</stafftype>
|
||||
<barlineSpan>1</barlineSpan>
|
||||
<drumset>1</drumset>
|
||||
<singleNoteDynamics>0</singleNoteDynamics>
|
||||
<Drum pitch="84"> <!--Belltree-->
|
||||
<head>normal</head>
|
||||
<line>0</line>
|
||||
<voice>0</voice>
|
||||
<name>Glissando Down</name>
|
||||
<stem>1</stem>
|
||||
<shortcut>A</shortcut>
|
||||
</Drum>
|
||||
<Channel>
|
||||
<!--MIDI: Bank 128, Prog 0; MS General: Standard-->
|
||||
<controller ctrl="0" value="1"/> <!--Bank MSB-->
|
||||
<program value="0"/> <!--Standard Kit-->
|
||||
</Channel>
|
||||
<genre>world</genre>
|
||||
</Instrument>
|
||||
<Instrument id="metal-castanets">
|
||||
<family>unpitched-metal-percussion</family>
|
||||
<trackName>Metal Castanets</trackName>
|
||||
|
|
|
@ -596,26 +596,26 @@ QT_TRANSLATE_NOOP3("engraving/instruments", "Contrabass Recorder", "contrabass-r
|
|||
//: shortName for Contrabass Recorder; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Cb. Rec.", "contrabass-recorder shortName"),
|
||||
|
||||
//: description for G Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: description for Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Soprano ocarina pitched in G.", "g-soprano-ocarina description"),
|
||||
//: trackName for G Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "G Soprano Ocarina", "g-soprano-ocarina trackName"),
|
||||
//: longName for G Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: trackName for Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Soprano Ocarina", "g-soprano-ocarina trackName"),
|
||||
//: longName for Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "G Soprano Ocarina", "g-soprano-ocarina longName"),
|
||||
//: shortName for G Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: shortName for Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "G S. Oc.", "g-soprano-ocarina shortName"),
|
||||
//: traitName for G Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: traitName for Soprano Ocarina; tuning: G; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "G", "g-soprano-ocarina traitName"),
|
||||
|
||||
//: description for F Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: description for Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Soprano ocarina pitched in F.", "f-soprano-ocarina description"),
|
||||
//: trackName for F Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "F Soprano Ocarina", "f-soprano-ocarina trackName"),
|
||||
//: longName for F Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: trackName for Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Soprano Ocarina", "f-soprano-ocarina trackName"),
|
||||
//: longName for Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "F Soprano Ocarina", "f-soprano-ocarina longName"),
|
||||
//: shortName for F Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: shortName for Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "F S. Oc.", "f-soprano-ocarina shortName"),
|
||||
//: traitName for F Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
//: traitName for Soprano Ocarina; tuning: F; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "F", "f-soprano-ocarina traitName"),
|
||||
|
||||
//: description for Ocarina; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
|
@ -2588,7 +2588,7 @@ QT_TRANSLATE_NOOP3("engraving/instruments", "Trumpet", "c-trumpet longName"),
|
|||
//: shortName for Trumpet; transposition: C; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Tpt.", "c-trumpet shortName"),
|
||||
//: traitName for Trumpet; transposition: C; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "*C", "c-trumpet traitName"),
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "C", "c-trumpet traitName"),
|
||||
//: channel for Trumpet; transposition: C; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "open", "c-trumpet channel"),
|
||||
//: channel for Trumpet; transposition: C; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
|
@ -2608,7 +2608,7 @@ QT_TRANSLATE_NOOP3("engraving/instruments", "open", "trumpet channel"),
|
|||
QT_TRANSLATE_NOOP3("engraving/instruments", "mute", "trumpet channel"),
|
||||
|
||||
//: description for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Trumpet in B♭.", "bb-trumpet description"),
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Trumpet in B♭. Still the most common trumpet in non-orchestral contexts.", "bb-trumpet description"),
|
||||
//: trackName for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Trumpet", "bb-trumpet trackName"),
|
||||
//: longName for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
|
@ -2616,7 +2616,7 @@ QT_TRANSLATE_NOOP3("engraving/instruments", "Trumpet", "bb-trumpet longName"),
|
|||
//: shortName for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Tpt.", "bb-trumpet shortName"),
|
||||
//: traitName for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "B♭", "bb-trumpet traitName"),
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "*B♭", "bb-trumpet traitName"),
|
||||
//: channel for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "open", "bb-trumpet channel"),
|
||||
//: channel for Trumpet; transposition: B♭; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
|
@ -3951,6 +3951,15 @@ QT_TRANSLATE_NOOP3("engraving/instruments", "Bell Plate", "bell-plate longName")
|
|||
//: shortName for Bell Plate; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Be. Pla.", "bell-plate shortName"),
|
||||
|
||||
//: description for Bell Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Inverted metal bowls nested on a vertical rod in order of pitch. The pitches are indefinite.", "bell-tree description"),
|
||||
//: trackName for Bell Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Bell Tree", "bell-tree trackName"),
|
||||
//: longName for Bell Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Bell Tree", "bell-tree longName"),
|
||||
//: shortName for Bell Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Be. Tr.", "bell-tree shortName"),
|
||||
|
||||
//: description for Bells; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Bells.", "bells description"),
|
||||
//: trackName for Bells; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
|
@ -4041,6 +4050,15 @@ QT_TRANSLATE_NOOP3("engraving/instruments", "Iron Pipes", "iron-pipes longName")
|
|||
//: shortName for Iron Pipes; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Ir. Pi.", "iron-pipes shortName"),
|
||||
|
||||
//: description for Mark Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Chimes hung from a horizontal bar in order of pitch. The pitches are indefinite.", "mark-tree description"),
|
||||
//: trackName for Mark Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Mark Tree", "mark-tree trackName"),
|
||||
//: longName for Mark Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Mark Tree", "mark-tree longName"),
|
||||
//: shortName for Mark Tree; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Mk. Tr.", "mark-tree shortName"),
|
||||
|
||||
//: description for Metal Castanets; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
QT_TRANSLATE_NOOP3("engraving/instruments", "Metal castanets.", "metal-castanets description"),
|
||||
//: trackName for Metal Castanets; Please see https://github.com/musescore/MuseScore/wiki/Translating-instrument-names
|
||||
|
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -383,6 +383,26 @@
|
|||
<render>striangle</render>
|
||||
</token>
|
||||
|
||||
<token class="modifier">
|
||||
<name>add</name>
|
||||
<render>add</render>
|
||||
</token>
|
||||
|
||||
<token class="modifier">
|
||||
<name>sus</name>
|
||||
<render>sus</render>
|
||||
</token>
|
||||
|
||||
<token class="modifier">
|
||||
<name>no</name>
|
||||
<render>no</render>
|
||||
</token>
|
||||
|
||||
<token class="modifier">
|
||||
<name>omit</name>
|
||||
<render>omit</render>
|
||||
</token>
|
||||
|
||||
<renderRoot>:n :a m:0.5:0</renderRoot>
|
||||
<renderFunction>:a m:0.5:0 :n</renderFunction>
|
||||
<renderBase>m:-0.2:1 / m:0.2:1 :n :a m:0:-2</renderBase>
|
||||
|
|
|
@ -69,7 +69,9 @@ int AppShell::run(int argc, char** argv)
|
|||
qputenv("QML_DISABLE_DISK_CACHE", "true");
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
qputenv("QT_QPA_PLATFORMTHEME", "gtk3");
|
||||
if (qEnvironmentVariable("QT_QPA_PLATFORM") != "offscreen") {
|
||||
qputenv("QT_QPA_PLATFORMTHEME", "gtk3");
|
||||
}
|
||||
#endif
|
||||
|
||||
const char* appName;
|
||||
|
@ -150,9 +152,10 @@ int AppShell::run(int argc, char** argv)
|
|||
m->onPreInit(runMode);
|
||||
}
|
||||
|
||||
SplashScreen splashScreen;
|
||||
SplashScreen* splashScreen = nullptr;
|
||||
if (runMode == framework::IApplication::RunMode::Editor) {
|
||||
splashScreen.show();
|
||||
splashScreen = new SplashScreen();
|
||||
splashScreen->show();
|
||||
}
|
||||
|
||||
// ====================================================
|
||||
|
@ -257,7 +260,10 @@ int AppShell::run(int argc, char** argv)
|
|||
|
||||
engine->load(url);
|
||||
|
||||
splashScreen.close();
|
||||
if (splashScreen) {
|
||||
splashScreen->close();
|
||||
delete splashScreen;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -285,6 +291,8 @@ int AppShell::run(int argc, char** argv)
|
|||
|
||||
// Deinit
|
||||
|
||||
globalModule.invokeQueuedCalls();
|
||||
|
||||
for (mu::modularity::IModuleSetup* m : m_modules) {
|
||||
m->onDeinit();
|
||||
}
|
||||
|
|
|
@ -9,9 +9,9 @@
|
|||
<file>qml/DevTools/Preferences/SettingsPage.qml</file>
|
||||
<file>qml/NotationPage/NotationStatusBar.qml</file>
|
||||
<file>qml/HomePage/PluginsPage.qml</file>
|
||||
<file>qml/DevTools/VST/VSTTests.qml</file>
|
||||
<file>qml/DevTools/Gallery/GeneralComponentsGallery.qml</file>
|
||||
<file>qml/DevTools/CrashHandler/CrashHandlerDevTools.qml</file>
|
||||
<file>qml/DevTools/CorruptScore/CorruptScoreDevTools.qml</file>
|
||||
<file>qml/AboutDialog.qml</file>
|
||||
<file>qml/AboutMusicXMLDialog.qml</file>
|
||||
<file>qml/resources/mu_logo.svg</file>
|
||||
|
@ -60,7 +60,6 @@
|
|||
<file>qml/Preferences/internal/IncrementalPropertyControlWithTitle.qml</file>
|
||||
<file>qml/Preferences/internal/KeyboardLayoutsSection.qml</file>
|
||||
<file>qml/Preferences/internal/AudioGenerationSection.qml</file>
|
||||
<file>qml/DevTools/Autobot/AutobotControl.qml</file>
|
||||
<file>qml/DevTools/KeyNav/KeyNavExample.qml</file>
|
||||
<file>qml/DevTools/KeyNav/KeyNavSection.qml</file>
|
||||
<file>qml/DevTools/KeyNav/KeyNavSubSection.qml</file>
|
||||
|
|
|
@ -200,6 +200,14 @@ void AppShellModule::onInit(const IApplication::RunMode&)
|
|||
#endif
|
||||
}
|
||||
|
||||
void AppShellModule::onAllInited(const framework::IApplication::RunMode&)
|
||||
{
|
||||
//! NOTE: process QEvent::FileOpen as early as possible if it was postponed
|
||||
#ifdef Q_OS_MACOS
|
||||
qApp->processEvents();
|
||||
#endif
|
||||
}
|
||||
|
||||
void AppShellModule::onDeinit()
|
||||
{
|
||||
s_sessionsManager->deinit();
|
||||
|
|
|
@ -41,6 +41,7 @@ public:
|
|||
|
||||
void onPreInit(const framework::IApplication::RunMode& mode) override;
|
||||
void onInit(const framework::IApplication::RunMode& mode) override;
|
||||
void onAllInited(const framework::IApplication::RunMode& mode) override;
|
||||
void onDeinit() override;
|
||||
};
|
||||
}
|
||||
|
|
|
@ -87,6 +87,8 @@ void CommandLineController::parse(const QStringList& args)
|
|||
// m_parser.addOption(QCommandLineOption("piano-position", "Show Piano top or bottom. Default bottom", "bottom"));
|
||||
m_parser.addOption(QCommandLineOption("resolution", "Resolution [2160p, 1440p, 1080p, 720p, 480p, 360p]", "1080p"));
|
||||
m_parser.addOption(QCommandLineOption("fps", "Frame per second [60, 30, 24]", "24"));
|
||||
m_parser.addOption(QCommandLineOption("ls", "Pause before playback in seconds (3.0)", "3.0"));
|
||||
m_parser.addOption(QCommandLineOption("ts", "Pause before end of video in seconds (3.0)", "3.0"));
|
||||
|
||||
m_parser.addOption(QCommandLineOption("gp-linked", "create tabulature linked staves for guitar pro"));
|
||||
m_parser.addOption(QCommandLineOption("gp-experimental", "experimental features for guitar pro import"));
|
||||
|
@ -316,6 +318,14 @@ void CommandLineController::apply()
|
|||
if (m_parser.isSet("fps")) {
|
||||
videoExportConfiguration()->setFps(intValue("fps"));
|
||||
}
|
||||
|
||||
if (m_parser.isSet("ls")) {
|
||||
videoExportConfiguration()->setLeadingSec(doubleValue("ls"));
|
||||
}
|
||||
|
||||
if (m_parser.isSet("ts")) {
|
||||
videoExportConfiguration()->setTrailingSec(doubleValue("ts"));
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -324,7 +334,7 @@ void CommandLineController::apply()
|
|||
}
|
||||
|
||||
if (m_parser.isSet("f")) {
|
||||
m_converterTask.params[CommandLineController::ParamKey::ForceMode] = m_parser.value("f");
|
||||
m_converterTask.params[CommandLineController::ParamKey::ForceMode] = true;
|
||||
}
|
||||
|
||||
if (m_parser.isSet("S")) {
|
||||
|
|
|
@ -51,7 +51,6 @@ public:
|
|||
virtual std::string handbookUrl() const = 0;
|
||||
virtual std::string askForHelpUrl() const = 0;
|
||||
virtual std::string bugReportUrl() const = 0;
|
||||
virtual std::string leaveFeedbackUrl() const = 0;
|
||||
virtual std::string museScoreUrl() const = 0;
|
||||
virtual std::string museScoreForumUrl() const = 0;
|
||||
virtual std::string museScoreContributionUrl() const = 0;
|
||||
|
|
|
@ -21,7 +21,6 @@
|
|||
*/
|
||||
#include "applicationactioncontroller.h"
|
||||
|
||||
#include <QCoreApplication>
|
||||
#include <QApplication>
|
||||
#include <QCloseEvent>
|
||||
#include <QFileOpenEvent>
|
||||
|
@ -31,6 +30,7 @@
|
|||
#include "async/async.h"
|
||||
#include "audio/synthtypes.h"
|
||||
|
||||
#include "defer.h"
|
||||
#include "translation.h"
|
||||
#include "log.h"
|
||||
|
||||
|
@ -63,7 +63,6 @@ void ApplicationActionController::init()
|
|||
dispatcher()->reg(this, "online-handbook", this, &ApplicationActionController::openOnlineHandbookPage);
|
||||
dispatcher()->reg(this, "ask-help", this, &ApplicationActionController::openAskForHelpPage);
|
||||
dispatcher()->reg(this, "report-bug", this, &ApplicationActionController::openBugReportPage);
|
||||
dispatcher()->reg(this, "leave-feedback", this, &ApplicationActionController::openLeaveFeedbackPage);
|
||||
dispatcher()->reg(this, "preference-dialog", this, &ApplicationActionController::openPreferencesDialog);
|
||||
|
||||
dispatcher()->reg(this, "revert-factory", this, &ApplicationActionController::revertToFactorySettings);
|
||||
|
@ -127,9 +126,10 @@ void ApplicationActionController::onDropEvent(QDropEvent* event)
|
|||
|
||||
bool ApplicationActionController::eventFilter(QObject* watched, QEvent* event)
|
||||
{
|
||||
if (event->type() == QEvent::Close && watched == mainWindow()->qWindow()) {
|
||||
quit(false);
|
||||
event->ignore();
|
||||
if ((event->type() == QEvent::Close && watched == mainWindow()->qWindow())
|
||||
|| event->type() == QEvent::Quit) {
|
||||
bool accepted = quit(false);
|
||||
event->setAccepted(accepted);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
@ -159,23 +159,39 @@ mu::ValCh<bool> ApplicationActionController::isFullScreen() const
|
|||
return result;
|
||||
}
|
||||
|
||||
void ApplicationActionController::quit(bool isAllInstances, const io::path_t& installerPath)
|
||||
bool ApplicationActionController::quit(bool isAllInstances, const io::path_t& installerPath)
|
||||
{
|
||||
if (projectFilesController()->closeOpenedProject()) {
|
||||
if (isAllInstances) {
|
||||
multiInstancesProvider()->quitForAll();
|
||||
}
|
||||
|
||||
if (multiInstancesProvider()->instances().size() == 1 && !installerPath.empty()) {
|
||||
interactive()->openUrl(QUrl::fromLocalFile(installerPath.toQString()));
|
||||
}
|
||||
|
||||
if (multiInstancesProvider()->instances().size() > 1) {
|
||||
multiInstancesProvider()->notifyAboutInstanceWasQuited();
|
||||
}
|
||||
|
||||
QCoreApplication::quit();
|
||||
if (m_quiting) {
|
||||
return false;
|
||||
}
|
||||
|
||||
m_quiting = true;
|
||||
DEFER {
|
||||
m_quiting = false;
|
||||
};
|
||||
|
||||
if (!projectFilesController()->closeOpenedProject()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (isAllInstances) {
|
||||
multiInstancesProvider()->quitForAll();
|
||||
}
|
||||
|
||||
if (multiInstancesProvider()->instances().size() == 1 && !installerPath.empty()) {
|
||||
#if defined(Q_OS_LINUX)
|
||||
interactive()->revealInFileBrowser(installerPath);
|
||||
#else
|
||||
interactive()->openUrl(QUrl::fromLocalFile(installerPath.toQString()));
|
||||
#endif
|
||||
}
|
||||
|
||||
if (multiInstancesProvider()->instances().size() > 1) {
|
||||
multiInstancesProvider()->notifyAboutInstanceWasQuited();
|
||||
}
|
||||
|
||||
QCoreApplication::quit();
|
||||
return true;
|
||||
}
|
||||
|
||||
void ApplicationActionController::restart()
|
||||
|
@ -231,12 +247,6 @@ void ApplicationActionController::openBugReportPage()
|
|||
interactive()->openUrl(bugReportUrl);
|
||||
}
|
||||
|
||||
void ApplicationActionController::openLeaveFeedbackPage()
|
||||
{
|
||||
std::string leaveFeedbackUrl = configuration()->leaveFeedbackUrl();
|
||||
interactive()->openUrl(leaveFeedbackUrl);
|
||||
}
|
||||
|
||||
void ApplicationActionController::openPreferencesDialog()
|
||||
{
|
||||
if (multiInstancesProvider()->isPreferencesAlreadyOpened()) {
|
||||
|
@ -258,8 +268,7 @@ void ApplicationActionController::revertToFactorySettings()
|
|||
IInteractive::Result result = interactive()->warning(title, question,
|
||||
{ interactive()->buttonData(IInteractive::Button::Cancel),
|
||||
IInteractive::ButtonData(revertBtn, trc("appshell", "Revert"), true) },
|
||||
revertBtn, IInteractive::WithIcon
|
||||
);
|
||||
revertBtn);
|
||||
|
||||
if (result.standardButton() == IInteractive::Button::Cancel) {
|
||||
return;
|
||||
|
@ -284,10 +293,3 @@ void ApplicationActionController::revertToFactorySettings()
|
|||
|
||||
restart();
|
||||
}
|
||||
|
||||
bool ApplicationActionController::canReceiveAction(const mu::actions::ActionCode& code) const
|
||||
{
|
||||
Q_UNUSED(code);
|
||||
auto focus = QGuiApplication::focusWindow();
|
||||
return !focus || focus->modality() == Qt::WindowModality::NonModal;
|
||||
}
|
||||
|
|
|
@ -65,14 +65,13 @@ public:
|
|||
void onDragEnterEvent(QDragEnterEvent* event) override;
|
||||
void onDragMoveEvent(QDragMoveEvent* event) override;
|
||||
void onDropEvent(QDropEvent* event) override;
|
||||
bool canReceiveAction(const mu::actions::ActionCode&) const override;
|
||||
|
||||
private:
|
||||
bool eventFilter(QObject* watched, QEvent* event) override;
|
||||
|
||||
void setupConnections();
|
||||
|
||||
void quit(bool isAllInstances, const io::path_t& installerPath = io::path_t());
|
||||
bool quit(bool isAllInstances, const io::path_t& installerPath = io::path_t());
|
||||
void restart();
|
||||
|
||||
void toggleFullScreen();
|
||||
|
@ -83,11 +82,12 @@ private:
|
|||
void openOnlineHandbookPage();
|
||||
void openAskForHelpPage();
|
||||
void openBugReportPage();
|
||||
void openLeaveFeedbackPage();
|
||||
void openPreferencesDialog();
|
||||
|
||||
void revertToFactorySettings();
|
||||
|
||||
bool m_quiting = false;
|
||||
|
||||
async::Channel<bool> m_fullScreenChannel;
|
||||
async::Channel<actions::ActionCodeList> m_actionsReceiveAvailableChanged;
|
||||
};
|
||||
|
|
|
@ -85,11 +85,6 @@ const UiActionList ApplicationUiActions::m_actions = {
|
|||
mu::context::CTX_ANY,
|
||||
TranslatableString("action", "&Report a bug")
|
||||
),
|
||||
UiAction("leave-feedback",
|
||||
mu::context::UiCtxAny,
|
||||
mu::context::CTX_ANY,
|
||||
TranslatableString("action", "F&eedback")
|
||||
),
|
||||
UiAction("revert-factory",
|
||||
mu::context::UiCtxAny,
|
||||
mu::context::CTX_ANY,
|
||||
|
|
|
@ -42,12 +42,11 @@ static const Settings::Key HAS_COMPLETED_FIRST_LAUNCH_SETUP(module_name, "applic
|
|||
static const Settings::Key STARTUP_MODE_TYPE(module_name, "application/startup/modeStart");
|
||||
static const Settings::Key STARTUP_SCORE_PATH(module_name, "application/startup/startScore");
|
||||
|
||||
static const std::string MUSESCORE_ONLINE_HANDBOOK_URL_PATH("/redirect/help");
|
||||
static const std::string MUSESCORE_ONLINE_HANDBOOK_URL_PATH("/handbook/4");
|
||||
static const std::string MUSESCORE_ASK_FOR_HELP_URL_PATH("/redirect/post/question");
|
||||
static const std::string MUSESCORE_BUG_REPORT_URL_PATH("/redirect/post/bug-report?locale=");
|
||||
static const std::string MUSESCORE_FORUM_URL_PATH("/forum");
|
||||
static const std::string MUSESCORE_CONTRIBUTE_URL_PATH("/contribute");
|
||||
static const std::string LEAVE_FEEDBACK_URL("https://musescore.com/content/editor-feedback");
|
||||
static const std::string MUSICXML_URL("https://w3.org");
|
||||
static const std::string MUSICXML_LICENSE_URL(MUSICXML_URL + "/community/about/process/final/");
|
||||
static const std::string MUSICXML_LICENSE_DEED_URL(MUSICXML_URL + "/community/about/process/fsa-deed/");
|
||||
|
@ -116,7 +115,7 @@ std::string AppShellConfiguration::handbookUrl() const
|
|||
QString::fromStdString(utm)
|
||||
};
|
||||
|
||||
return MUSESCORE_ONLINE_HANDBOOK_URL_PATH + "?" + params.join("&").toStdString();
|
||||
return museScoreUrl() + MUSESCORE_ONLINE_HANDBOOK_URL_PATH + "?" + params.join("&").toStdString();
|
||||
}
|
||||
|
||||
std::string AppShellConfiguration::askForHelpUrl() const
|
||||
|
@ -127,7 +126,7 @@ std::string AppShellConfiguration::askForHelpUrl() const
|
|||
"locale=" + QString::fromStdString(languageCode)
|
||||
};
|
||||
|
||||
return MUSESCORE_ASK_FOR_HELP_URL_PATH + "?" + params.join("&").toStdString();
|
||||
return museScoreUrl() + MUSESCORE_ASK_FOR_HELP_URL_PATH + "?" + params.join("&").toStdString();
|
||||
}
|
||||
|
||||
std::string AppShellConfiguration::bugReportUrl() const
|
||||
|
@ -142,18 +141,7 @@ std::string AppShellConfiguration::bugReportUrl() const
|
|||
QString::fromStdString(_sha)
|
||||
};
|
||||
|
||||
return MUSESCORE_BUG_REPORT_URL_PATH + "?" + params.join("&").toStdString();
|
||||
}
|
||||
|
||||
std::string AppShellConfiguration::leaveFeedbackUrl() const
|
||||
{
|
||||
std::string utm = utmParameters(UTM_MEDIUM_MENU);
|
||||
|
||||
QStringList params = {
|
||||
QString::fromStdString(utm)
|
||||
};
|
||||
|
||||
return LEAVE_FEEDBACK_URL + "?" + params.join("&").toStdString();
|
||||
return museScoreUrl() + MUSESCORE_BUG_REPORT_URL_PATH + "?" + params.join("&").toStdString();
|
||||
}
|
||||
|
||||
std::string AppShellConfiguration::museScoreUrl() const
|
||||
|
@ -163,12 +151,12 @@ std::string AppShellConfiguration::museScoreUrl() const
|
|||
|
||||
std::string AppShellConfiguration::museScoreForumUrl() const
|
||||
{
|
||||
return globalConfiguration()->museScoreUrl() + MUSESCORE_FORUM_URL_PATH;
|
||||
return museScoreUrl() + MUSESCORE_FORUM_URL_PATH;
|
||||
}
|
||||
|
||||
std::string AppShellConfiguration::museScoreContributionUrl() const
|
||||
{
|
||||
return globalConfiguration()->museScoreUrl() + MUSESCORE_CONTRIBUTE_URL_PATH;
|
||||
return museScoreUrl() + MUSESCORE_CONTRIBUTE_URL_PATH;
|
||||
}
|
||||
|
||||
std::string AppShellConfiguration::musicXMLLicenseUrl() const
|
||||
|
|
|
@ -65,7 +65,6 @@ public:
|
|||
std::string handbookUrl() const override;
|
||||
std::string askForHelpUrl() const override;
|
||||
std::string bugReportUrl() const override;
|
||||
std::string leaveFeedbackUrl() const override;
|
||||
std::string museScoreUrl() const override;
|
||||
std::string museScoreForumUrl() const override;
|
||||
std::string museScoreContributionUrl() const override;
|
||||
|
|
|
@ -46,6 +46,9 @@ static void updateWindowPosition()
|
|||
WinFramelessWindowController::WinFramelessWindowController()
|
||||
: FramelessWindowController()
|
||||
{
|
||||
memset(&m_monitorInfo, 0, sizeof(MONITORINFO));
|
||||
m_monitorInfo.cbSize = sizeof(MONITORINFO);
|
||||
|
||||
qApp->installEventFilter(this);
|
||||
qApp->installNativeEventFilter(this);
|
||||
}
|
||||
|
@ -129,7 +132,7 @@ bool WinFramelessWindowController::nativeEventFilter(const QByteArray& eventType
|
|||
return false;
|
||||
}
|
||||
|
||||
bool WinFramelessWindowController::removeWindowFrame(MSG* message, long* result) const
|
||||
bool WinFramelessWindowController::removeWindowFrame(MSG* message, long* result)
|
||||
{
|
||||
NCCALCSIZE_PARAMS& params = *reinterpret_cast<NCCALCSIZE_PARAMS*>(message->lParam);
|
||||
|
||||
|
@ -138,11 +141,15 @@ bool WinFramelessWindowController::removeWindowFrame(MSG* message, long* result)
|
|||
GetWindowPlacement(s_hwnd, &placement);
|
||||
|
||||
if (placement.showCmd == SW_SHOWMAXIMIZED) {
|
||||
qreal borderWidth = this->borderWidth();
|
||||
params.rgrc[0].left += borderWidth;
|
||||
params.rgrc[0].top += borderWidth;
|
||||
params.rgrc[0].right -= borderWidth;
|
||||
params.rgrc[0].bottom -= borderWidth;
|
||||
HMONITOR hMonitor = MonitorFromWindow(message->hwnd, MONITOR_DEFAULTTONULL);
|
||||
if (hMonitor != NULL) {
|
||||
GetMonitorInfoW(hMonitor, &m_monitorInfo);
|
||||
}
|
||||
|
||||
params.rgrc[0].left = m_monitorInfo.rcWork.left;
|
||||
params.rgrc[0].top = m_monitorInfo.rcWork.top;
|
||||
params.rgrc[0].right = m_monitorInfo.rcWork.right;
|
||||
params.rgrc[0].bottom = m_monitorInfo.rcWork.bottom;
|
||||
}
|
||||
|
||||
/// NOTE: remove window frame
|
||||
|
@ -150,35 +157,34 @@ bool WinFramelessWindowController::removeWindowFrame(MSG* message, long* result)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool WinFramelessWindowController::calculateWindowSize(MSG* message, long* result) const
|
||||
bool WinFramelessWindowController::calculateWindowSize(MSG* message, long* result)
|
||||
{
|
||||
QWindow* window = mainWindow()->qWindow();
|
||||
if (!window) {
|
||||
if (!isWindowMaximized(message->hwnd)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
QScreen* windowScreen = window->screen();
|
||||
if (!windowScreen) {
|
||||
RECT windowRect;
|
||||
if (!GetWindowRect(message->hwnd, &windowRect)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const QRect availableGeometry = windowScreen->availableGeometry();
|
||||
double scaleFactor = uiConfiguration()->guiScaling();
|
||||
HMONITOR hMonitor = MonitorFromRect(&windowRect, MONITOR_DEFAULTTONULL);
|
||||
if (!hMonitor) {
|
||||
return false;
|
||||
}
|
||||
|
||||
GetMonitorInfoW(hMonitor, &m_monitorInfo);
|
||||
RECT monitorRect = m_monitorInfo.rcMonitor;
|
||||
RECT monitorWorkAreaRect = m_monitorInfo.rcWork;
|
||||
|
||||
auto minMaxInfo = reinterpret_cast<MINMAXINFO*>(message->lParam);
|
||||
|
||||
minMaxInfo->ptMaxSize.x = availableGeometry.width() * scaleFactor;
|
||||
minMaxInfo->ptMaxSize.y = availableGeometry.height() * scaleFactor;
|
||||
|
||||
if (windowScreen == QGuiApplication::primaryScreen()) {
|
||||
minMaxInfo->ptMaxPosition.x = availableGeometry.x();
|
||||
minMaxInfo->ptMaxPosition.y = availableGeometry.y();
|
||||
}
|
||||
|
||||
minMaxInfo->ptMinTrackSize.x = window->minimumWidth() * scaleFactor;
|
||||
minMaxInfo->ptMinTrackSize.y = window->minimumHeight() * scaleFactor;
|
||||
|
||||
minMaxInfo->ptMaxTrackSize = minMaxInfo->ptMaxSize;
|
||||
minMaxInfo->ptMaxSize.x = monitorWorkAreaRect.right - monitorWorkAreaRect.left;
|
||||
minMaxInfo->ptMaxSize.y = monitorWorkAreaRect.bottom - monitorWorkAreaRect.top;
|
||||
minMaxInfo->ptMaxPosition.x = abs(windowRect.left - monitorRect.left);
|
||||
minMaxInfo->ptMaxPosition.y = abs(windowRect.top - monitorRect.top);
|
||||
minMaxInfo->ptMinTrackSize.x = minMaxInfo->ptMaxSize.x;
|
||||
minMaxInfo->ptMinTrackSize.y = minMaxInfo->ptMaxSize.y;
|
||||
|
||||
*result = 0;
|
||||
return true;
|
||||
|
@ -187,8 +193,10 @@ bool WinFramelessWindowController::calculateWindowSize(MSG* message, long* resul
|
|||
bool WinFramelessWindowController::processMouseMove(MSG* message, long* result) const
|
||||
{
|
||||
const LONG borderWidth = this->borderWidth();
|
||||
RECT winrect;
|
||||
GetWindowRect(message->hwnd, &winrect);
|
||||
RECT windowRect;
|
||||
if (!GetWindowRect(message->hwnd, &windowRect)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
long x = GET_X_LPARAM(message->lParam);
|
||||
long y = GET_Y_LPARAM(message->lParam);
|
||||
|
@ -197,8 +205,8 @@ bool WinFramelessWindowController::processMouseMove(MSG* message, long* result)
|
|||
QRect moveAreaRect = windowTitleBarMoveArea();
|
||||
int moveAreaHeight = static_cast<int>(moveAreaRect.height() * scaleFactor);
|
||||
int moveAreaWidth = static_cast<int>(moveAreaRect.width() * scaleFactor);
|
||||
int moveAreaX = winrect.left + static_cast<int>(moveAreaRect.x() * scaleFactor);
|
||||
int moveAreaY = winrect.top + borderWidth + static_cast<int>(moveAreaRect.y() * scaleFactor);
|
||||
int moveAreaX = windowRect.left + static_cast<int>(moveAreaRect.x() * scaleFactor);
|
||||
int moveAreaY = windowRect.top + borderWidth + static_cast<int>(moveAreaRect.y() * scaleFactor);
|
||||
|
||||
/// NOTE: titlebar`s move area
|
||||
if (x >= moveAreaX && x < moveAreaX + moveAreaWidth
|
||||
|
@ -208,53 +216,53 @@ bool WinFramelessWindowController::processMouseMove(MSG* message, long* result)
|
|||
}
|
||||
|
||||
/// NOTE: bottom left corner
|
||||
if (x >= winrect.left && x < winrect.left + borderWidth
|
||||
&& y < winrect.bottom && y >= winrect.bottom - borderWidth) {
|
||||
if (x >= windowRect.left && x < windowRect.left + borderWidth
|
||||
&& y < windowRect.bottom && y >= windowRect.bottom - borderWidth) {
|
||||
*result = HTBOTTOMLEFT;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: bottom right corner
|
||||
if (x < winrect.right && x >= winrect.right - borderWidth
|
||||
&& y < winrect.bottom && y >= winrect.bottom - borderWidth) {
|
||||
if (x < windowRect.right && x >= windowRect.right - borderWidth
|
||||
&& y < windowRect.bottom && y >= windowRect.bottom - borderWidth) {
|
||||
*result = HTBOTTOMRIGHT;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: top left corner
|
||||
if (x >= winrect.left && x < winrect.left + borderWidth
|
||||
&& y >= winrect.top && y < winrect.top + borderWidth) {
|
||||
if (x >= windowRect.left && x < windowRect.left + borderWidth
|
||||
&& y >= windowRect.top && y < windowRect.top + borderWidth) {
|
||||
*result = HTTOPLEFT;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: top right corner
|
||||
if (x < winrect.right && x >= winrect.right - borderWidth
|
||||
&& y >= winrect.top && y < winrect.top + borderWidth) {
|
||||
if (x < windowRect.right && x >= windowRect.right - borderWidth
|
||||
&& y >= windowRect.top && y < windowRect.top + borderWidth) {
|
||||
*result = HTTOPRIGHT;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: left border
|
||||
if (x >= winrect.left && x < winrect.left + borderWidth) {
|
||||
if (x >= windowRect.left && x < windowRect.left + borderWidth) {
|
||||
*result = HTLEFT;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: right border
|
||||
if (x < winrect.right && x >= winrect.right - borderWidth) {
|
||||
if (x < windowRect.right && x >= windowRect.right - borderWidth) {
|
||||
*result = HTRIGHT;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: bottom border
|
||||
if (y < winrect.bottom && y >= winrect.bottom - borderWidth) {
|
||||
if (y < windowRect.bottom && y >= windowRect.bottom - borderWidth) {
|
||||
*result = HTBOTTOM;
|
||||
return true;
|
||||
}
|
||||
|
||||
/// NOTE: top border
|
||||
if (y >= winrect.top && y < winrect.top + borderWidth) {
|
||||
if (y >= windowRect.top && y < windowRect.top + borderWidth) {
|
||||
*result = HTTOP;
|
||||
return true;
|
||||
}
|
||||
|
@ -325,6 +333,17 @@ bool WinFramelessWindowController::showSystemMenuIfNeed(MSG* message) const
|
|||
return true;
|
||||
}
|
||||
|
||||
bool WinFramelessWindowController::isWindowMaximized(HWND hWnd) const
|
||||
{
|
||||
WINDOWPLACEMENT wp;
|
||||
wp.length = sizeof(WINDOWPLACEMENT);
|
||||
if (!GetWindowPlacement(hWnd, &wp)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return wp.showCmd == SW_MAXIMIZE;
|
||||
}
|
||||
|
||||
int WinFramelessWindowController::borderWidth() const
|
||||
{
|
||||
NONCLIENTMETRICS nonClientMetrics = {};
|
||||
|
|
|
@ -31,6 +31,8 @@
|
|||
#include "ui/iuiconfiguration.h"
|
||||
#include "ui/imainwindow.h"
|
||||
|
||||
#include "windows.h"
|
||||
|
||||
namespace mu::appshell {
|
||||
class WinFramelessWindowController : public QObject, public FramelessWindowController
|
||||
{
|
||||
|
@ -46,17 +48,21 @@ private:
|
|||
bool eventFilter(QObject* watched, QEvent* event) override;
|
||||
bool nativeEventFilter(const QByteArray& eventType, void* message, long* result) override;
|
||||
|
||||
bool removeWindowFrame(MSG* message, long* result) const;
|
||||
bool calculateWindowSize(MSG* message, long* result) const;
|
||||
bool removeWindowFrame(MSG* message, long* result);
|
||||
bool calculateWindowSize(MSG* message, long* result);
|
||||
bool processMouseMove(MSG* message, long* result) const;
|
||||
bool processMouseRightClick(MSG* message) const;
|
||||
|
||||
void updateContextMenuState(MSG* message) const;
|
||||
bool showSystemMenuIfNeed(MSG* message) const;
|
||||
|
||||
bool isWindowMaximized(HWND hWnd) const;
|
||||
|
||||
int borderWidth() const;
|
||||
|
||||
QScreen* m_screen = nullptr;
|
||||
|
||||
MONITORINFO m_monitorInfo;
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -59,6 +59,20 @@ StyledDialogView {
|
|||
|
||||
source: "qrc:/qml/resources/mu_logo.svg"
|
||||
sourceSize: Qt.size(100, 100)
|
||||
|
||||
MouseArea {
|
||||
anchors.fill: parent
|
||||
|
||||
property int clickCount: 0
|
||||
|
||||
onClicked: {
|
||||
clickCount++
|
||||
|
||||
if (clickCount % 3 == 0) {
|
||||
aboutModel.toggleDevMode()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
|
@ -122,7 +136,7 @@ StyledDialogView {
|
|||
|
||||
StyledTextLabel {
|
||||
Layout.fillWidth: true
|
||||
text: qsTrc("appshell/about", "Copyright © 1999-2022 MuseScore BVBA and others.\nPublished under the <a href=\"%1\">GNU General Public License version 3</a>.")
|
||||
text: qsTrc("appshell/about", "Copyright © 1999-2023 MuseScore BVBA and others.\nPublished under the <a href=\"%1\">GNU General Public License version 3</a>.")
|
||||
.arg("https://www.gnu.org/licenses/gpl-3.0.html")
|
||||
.replace("\n", "<br>")
|
||||
|
||||
|
|
|
@ -0,0 +1,74 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import QtQuick 2.15
|
||||
|
||||
import MuseScore.Ui 1.0
|
||||
import MuseScore.UiComponents 1.0
|
||||
import MuseScore.Diagnostics 1.0
|
||||
|
||||
Rectangle {
|
||||
color: ui.theme.backgroundSecondaryColor
|
||||
|
||||
CorruptScoreDevToolsModel {
|
||||
id: model
|
||||
}
|
||||
|
||||
Column {
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.margins: 12
|
||||
|
||||
spacing: 12
|
||||
|
||||
Rectangle {
|
||||
readonly property real padding: 12
|
||||
|
||||
width: hintLabel.implicitWidth + 2 * padding
|
||||
height: hintLabel.implicitHeight + 2 * padding
|
||||
|
||||
color: Utils.colorWithAlpha(border.color, 0.25)
|
||||
border.color: "red"
|
||||
border.width: 1
|
||||
radius: 6
|
||||
|
||||
Row {
|
||||
id: hintLabel
|
||||
anchors.fill: parent
|
||||
anchors.margins: parent.padding
|
||||
spacing: 4
|
||||
|
||||
StyledIconLabel {
|
||||
iconCode: IconCode.WARNING
|
||||
}
|
||||
|
||||
StyledTextLabel {
|
||||
text: "DANGER! This button does exactly what it says!"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
text: "Corrupt the open score"
|
||||
onClicked: model.corruptOpenScore()
|
||||
}
|
||||
}
|
||||
}
|
|
@ -31,7 +31,7 @@ import MuseScore.Mpe 1.0
|
|||
import "./Gallery"
|
||||
import "./Interactive"
|
||||
import "./CrashHandler"
|
||||
import "./VST"
|
||||
import "./CorruptScore"
|
||||
import "./KeyNav"
|
||||
import "./Preferences"
|
||||
|
||||
|
@ -49,12 +49,8 @@ DockPage {
|
|||
case "gallery": root.central = galleryComp; break
|
||||
case "interactive": root.central = interactiveComp; break
|
||||
case "crashhandler": root.central = crashhandlerComp; break
|
||||
case "audio": root.central = audioComp; break
|
||||
case "synth": root.central = synthSettingsComp; break
|
||||
case "midiports": root.central = midiPortsComp; break
|
||||
case "vst": root.central = vstComponent; break
|
||||
case "corruptscore": root.central = corruptScoreComp; break
|
||||
case "mpe": root.central = mpeComponent; break
|
||||
case "autobot": root.central = autobotComp; break
|
||||
case "navigation": root.central = keynavComp; break
|
||||
}
|
||||
}
|
||||
|
@ -84,12 +80,8 @@ DockPage {
|
|||
{ "name": "gallery", "title": "UI Gallery" },
|
||||
{ "name": "interactive", "title": "Interactive" },
|
||||
{ "name": "crashhandler", "title": "Crash handler" },
|
||||
{ "name": "audio", "title": "Audio" },
|
||||
{ "name": "synth", "title": "Synth" },
|
||||
{ "name": "midiports", "title": "MIDI ports" },
|
||||
{ "name": "vst", "title": "VST" },
|
||||
{ "name": "corruptscore", "title": "Corrupt score" },
|
||||
{ "name": "mpe", "title": "MPE" },
|
||||
{ "name": "autobot", "title": "Autobot" },
|
||||
{ "name": "navigation", "title": "KeyNav" }
|
||||
]
|
||||
|
||||
|
@ -128,30 +120,9 @@ DockPage {
|
|||
}
|
||||
|
||||
Component {
|
||||
id: audioComp
|
||||
id: corruptScoreComp
|
||||
|
||||
Playback {}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: synthSettingsComp
|
||||
|
||||
SynthSettings {}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: midiPortsComp
|
||||
|
||||
MidiPorts {}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: vstComponent
|
||||
|
||||
//safe if VST is not available
|
||||
Loader {
|
||||
source: "qrc:/qml/DevTools/VST/VSTTests.qml"
|
||||
}
|
||||
CorruptScoreDevTools {}
|
||||
}
|
||||
|
||||
Component {
|
||||
|
@ -162,14 +133,6 @@ DockPage {
|
|||
}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: autobotComp
|
||||
|
||||
Loader {
|
||||
source: "qrc:/qml/DevTools/Autobot/AutobotControl.qml"
|
||||
}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: keynavComp
|
||||
|
||||
|
|
|
@ -366,12 +366,36 @@ Rectangle {
|
|||
text: "Text with icon"
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
icon: IconCode.SAVE
|
||||
text: "Suuuuuuuuuuuuuper long text with icon"
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
icon: IconCode.SAVE
|
||||
text: "Elided suuuuuuuuuuuuuper long text with icon"
|
||||
width: 132
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
icon: IconCode.SAVE
|
||||
text: "Text with icon"
|
||||
orientation: Qt.Horizontal
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
icon: IconCode.SAVE
|
||||
text: "Suuuuuuuuuuuuuper long text with icon"
|
||||
orientation: Qt.Horizontal
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
icon: IconCode.SAVE
|
||||
text: "Elided suuuuuuuuuuuuuper long text with icon"
|
||||
orientation: Qt.Horizontal
|
||||
width: 132
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
text: "Just text"
|
||||
}
|
||||
|
|
|
@ -50,7 +50,7 @@ StyledDialogView {
|
|||
|
||||
property string value: ""
|
||||
width: 150
|
||||
onCurrentTextEdited: input.value = newTextValue
|
||||
onTextChanged: input.value = newTextValue
|
||||
}
|
||||
|
||||
StyledTextLabel {
|
||||
|
|
|
@ -1,212 +0,0 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import QtQuick 2.15
|
||||
import MuseScore.UiComponents 1.0
|
||||
import MuseScore.Ui 1.0
|
||||
import MuseScore.Vst 1.0
|
||||
|
||||
Rectangle {
|
||||
id: root
|
||||
|
||||
color: ui.theme.backgroundPrimaryColor
|
||||
|
||||
NavigationSection {
|
||||
id: navSec
|
||||
name: "VstTests"
|
||||
enabled: root.visible
|
||||
order: 1
|
||||
}
|
||||
|
||||
VstPluginListModelExample {
|
||||
id: pluginListModel
|
||||
|
||||
Component.onCompleted: {
|
||||
load()
|
||||
}
|
||||
}
|
||||
|
||||
Row {
|
||||
anchors {
|
||||
top: parent.top
|
||||
topMargin: 24
|
||||
left: parent.left
|
||||
leftMargin: 24
|
||||
right: parent.right
|
||||
rightMargin: 24
|
||||
}
|
||||
|
||||
NavigationPanel {
|
||||
id: dropdownNav
|
||||
name: "Dropdowns"
|
||||
section: navSec
|
||||
order: 1
|
||||
}
|
||||
|
||||
Column {
|
||||
|
||||
spacing: 4
|
||||
|
||||
StyledTextLabel {
|
||||
id: sequencesTitle
|
||||
|
||||
text: "Track sequence"
|
||||
}
|
||||
|
||||
StyledDropdown {
|
||||
id: sequences
|
||||
|
||||
navigation.name: "TrackSequence Dropdown"
|
||||
navigation.panel: dropdownNav
|
||||
navigation.order: 1
|
||||
|
||||
textRole: "value"
|
||||
valueRole: "value"
|
||||
|
||||
currentIndex: sequences.indexOfValue(pluginListModel.currentSequenceId)
|
||||
model: pluginListModel.sequenceIdList
|
||||
|
||||
onActivated: function(index, value) {
|
||||
pluginListModel.currentSequenceId = value
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
|
||||
spacing: 4
|
||||
|
||||
StyledTextLabel {
|
||||
id: tracksTitle
|
||||
|
||||
text: "Track"
|
||||
}
|
||||
|
||||
StyledDropdown {
|
||||
id: tracks
|
||||
|
||||
navigation.name: "Tracks Dropdown"
|
||||
navigation.panel: dropdownNav
|
||||
navigation.order: 2
|
||||
|
||||
textRole: "value"
|
||||
valueRole: "value"
|
||||
|
||||
model: pluginListModel.trackIdList
|
||||
currentIndex: tracks.indexOfValue(pluginListModel.currentTrackId)
|
||||
|
||||
onActivated: function(index, value) {
|
||||
pluginListModel.currentTrackId = value
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
|
||||
spacing: 4
|
||||
|
||||
StyledTextLabel {
|
||||
id: synthResourceTitle
|
||||
|
||||
text: "Synth resource"
|
||||
}
|
||||
|
||||
StyledDropdown {
|
||||
id: synthResources
|
||||
|
||||
width: 200
|
||||
|
||||
navigation.name: "Synth Resources Dropdown"
|
||||
navigation.panel: dropdownNav
|
||||
navigation.order: 3
|
||||
|
||||
textRole: "value"
|
||||
valueRole: "value"
|
||||
|
||||
model: pluginListModel.availableSynthResources
|
||||
currentIndex: synthResources.indexOfValue(pluginListModel.currentSynthResource)
|
||||
|
||||
onActivated: function(index, value) {
|
||||
pluginListModel.currentSynthResource = value
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
|
||||
spacing: 4
|
||||
|
||||
StyledTextLabel {
|
||||
id: fxResourcesTitle
|
||||
|
||||
text: "Synth resource"
|
||||
}
|
||||
|
||||
StyledDropdown {
|
||||
id: fxResources
|
||||
|
||||
width: 200
|
||||
|
||||
navigation.name: "Synth Resources Dropdown"
|
||||
navigation.panel: dropdownNav
|
||||
navigation.order: 3
|
||||
|
||||
textRole: "value"
|
||||
valueRole: "value"
|
||||
|
||||
model: pluginListModel.availableFxResources
|
||||
currentIndex: fxResources.indexOfValue(pluginListModel.currentFxResource)
|
||||
|
||||
onCurrentValueChanged: {
|
||||
if (fxResources.currentIndex == -1) {
|
||||
return
|
||||
}
|
||||
|
||||
pluginListModel.currentFxResource = fxResources.currentValue
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
id: synthEditorButton
|
||||
|
||||
height: parent.height
|
||||
|
||||
text: "Show plugin view"
|
||||
|
||||
onClicked: {
|
||||
pluginListModel.showSynthPluginEditor()
|
||||
}
|
||||
}
|
||||
|
||||
FlatButton {
|
||||
id: fxEditorButton
|
||||
|
||||
height: parent.height
|
||||
|
||||
text: "Show plugin view"
|
||||
|
||||
onClicked: {
|
||||
pluginListModel.showFxPluginEditor()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -333,6 +333,7 @@ DockPage {
|
|||
|
||||
MixerPanel {
|
||||
navigationSection: mixerPanel.navigationSection
|
||||
navigationPanelOrderStart: mixerPanel.navigationPanelOrderStart
|
||||
|
||||
Component.onCompleted: {
|
||||
mixerPanel.contextMenuModel = contextMenuModel
|
||||
|
|
|
@ -57,7 +57,7 @@ Rectangle {
|
|||
FlatButton {
|
||||
anchors.left: parent.left
|
||||
|
||||
width: 160
|
||||
minWidth: 160
|
||||
|
||||
navigation.panel: root.navigation
|
||||
navigation.order: 2
|
||||
|
@ -76,7 +76,6 @@ Rectangle {
|
|||
navigation.panel: root.navigation
|
||||
navigation.order: 3
|
||||
|
||||
width: 132
|
||||
text: qsTrc("global", "Cancel")
|
||||
|
||||
onClicked: {
|
||||
|
@ -92,7 +91,6 @@ Rectangle {
|
|||
navigation.panel: root.navigation
|
||||
navigation.order: 1
|
||||
|
||||
width: 132
|
||||
accentButton: true
|
||||
|
||||
text: qsTrc("global", "OK")
|
||||
|
|
|
@ -51,12 +51,14 @@ BaseSection {
|
|||
width: parent.width
|
||||
|
||||
delegate: Row {
|
||||
width: parent.width
|
||||
spacing: root.columnSpacing
|
||||
|
||||
RoundedRadioButton {
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
|
||||
width: root.columnWidth
|
||||
width: filePicker.visible ? Math.max(implicitWidth, root.columnWidth)
|
||||
: parent.width
|
||||
|
||||
checked: modelData.checked
|
||||
text: modelData.title
|
||||
|
@ -72,6 +74,8 @@ BaseSection {
|
|||
}
|
||||
|
||||
FilePicker {
|
||||
id: filePicker
|
||||
|
||||
pathFieldWidth: root.columnWidth
|
||||
spacing: root.columnSpacing
|
||||
|
||||
|
@ -102,6 +106,8 @@ BaseSection {
|
|||
height: contentHeight
|
||||
|
||||
delegate: CheckBox {
|
||||
width: parent.width
|
||||
|
||||
text: modelData.title
|
||||
checked: modelData.visible
|
||||
|
||||
|
|
|
@ -67,7 +67,7 @@ Rectangle {
|
|||
|
||||
text: Boolean(item) ? item.title : ""
|
||||
icon: Boolean(item) ? item.icon : IconCode.NONE
|
||||
//enabled: Boolean(item) ? item.enabled : false
|
||||
enabled: Boolean(item) ? item.enabled : false
|
||||
toolTipTitle: Boolean(item) ? item.title : ""
|
||||
toolTipDescription: Boolean(item) ? item.description : ""
|
||||
toolTipShortcut: Boolean(item) ? item.shortcuts : ""
|
||||
|
|
|
@ -70,7 +70,7 @@ Rectangle {
|
|||
order: 1
|
||||
|
||||
onNavigationEvent: function(event) {
|
||||
if (event.type === NavigationEvent.AboutActive) {
|
||||
if (event.type === NavigationEvent.AboutActive && tabsPanel.visible) {
|
||||
event.setData("controlName", tabs.currentItem.navigation.name)
|
||||
}
|
||||
}
|
||||
|
@ -87,6 +87,9 @@ Rectangle {
|
|||
visible: frameModel.titleBarVisible
|
||||
isHorizontalPanel: frameModel.isHorizontalPanel
|
||||
|
||||
navigation.panel: navPanel
|
||||
navigation.order: 1
|
||||
|
||||
onHandleContextMenuItemRequested: function(itemId) {
|
||||
frameModel.handleMenuItem(itemId)
|
||||
}
|
||||
|
|
|
@ -28,6 +28,8 @@ DockPanelView {
|
|||
|
||||
default property alias contentComponent : contentLoader.sourceComponent
|
||||
|
||||
property int navigationPanelOrderStart: 1 // take into account the context menu button
|
||||
|
||||
Loader {
|
||||
id: contentLoader
|
||||
|
||||
|
|
|
@ -37,6 +37,8 @@ Item {
|
|||
property alias heightWhenVisible: titleBar.heightWhenVisible
|
||||
property bool isHorizontalPanel: false
|
||||
|
||||
property alias navigation: contextMenuButton.navigation
|
||||
|
||||
signal handleContextMenuItemRequested(string itemId)
|
||||
|
||||
width: parent.width
|
||||
|
|
|
@ -45,8 +45,13 @@ Rectangle {
|
|||
signal toggleWindowMaximizedRequested()
|
||||
signal closeWindowRequested()
|
||||
|
||||
height: content.childrenRect.height
|
||||
|
||||
RowLayout {
|
||||
anchors.fill: parent
|
||||
id: content
|
||||
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
|
||||
spacing: 8
|
||||
|
||||
|
@ -95,7 +100,7 @@ Rectangle {
|
|||
AppSystemButtons {
|
||||
id: systemButtons
|
||||
|
||||
Layout.alignment: Qt.RightLeft | Qt.AlignVCenter
|
||||
Layout.alignment: Qt.AlignRight | Qt.AlignVCenter
|
||||
Layout.preferredWidth: width
|
||||
Layout.preferredHeight: height
|
||||
|
||||
|
|
|
@ -97,6 +97,11 @@ void AboutModel::copyRevisionToClipboard() const
|
|||
.arg(MUSESCORE_REVISION));
|
||||
}
|
||||
|
||||
void AboutModel::toggleDevMode()
|
||||
{
|
||||
globalConfiguration()->setDevModeEnabled(!globalConfiguration()->devModeEnabled());
|
||||
}
|
||||
|
||||
QVariantMap AboutModel::makeUrl(const QUrl& url, bool showPath) const
|
||||
{
|
||||
QVariantMap urlMap;
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
#include "modularity/ioc.h"
|
||||
#include "iappshellconfiguration.h"
|
||||
#include "update/iupdateconfiguration.h"
|
||||
#include "global/iglobalconfiguration.h"
|
||||
|
||||
class QUrl;
|
||||
|
||||
|
@ -37,6 +38,7 @@ class AboutModel : public QObject
|
|||
|
||||
INJECT(appshell, IAppShellConfiguration, configuration)
|
||||
INJECT(appshell, update::IUpdateConfiguration, updateConfiguration)
|
||||
INJECT(appshell, framework::IGlobalConfiguration, globalConfiguration)
|
||||
|
||||
public:
|
||||
explicit AboutModel(QObject* parent = nullptr);
|
||||
|
@ -53,6 +55,8 @@ public:
|
|||
|
||||
Q_INVOKABLE void copyRevisionToClipboard() const;
|
||||
|
||||
Q_INVOKABLE void toggleDevMode();
|
||||
|
||||
private:
|
||||
QVariantMap makeUrl(const QUrl& url, bool showPath = true) const;
|
||||
};
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
#include "types/translatablestring.h"
|
||||
|
||||
#include "config.h"
|
||||
#include "version.h"
|
||||
#include "log.h"
|
||||
|
||||
using namespace mu::appshell;
|
||||
|
@ -323,7 +322,6 @@ MenuItem* AppMenuModel::makeHelpMenu()
|
|||
makeSeparator(),
|
||||
makeMenuItem("ask-help"),
|
||||
makeMenuItem("report-bug"),
|
||||
makeMenuItem("leave-feedback"),
|
||||
makeSeparator(),
|
||||
makeMenuItem("about", MenuItemRole::AboutRole),
|
||||
makeMenuItem("about-qt", MenuItemRole::AboutQtRole),
|
||||
|
@ -348,29 +346,8 @@ MenuItem* AppMenuModel::makeDiagnosticMenu()
|
|||
makeMenuItem("diagnostic-show-profiler"),
|
||||
};
|
||||
|
||||
MenuItemList accessibilityItems {
|
||||
makeMenuItem("diagnostic-show-navigation-tree"),
|
||||
makeMenuItem("diagnostic-show-accessible-tree"),
|
||||
makeMenuItem("diagnostic-accessible-tree-dump"),
|
||||
};
|
||||
|
||||
MenuItemList engravingItems {
|
||||
makeMenuItem("diagnostic-show-engraving-elements"),
|
||||
makeSeparator(),
|
||||
makeMenuItem("show-element-bounding-rects"),
|
||||
makeMenuItem("color-element-shapes"),
|
||||
makeMenuItem("show-segment-shapes"),
|
||||
makeMenuItem("color-segment-shapes"),
|
||||
makeMenuItem("show-skylines"),
|
||||
makeMenuItem("show-system-bounding-rects"),
|
||||
makeMenuItem("show-corrupted-measures")
|
||||
};
|
||||
|
||||
MenuItemList autobotItems {
|
||||
makeMenuItem("autobot-show-scripts"),
|
||||
};
|
||||
|
||||
MenuItemList items {
|
||||
makeMenuItem("diagnostic-save-diagnostic-files"),
|
||||
makeMenu(TranslatableString("appshell/menu/diagnostic", "&System"), systemItems, "menu-system")
|
||||
};
|
||||
|
||||
|
@ -382,7 +359,29 @@ MenuItem* AppMenuModel::makeDiagnosticMenu()
|
|||
items << makeMenu(TranslatableString("appshell/menu/diagnostic", "&Muse Sampler"), museSamplerItems, "menu-musesampler");
|
||||
#endif
|
||||
|
||||
if (framework::Version::unstable()) {
|
||||
if (globalConfiguration()->devModeEnabled()) {
|
||||
MenuItemList engravingItems {
|
||||
makeMenuItem("diagnostic-show-engraving-elements"),
|
||||
makeSeparator(),
|
||||
makeMenuItem("show-element-bounding-rects"),
|
||||
makeMenuItem("color-element-shapes"),
|
||||
makeMenuItem("show-segment-shapes"),
|
||||
makeMenuItem("color-segment-shapes"),
|
||||
makeMenuItem("show-skylines"),
|
||||
makeMenuItem("show-system-bounding-rects"),
|
||||
makeMenuItem("show-corrupted-measures")
|
||||
};
|
||||
|
||||
MenuItemList autobotItems {
|
||||
makeMenuItem("autobot-show-scripts"),
|
||||
};
|
||||
|
||||
MenuItemList accessibilityItems {
|
||||
makeMenuItem("diagnostic-show-navigation-tree"),
|
||||
makeMenuItem("diagnostic-show-accessible-tree"),
|
||||
makeMenuItem("diagnostic-accessible-tree-dump"),
|
||||
};
|
||||
|
||||
items << makeMenu(TranslatableString("appshell/menu/diagnostic", "&Accessibility"), accessibilityItems, "menu-accessibility")
|
||||
<< makeMenu(TranslatableString("appshell/menu/diagnostic", "&Engraving"), engravingItems, "menu-engraving")
|
||||
<< makeMenu(TranslatableString("appshell/menu/diagnostic", "Auto&bot"), autobotItems, "menu-autobot")
|
||||
|
|
|
@ -38,6 +38,7 @@
|
|||
#include "internal/iappmenumodelhook.h"
|
||||
#include "plugins/ipluginsservice.h"
|
||||
#include "update/iupdateconfiguration.h"
|
||||
#include "global/iglobalconfiguration.h"
|
||||
|
||||
namespace mu::appshell {
|
||||
class AppMenuModel : public uicomponents::AbstractMenuModel
|
||||
|
@ -54,6 +55,7 @@ class AppMenuModel : public uicomponents::AbstractMenuModel
|
|||
INJECT(appshell, IAppMenuModelHook, appMenuModelHook)
|
||||
INJECT(appshell, plugins::IPluginsService, pluginsService)
|
||||
INJECT(appshell, update::IUpdateConfiguration, updateConfiguration)
|
||||
INJECT(appshell, framework::IGlobalConfiguration, globalConfiguration)
|
||||
|
||||
public:
|
||||
explicit AppMenuModel(QObject* parent = nullptr);
|
||||
|
|
|
@ -107,8 +107,7 @@ bool FirstLaunchSetupModel::askAboutClosingEarly()
|
|||
trc("appshell/gettingstarted", "If you choose to cancel, then be sure to check out "
|
||||
"our free Muse Sounds playback library on musescore.org."),
|
||||
buttons,
|
||||
int(IInteractive::Button::Cancel),
|
||||
IInteractive::Option::WithIcon);
|
||||
int(IInteractive::Button::Cancel));
|
||||
|
||||
return result.standardButton() == IInteractive::Button::Cancel;
|
||||
}
|
||||
|
|
|
@ -24,8 +24,6 @@
|
|||
|
||||
#include "translation.h"
|
||||
|
||||
#include "version.h"
|
||||
|
||||
using namespace mu::appshell;
|
||||
|
||||
static const QString HOME_PAGE("musescore://home");
|
||||
|
@ -93,7 +91,7 @@ void MainToolBarModel::load()
|
|||
m_items << buildItem(mu::qtrc("appshell", "Score"), NOTATION_PAGE);
|
||||
m_items << buildItem(mu::qtrc("appshell", "Publish"), PUBLISH_PAGE);
|
||||
|
||||
if (framework::Version::unstable()) {
|
||||
if (globalConfiguration()->devModeEnabled()) {
|
||||
m_items << buildItem(mu::qtrc("appshell", "DevTools"), DEVTOOLS_PAGE);
|
||||
}
|
||||
|
||||
|
|
|
@ -29,6 +29,7 @@
|
|||
|
||||
#include "modularity/ioc.h"
|
||||
#include "context/iglobalcontext.h"
|
||||
#include "iglobalconfiguration.h"
|
||||
|
||||
namespace mu::appshell {
|
||||
class MainToolBarModel : public QAbstractListModel, public async::Asyncable
|
||||
|
@ -36,6 +37,7 @@ class MainToolBarModel : public QAbstractListModel, public async::Asyncable
|
|||
Q_OBJECT
|
||||
|
||||
INJECT(appshell, context::IGlobalContext, context)
|
||||
INJECT(appshell, framework::IGlobalConfiguration, globalConfiguration)
|
||||
|
||||
public:
|
||||
explicit MainToolBarModel(QObject* parent = nullptr);
|
||||
|
|
|
@ -35,8 +35,6 @@ void MainWindowTitleProvider::load()
|
|||
update();
|
||||
|
||||
context()->currentProjectChanged().onNotify(this, [this]() {
|
||||
update();
|
||||
|
||||
if (auto currentProject = context()->currentProject()) {
|
||||
currentProject->pathChanged().onNotify(this, [this]() {
|
||||
update();
|
||||
|
@ -47,6 +45,10 @@ void MainWindowTitleProvider::load()
|
|||
});
|
||||
}
|
||||
});
|
||||
|
||||
context()->currentNotationChanged().onNotify(this, [this]() {
|
||||
update();
|
||||
});
|
||||
}
|
||||
|
||||
QString MainWindowTitleProvider::title() const
|
||||
|
|
|
@ -91,6 +91,8 @@ QList<unsigned int> CommonAudioApiConfigurationModel::bufferSizeList() const
|
|||
result << bufferSize;
|
||||
}
|
||||
|
||||
std::sort(result.begin(), result.end());
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
|
|
@ -78,6 +78,13 @@ IInteractive::Result AutobotInteractive::warning(const std::string& title, const
|
|||
return m_real->warning(title, text, buttons, defBtn, options);
|
||||
}
|
||||
|
||||
IInteractive::Result AutobotInteractive::warning(const std::string& title, const Text& text, const std::string& detailedText,
|
||||
const ButtonDatas& buttons, int defBtn,
|
||||
const Options& options) const
|
||||
{
|
||||
return m_real->warning(title, text, detailedText, buttons, defBtn, options);
|
||||
}
|
||||
|
||||
IInteractive::Result AutobotInteractive::error(const std::string& title, const std::string& text, const Buttons& buttons,
|
||||
const Button& def, const Options& options) const
|
||||
{
|
||||
|
@ -90,6 +97,12 @@ IInteractive::Result AutobotInteractive::error(const std::string& title, const T
|
|||
return m_real->error(title, text, buttons, defBtn, options);
|
||||
}
|
||||
|
||||
IInteractive::Result AutobotInteractive::error(const std::string& title, const Text& text, const std::string& detailedText,
|
||||
const ButtonDatas& buttons, int defBtn, const Options& options) const
|
||||
{
|
||||
return m_real->error(title, text, detailedText, buttons, defBtn, options);
|
||||
}
|
||||
|
||||
io::path_t AutobotInteractive::selectOpeningFile(const QString& title, const io::path_t& dir, const std::vector<std::string>& filter)
|
||||
{
|
||||
return m_real->selectOpeningFile(title, dir, filter);
|
||||
|
|
|
@ -57,6 +57,9 @@ public:
|
|||
Result warning(const std::string& title, const Text& text, const ButtonDatas& buttons = {}, int defBtn = int(Button::NoButton),
|
||||
const Options& options = {}) const override;
|
||||
|
||||
Result warning(const std::string& title, const Text& text, const std::string& detailedText, const ButtonDatas& buttons = {},
|
||||
int defBtn = int(Button::NoButton), const Options& options = {}) const override;
|
||||
|
||||
// error
|
||||
Result error(const std::string& title, const std::string& text, const Buttons& buttons = {}, const Button& def = Button::NoButton,
|
||||
const Options& options = {}) const override;
|
||||
|
@ -64,6 +67,9 @@ public:
|
|||
Result error(const std::string& title, const Text& text, const ButtonDatas& buttons = {}, int defBtn = int(Button::NoButton),
|
||||
const Options& options = {}) const override;
|
||||
|
||||
Result error(const std::string& title, const Text& text, const std::string& detailedText, const ButtonDatas& buttons = {},
|
||||
int defBtn = int(Button::NoButton), const Options& options = {}) const override;
|
||||
|
||||
// files
|
||||
io::path_t selectOpeningFile(const QString& title, const io::path_t& dir, const std::vector<std::string>& filter) override;
|
||||
io::path_t selectSavingFile(const QString& title, const io::path_t& dir, const std::vector<std::string>& filter,
|
||||
|
|
|
@ -39,7 +39,7 @@ public:
|
|||
virtual void signIn() = 0;
|
||||
virtual void signOut() = 0;
|
||||
|
||||
virtual Ret requireAuthorization(const std::string& text = {}) = 0;
|
||||
virtual Ret ensureAuthorization(const std::string& text = {}) = 0;
|
||||
|
||||
virtual ValCh<bool> userAuthorized() const = 0;
|
||||
virtual ValCh<AccountInfo> accountInfo() const = 0;
|
||||
|
|
|
@ -158,5 +158,5 @@ mu::io::path_t CloudConfiguration::tokensFilePath() const
|
|||
|
||||
QString CloudConfiguration::apiRootUrl() const
|
||||
{
|
||||
return "https://api.musescore.com/editor/v1";
|
||||
return "https://desktop.musescore.com/editor/v1";
|
||||
}
|
||||
|
|
|
@ -416,8 +416,12 @@ void CloudService::signOut()
|
|||
clearTokens();
|
||||
}
|
||||
|
||||
mu::Ret CloudService::requireAuthorization(const std::string& text)
|
||||
mu::Ret CloudService::ensureAuthorization(const std::string& text)
|
||||
{
|
||||
if (m_userAuthorized.val) {
|
||||
return make_ok();
|
||||
}
|
||||
|
||||
UriQuery query("musescore://cloud/requireauthorization");
|
||||
query.addParam("text", Val(text));
|
||||
return interactive()->open(query).ret;
|
||||
|
|
|
@ -60,7 +60,7 @@ public:
|
|||
void signIn() override;
|
||||
void signOut() override;
|
||||
|
||||
Ret requireAuthorization(const std::string& text = {}) override;
|
||||
Ret ensureAuthorization(const std::string& text = {}) override;
|
||||
|
||||
ValCh<bool> userAuthorized() const override;
|
||||
ValCh<AccountInfo> accountInfo() const override;
|
||||
|
|
|
@ -109,7 +109,7 @@ FocusScope {
|
|||
|
||||
FlatButton {
|
||||
id: accountInfoButton
|
||||
width: prv.buttonWidth
|
||||
minWidth: prv.buttonWidth
|
||||
text: qsTrc("cloud", "Account info")
|
||||
|
||||
accentButton: true
|
||||
|
@ -131,7 +131,7 @@ FocusScope {
|
|||
}
|
||||
|
||||
FlatButton {
|
||||
width: prv.buttonWidth
|
||||
minWidth: prv.buttonWidth
|
||||
text: qsTrc("cloud", "Sign out")
|
||||
|
||||
navigation.name: "SignOut"
|
||||
|
|
|
@ -108,7 +108,7 @@ FocusScope {
|
|||
FlatButton {
|
||||
Layout.alignment: Qt.AlignLeft
|
||||
|
||||
width: privateProperties.buttonWidth
|
||||
minWidth: privateProperties.buttonWidth
|
||||
text: qsTrc("cloud", "Learn more")
|
||||
|
||||
navigation.name: "LearnMore"
|
||||
|
@ -126,7 +126,7 @@ FocusScope {
|
|||
spacing: 22
|
||||
|
||||
FlatButton {
|
||||
width: privateProperties.buttonWidth
|
||||
minWidth: privateProperties.buttonWidth
|
||||
text: qsTrc("cloud", "Sign in")
|
||||
|
||||
navigation.name: "SignIn"
|
||||
|
@ -140,7 +140,7 @@ FocusScope {
|
|||
|
||||
FlatButton {
|
||||
id: createNewAccount
|
||||
width: privateProperties.buttonWidth
|
||||
minWidth: privateProperties.buttonWidth
|
||||
text: qsTrc("cloud", "Create new account")
|
||||
|
||||
accentButton: true
|
||||
|
|
|
@ -56,7 +56,7 @@ void UiContextResolver::init()
|
|||
notifyAboutContextChanged();
|
||||
});
|
||||
|
||||
notation->interaction()->textEditingEnded().onNotify(this, [this]() {
|
||||
notation->interaction()->textEditingEnded().onReceive(this, [this](engraving::TextBase*) {
|
||||
notifyAboutContextChanged();
|
||||
});
|
||||
|
||||
|
|
|
@ -223,6 +223,9 @@ RetVal<project::INotationProjectPtr> BackendApi::openProject(const io::path_t& p
|
|||
}
|
||||
|
||||
notation->setViewMode(ViewMode::PAGE);
|
||||
for (IExcerptNotationPtr excerpt : notationProject->masterNotation()->excerpts().val) {
|
||||
excerpt->notation()->setViewMode(ViewMode::PAGE);
|
||||
}
|
||||
|
||||
return RetVal<INotationProjectPtr>::make_ok(notationProject);
|
||||
}
|
||||
|
@ -565,6 +568,7 @@ Ret BackendApi::doExportScorePartsPdfs(const IMasterNotationPtr masterNotation,
|
|||
jsonForPdfs["scoreBin"] = QString::fromLatin1(scoreBin);
|
||||
|
||||
INotationPtrList notations;
|
||||
notations.push_back(masterNotation->notation());
|
||||
|
||||
QJsonArray partsArray;
|
||||
QJsonArray partsNamesArray;
|
||||
|
|
|
@ -92,6 +92,8 @@ mu::Ret ConverterController::fileConvert(const io::path_t& in, const io::path_t&
|
|||
ret = convertFullNotation(writer, notationProject->masterNotation()->notation(), out);
|
||||
}
|
||||
|
||||
globalContext()->setCurrentProject(nullptr);
|
||||
|
||||
return make_ret(Ret::Code::Ok);
|
||||
}
|
||||
|
||||
|
|
|
@ -29,6 +29,7 @@ set(MODULE_SRC
|
|||
${CMAKE_CURRENT_LIST_DIR}/diagnosticsmodule.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/diagnosticutils.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/idiagnosticspathsregister.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/idiagnosticsconfiguration.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/iengravingelementsprovider.h
|
||||
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/diagnosticsconfiguration.cpp
|
||||
|
@ -42,6 +43,12 @@ set(MODULE_SRC
|
|||
${CMAKE_CURRENT_LIST_DIR}/internal/engravingelementsprovider.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/engravingelementsprovider.h
|
||||
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/isavediagnosticfilesscenario.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/savediagnosticfilesscenario.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/savediagnosticfilesscenario.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/diagnosticfileswriter.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/internal/diagnosticfileswriter.h
|
||||
|
||||
${CMAKE_CURRENT_LIST_DIR}/view/diagnosticspathsmodel.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/view/diagnosticspathsmodel.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/view/diagnosticaccessiblemodel.cpp
|
||||
|
@ -66,6 +73,8 @@ set(MODULE_SRC
|
|||
|
||||
${CMAKE_CURRENT_LIST_DIR}/devtools/crashhandlerdevtoolsmodel.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/devtools/crashhandlerdevtoolsmodel.h
|
||||
${CMAKE_CURRENT_LIST_DIR}/devtools/corruptscoredevtoolsmodel.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/devtools/corruptscoredevtoolsmodel.h
|
||||
)
|
||||
|
||||
# --- Crashpad ---
|
||||
|
|
|
@ -0,0 +1,67 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "corruptscoredevtoolsmodel.h"
|
||||
|
||||
using namespace mu::diagnostics;
|
||||
|
||||
CorruptScoreDevToolsModel::CorruptScoreDevToolsModel(QObject* parent)
|
||||
: QObject(parent)
|
||||
{
|
||||
}
|
||||
|
||||
void CorruptScoreDevToolsModel::corruptOpenScore()
|
||||
{
|
||||
project::INotationProjectPtr project = globalContext()->currentProject();
|
||||
if (!project) {
|
||||
return;
|
||||
}
|
||||
|
||||
LOGW() << "Score corruption on demand!";
|
||||
|
||||
mu::notation::INotationPtr notation = project->masterNotation()->notation();
|
||||
|
||||
notation->undoStack()->prepareChanges();
|
||||
|
||||
for (engraving::System* system : notation->elements()->msScore()->systems()) {
|
||||
for (engraving::MeasureBase* measureBase : system->measures()) {
|
||||
if (!measureBase->isMeasure()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
mu::engraving::Measure* measure = mu::engraving::toMeasure(measureBase);
|
||||
mu::engraving::Segment* firstSegment = measure->first(mu::engraving::SegmentType::ChordRest);
|
||||
|
||||
for (mu::engraving::Segment* s = firstSegment; s; s = s->next(mu::engraving::SegmentType::ChordRest)) {
|
||||
mu::engraving::EngravingItem* element = s->element(0);
|
||||
if (!element) {
|
||||
continue;
|
||||
}
|
||||
|
||||
mu::engraving::ChordRest* cr = toChordRest(element);
|
||||
cr->undoChangeProperty(mu::engraving::Pid::DURATION, mu::engraving::Fraction::fromString(u"0/4"));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
notation->undoStack()->commitChanges();
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef MU_DIAGNOSTICS_CORRUPTSCORENDEVTOOLSMODEL_H
|
||||
#define MU_DIAGNOSTICS_CORRUPTSCORENDEVTOOLSMODEL_H
|
||||
|
||||
#include <QObject>
|
||||
|
||||
#include "modularity/ioc.h"
|
||||
#include "context/iglobalcontext.h"
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class CorruptScoreDevToolsModel : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
INJECT(diagnostics, context::IGlobalContext, globalContext)
|
||||
|
||||
public:
|
||||
explicit CorruptScoreDevToolsModel(QObject* parent = nullptr);
|
||||
|
||||
Q_INVOKABLE void corruptOpenScore();
|
||||
};
|
||||
}
|
||||
|
||||
#endif // MU_DIAGNOSTICS_CORRUPTSCORENDEVTOOLSMODEL_H
|
|
@ -33,6 +33,7 @@
|
|||
#include "internal/diagnosticsactionscontroller.h"
|
||||
#include "internal/diagnosticspathsregister.h"
|
||||
#include "internal/engravingelementsprovider.h"
|
||||
#include "internal/savediagnosticfilesscenario.h"
|
||||
|
||||
#include "internal/crashhandler/crashhandler.h"
|
||||
|
||||
|
@ -50,6 +51,7 @@
|
|||
#include "view/engraving/engravingelementsmodel.h"
|
||||
|
||||
#include "devtools/crashhandlerdevtoolsmodel.h"
|
||||
#include "devtools/corruptscoredevtoolsmodel.h"
|
||||
|
||||
#include "log.h"
|
||||
#include "config.h"
|
||||
|
@ -57,8 +59,8 @@
|
|||
using namespace mu::diagnostics;
|
||||
using namespace mu::modularity;
|
||||
|
||||
static std::shared_ptr<DiagnosticsConfiguration> s_configuration = std::make_shared<DiagnosticsConfiguration>();
|
||||
static std::shared_ptr<DiagnosticsActionsController> s_actionsController = std::make_shared<DiagnosticsActionsController>();
|
||||
static std::shared_ptr<DiagnosticsConfiguration> s_configuration = {};
|
||||
static std::shared_ptr<DiagnosticsActionsController> s_actionsController = {};
|
||||
|
||||
std::string DiagnosticsModule::moduleName() const
|
||||
{
|
||||
|
@ -67,8 +69,13 @@ std::string DiagnosticsModule::moduleName() const
|
|||
|
||||
void DiagnosticsModule::registerExports()
|
||||
{
|
||||
s_configuration = std::make_shared<DiagnosticsConfiguration>();
|
||||
s_actionsController = std::make_shared<DiagnosticsActionsController>();
|
||||
|
||||
ioc()->registerExport<IDiagnosticsPathsRegister>(moduleName(), new DiagnosticsPathsRegister());
|
||||
ioc()->registerExport<EngravingElementsProvider>(moduleName(), new EngravingElementsProvider());
|
||||
ioc()->registerExport<IDiagnosticsConfiguration>(moduleName(), s_configuration);
|
||||
ioc()->registerExport<ISaveDiagnosticFilesScenario>(moduleName(), new SaveDiagnosticFilesScenario());
|
||||
}
|
||||
|
||||
void DiagnosticsModule::resolveImports()
|
||||
|
@ -104,6 +111,7 @@ void DiagnosticsModule::registerUiTypes()
|
|||
qmlRegisterType<EngravingElementsModel>("MuseScore.Diagnostics", 1, 0, "EngravingElementsModel");
|
||||
|
||||
qmlRegisterType<CrashHandlerDevToolsModel>("MuseScore.Diagnostics", 1, 0, "CrashHandlerDevToolsModel");
|
||||
qmlRegisterType<CorruptScoreDevToolsModel>("MuseScore.Diagnostics", 1, 0, "CorruptScoreDevToolsModel");
|
||||
}
|
||||
|
||||
void DiagnosticsModule::onInit(const framework::IApplication::RunMode&)
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#ifndef MU_DIAGNOSTICS_IDIAGNOSTICSCONFIGURATION_H
|
||||
#define MU_DIAGNOSTICS_IDIAGNOSTICSCONFIGURATION_H
|
||||
|
||||
#include "modularity/imoduleexport.h"
|
||||
|
||||
#include "io/path.h"
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class IDiagnosticsConfiguration : MODULE_EXPORT_INTERFACE
|
||||
{
|
||||
INTERFACE_ID(IDiagnosticsConfiguration)
|
||||
|
||||
public:
|
||||
virtual bool isDumpUploadAllowed() const = 0;
|
||||
virtual void setIsDumpUploadAllowed(bool val) = 0;
|
||||
|
||||
virtual bool shouldWarnBeforeSavingDiagnosticFiles() const = 0;
|
||||
virtual void setShouldWarnBeforeSavingDiagnosticFiles(bool val) = 0;
|
||||
|
||||
virtual io::path_t diagnosticFilesDefaultSavingPath() const = 0;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // MU_DIAGNOSTICS_IDIAGNOSTICSCONFIGURATION_H
|
|
@ -0,0 +1,97 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "diagnosticfileswriter.h"
|
||||
|
||||
#include "serialization/zipwriter.h"
|
||||
#include "containers.h"
|
||||
|
||||
#include "log.h"
|
||||
|
||||
using namespace mu::diagnostics;
|
||||
using namespace mu::io;
|
||||
|
||||
mu::Ret DiagnosticFilesWriter::writeDiagnosticFiles(const path_t& destinationPath)
|
||||
{
|
||||
TRACEFUNC;
|
||||
|
||||
static const std::vector<std::string> DIRS_TO_WRITE {
|
||||
"logs",
|
||||
"vst",
|
||||
"plugins",
|
||||
"workspaces",
|
||||
};
|
||||
|
||||
ZipWriter zip(destinationPath);
|
||||
|
||||
for (const std::string& dirName : DIRS_TO_WRITE) {
|
||||
RetVal<io::paths_t> files = scanDir(dirName);
|
||||
if (!files.ret) {
|
||||
LOGE() << files.ret;
|
||||
continue;
|
||||
}
|
||||
|
||||
for (const io::path_t& filePath : files.val) {
|
||||
Ret ret = addFileToZip(filePath, zip, dirName);
|
||||
if (!ret) {
|
||||
LOGE() << ret.toString();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const std::vector<std::string> FILES_TO_WRITE {
|
||||
"shortcuts.xml",
|
||||
"midi_mappings.xml",
|
||||
};
|
||||
|
||||
for (const std::string& fileName : FILES_TO_WRITE) {
|
||||
Ret ret = addFileToZip(globalConfiguration()->userAppDataPath() + "/" + fileName, zip);
|
||||
if (!ret) {
|
||||
LOGE() << ret.toString();
|
||||
}
|
||||
}
|
||||
|
||||
return make_ok();
|
||||
}
|
||||
|
||||
mu::RetVal<mu::io::paths_t> DiagnosticFilesWriter::scanDir(const std::string& dirName)
|
||||
{
|
||||
RetVal<io::paths_t> paths = fileSystem()->scanFiles(globalConfiguration()->userAppDataPath() + "/" + dirName,
|
||||
{ "*" },
|
||||
ScanMode::FilesInCurrentDirAndSubdirs);
|
||||
return paths;
|
||||
}
|
||||
|
||||
mu::Ret DiagnosticFilesWriter::addFileToZip(const path_t& filePath, ZipWriter& zip, const std::string& destinationDirName)
|
||||
{
|
||||
RetVal<ByteArray> data = fileSystem()->readFile(filePath);
|
||||
if (!data.ret) {
|
||||
return data.ret;
|
||||
}
|
||||
|
||||
std::string fileName = io::filename(filePath).toStdString();
|
||||
std::string filePathInZip = destinationDirName.empty() ? fileName : destinationDirName + "/" + fileName;
|
||||
|
||||
zip.addFile(filePathInZip, data.val);
|
||||
|
||||
return make_ok();
|
||||
}
|
|
@ -0,0 +1,51 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#ifndef MU_DIAGNOSTICS_DIAGNOSTICFILESWRITER_H
|
||||
#define MU_DIAGNOSTICS_DIAGNOSTICFILESWRITER_H
|
||||
|
||||
#include "modularity/ioc.h"
|
||||
#include "io/ifilesystem.h"
|
||||
#include "global/iglobalconfiguration.h"
|
||||
|
||||
#include "types/ret.h"
|
||||
#include "io/path.h"
|
||||
|
||||
namespace mu {
|
||||
class ZipWriter;
|
||||
}
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class DiagnosticFilesWriter
|
||||
{
|
||||
INJECT_STATIC(diagnostics, io::IFileSystem, fileSystem)
|
||||
INJECT_STATIC(diagnostics, framework::IGlobalConfiguration, globalConfiguration)
|
||||
|
||||
public:
|
||||
static Ret writeDiagnosticFiles(const io::path_t& destinationZipPath);
|
||||
|
||||
private:
|
||||
static RetVal<io::paths_t> scanDir(const std::string& dirName);
|
||||
static mu::Ret addFileToZip(const io::path_t& filePath, ZipWriter& zip, const std::string& destinationDirName = std::string());
|
||||
};
|
||||
}
|
||||
|
||||
#endif // MU_DIAGNOSTICS_DIAGNOSTICFILESWRITER_H
|
|
@ -29,6 +29,11 @@ using namespace mu::actions;
|
|||
using namespace mu::diagnostics;
|
||||
|
||||
const UiActionList DiagnosticsActions::m_actions = {
|
||||
UiAction("diagnostic-save-diagnostic-files",
|
||||
mu::context::UiCtxAny,
|
||||
mu::context::CTX_ANY,
|
||||
TranslatableString("action", "Save diagnostic files")
|
||||
),
|
||||
UiAction("diagnostic-show-paths",
|
||||
mu::context::UiCtxAny,
|
||||
mu::context::CTX_ANY,
|
||||
|
|
|
@ -25,8 +25,11 @@
|
|||
|
||||
#include "view/diagnosticaccessiblemodel.h"
|
||||
|
||||
#include "log.h"
|
||||
|
||||
using namespace mu::diagnostics;
|
||||
using namespace mu::accessibility;
|
||||
using namespace mu::framework;
|
||||
|
||||
static const mu::UriQuery SYSTEM_PATHS_URI("musescore://diagnostics/system/paths?sync=false&modal=false&floating=true");
|
||||
static const mu::UriQuery PROFILER_URI("musescore://diagnostics/system/profiler?sync=false&modal=false&floating=true");
|
||||
|
@ -42,6 +45,7 @@ void DiagnosticsActionsController::init()
|
|||
dispatcher()->reg(this, "diagnostic-show-accessible-tree", [this]() { openUri(ACCESSIBLE_TREE_URI); });
|
||||
dispatcher()->reg(this, "diagnostic-accessible-tree-dump", []() { DiagnosticAccessibleModel::dumpTree(); });
|
||||
dispatcher()->reg(this, "diagnostic-show-engraving-elements", [this]() { openUri(ENGRAVING_ELEMENTS_URI, false); });
|
||||
dispatcher()->reg(this, "diagnostic-save-diagnostic-files", this, &DiagnosticsActionsController::saveDiagnosticFiles);
|
||||
}
|
||||
|
||||
void DiagnosticsActionsController::openUri(const mu::UriQuery& uri, bool isSingle)
|
||||
|
@ -52,3 +56,11 @@ void DiagnosticsActionsController::openUri(const mu::UriQuery& uri, bool isSingl
|
|||
|
||||
interactive()->open(uri);
|
||||
}
|
||||
|
||||
void DiagnosticsActionsController::saveDiagnosticFiles()
|
||||
{
|
||||
Ret ret = saveDiagnosticsScenario()->saveDiagnosticFiles();
|
||||
if (!ret) {
|
||||
LOGE() << ret.toString();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -27,12 +27,14 @@
|
|||
#include "actions/actionable.h"
|
||||
#include "iinteractive.h"
|
||||
#include "accessibility/iaccessibilitycontroller.h"
|
||||
#include "isavediagnosticfilesscenario.h"
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class DiagnosticsActionsController : public actions::Actionable
|
||||
{
|
||||
INJECT(diagnostics, actions::IActionsDispatcher, dispatcher)
|
||||
INJECT(diagnostics, framework::IInteractive, interactive)
|
||||
INJECT(diagnostics, diagnostics::ISaveDiagnosticFilesScenario, saveDiagnosticsScenario)
|
||||
|
||||
public:
|
||||
DiagnosticsActionsController() = default;
|
||||
|
@ -41,6 +43,7 @@ public:
|
|||
|
||||
private:
|
||||
void openUri(const mu::UriQuery& uri, bool isSingle = true);
|
||||
void saveDiagnosticFiles();
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -27,10 +27,12 @@ using namespace mu::diagnostics;
|
|||
using namespace mu::framework;
|
||||
|
||||
static const Settings::Key IS_DUMP_UPLOAD_ALLOWED("diagnostics", "diagnostics/is_dump_upload_allowed");
|
||||
static const Settings::Key SHOULD_WARN_BEFORE_SAVING_DIAGNOSTIC_FILES("diagnostics", "diagnostics/shouldWarnBeforeSavingDiagnosticFiles");
|
||||
|
||||
void DiagnosticsConfiguration::init()
|
||||
{
|
||||
settings()->setDefaultValue(IS_DUMP_UPLOAD_ALLOWED, Val(true));
|
||||
settings()->setDefaultValue(SHOULD_WARN_BEFORE_SAVING_DIAGNOSTIC_FILES, Val(true));
|
||||
}
|
||||
|
||||
bool DiagnosticsConfiguration::isDumpUploadAllowed() const
|
||||
|
@ -42,3 +44,18 @@ void DiagnosticsConfiguration::setIsDumpUploadAllowed(bool val)
|
|||
{
|
||||
settings()->setSharedValue(IS_DUMP_UPLOAD_ALLOWED, Val(val));
|
||||
}
|
||||
|
||||
bool DiagnosticsConfiguration::shouldWarnBeforeSavingDiagnosticFiles() const
|
||||
{
|
||||
return settings()->value(SHOULD_WARN_BEFORE_SAVING_DIAGNOSTIC_FILES).toBool();
|
||||
}
|
||||
|
||||
void DiagnosticsConfiguration::setShouldWarnBeforeSavingDiagnosticFiles(bool val)
|
||||
{
|
||||
settings()->setSharedValue(SHOULD_WARN_BEFORE_SAVING_DIAGNOSTIC_FILES, Val(val));
|
||||
}
|
||||
|
||||
mu::io::path_t DiagnosticsConfiguration::diagnosticFilesDefaultSavingPath() const
|
||||
{
|
||||
return globalConfiguration()->homePath();
|
||||
}
|
||||
|
|
|
@ -22,16 +22,28 @@
|
|||
#ifndef MU_DIAGNOSTICS_DIAGNOSTICSCONFIGURATION_H
|
||||
#define MU_DIAGNOSTICS_DIAGNOSTICSCONFIGURATION_H
|
||||
|
||||
#include "idiagnosticsconfiguration.h"
|
||||
|
||||
#include "modularity/ioc.h"
|
||||
#include "iglobalconfiguration.h"
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class DiagnosticsConfiguration
|
||||
class DiagnosticsConfiguration : public IDiagnosticsConfiguration
|
||||
{
|
||||
INJECT(diagnostics, framework::IGlobalConfiguration, globalConfiguration)
|
||||
|
||||
public:
|
||||
DiagnosticsConfiguration() = default;
|
||||
|
||||
void init();
|
||||
|
||||
bool isDumpUploadAllowed() const;
|
||||
void setIsDumpUploadAllowed(bool val);
|
||||
bool isDumpUploadAllowed() const override;
|
||||
void setIsDumpUploadAllowed(bool val) override;
|
||||
|
||||
bool shouldWarnBeforeSavingDiagnosticFiles() const override;
|
||||
void setShouldWarnBeforeSavingDiagnosticFiles(bool val) override;
|
||||
|
||||
io::path_t diagnosticFilesDefaultSavingPath() const override;
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -19,25 +19,23 @@
|
|||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#ifndef MU_AUDIO_IAUDIOBUFFER_H
|
||||
#define MU_AUDIO_IAUDIOBUFFER_H
|
||||
#ifndef MU_DIAGNOSTICS_ISAVEDIAGNOSTICFILESSCENARIO_H
|
||||
#define MU_DIAGNOSTICS_ISAVEDIAGNOSTICFILESSCENARIO_H
|
||||
|
||||
#include <memory>
|
||||
#include "../iaudiosource.h"
|
||||
#include "modularity/imoduleexport.h"
|
||||
|
||||
namespace mu::audio {
|
||||
class IAudioBuffer
|
||||
#include "types/ret.h"
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class ISaveDiagnosticFilesScenario : MODULE_EXPORT_INTERFACE
|
||||
{
|
||||
INTERFACE_ID(ISaveDiagnosticFilesScenario)
|
||||
|
||||
public:
|
||||
virtual ~IAudioBuffer() = default;
|
||||
virtual ~ISaveDiagnosticFilesScenario() = default;
|
||||
|
||||
virtual void setSource(std::shared_ptr<IAudioSource> source) = 0;
|
||||
virtual void forward() = 0;
|
||||
|
||||
virtual void pop(float* dest, size_t sampleCount) = 0;
|
||||
virtual void setMinSampleLag(size_t lag) = 0;
|
||||
virtual mu::Ret saveDiagnosticFiles() = 0;
|
||||
};
|
||||
|
||||
using IAudioBufferPtr = std::shared_ptr<IAudioBuffer>;
|
||||
}
|
||||
#endif // MU_AUDIO_IAUDIOBUFFER_H
|
||||
|
||||
#endif // MU_DIAGNOSTICS_ISAVEDIAGNOSTICFILESSCENARIO_H
|
|
@ -0,0 +1,74 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "savediagnosticfilesscenario.h"
|
||||
|
||||
#include "diagnosticfileswriter.h"
|
||||
#include "translation.h"
|
||||
|
||||
#include <QApplication>
|
||||
|
||||
using namespace mu::diagnostics;
|
||||
using namespace mu::framework;
|
||||
|
||||
mu::Ret SaveDiagnosticFilesScenario::saveDiagnosticFiles()
|
||||
{
|
||||
if (configuration()->shouldWarnBeforeSavingDiagnosticFiles()) {
|
||||
IInteractive::Result result = interactive()->warning(
|
||||
trc("diagnostics", "Save diagnostic files?"),
|
||||
trc("diagnostics", "This will create a .zip file with information about your MuseScore setup "
|
||||
"to help developers diagnose any problems you are having. "
|
||||
"You can inspect the contents of this file before sending it to anyone."),
|
||||
{ IInteractive::Button::Cancel, IInteractive::Button::Save }, IInteractive::Button::Save,
|
||||
IInteractive::Option::WithIcon | IInteractive::Option::WithDontShowAgainCheckBox);
|
||||
|
||||
if (result.standardButton() != IInteractive::Button::Save) {
|
||||
return make_ret(Ret::Code::Cancel);
|
||||
}
|
||||
|
||||
configuration()->setShouldWarnBeforeSavingDiagnosticFiles(result.showAgain());
|
||||
}
|
||||
|
||||
io::path_t path = interactive()->selectSavingFile(
|
||||
qtrc("diagnostics", "Save diagnostic files"),
|
||||
configuration()->diagnosticFilesDefaultSavingPath(),
|
||||
{ "(*.zip)" });
|
||||
|
||||
if (path.empty()) {
|
||||
return make_ret(Ret::Code::Cancel);
|
||||
}
|
||||
|
||||
qApp->setOverrideCursor(Qt::WaitCursor);
|
||||
qApp->processEvents();
|
||||
|
||||
Ret ret = DiagnosticFilesWriter::writeDiagnosticFiles(path);
|
||||
|
||||
qApp->restoreOverrideCursor();
|
||||
|
||||
if (!ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
interactive()->revealInFileBrowser(path);
|
||||
|
||||
return make_ok();
|
||||
}
|
|
@ -0,0 +1,42 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: GPL-3.0-only
|
||||
* MuseScore-CLA-applies
|
||||
*
|
||||
* MuseScore
|
||||
* Music Composition & Notation
|
||||
*
|
||||
* Copyright (C) 2021 MuseScore BVBA and others
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 3 as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#ifndef MU_DIAGNOSTICS_SAVEDIAGNOSTICFILESSCENARIO_H
|
||||
#define MU_DIAGNOSTICS_SAVEDIAGNOSTICFILESSCENARIO_H
|
||||
|
||||
#include "isavediagnosticfilesscenario.h"
|
||||
|
||||
#include "modularity/ioc.h"
|
||||
#include "idiagnosticsconfiguration.h"
|
||||
#include "iinteractive.h"
|
||||
|
||||
namespace mu::diagnostics {
|
||||
class SaveDiagnosticFilesScenario : public ISaveDiagnosticFilesScenario
|
||||
{
|
||||
INJECT(diagnostics, diagnostics::IDiagnosticsConfiguration, configuration)
|
||||
INJECT(diagnostics, framework::IInteractive, interactive)
|
||||
|
||||
public:
|
||||
Ret saveDiagnosticFiles() override;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // MU_DIAGNOSTICS_SAVEDIAGNOSTICFILESSCENARIO_H
|
|
@ -55,7 +55,7 @@ Rectangle {
|
|||
anchors.verticalCenter: parent.verticalCenter
|
||||
anchors.margins: 16
|
||||
clearTextButtonVisible: true
|
||||
onCurrentTextEdited: function(newTextValue) {
|
||||
onTextChanged: function(newTextValue) {
|
||||
profModel.find(newTextValue)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -29,6 +29,7 @@
|
|||
#include "libmscore/segment.h"
|
||||
#include "libmscore/chord.h"
|
||||
#include "libmscore/note.h"
|
||||
#include "libmscore/bracketItem.h"
|
||||
|
||||
#ifndef ENGRAVING_NO_ACCESSIBILITY
|
||||
#include "accessibility/accessibleitem.h"
|
||||
|
@ -44,6 +45,7 @@ DummyElement::DummyElement(EngravingObject* parent)
|
|||
|
||||
DummyElement::~DummyElement()
|
||||
{
|
||||
delete m_bracketItem;
|
||||
delete m_note;
|
||||
delete m_chord;
|
||||
delete m_segment;
|
||||
|
@ -83,6 +85,9 @@ void DummyElement::init()
|
|||
|
||||
m_note = Factory::createNote(m_chord);
|
||||
m_note->setParent(m_chord);
|
||||
|
||||
m_bracketItem = Factory::createBracketItem(m_system);
|
||||
m_bracketItem->setParent(m_system);
|
||||
}
|
||||
|
||||
RootItem* DummyElement::rootItem()
|
||||
|
@ -120,6 +125,11 @@ Note* DummyElement::note()
|
|||
return m_note;
|
||||
}
|
||||
|
||||
BracketItem* DummyElement::bracketItem()
|
||||
{
|
||||
return m_bracketItem;
|
||||
}
|
||||
|
||||
EngravingItem* DummyElement::clone() const
|
||||
{
|
||||
return nullptr;
|
||||
|
|
|
@ -48,6 +48,7 @@ public:
|
|||
Segment* segment();
|
||||
Chord* chord();
|
||||
Note* note();
|
||||
BracketItem* bracketItem();
|
||||
|
||||
EngravingItem* clone() const override;
|
||||
|
||||
|
@ -66,6 +67,7 @@ private:
|
|||
Segment* m_segment = nullptr;
|
||||
Chord* m_chord = nullptr;
|
||||
Note* m_note = nullptr;
|
||||
BracketItem* m_bracketItem = nullptr;
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -33,12 +33,11 @@
|
|||
using namespace mu::io;
|
||||
using namespace mu::engraving;
|
||||
|
||||
Err mu::engraving::compat::mscxToMscz(const String& mscxFilePath, ByteArray* msczData)
|
||||
mu::Ret mu::engraving::compat::mscxToMscz(const String& mscxFilePath, ByteArray* msczData)
|
||||
{
|
||||
File mscxFile(mscxFilePath);
|
||||
if (!mscxFile.open(IODevice::ReadOnly)) {
|
||||
LOGE() << "failed open file: " << mscxFilePath;
|
||||
return Err::FileOpenError;
|
||||
return make_ret(Err::FileOpenError, mscxFilePath);
|
||||
}
|
||||
|
||||
ByteArray mscxData = mscxFile.readAll();
|
||||
|
@ -52,30 +51,27 @@ Err mu::engraving::compat::mscxToMscz(const String& mscxFilePath, ByteArray* msc
|
|||
writer.open();
|
||||
writer.writeScoreFile(mscxData);
|
||||
|
||||
return Err::NoError;
|
||||
return make_ok();
|
||||
}
|
||||
|
||||
Err mu::engraving::compat::loadMsczOrMscx(MasterScore* score, const String& path, bool ignoreVersionError)
|
||||
mu::Ret mu::engraving::compat::loadMsczOrMscx(MasterScore* score, const String& path, bool ignoreVersionError)
|
||||
{
|
||||
ByteArray msczData;
|
||||
if (path.endsWith(u".mscx", mu::CaseInsensitive)) {
|
||||
//! NOTE Convert mscx -> mscz
|
||||
|
||||
Err err = mscxToMscz(path, &msczData);
|
||||
if (err != Err::NoError) {
|
||||
return err;
|
||||
Ret ret = mscxToMscz(path, &msczData);
|
||||
if (!ret) {
|
||||
return ret;
|
||||
}
|
||||
} else if (path.endsWith(u".mscz", mu::CaseInsensitive)) {
|
||||
File msczFile(path);
|
||||
if (!msczFile.open(IODevice::ReadOnly)) {
|
||||
LOGE() << "failed open file: " << path;
|
||||
return Err::FileOpenError;
|
||||
return make_ret(Err::FileOpenError, path);
|
||||
}
|
||||
|
||||
msczData = msczFile.readAll();
|
||||
} else {
|
||||
LOGE() << "unknown type, path: " << path;
|
||||
return Err::FileUnknownType;
|
||||
return make_ret(Err::FileUnknownType, path);
|
||||
}
|
||||
|
||||
score->setFileInfoProvider(std::make_shared<LocalFileInfoProvider>(path));
|
||||
|
@ -90,32 +86,29 @@ Err mu::engraving::compat::loadMsczOrMscx(MasterScore* score, const String& path
|
|||
reader.open();
|
||||
|
||||
ScoreReader scoreReader;
|
||||
Err err = scoreReader.loadMscz(score, reader, ignoreVersionError);
|
||||
return err;
|
||||
return scoreReader.loadMscz(score, reader, ignoreVersionError);
|
||||
}
|
||||
|
||||
Err mu::engraving::compat::loadMsczOrMscx(EngravingProjectPtr project, const String& path, bool ignoreVersionError)
|
||||
mu::Ret mu::engraving::compat::loadMsczOrMscx(EngravingProjectPtr project, const String& path, bool ignoreVersionError)
|
||||
{
|
||||
ByteArray msczData;
|
||||
String filePath = path;
|
||||
if (path.endsWith(u".mscx", mu::CaseInsensitive)) {
|
||||
//! NOTE Convert mscx -> mscz
|
||||
|
||||
Err err = mscxToMscz(path, &msczData);
|
||||
if (err != Err::NoError) {
|
||||
return err;
|
||||
Ret ret = mscxToMscz(path, &msczData);
|
||||
if (!ret) {
|
||||
return ret;
|
||||
}
|
||||
} else if (path.endsWith(u".mscz", mu::CaseInsensitive)) {
|
||||
File msczFile(path);
|
||||
if (!msczFile.open(IODevice::ReadOnly)) {
|
||||
LOGE() << "failed open file: " << path;
|
||||
return Err::FileOpenError;
|
||||
return make_ret(Err::FileOpenError, path);
|
||||
}
|
||||
|
||||
msczData = msczFile.readAll();
|
||||
} else {
|
||||
LOGE() << "unknown type, path: " << path;
|
||||
return Err::FileUnknownType;
|
||||
return make_ret(Err::FileUnknownType, path);
|
||||
}
|
||||
|
||||
project->setFileInfoProvider(std::make_shared<LocalFileInfoProvider>(path));
|
||||
|
@ -129,6 +122,5 @@ Err mu::engraving::compat::loadMsczOrMscx(EngravingProjectPtr project, const Str
|
|||
MscReader reader(params);
|
||||
reader.open();
|
||||
|
||||
Err err = project->loadMscz(reader, ignoreVersionError);
|
||||
return err;
|
||||
return project->loadMscz(reader, ignoreVersionError);
|
||||
}
|
||||
|
|
|
@ -26,9 +26,9 @@
|
|||
#include "engravingproject.h"
|
||||
|
||||
namespace mu::engraving::compat {
|
||||
Err mscxToMscz(const String& mscxFilePath, ByteArray* msczData);
|
||||
Err loadMsczOrMscx(MasterScore* score, const String& path, bool ignoreVersionError = false);
|
||||
Err loadMsczOrMscx(EngravingProjectPtr project, const String& path, bool ignoreVersionError = false);
|
||||
Ret mscxToMscz(const String& mscxFilePath, ByteArray* msczData);
|
||||
Ret loadMsczOrMscx(MasterScore* score, const String& path, bool ignoreVersionError = false);
|
||||
Ret loadMsczOrMscx(EngravingProjectPtr project, const String& path, bool ignoreVersionError = false);
|
||||
}
|
||||
|
||||
#endif // MU_ENGRAVING_MSCXCOMPAT_H
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<museScore version="4.00">
|
||||
<Style>
|
||||
<pageWidth>8.5</pageWidth>
|
||||
<pageHeight>11</pageHeight>
|
||||
<pageWidth>8.26772</pageWidth>
|
||||
<pageHeight>11.6929</pageHeight>
|
||||
<pagePrintableWidth>7.08661</pagePrintableWidth>
|
||||
<pageEvenLeftMargin>0.590551</pageEvenLeftMargin>
|
||||
<pageOddLeftMargin>0.590551</pageOddLeftMargin>
|
||||
|
|
|
@ -55,6 +55,8 @@ inline Ret make_ret(Err err, const io::path_t& filePath = "")
|
|||
String text;
|
||||
|
||||
switch (err) {
|
||||
case Err::NoError:
|
||||
return make_ok();
|
||||
case Err::FileUnknownError:
|
||||
text = mtrc("engraving", "Unknown error");
|
||||
break;
|
||||
|
@ -92,7 +94,6 @@ inline Ret make_ret(Err err, const io::path_t& filePath = "")
|
|||
text = mtrc("engraving", "File \"%1\" is critically corrupted and cannot be processed.").arg(filePath.toString());
|
||||
break;
|
||||
case Err::Undefined:
|
||||
case Err::NoError:
|
||||
case Err::UnknownError:
|
||||
case Err::IgnoreError:
|
||||
case Err::UserAbort:
|
||||
|
|
|
@ -101,43 +101,38 @@ bool EngravingProject::readOnly() const
|
|||
return m_masterScore->readOnly();
|
||||
}
|
||||
|
||||
Err EngravingProject::setupMasterScore(bool forceMode)
|
||||
Ret EngravingProject::setupMasterScore(bool forceMode)
|
||||
{
|
||||
TRACEFUNC;
|
||||
Err err = doSetupMasterScore(m_masterScore, forceMode);
|
||||
return err;
|
||||
return doSetupMasterScore(forceMode);
|
||||
}
|
||||
|
||||
Err EngravingProject::doSetupMasterScore(MasterScore* score, bool forceMode)
|
||||
Ret EngravingProject::doSetupMasterScore(bool forceMode)
|
||||
{
|
||||
TRACEFUNC;
|
||||
|
||||
score->createPaddingTable();
|
||||
score->connectTies();
|
||||
m_masterScore->createPaddingTable();
|
||||
m_masterScore->connectTies();
|
||||
|
||||
for (Part* p : score->parts()) {
|
||||
for (Part* p : m_masterScore->parts()) {
|
||||
p->updateHarmonyChannels(false);
|
||||
}
|
||||
|
||||
score->rebuildMidiMapping();
|
||||
score->setSoloMute();
|
||||
m_masterScore->rebuildMidiMapping();
|
||||
m_masterScore->setSoloMute();
|
||||
|
||||
for (Score* s : score->scoreList()) {
|
||||
for (Score* s : m_masterScore->scoreList()) {
|
||||
s->setPlaylistDirty();
|
||||
s->addLayoutFlags(LayoutFlag::FIX_PITCH_VELO);
|
||||
s->setLayoutAll();
|
||||
}
|
||||
|
||||
score->updateChannel();
|
||||
score->update();
|
||||
m_masterScore->updateChannel();
|
||||
m_masterScore->update();
|
||||
|
||||
if (!forceMode) {
|
||||
if (!score->sanityCheck()) {
|
||||
return Err::FileCorrupted;
|
||||
}
|
||||
}
|
||||
Ret ret = checkCorrupted();
|
||||
m_isCorruptedUponLoading = !ret;
|
||||
|
||||
return Err::NoError;
|
||||
return forceMode ? make_ok() : ret;
|
||||
}
|
||||
|
||||
MasterScore* EngravingProject::masterScore() const
|
||||
|
@ -145,13 +140,12 @@ MasterScore* EngravingProject::masterScore() const
|
|||
return m_masterScore;
|
||||
}
|
||||
|
||||
Err EngravingProject::loadMscz(const MscReader& msc, bool ignoreVersionError)
|
||||
Ret EngravingProject::loadMscz(const MscReader& msc, bool ignoreVersionError)
|
||||
{
|
||||
TRACEFUNC;
|
||||
MScore::setError(MsError::MS_NO_ERROR);
|
||||
ScoreReader scoreReader;
|
||||
Err err = scoreReader.loadMscz(m_masterScore, msc, ignoreVersionError);
|
||||
return err;
|
||||
return scoreReader.loadMscz(m_masterScore, msc, ignoreVersionError);
|
||||
}
|
||||
|
||||
bool EngravingProject::writeMscz(MscWriter& writer, bool onlySelection, bool createThumbnail)
|
||||
|
@ -164,3 +158,15 @@ bool EngravingProject::writeMscz(MscWriter& writer, bool onlySelection, bool cre
|
|||
|
||||
return ok;
|
||||
}
|
||||
|
||||
bool EngravingProject::isCorruptedUponLoading() const
|
||||
{
|
||||
return m_isCorruptedUponLoading;
|
||||
}
|
||||
|
||||
Ret EngravingProject::checkCorrupted() const
|
||||
{
|
||||
TRACEFUNC;
|
||||
|
||||
return m_masterScore->sanityCheck();
|
||||
}
|
||||
|
|
|
@ -65,11 +65,14 @@ public:
|
|||
bool readOnly() const;
|
||||
|
||||
MasterScore* masterScore() const;
|
||||
Err setupMasterScore(bool forceMode);
|
||||
Ret setupMasterScore(bool forceMode);
|
||||
|
||||
Err loadMscz(const MscReader& msc, bool ignoreVersionError);
|
||||
Ret loadMscz(const MscReader& msc, bool ignoreVersionError);
|
||||
bool writeMscz(MscWriter& writer, bool onlySelection, bool createThumbnail);
|
||||
|
||||
bool isCorruptedUponLoading() const;
|
||||
Ret checkCorrupted() const;
|
||||
|
||||
private:
|
||||
friend class MasterScore;
|
||||
|
||||
|
@ -77,9 +80,11 @@ private:
|
|||
|
||||
void init(const MStyle& style);
|
||||
|
||||
Err doSetupMasterScore(MasterScore* score, bool forceMode);
|
||||
Ret doSetupMasterScore(bool forceMode);
|
||||
|
||||
MasterScore* m_masterScore = nullptr;
|
||||
|
||||
bool m_isCorruptedUponLoading = false;
|
||||
};
|
||||
|
||||
using EngravingProjectPtr = std::shared_ptr<EngravingProject>;
|
||||
|
|
|
@ -48,6 +48,8 @@ public:
|
|||
virtual io::path_t partStyleFilePath() const = 0;
|
||||
virtual void setPartStyleFilePath(const io::path_t& path) = 0;
|
||||
|
||||
virtual SizeF defaultPageSize() const = 0;
|
||||
|
||||
virtual String iconsFontFamily() const = 0;
|
||||
|
||||
virtual draw::Color defaultColor() const = 0;
|
||||
|
|
|
@ -560,7 +560,7 @@ bool SymbolFont::isValid(SymId id) const
|
|||
|
||||
bool SymbolFont::useFallbackFont(SymId id) const
|
||||
{
|
||||
return MScore::useFallbackFont && !sym(id).isValid() && this != SymbolFonts::fallbackFont();
|
||||
return MScore::useFallbackFont && !sym(id).isValid() && this != SymbolFonts::fallbackFont(false);
|
||||
}
|
||||
|
||||
// =============================================
|
||||
|
|
|
@ -52,17 +52,7 @@ SymbolFont* SymbolFonts::fontByName(const String& name)
|
|||
}
|
||||
|
||||
if (!font) {
|
||||
LOGE() << "ScoreFont not found in list: " << name;
|
||||
LOGE() << "ScoreFonts in list:";
|
||||
|
||||
for (const SymbolFont& f : s_symbolFonts) {
|
||||
LOGE() << " " << f.name();
|
||||
}
|
||||
|
||||
font = fallbackFont();
|
||||
|
||||
LOGE() << "Using fallback font " << font->name() << " instead.";
|
||||
return font;
|
||||
return fallbackFont();
|
||||
}
|
||||
|
||||
if (!font->m_loaded) {
|
||||
|
@ -92,11 +82,11 @@ void SymbolFonts::setFallbackFont(const String& name)
|
|||
}
|
||||
}
|
||||
|
||||
SymbolFont* SymbolFonts::fallbackFont()
|
||||
SymbolFont* SymbolFonts::fallbackFont(bool load)
|
||||
{
|
||||
SymbolFont* font = &s_symbolFonts[s_fallback.index];
|
||||
|
||||
if (!font->m_loaded) {
|
||||
if (load && !font->m_loaded) {
|
||||
font->load();
|
||||
}
|
||||
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue