Save the setting of plugins
Save the setting of plugins
Now I'm improving the shakuhachi, koto and shinobue notation plugins.
I‘d like to save the setting of plugins.
Prototype code is
import QtQuick 2.2
import MuseScore 1.0
import FileIO 1.0
import QtQuick.Controls 1.0
import QtQuick.Dialogs 1.0
import QtQuick.Layouts 1.1
MuseScore {
menuPath: "Plugins.writeReadSeettingsDemo"
version: "2.0"
description: qsTr("This plugin Write and Read the setting of plugin")
pluginType: "dialog"
id: window
width:200
height:100
ExclusiveGroup { id: exclusiveGroupKey }
RowLayout {
id: column
x : 10
y : 10
Label {
font.pointSize: 14
text: "Select"
}
}
RowLayout {
x : 60
y : 10
ComboBox {
// currentIndex: Number(fileContents[0]) // doesn't work
currentIndex: comboBoxInitValue // doesn't work
model: ListModel {
id: chooseList
property var key
ListElement { text: "choose A"; fName: 1 }
ListElement { text: "choose B"; fName: 2 }
ListElement { text: "choose C"; fName: 3 }
}
width: 100
onCurrentIndexChanged: {
console.debug(chooseList.get(currentIndex).text + ", " +chooseList.get(currentIndex).fName)
chooseList.key = chooseList.get(currentIndex).fName
console.debug(chooseList.key)
}
} // end ComboBox
}
RowLayout {
x : 50
y : 60
Button {
id: closeButton
text: "Close"
onClicked: { Qt.quit() }
}
Button {
id: okButton
text: "Ok"
onClicked: {
apply()
Qt.quit()
}
}
}
function apply() {
curScore.startCmd()
my_file1.write(chooseList.key);
curScore.endCmd()
}
onRun: {
var fileContents = my_file1.read();
console.log("Read from file value="+ Number(fileContents[0]));
var comboBoxInitValue =Number(fileContents[0]) // <<
if (typeof curScore === 'undefined') Qt.quit();
}
FileIO {
id: my_file1
source: tempPath() + "/temp9999.txt" // <<<
onError: console.log(msg)
}
}
Q1. The stored value could be read, but couldn't use at the next run. Line 35 or 36 doesn’t work. 35: // currentIndex: Number(fileContents[0]) // doesn't work 36: currentIndex: comboBoxInitValue // doesn't work Is there method to set "currentIndex:” from variable? Q2. Line 93 93: source: tempPath() + "/temp9999.txt" Where is the tempPath()? I couldn’t find temp9999.txt file. If possible, I want to save as a permanent file, like ./temp9999.txt Please advise me.
Comments
Initialize comboBoxInitValue as a MuseScore item property:
property var comboBoxInitValue : 1 // somewhere before the first RowLayout
rather than as a var in the onRun: function. Then line 36 will work.
To get the tempPath(), just write it out to the console:
console.log("tempPath(): " + my_file1.tempPath());
In reply to Initialize comboBoxInitValue by jensm
Thank you.
It worked correctly.
Have you seen the QML Settings type?
http://doc.qt.io/qt-5/qml-qt-labs-settings-settings.html
In reply to Have you seen the QML by Joseph Eoff
Thank you.
I've never seen it.
I have improved the Shakuhachi notation plugin.
Plugin parameters are preserved until OS restart.
In reply to Have you seen the QML by Joseph Eoff
Thank you: QML Settings works great.
Just added it to the courtesy accidental and batch export plugins.
In reply to Thank you: QML Settings works by heuchi
Hmm, not sure I like it:
The information is stored in the system registry on Windows, and in XML preferences files on OS X. On other Unix systems, in the absence of a standard, INI text files are used.
Don't get me wrong, I like setting being saved, but I'd prefer an ini file on Windows too.
Esp. when using the portable version of MuseScore, tampering with the registry is to be avoided.
In reply to Hmm, not sure I like it: The by Jojo-Schmitz
2nd. Edit:
For non-Mac platforms, INI format for QSettings is forced in mscore/musescore.cpp:4542.
So, no problem here anyway...
In reply to 2nd. Edit: For non-Mac by heuchi
Do plugins inherit that?
In reply to Do plugins inherit that? by Jojo-Schmitz
I think this should be application wide, since QSettings::setDefaultFormat() is static...
But I don't know, because I don't use Windows.
If you're on Windows, it shouldn't be hard to check.
In reply to I think this should be by heuchi
Hmm, can't find any related setting in MuseScore*.ini, nor found any ini file that looked related, but also can't find any in the registry.
In reply to Hmm, can't find any related by Jojo-Schmitz
On Linux, after calling batch_convert.qml, I get a section called "BatchConvertPlugin" in MuseScoreDevelopment.ini starting with
In reply to On Linux, after calling by heuchi
Not here (Windows 7)
In reply to Not here (Windows 7) by Jojo-Schmitz
Hm, but does the plugin remember the options you set?
In reply to Hm, but does the plugin by heuchi
Yes, at least across sessions, not sure whether across a reboot, but will try shortly
In reply to Not here (Windows 7) by Jojo-Schmitz
Error... It is in MuseScoreDevelopment.ini, I've just been too blind
In reply to Hmm, not sure I like it: The by Jojo-Schmitz
I learned also from abc_imput.qml.
tempPath() is used in abc_import.qml
Is this a same problem?
In reply to I learned also from by tcbnhrs
Is this more safer than previous one?
In reply to Is this more safer than by tcbnhrs
Check how it is now done in the batch export plugin, it does save it's settings in the MuserScoreDevelopment.ini (or will do so MuseScore.ini, once 2.0.1 is out), under Linux and Windows (on Mac it should use whatever method is used there, but identical to MuseScore itself)
Check the 2 commits 4837dc5 and bda8d29
In reply to Check how it is now done in by Jojo-Schmitz
I'm sorry Jojo, but there is no "Batch Export" plugin in my 2.0.2 installation of MuseScore!
Where can I get it?
In reply to I'm sorry Jojo, but there is by straannick
From https://musescore.org/project/batchexport
In reply to From by Jojo-Schmitz
Thank you, it helps!
In reply to From by Jojo-Schmitz
Thank you!
I'll try in the new future.
In reply to Check how it is now done in by Jojo-Schmitz
Are there any ideas how save string array, for example, contents of ComboBox?
In reply to Are there any ideas how save by straannick
Use the JSON representation? JSON.stringify and JSON.parse
Consider the following plugin:
It has the following result:
Debug: hello world
Debug: [[nodetitle:object Object],[object Object],[object Object]]
Debug: [{"text":"T1","value":1},{"text":"T2","value":2},{"text":"T3","value":3}]
Debug: [[nodetitle:object Object],[object Object],[object Object]]
Debug: T2 2
In reply to Use the JSON representation? by jeetee
Thank you, jeetee!
For me no problem to transform something to string. The problem is - how to save it to .ini file using Setting
Let's change your example this way:
import QtQuick 2.0
import MuseScore 1.0
import QtQuick.Dialogs 1.2
import QtQuick.Controls 1.2
import Qt.labs.settings 1.0
MuseScore {
menuPath: "Plugins.myPlugin"
pluginType: "dialog"
id:window
width: 100; height: 100;
Settings {
id: settings
category: "myPlugin"
property alias width: window.width
property alias testObj: //----> testObj = testStr - how ?????
}
onRun: {
console.log("hello world");
var testObj = [
{ text: 'T1', value: 1 },
{ text: 'T2', value: 2 },
{ text: 'T3', value: 3 }
];
console.log(testObj);
var testStr = JSON.stringify(testObj);
console.log(testStr);
var resultObj = JSON.parse(testStr);
console.log(resultObj);
console.log(resultObj[1].text + ' ' + resultObj[1].value);
Qt.quit();
}
}
In reply to Use the JSON representation? by jeetee
About ComboBox. ComboBox model is property, isn't it?
It's intersting that when I set
Settings {
. . .
property alias testObj: comboBox.model
. . .
For ComboBox with 4 elements I get in .ini
testObj=@Variant(\0\0\0\x7f\0\0\0\xfQQmlListModel*\0)
And, of course, after plugin restart I have empty ComboBox.
In reply to About ComboBox. ComboBox by straannick
Directly saving the model won't work, as it won't store the contents of the list, but only the (temporary) reference to it.
I've been having a go at trying out a workaround and have it almost functional; The issue I have is that it runs perfectly fine from the Plugin Creator, but fails to update the combobox when ran from the menu.
It does still load the list from its settings and adds a new item, but somehow the visual component is not updated if ran from the Menu vs when ran from the Plugin Creator.
Attempt to be found at: jeetee/MuseScore_Plugin_Examples/serializedSettings.qml
If we can somehow force the combobox to refresh when being ran from the Menu as well we're good to go.
In reply to Directly saving the model by jeetee
Thank you, jeetee!
I my case I'd prefer more universal variant - to build storedList from the ComboBox, so I replace your
settings.comboBoxList = JSON.stringify(storedList);
with
var anotherStoredList = JSON.parse("[{ \"text\": \"Default Item\", \"value\": 0 }]")
for (var i=1; i < myDrop.count; i++)
anotherStoredList.push ( {text: myDrop.textAt(i), value: i })
settings.comboBoxList = JSON.stringify (anotherStoredList)
but it should be noted, that I wrote "var anotherStoredList = JSON.parse.." just because I don't know how to create empty "var" of type which JSON.parse will return. Do you know this?
And, of course, it would be great to force the combobox to refresh.
By the way, do you know what next diagnostic in your example means?
Warning: QVariant::load: unable to load type 39.
Warning: QVariant::save: unable to save type 'QObject*' (type id: 39).
In reply to Thank you, jeetee! I my case by straannick
The result of JSON.parse depends on what string is put in there. The result can be any type of basic JavaScript object/array/string/number depending on what the inputstring is.
In your case, you expect an array with a nested object to be the default, so you could write the following:
As for the Warning messages you're getting: The Settings object can only store 'basic types'. This is one of the reasons we're looking into the JSON parsers: to reduce non-basic types into a string.
It looks like you're trying to save a QObject* into the Settings, which the Settings object does not know how to do. It is not supported.
In reply to The result of JSON.parse by jeetee
I used JSON here "just for sure". The problem is that in real life, especially with editable ComboBox, "defaul item" at 0 position it's not obligatory. So the better solution is
var storedList = [{ text: myDrop.textAt(0), value: 0}]
for (var i=1; i < myDrop.count; i++)
anotherStoredList.push ( {text: myDrop.textAt(i), value: i })
And, of course, we also need to save/restore currentIndex of ComboBox
About warning - you're getting it too. I suppose in your case it happened at
myDropList.append(storedList[storedList.length - 1]);
In my case - every time I append into ComboBox new item.
In reply to I used JSON here "just for by straannick
On which OS/build are you getting this? I don't get the warning running my example project, not in 2.0.2, nor in the master from this morning. Running on Windows7.
In reply to On which OS/build are you by jeetee
Windows 8.1 x64 pro, MS - see picture. And, of course, I see this warnings in PluginCreator.
update: add picture with your example
In reply to Windows 8.1 x64 pro, MS - see by straannick
Wierd.
From what 'the truth of the interwebs' show, it is most definitely related to the saving in the settings view. I can't imagine the result of JSON.stringify to become a QObject* rather than a string (typeof(JSON.stringify()) does return string as well).
If you didn't add another property then I'm stumped. The only other thing is perhaps our Qt versions being different. When looking to 'About Qt' from MuseScore, it reports version 5.4.2 for me.
It would also be interesting to see what happens on other platforms (Mac/Linuxes).
In reply to Wierd. From what 'the truth by jeetee
In my case MuseScore Qt version is also 5.4.2.
But I also have two Qt version installed - 5.4 and 5.5 and current PATH is set to 5.4 version:
C:\Qt\5.4\mingw491_32\bin;C:\Qt\Tools\mingw491_32\bin;...
When I checked your example I didn't add another property because I just copy/pasted text from your project.
In reply to Directly saving the model by jeetee
> visual component is not updated
Hmm, what do you mean? In my plugin ComboBox updated when I add items to it and after plugin restart contains all changes that have been made at previous run.
In reply to > visual component is not by straannick
If you could be bothered to use https://github.com/jeetee/MuseScore_Plugin_Examples/blob/master/seriali… you should see this for yourself with the following steps:
The comboBox isn't visually updated, but the settings were loaded, appended and stored again
These steps show that the plugin does load its settings, does add its element and does save the new list. But for some (yet unknown reason) doesn't update the comboBox when ran from the Menu.
EDIT: And it seems to be a known issue related to plugins with the pluginType set to 'dialog'
https://musescore.org/en/node/71081
EDIT2: Workaround implemented by using a standard QtQuick.Dialog item for now. Sample has been updated as well.
In reply to If you could be bothered to by jeetee
Oh, yes, of course, I also use
import QtQuick.Dialogs 1.2
solved :-)