add some more templates and fix issues in the template generation code

This commit is contained in:
Michael Zanetti 2019-01-08 01:12:39 +01:00
parent ea3e2d2106
commit d274b1b61a
6 changed files with 409 additions and 289 deletions

View File

@ -128,5 +128,6 @@ INSTALLS += target
DISTFILES += \
ruletemplates/smartmetertemplates.json \
ruletemplates/presencesensortemplates.json \
ruletemplates/daylightsensor.json
ruletemplates/daylightsensor.json \
ruletemplates/lighttemplates.json

View File

@ -6,5 +6,6 @@
<file>ruletemplates/smartmetertemplates.json</file>
<file>ruletemplates/presencesensortemplates.json</file>
<file>ruletemplates/daylightsensor.json</file>
<file>ruletemplates/lighttemplates.json</file>
</qresource>
</RCC>

View File

@ -0,0 +1,85 @@
{
"templates": [
{
"interfaceName": "power",
"description": "Turn on while its dark outside.",
"ruleNameTemplate": "Turn on %1 while it's dark outside",
"stateEvaluatorTemplate": {
"stateDescriptorTemplate": {
"interfaceName": "daylightsensor",
"interfaceState": "daylight",
"selectionId": 0,
"operator": "ValueOperatorEquals",
"value": false
}
},
"ruleActionTemplates": [
{
"interfaceName": "power",
"interfaceAction": "power",
"selectionId": 1,
"params": [
{
"name": "power",
"value": "true"
}
]
}
],
"ruleExitActionTemplates": [
{
"interfaceName": "power",
"interfaceAction": "power",
"selectionId": 1,
"params": [
{
"name": "power",
"value": "false"
}
]
}
]
},
{
"interfaceName": "power",
"description": "Turn on while someone is around.",
"ruleNameTemplate": "Turn on %1 while %0 is present",
"stateEvaluatorTemplate": {
"stateDescriptorTemplate": {
"interfaceName": "presencesensor",
"interfaceState": "isPresent",
"selectionId": 0,
"operator": "ValueOperatorEquals",
"value": true
}
},
"ruleActionTemplates": [
{
"interfaceName": "power",
"interfaceAction": "power",
"selectionId": 1,
"params": [
{
"name": "power",
"value": "true"
}
]
}
],
"ruleExitActionTemplates": [
{
"interfaceName": "power",
"interfaceAction": "power",
"selectionId": 1,
"params": [
{
"name": "power",
"value": "false"
}
]
}
]
}
]
}

View File

@ -255,6 +255,10 @@ ApplicationWindow {
return qsTr("connectable thing")
case "power":
return qsTr("switchable thing")
case "daylightsensor":
return qsTr("daylight sensor")
case "presencesensor":
return qsTr("presence sensor")
default:
console.warn("Unhandled interfaceToDisplayName:", name)
}

View File

