From 367456a546b356eda5625dd0c59ce1ae3cf27970 Mon Sep 17 00:00:00 2001 From: Manuel Krombholz <s3866577@msx.tu-dresden.de> Date: Mon, 15 Feb 2021 21:13:25 +0100 Subject: [PATCH] Added state transfer and sync as Rule --- eraser-base/src/main/jastadd/Item.jrag | 72 +++++++++++++++---- eraser-base/src/main/jastadd/Rules.jrag | 7 ++ .../inf/st/eraser/ControllingItemTest.java | 13 ++++ 3 files changed, 79 insertions(+), 13 deletions(-) diff --git a/eraser-base/src/main/jastadd/Item.jrag b/eraser-base/src/main/jastadd/Item.jrag index 6ccdfb49..5c03824f 100644 --- a/eraser-base/src/main/jastadd/Item.jrag +++ b/eraser-base/src/main/jastadd/Item.jrag @@ -397,25 +397,71 @@ aspect ItemHandling { addControlling(item); } - - private Rule Item.createControllerRule(Item controllerItem, Item controlledItem) { - Rule rule = new Rule(); + Rule rule = new Rule(); + + ItemStateChangeCondition condition = new ItemStateChangeCondition(); + condition.setItem(controllerItem); + rule.addCondition(condition); - ItemStateChangeCondition condition = new ItemStateChangeCondition(); - condition.setItem(controllerItem); - rule.addCondition(condition); + SetStateFromTriggeringItemAction action = new SetStateFromTriggeringItemAction(); + action.setAffectedItem(controlledItem); + rule.addAction(action); + rule.activateFor(controllerItem); + + return rule; - SetStateFromTriggeringItemAction action = new SetStateFromTriggeringItemAction(); - action.setAffectedItem(controlledItem); - rule.addAction(action); - rule.activateFor(controllerItem); - - return rule; - } + + public void Item.removeControlling(Item controlledItem) { + JastAddList<Rule> rules = getRoot().getRules(); + HashMap<Rule, Item> removeMap = new HashMap<Rule, Item>(); + for (Rule rule : rules) { + // check if rule has one ItemStateChangeCondition with controllerItem + int size = 0; + Condition lastCondition = null; + for (Condition condition : rule.getConditions()) { + size++; + lastCondition = condition; + } + + // check condition pattern + if (size!=1) + continue; + if (!(lastCondition instanceof ItemStateChangeCondition)) + continue; + Item controlling = ((ItemStateChangeCondition) lastCondition).getItem(); + + // check if action has one SetStateFromTriggeringItemAction + size = 0; + Action lastAction = null; + for (Action action : rule.getActions()) { + size++; + lastAction = action; + } + + // check action pattern + if (size!=1) + continue; + if (!(lastAction instanceof SetStateFromTriggeringItemAction)) + continue; + if (((SetStateFromTriggeringItemAction)lastAction).getAffectedItem() != controlledItem) + continue; + + removeMap.put(rule,controlling); + } + for (Rule rule : removeMap.keySet()) { + rule.deactivateFor(removeMap.get(rule)); + int idx = rules.getIndexOfChild(rule); + rules.removeChild(idx); + } + + } + + + //--- copyStateTo --- protected abstract void Item.copyStateTo(Item stateReceiver); protected void ItemWithBooleanState.copyStateTo(Item stateReceiver) { diff --git a/eraser-base/src/main/jastadd/Rules.jrag b/eraser-base/src/main/jastadd/Rules.jrag index 464b3d3d..26c18ae2 100644 --- a/eraser-base/src/main/jastadd/Rules.jrag +++ b/eraser-base/src/main/jastadd/Rules.jrag @@ -43,6 +43,13 @@ aspect Rules { itemObserver.addTriggeredRule(this); } + public void Rule.deactivateFor(Item item) { + if (item.hasItemObserver()) { + item.getItemObserver().removeTriggeredRule(this); + } + + } + private static java.util.concurrent.ScheduledExecutorService Rule.executor = java.util.concurrent.Executors.newScheduledThreadPool(4); /** diff --git a/eraser-base/src/test/java/de/tudresden/inf/st/eraser/ControllingItemTest.java b/eraser-base/src/test/java/de/tudresden/inf/st/eraser/ControllingItemTest.java index 289ee0ec..e9ebe848 100644 --- a/eraser-base/src/test/java/de/tudresden/inf/st/eraser/ControllingItemTest.java +++ b/eraser-base/src/test/java/de/tudresden/inf/st/eraser/ControllingItemTest.java @@ -32,6 +32,19 @@ public class ControllingItemTest { assertEquals(5, item1.getState(), DELTA); assertEquals(5, item2.getState(), DELTA, "Item was not controlled correctly"); } + @Test + public void testRemoveControlling() { + ModelAndItem mai = TestUtils.createModelAndItem(0, true); + NumberItem controlledItem = mai.item; + NumberItem controllingItem = TestUtils.addItemTo(mai.model, 4, true); + controllingItem.addControlling(controlledItem); + controllingItem.removeControlling(controlledItem); + + controllingItem.setState(8); + + assertEquals(8, controllingItem.getState(), DELTA); + assertEquals(0, controlledItem.getState(), DELTA, "Item was still controlled although the controlling was removed"); + } @Test public void testOneToManyNumber() { -- GitLab