Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Master Thesis - SCChart Edge Merge - Code Review #7

Draft
wants to merge 5 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
de.cau.cs.kieler.sccharts.ui.synthesis.hooks.DeclarationsHook
de.cau.cs.kieler.sccharts.ui.synthesis.hooks.EdgeMergeHook
de.cau.cs.kieler.sccharts.ui.synthesis.hooks.LocalDeclarationsHook
de.cau.cs.kieler.sccharts.ui.synthesis.hooks.StateActionsHook
de.cau.cs.kieler.sccharts.ui.synthesis.hooks.BlackWhiteModeHook
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ import static extension de.cau.cs.kieler.klighd.syntheses.DiagramSyntheses.*
class TransitionSynthesis extends SubSynthesis<Transition, KEdge> {

/**
* Immediate transition will be more likely drwn from left to right as long as there are no more than this threshold
* Immediate transition will be more likely drawn from left to right as long as there are no more than this threshold
* number of other edges to flip to break a cycle.
*/
public static val IMMEDIATE_TRANSITION_DIRECTION_THRESHOLD = 6
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
/*
* KIELER - Kiel Integrated Environment for Layout Eclipse RichClient
*
* http://www.informatik.uni-kiel.de/rtsys/kieler/
*
* Copyright 2021,2022 by
* + Kiel University
* + Department of Computer Science
* + Real-Time and Embedded Systems Group
*
* This code is provided under the terms of the Eclipse Public License (EPL).
* See the file epl-v10.html for the license text.
*/
package de.cau.cs.kieler.sccharts.ui.synthesis.hooks

import de.cau.cs.kieler.klighd.krendering.ViewSynthesisShared
import de.cau.cs.kieler.sccharts.ui.synthesis.hooks.SynthesisHook
import de.cau.cs.kieler.klighd.kgraph.KNode
import de.cau.cs.kieler.sccharts.State
import de.cau.cs.kieler.klighd.kgraph.KEdge
import de.cau.cs.kieler.sccharts.Transition
import de.cau.cs.kieler.sccharts.Scope
import org.eclipse.xtend.lib.annotations.Data
import de.cau.cs.kieler.sccharts.PreemptionType
import de.cau.cs.kieler.sccharts.HistoryType
import de.cau.cs.kieler.sccharts.DeferredType
import java.util.HashMap
import de.cau.cs.kieler.sccharts.ui.synthesis.GeneralSynthesisOptions
import de.cau.cs.kieler.klighd.SynthesisOption
import de.cau.cs.kieler.sccharts.DelayType

/**
* Merge transitions that are considered semantically similar to be visualized using one edge.
*/
@ViewSynthesisShared
class EdgeMergeHook extends SynthesisHook {


/** The related synthesis option */
public static final SynthesisOption MERGE_SIMILAR_EDGES = SynthesisOption.createCheckOption(EdgeMergeHook, "Merge Similar Edges",
false).setCategory(GeneralSynthesisOptions::APPEARANCE);

override getDisplayedSynthesisOptions() {
return newLinkedList(de.cau.cs.kieler.sccharts.ui.synthesis.hooks.EdgeMergeHook.MERGE_SIMILAR_EDGES)
}

/**
* a mapping of an edge group key to the representative edge for that group
*/
HashMap<EdgeGroupKey, KEdge> map = new HashMap<EdgeGroupKey,KEdge>();

/**
* A Key used to determine if two transitions are semantically similar to be represented by one edge
*/
@Data
static class EdgeGroupKey {
State source;
State target;
PreemptionType preemption;
HistoryType history;
DeferredType deferred;
DelayType delay;
boolean deterministic;
}

/**
* Invoked before the translation of the model starts.
* @param scopethe input model
* @param nodethe empty diagram root node
*/
override void start(Scope scope, KNode node) {
// reset the map of representative edges as we start a new synthesis
map.clear()
}

/**
* Invoked after a {@link Transition} is translated.
* @param transitionthe transition
* @param edgethe translated edge
*/
override void processTransition(Transition transition, KEdge edge) {

if (MERGE_SIMILAR_EDGES.booleanValue) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Documentation on what this hook does and comments about how is accomplished in the code help understand in this file (other than the methods that are overriden and are by that kind of documented already).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have added some comments, anything that is still missing sufficient explanation?
Should I remove javadoc comments from the overridden functions?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In general, anything that is API of new code should be documented so that someone not knowing what some class/method is about gets to know it by reading the JavaDoc for it. Ideally as you did here also with some comments sprinkled inbetween for calculations you do that are not immedeately obvious.
The only thing missing for me would now be a JavaDoc on the class itself explaining what this hook does.

The JavaDoc for overridden functions are imo not necessary, but they do not hurt either, so I would let them in.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have now added a doc comment for the class.
I attempted to keep it similar detailed to other hooks' class comment.
I believe this was the only outstanding review comment from you and should therefore be ready for @a-sr to review.


// build the transitions key to find the representing edge
// or insert the current edge if no edge was already chosen
var key = new EdgeGroupKey(
transition.sourceState,
transition.targetState,
transition.preemption,
transition.history,
transition.deferred,
transition.delay,
transition.isNondeterministic
);

// if we do not already have a representative use the current edge as the representative
val rep = map.computeIfAbsent(key, [EdgeGroupKey _key | edge]);

if (edge != rep) {
// if this was not just chosen as the representative transfer all edge labels to the representative
rep.labels.addAll(edge.labels)
for (label : edge.labels) {
// adjust the transfered labels parent
label.parent = rep
}
// remove the current edge from the graph, as it will be represented by the representative edge
edge.source.outgoingEdges.remove(edge)
edge.target.outgoingEdges.remove(edge)
}

}
}

}