@ -14,312 +14,341 @@ Page {
signal done();
signal manualCreation();
function fillRuleFromTemplate(rule, ruleTemplate, selectedThings) {
if (selectedThings === undefined) {
selectedThings = [];
}
function createRuleFromTemplate(ruleTemplate) {
d.selectedThings = {}
d.selectedInterfaces = {}
var rule = engine.ruleManager.createNewRule();
d.fillRuleFromTemplate(rule, ruleTemplate);
}
// Fill in all EventDescriptors
for (var i = rule.eventDescriptors.count; i < ruleTemplate.eventDescriptorTemplates.count; i++) {
var eventDescriptorTemplate = ruleTemplate.eventDescriptorTemplates.get(i);
print("RuleFromTemplate: Filling eventDescriptor:", eventDescriptorTemplate.interfaceName, eventDescriptorTemplate.interfaceEvent, eventDescriptorTemplate.selectionId)
// If we already have a thing selected for this selectionIndex, use that
if (selectedThings.length > eventDescriptorTemplate.selectionId) {
var device = engine.deviceManager.devices.getDevice(selectedThings[eventDescriptorTemplate.selectionId]);
createEventDescriptor(rule, ruleTemplate, selectedThings, device, eventDescriptorTemplate)
return;
}
// Ok, we didn't pick a thing for this selectionId before. Did we already use the one we opened this page from?
if (selectedThings.indexOf(root.device.id) === -1 && root.deviceClass.interfaces.indexOf(eventDescriptorTemplate.interfaceName) >= 0 && eventDescriptorTemplate.interfaceName === ruleTemplate.interfaceName) {
selectedThings.push(root.device.id);
createEventDescriptor(rule, ruleTemplate, selectedThings, root.device, eventDescriptorTemplate)
return;
}
QtObject {
id: d
property var selectedThings: ({})
property var selectedInterfaces: ({})
// We need to pick a thing
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [eventDescriptorTemplate.interfaceName]});
page.thingSelected.connect(function(device) {
selectedThings.push(device.id);
createEventDescriptor(rule, ruleTemplate, selectedThings, device, eventDescriptorTemplate)
return;
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return;
}
function fillRuleFromTemplate(rule, ruleTemplate) {
print("Filling rule")
// Fill in StateEvaluator
if (ruleTemplate.stateEvaluatorTemplate !== null) {
if (rule.stateEvaluator === null) {
var stateEvaluator = rule.createStateEvaluator();
rule.setStateEvaluator(stateEvaluator);
fillStateEvaluatorFromTemplate(rule, ruleTemplate, stateEvaluator, ruleTemplate.stateEvaluatorTemplate, selectedThings);
return;
}
var more = fillStateEvaluatorFromTemplate(rule, ruleTemplate, rule.stateEvaluator, ruleTemplate.stateEvaluatorTemplate, selectedThings);
if (more) {
return;
}
}
for (var i = rule.actions.count; i < ruleTemplate.ruleActionTemplates.count; i++) {
var ruleActionTemplate = ruleTemplate.ruleActionTemplates.get(i);
if (ruleActionTemplate.selectionMode === RuleActionTemplate.SelectionModeInterface) {
// TODO: Implement blacklist for interface based actions
var ruleAction = rule.actions.createNewRuleAction();
ruleAction.interfaceName = ruleActionTemplate.interfaceName;
ruleAction.interfaceAction = ruleActionTemplate.interfaceAction;
for (var j = 0; j < ruleActionTemplate.ruleActionParamTemplates.count; j++) {
var ruleActionParam = ruleActionTemplate.ruleActionParamTemplates.get(j)
ruleAction.ruleActionParams.setRuleActionParamByName(ruleActionParam.paramName, ruleActionParam.value)
// Fill in all EventDescriptors
for (var i = rule.eventDescriptors.count; i < ruleTemplate.eventDescriptorTemplates.count; i++) {
var eventDescriptorTemplate = ruleTemplate.eventDescriptorTemplates.get(i);
print("RuleFromTemplate: Filling eventDescriptor:", eventDescriptorTemplate.interfaceName, eventDescriptorTemplate.interfaceEvent, eventDescriptorTemplate.selectionId)
// If we already have a thing selected for this selectionIndex, use that
if (eventDescriptorTemplate.selectionId in selectedThings) {
var device = engine.deviceManager.devices.getDevice(selectedThings[eventDescriptorTemplate.selectionId]);
createEventDescriptor(rule, ruleTemplate, device, eventDescriptorTemplate)
return;
}
rule.actions.addRuleAction(ruleAction);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
return;
}
// Did we pick a thing for this index before?
if (selectedThings.length > ruleActionTemplate.selectionId) {
var device = engine.deviceManager.devices.getDevice(selectedThings[ruleActionTemplate.selectionId]);
createRuleAction(rule, ruleTemplate, selectedThings, rule.actions, device, ruleActionTemplate)
return;
}
// Did we already use the thing we opened this page from?
if (selectedThings.indexOf(root.device.id) === -1 && root.deviceClass.interfaces.indexOf(ruleActionTemplate.interfaceName) >= 0 && ruleActionTemplate.interfaceName === ruleTemplate.interfaceName) {
selectedThings.push(root.device.id);
createRuleAction(rule, ruleTemplate, selectedThings, rule.actions, root.device, ruleActionTemplate)
return;
}
// Ok, we need to pick a thing
print("Need to select a thing")
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [ruleActionTemplate.interfaceName]});
page.thingSelected.connect(function(device) {
selectedThings.push(device.id);
createRuleAction(rule, ruleTemplate, selectedThings, rule.actions, device, ruleActionTemplate)
return;
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return;
}
for (var i = rule.exitActions.count; i < ruleTemplate.ruleExitActionTemplates.count; i++) {
var ruleExitActionTemplate = ruleTemplate.ruleExitActionTemplates.get(i);
if (ruleExitActionTemplate.selectionMode === RuleActionTemplate.SelectionModeInterface) {
// TODO: Implement blacklist for interface based actions
var ruleExitAction = rule.exitActions.createNewRuleAction();
ruleExitAction.interfaceName = ruleExitActionTemplate.interfaceName;
ruleExitAction.interfaceAction = ruleExitActionTemplate.interfaceAction;
for (var j = 0; j < ruleExitActionTemplate.ruleActionParamTemplates.count; j++) {
var ruleActionParam = ruleExitActionTemplate.ruleActionParamTemplates.get(j)
ruleExitAction.ruleActionParams.setRuleActionParam(ruleActionParam.paramName, ruleActionParam.value)
// Ok, we didn't pick a thing for this selectionId before. Did we already use the one we opened this page from?
if (!deviceIsUsed(root.device.id) && root.deviceClass.interfaces.indexOf(eventDescriptorTemplate.interfaceName) >= 0 && eventDescriptorTemplate.interfaceName === ruleTemplate.interfaceName) {
selectedThings[eventDescriptorTemplate.selectionId] = root.device.id;
createEventDescriptor(rule, ruleTemplate, root.device, eventDescriptorTemplate)
return;
}
rule.exitActions.addRuleAction(ruleAction);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
// We need to pick a thing
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [eventDescriptorTemplate.interfaceName]});
page.thingSelected.connect(function(device) {
selectedThings[eventDescriptorTemplate.selectionId] = device.id;
createEventDescriptor(rule, ruleTemplate, device, eventDescriptorTemplate)
return;
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return;
}
// Did we pick a thing for this index before?
if (selectedThings.length > ruleExitActionTemplate.selectionId) {
var device = engine.deviceManager.devices.getDevice(selectedThings[ruleExitActionTemplate.selectionId]);
createRuleAction(rule, ruleTemplate, selectedThings, rule.exitActions, device, ruleExitActionTemplate);
// Fill in StateEvaluator
if (ruleTemplate.stateEvaluatorTemplate !== null) {
if (rule.stateEvaluator === null) {
var stateEvaluator = rule.createStateEvaluator();
rule.setStateEvaluator(stateEvaluator);
fillStateEvaluatorFromTemplate(rule, ruleTemplate, stateEvaluator, ruleTemplate.stateEvaluatorTemplate);
return;
}
var more = fillStateEvaluatorFromTemplate(rule, ruleTemplate, rule.stateEvaluator, ruleTemplate.stateEvaluatorTemplate);
if (more) {
return;
}
}
for (var i = rule.actions.count; i < ruleTemplate.ruleActionTemplates.count; i++) {
var ruleActionTemplate = ruleTemplate.ruleActionTemplates.get(i);
if (ruleActionTemplate.selectionMode === RuleActionTemplate.SelectionModeInterface) {
// TODO: Implement blacklist for interface based actions
var ruleAction = rule.actions.createNewRuleAction();
ruleAction.interfaceName = ruleActionTemplate.interfaceName;
ruleAction.interfaceAction = ruleActionTemplate.interfaceAction;
for (var j = 0; j < ruleActionTemplate.ruleActionParamTemplates.count; j++) {
var ruleActionParam = ruleActionTemplate.ruleActionParamTemplates.get(j)
ruleAction.ruleActionParams.setRuleActionParamByName(ruleActionParam.paramName, ruleActionParam.value)
}
selectedInterfaces[ruleActionTemplate.selectionId] = ruleAction.interfaceName;
rule.actions.addRuleAction(ruleAction);
fillRuleFromTemplate(rule, ruleTemplate);
return;
}
// Did we pick a thing for this index before?
if (ruleActionTemplate.selectionId in selectedThings) {
var device = engine.deviceManager.devices.getDevice(selectedThings[ruleActionTemplate.selectionId]);
createRuleAction(rule, ruleTemplate, rule.actions, device, ruleActionTemplate)
return;
}
// Did we already use the thing we opened this page from?
if (!deviceIsUsed(root.device.id) && root.deviceClass.interfaces.indexOf(ruleActionTemplate.interfaceName) >= 0 && ruleActionTemplate.interfaceName === ruleTemplate.interfaceName) {
selectedThings[ruleActionTemplate.selectionId] = root.device.id;
createRuleAction(rule, ruleTemplate, rule.actions, root.device, ruleActionTemplate)
return;
}
// Ok, we need to pick a thing
print("Need to select a thing")
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [ruleActionTemplate.interfaceName]});
page.thingSelected.connect(function(device) {
selectedThings[ruleActionTemplate.selectionId] = device.id;
createRuleAction(rule, ruleTemplate, rule.actions, device, ruleActionTemplate)
return;
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return;
}
// Did we already use the thing we opened this page from?
if (selectedThings.indexOf(root.device.id) === -1 && root.deviceClass.interfaces.indexOf(ruleExitActionTemplate.interfaceName) >= 0 && ruleExitActionTemplate.interfaceName === ruleTemplate.interfaceName) {
selectedThings.push(root.device.id);
createRuleAction(rule, ruleTemplate, selectedThings, rule.exitActions, root.device, ruleExitActionTemplate);
for (var i = rule.exitActions.count; i < ruleTemplate.ruleExitActionTemplates.count; i++) {
var ruleExitActionTemplate = ruleTemplate.ruleExitActionTemplates.get(i);
if (ruleExitActionTemplate.selectionMode === RuleActionTemplate.SelectionModeInterface) {
// TODO: Implement blacklist for interface based actions
var ruleExitAction = rule.exitActions.createNewRuleAction();
ruleExitAction.interfaceName = ruleExitActionTemplate.interfaceName;
ruleExitAction.interfaceAction = ruleExitActionTemplate.interfaceAction;
for (var j = 0; j < ruleExitActionTemplate.ruleActionParamTemplates.count; j++) {
var ruleActionParam = ruleExitActionTemplate.ruleActionParamTemplates.get(j)
ruleExitAction.ruleActionParams.setRuleActionParam(ruleActionParam.paramName, ruleActionParam.value)
}
selectedInterfaces[ruleExitActionTemplate.selectionId] = ruleExitAction.interfaceName;
rule.exitActions.addRuleAction(ruleExitAction);
fillRuleFromTemplate(rule, ruleTemplate);
return;
}
// Did we pick a thing for this index before?
if (ruleExitActionTemplate.selectionId in selectedThings) {
var device = engine.deviceManager.devices.getDevice(selectedThings[ruleExitActionTemplate.selectionId]);
createRuleAction(rule, ruleTemplate, rule.exitActions, device, ruleExitActionTemplate);
return;
}
// Did we already use the thing we opened this page from?
if (!deviceIsUsed(root.device.id) && root.deviceClass.interfaces.indexOf(ruleExitActionTemplate.interfaceName) >= 0 && ruleExitActionTemplate.interfaceName === ruleTemplate.interfaceName) {
selectedThings[ruleExitActionTemplate.selectionId] = root.device.id;
createRuleAction(rule, ruleTemplate, rule.exitActions, root.device, ruleExitActionTemplate);
return;
}
// Ok, we need to pick a thing
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [ruleExitActionTemplate.interfaceName]});
page.thingSelected.connect(function(device) {
selectedThings[ruleExitActionTemplate.selectionId] = device.id;
createRuleAction(rule, ruleTemplate, rule.exitActions, device, ruleExitActionTemplate);
return;
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return;
}
// Ok, we need to pick a thing
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [ruleExitActionTemplate.interfaceName]});
page.thingSelected.connect(function(device) {
selectedThings.push(device.id);
createRuleAction(rule, ruleTemplate, selectedThings, rule.exitActions, device, ruleExitActionTemplate);
return;
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return;
}
// Now replace %i in title and action params with selectedThings[i].name
rule.name = ruleTemplate.ruleNameTemplate;
for (var selectionId in selectedThings) {
print("Replacing", selectionId, "with", selectedThings[selectionId], selectedInterfaces[selectionId])
var device = engine.deviceManager.devices.getDevice(selectedThings[selectionId]);
rule.name = rule.name.replace("%" + selectionId, device.name)
// Now replace %i in title and action params with selectedThings[i].name
rule.name = ruleTemplate.ruleNameTemplate;
for (var i = 0; i < selectedThings.length; i++) {
var device = engine.deviceManager.devices.getDevice(selectedThings[i]);
rule.name = rule.name.arg(device.name)
for (var j = 0; j < rule.actions.count; j++) {
var action = rule.actions.get(j);
for(var k = 0; k < action.ruleActionParams.count; k++) {
var actionParam = action.ruleActionParams.get(k);
print("replacing args", typeof actionParam.value)
if (typeof actionParam.value === "string") {
actionParam.value = actionParam.value.arg(device.name);
for (var j = 0; j < rule.actions.count; j++) {
var action = rule.actions.get(j);
for(var k = 0; k < action.ruleActionParams.count; k++) {
var actionParam = action.ruleActionParams.get(k);
print("replacing args", typeof actionParam.value)
if (typeof actionParam.value === "string") {
actionParam.value = actionParam.value.replace("%" + selectionId, device.name);
}
}
}
for (var j = 0; j < rule.exitActions.count; j++) {
var action = rule.exitActions.get(j);
for(var k = 0; k < action.ruleActionParams.count; k++) {
var actionParam = action.ruleActionParams.get(k);
if (typeof actionParam.value === "string") {
actionParam.value = actionParam.value.replace("%" + selectionId, device.name);
}
}
}
}
for (var j = 0; j < rule.exitActions.count; j++) {
var action = rule.exitActions.get(j);
for(var k = 0; k < action.ruleActionParams.count; k++) {
var actionParam = action.ruleActionParams.get(k);
if (typeof actionParam.value === "string") {
actionParam.value = actionParam.value.arg(device.name);
for (selectionId in selectedInterfaces) {
rule.name = rule.name.replace("%" + selectionId, qsTr("any " + app.interfaceToDisplayName(selectedInterfaces[selectionId])))
}
print("Rule complete!")
engine.ruleManager.addRule(rule);
rule.destroy();
root.done();
}
function fillStateEvaluatorFromTemplate(rule, ruleTemplate, stateEvaluator, stateEvaluatorTemplate) {
if (stateEvaluatorTemplate.stateDescriptorTemplate !== null && !deviceIsUsed(stateEvaluator.stateDescriptor.deviceId) && stateEvaluator.stateDescriptor.interfaceName.length === 0) {
// need to fill stateDescriptor
print("filling in state evaluator for selection mode:", stateEvaluatorTemplate.stateDescriptorTemplate.selectionMode)
if (stateEvaluatorTemplate.stateDescriptorTemplate.selectionMode === StateDescriptor.SelectionModeInterface) {
stateEvaluator.stateDescriptor.interfaceName = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName;
stateEvaluator.stateDescriptor.interfaceState = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState;
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
selectedInterfaces[stateEvaluatorTemplate.stateDescriptorTemplate.selectionId] = stateEvaluator.stateDescriptor.interfaceName;
fillRuleFromTemplate(rule, ruleTemplate);
return true;
}
// did we pick a thing for this index before?
if (stateEvaluatorTemplate.stateDescriptorTemplate.selectionId in selectedThings) {
var deviceId = selectedThings[stateEvaluatorTemplate.stateDescriptorTemplate.selectionId]
var device = engine.deviceManager.devices.getDevice(deviceId)
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
stateEvaluator.stateDescriptor.deviceId = deviceId;
stateEvaluator.stateDescriptor.stateTypeId = deviceClass.stateTypes.findByName(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState).id
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
fillRuleFromTemplate(rule, ruleTemplate);
return true;
}
if (!deviceIsUsed(root.device.id) && root.deviceClass.interfaces.indexOf(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName) >= 0 && stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName === ruleTemplate.interfaceName) {
stateEvaluator.stateDescriptor.deviceId = root.device.id;
stateEvaluator.stateDescriptor.stateTypeId = root.deviceClass.stateTypes.findByName(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState).id
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
selectedThings[stateEvaluatorTemplate.stateDescriptorTemplate.selectionId] = root.device.id;
fillRuleFromTemplate(rule, ruleTemplate);
return true;
}
print("opening SelectThingPage for shownInterfaces:")
print("..", stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName)
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName], allowSelectAny: stateEvaluatorTemplate.stateDescriptorTemplate.selectionMode === StateDescriptorTemplate.SelectionModeAny});
page.thingSelected.connect(function(device) {
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
stateEvaluator.stateDescriptor.deviceId = device.id;
stateEvaluator.stateDescriptor.stateTypeId = deviceClass.stateTypes.findByName(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState).id;
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
selectedThings[stateEvaluatorTemplate.stateDescriptorTemplate.selectionId] = device.id;
fillRuleFromTemplate(rule, ruleTemplate)
})
page.onAnySelected.connect(function() {
stateEvaluator.stateDescriptor.interfaceName = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName;
stateEvaluator.stateDescriptor.interfaceState = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState;
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
selectedInterfaces[stateEvaluatorTemplate.stateDescriptorTemplate.selectionId] = stateEvaluator.stateDescriptor.interfaceName;
fillRuleFromTemplate(rule, ruleTemplate);
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return true;
}
stateEvaluator.stateOperator = stateEvaluatorTemplate.stateOperator;
if (stateEvaluatorTemplate.childEvaluatorTemplates.count > stateEvaluator.childEvaluators.count) {
var childEvaluator = rule.createStateEvaluator();
var more = fillStateEvaluatorFromTemplate(rule, ruleTemplate, childEvaluator, stateEvaluatorTemplate.childEvaluatorTemplates.get(stateEvaluator.childEvaluators.count))
stateEvaluator.childEvaluators.addStateEvaluator(childEvaluator);
return more;
}
return false;
}
function createEventDescriptor(rule, ruleTemplate, device, eventDescriptorTemplate) {
var eventDescriptor = rule.eventDescriptors.createNewEventDescriptor();
eventDescriptor.deviceId = device.id;
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
eventDescriptor.eventTypeId = deviceClass.eventTypes.findByName(eventDescriptorTemplate.interfaceEvent).id
var needsParams = false;
for (var j = 0; j < eventDescriptorTemplate.paramDescriptors.count; j++) {
var paramDescriptorTemplate = eventDescriptorTemplate.paramDescriptors.get(j);
if (paramDescriptorTemplate.value !== undefined) {
print("Adding operator:", paramDescriptorTemplate.operatorType)
eventDescriptor.paramDescriptors.setParamDescriptorByName(paramDescriptorTemplate.paramName, paramDescriptorTemplate.value, paramDescriptorTemplate.operatorType);
} else {
needsParams = true;
}
}
if (needsParams) {
var page = pageStack.push(Qt.resolvedUrl("SelectEventDescriptorParamsPage.qml"), { eventDescriptor: eventDescriptor })
page.completed.connect(function() {
rule.eventDescriptors.addEventDescriptor(eventDescriptor);
fillRuleFromTemplate(rule, ruleTemplate);
})
page.onBackPressed.connect(function() {
eventDescriptor.destroy();
pageStack.pop();
});
return;
}
rule.eventDescriptors.addEventDescriptor(eventDescriptor);
fillRuleFromTemplate(rule, ruleTemplate);
}
function createRuleAction(rule, ruleTemplate, ruleActions, device, ruleActionTemplate) {
var ruleAction = ruleActions.createNewRuleAction();
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
ruleAction.deviceId = device.id;
print("Creating action", ruleActionTemplate.interfaceAction, "on device class", deviceClass.displayName)
ruleAction.actionTypeId = deviceClass.actionTypes.findByName(ruleActionTemplate.interfaceAction).id
for (var j = 0; j < ruleActionTemplate.ruleActionParamTemplates.count; j++) {
var ruleActionParamTemplate = ruleActionTemplate.ruleActionParamTemplates.get(j)
var actionType = deviceClass.actionTypes.getActionType(ruleAction.actionTypeId);
var paramType = actionType.paramTypes.findByName(ruleActionParamTemplate.paramName);
if (ruleActionParamTemplate.value !== undefined) {
ruleAction.ruleActionParams.setRuleActionParam(paramType.id, ruleActionParamTemplate.value)
} else if (ruleActionParamTemplate.eventInterface && ruleActionParamTemplate.eventName && ruleActionParamTemplate.eventParamName) {
print("should create rule action param from interface", ruleActionParamTemplate.eventInterface, ruleActionParamTemplate.eventName, ruleActionParamTemplate.eventParamName)
// find matching eventDescriptor
var eventDescriptorTemplate = null;
for (var k = 0; k < ruleTemplate.eventDescriptorTemplates.count; k++) {
var tmp = ruleTemplate.eventDescriptorTemplates.get(k);
print("evaluating eventDescriptor", tmp.interfaceName)
if (tmp.interfaceName === ruleActionParamTemplate.eventInterface && tmp.interfaceEvent === ruleActionParamTemplate.eventName) {
eventDescriptorTemplate = tmp;
break;
}
}
}
}
}
print("Rule complete!")
engine.ruleManager.addRule(rule);
rule.destroy();
root.done();
}
function fillStateEvaluatorFromTemplate(rule, ruleTemplate, stateEvaluator, stateEvaluatorTemplate, selectedThings) {
if (stateEvaluatorTemplate.stateDescriptorTemplate !== null && selectedThings.indexOf(stateEvaluator.stateDescriptor.deviceId) === -1 && stateEvaluator.stateDescriptor.interfaceName.length === 0) {
// need to fill stateDescriptor
print("filling in state evaluator for selection mode:", stateEvaluatorTemplate.stateDescriptorTemplate.selectionMode)
if (stateEvaluatorTemplate.stateDescriptorTemplate.selectionMode === StateDescriptor.SelectionModeInterface) {
stateEvaluator.stateDescriptor.interfaceName = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName;
stateEvaluator.stateDescriptor.interfaceState = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState;
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
return true;
}
// did we pick a thing for this index before?
if (selectedThings.length > stateEvaluatorTemplate.stateDescriptorTemplate.selectionId) {
var deviceId = selectedThings[stateEvaluatorTemplate.stateDescriptorTemplate.selectionId]
var device = engine.deviceManager.devices.getDevice(deviceId)
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
stateEvaluator.stateDescriptor.deviceId = deviceId;
stateEvaluator.stateDescriptor.stateTypeId = deviceClass.stateTypes.findByName(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState).id
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
return true;
}
if (selectedThings.indexOf(root.device.id) === -1 && root.deviceClass.interfaces.indexOf(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName) >= 0 && stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName === ruleTemplate.interfaceName) {
stateEvaluator.stateDescriptor.deviceId = root.device.id;
stateEvaluator.stateDescriptor.stateTypeId = root.deviceClass.stateTypes.findByName(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState).id
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
selectedThings.push(root.device.id);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
return true;
}
print("opening SelectThingPage for shownInterfaces:")
print("..", stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName)
var page = pageStack.push(Qt.resolvedUrl("SelectThingPage.qml"), {shownInterfaces: [stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName], allowSelectAny: stateEvaluatorTemplate.stateDescriptorTemplate.selectionMode === StateDescriptorTemplate.SelectionModeAny});
page.thingSelected.connect(function(device) {
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
stateEvaluator.stateDescriptor.deviceId = device.id;
stateEvaluator.stateDescriptor.stateTypeId = deviceClass.stateTypes.findByName(stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState).id;
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
selectedThings.push(device.id);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings)
})
page.onAnySelected.connect(function() {
stateEvaluator.stateDescriptor.interfaceName = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceName;
stateEvaluator.stateDescriptor.interfaceState = stateEvaluatorTemplate.stateDescriptorTemplate.interfaceState;
stateEvaluator.stateDescriptor.valueOperator = stateEvaluatorTemplate.stateDescriptorTemplate.valueOperator;
stateEvaluator.stateDescriptor.value = stateEvaluatorTemplate.stateDescriptorTemplate.value;
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
})
page.backPressed.connect(function() {rule.destroy(); root.done();})
return true;
}
stateEvaluator.stateOperator = stateEvaluatorTemplate.stateOperator;
if (stateEvaluatorTemplate.childEvaluatorTemplates.count > stateEvaluator.childEvaluators.count) {
var childEvaluator = rule.createStateEvaluator();
var more = fillStateEvaluatorFromTemplate(rule, ruleTemplate, childEvaluator, stateEvaluatorTemplate.childEvaluatorTemplates.get(stateEvaluator.childEvaluators.count))
stateEvaluator.childEvaluators.addStateEvaluator(childEvaluator);
return more;
}
return false;
}
function createEventDescriptor(rule, ruleTemplate, selectedThings, device, eventDescriptorTemplate) {
var eventDescriptor = rule.eventDescriptors.createNewEventDescriptor();
eventDescriptor.deviceId = device.id;
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
eventDescriptor.eventTypeId = deviceClass.eventTypes.findByName(eventDescriptorTemplate.interfaceEvent).id
var needsParams = false;
for (var j = 0; j < eventDescriptorTemplate.paramDescriptors.count; j++) {
var paramDescriptorTemplate = eventDescriptorTemplate.paramDescriptors.get(j);
if (paramDescriptorTemplate.value !== undefined) {
print("Adding operator:", paramDescriptorTemplate.operatorType)
eventDescriptor.paramDescriptors.setParamDescriptorByName(paramDescriptorTemplate.paramName, paramDescriptorTemplate.value, paramDescriptorTemplate.operatorType);
} else {
needsParams = true;
}
}
if (needsParams) {
var page = pageStack.push(Qt.resolvedUrl("SelectEventDescriptorParamsPage.qml"), { eventDescriptor: eventDescriptor })
page.completed.connect(function() {
rule.eventDescriptors.addEventDescriptor(eventDescriptor);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
})
page.onBackPressed.connect(function() {
eventDescriptor.destroy();
pageStack.pop();
});
return;
}
rule.eventDescriptors.addEventDescriptor(eventDescriptor);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
}
function createRuleAction(rule, ruleTemplate, selectedThings, ruleActions, device, ruleActionTemplate) {
var ruleAction = ruleActions.createNewRuleAction();
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
ruleAction.deviceId = device.id;
ruleAction.actionTypeId = deviceClass.actionTypes.findByName(ruleActionTemplate.interfaceAction).id
for (var j = 0; j < ruleActionTemplate.ruleActionParamTemplates.count; j++) {
var ruleActionParamTemplate = ruleActionTemplate.ruleActionParamTemplates.get(j)
var actionType = deviceClass.actionTypes.getActionType(ruleAction.actionTypeId);
var paramType = actionType.paramTypes.findByName(ruleActionParamTemplate.paramName);
if (ruleActionParamTemplate.value !== undefined) {
ruleAction.ruleActionParams.setRuleActionParam(paramType.id, ruleActionParamTemplate.value)
} else if (ruleActionParamTemplate.eventInterface && ruleActionParamTemplate.eventName && ruleActionParamTemplate.eventParamName) {
print("should create rule action param from interface", ruleActionParamTemplate.eventInterface, ruleActionParamTemplate.eventName, ruleActionParamTemplate.eventParamName)
// find matching eventDescriptor
var eventDescriptorTemplate = null;
for (var k = 0; k < ruleTemplate.eventDescriptorTemplates.count; k++) {
var tmp = ruleTemplate.eventDescriptorTemplates.get(k);
print("evaluating eventDescriptor", tmp.interfaceName)
if (tmp.interfaceName === ruleActionParamTemplate.eventInterface && tmp.interfaceEvent === ruleActionParamTemplate.eventName) {
eventDescriptorTemplate = tmp;
break;
if (eventDescriptorTemplate === null) {
console.warn("Unable to find an event matching the criteria:", ruleActionParamTemplate.eventInterface, ruleActionParamTemplate.eventName, ruleActionParamTemplate.eventParamName)
break
}
}
if (eventDescriptorTemplate === null) {
console.warn("Unable to find an event matching the criteria:", ruleActionParamTemplate.eventInterface, ruleActionParamTemplate.eventName, ruleActionParamTemplate.eventParamName)
break
}
print("selected device:", selectedThings, eventDescriptorTemplate.selectionId)
var eventDevice = engine.deviceManager.devices.getDevice(selectedThings[eventDescriptorTemplate.selectionId])
var eventDeviceClass = engine.deviceManager.deviceClasses.getDeviceClass(eventDevice.deviceClassId);
var eventType = eventDeviceClass.eventTypes.findByName(ruleActionParamTemplate.eventName);
var eventParamType = eventType.paramTypes.findByName(ruleActionParamTemplate.eventParamName);
print("selected device:", selectedThings, eventDescriptorTemplate.selectionId)
var eventDevice = engine.deviceManager.devices.getDevice(selectedThings[eventDescriptorTemplate.selectionId])
var eventDeviceClass = engine.deviceManager.deviceClasses.getDeviceClass(eventDevice.deviceClassId);
var eventType = eventDeviceClass.eventTypes.findByName(ruleActionParamTemplate.eventName);
var eventParamType = eventType.paramTypes.findByName(ruleActionParamTemplate.eventParamName);
ruleAction.ruleActionParams.setRuleActionParamEvent(paramType.id, eventType.id, eventParamType.id)
} else {
console.warn("Invalid RuleActionParamTemplate. Has neither value nor event spec")
}
ruleAction.ruleActionParams.setRuleActionParamEvent(paramType.id, eventType.id, eventParamType.id)
} else {
console.warn("Invalid RuleActionParamTemplate. Has neither value nor event spec")
}
ruleActions.addRuleAction(ruleAction);
fillRuleFromTemplate(rule, ruleTemplate);
}
function deviceIsUsed(deviceId) {
for (var key in selectedThings) {
if (selectedThings.hasOwnProperty(key) && selectedThings[key] === deviceId) {
return true;
}
}
return false;
}
ruleActions.addRuleAction(ruleAction);
fillRuleFromTemplate(rule, ruleTemplate, selectedThings);
}
header: GuhHeader {
@ -343,8 +372,7 @@ Page {
onClicked: {
var ruleTemplate = ruleTemplatesModel.get(index);
var rule = engine.ruleManager.createNewRule();
root.fillRuleFromTemplate(rule, ruleTemplate)
root.createRuleFromTemplate(ruleTemplate)
}
}
}

View File

@ -48,6 +48,11 @@ Page {
ColumnLayout {
anchors.fill: parent
ListFilterInput {
id: filterInput
Layout.fillWidth: true
}
MeaListItemDelegate {
Layout.fillWidth: true
text: qsTr("Any %1").arg(app.interfaceToDisplayName(root.shownInterfaces[0]))
@ -58,10 +63,6 @@ Page {
}
ThinDivider { visible: root.allowSelectAny }
ListFilterInput {
id: filterInput
Layout.fillWidth: true
}
ListView {
Layout.fillWidth: true