How can I detect link creation?


#1

Hello,
I am working on implementing a client-server solution and I am interested in geting notified when a link is beeing created in a document, in order to inform the other clients.
I am saving the link information (“path points”) and I broadcast it to all the clients, so they could recreated the link.
The problem is that I am unable to detect the link creation on my document.
All the best
Mihai


#2

As the User Guide describes, there are two kinds of events: interactive ones generated by the GoView, and programmatic ones generated by the GoDocument. User behavior (gestures) cause interactive events; modifications to a document and its objects cause programmatic events.
So if you just want to know when the user has just drawn a new link, you can define a GoView.LinkCreated event handler.
Or if you want to know whenever any code adds a link to a document, you can define a GoDocument.Changed event handler, looking for the GoLayer.InsertedObject hint, with an object that is a link (i.e., implements IGoLink or is a subclass of GoLink or of GoLabeledLink).
In this case a GoView event is associated with a GoDocument event, but of course there can be other view events, such as GoView.ObjectDoubleClicked or GoView.BackgroundHover, that are not associated with changing a document.
And other code that executes could easily create new links in a document without the user having “drawn” one.
I suspect you are trying to synchronize documents, so you probably just care about the GoDocument.Changed event. For the simple case I recommend overriding GoDocument.OnChanged. But in the long run you may find it best to override GoDocument.FinishTransaction, so that you have the opportunity to process all of the changes in a “batch” manner. This involves looking at the GoDocument.UndoManager’s list of changes that just got recorded, and sending out to your other clients whatever information you need so they can reproduce the same changes.


#3

Thank you very much for your reply.
You are right, I am trying to synchronize the documents. For the moment it seems to work wonderfull with overriding OnChanged event.
And again, you are right, because the undo/redo functionality should be considered. Therefore I will definetly have a look on the FinishTransaction and overriding it.
P.S. I really apreciate your fast, precise and definetly helpfull answers.


#4

[Serializable]
public class SpecialDoc : GoDocument {
public SpecialDoc() {}
public override bool FinishTransaction(String tname) {
GoUndoManagerCompoundEdit edit = null;
if (this.UndoManager != null)
edit = this.UndoManager.CurrentEdit;
bool result = base.FinishTransaction(tname);
if (result && edit != null) {
System.Diagnostics.Debug.WriteLine(edit.PresentationName);
foreach (GoChangedEventArgs ea in edit.AllEdits) {
if (ea.Hint == GoLayer.InsertedObject) {
IGoIdentifiablePart part = ea.Object as IGoIdentifiablePart;
if (part != null)
System.Diagnostics.Debug.WriteLine("inserted " + part.PartID.ToString());
} else if (ea.Hint == GoLayer.RemovedObject) {
IGoIdentifiablePart part = ea.Object as IGoIdentifiablePart;
if (part != null)
System.Diagnostics.Debug.WriteLine("removed " + part.PartID.ToString());
}
}
}
return result;
}
public override void Undo() {
GoUndoManagerCompoundEdit edit = null;
if (this.UndoManager != null)
edit = this.UndoManager.EditToUndo as GoUndoManagerCompoundEdit;
if (edit != null) {
System.Diagnostics.Debug.WriteLine(edit.PresentationName);
foreach (GoChangedEventArgs ea in edit.AllEdits) {
if (ea.Hint == GoLayer.InsertedObject) {
IGoIdentifiablePart part = ea.Object as IGoIdentifiablePart;
if (part != null)
System.Diagnostics.Debug.WriteLine("undo insert of " + part.PartID.ToString());
} else if (ea.Hint == GoLayer.RemovedObject) {
IGoIdentifiablePart part = ea.Object as IGoIdentifiablePart;
if (part != null)
System.Diagnostics.Debug.WriteLine("undo remove of " + part.PartID.ToString());
}
}
}
base.Undo();
}
public override void Redo() {
GoUndoManagerCompoundEdit edit = null;
if (this.UndoManager != null)
edit = this.UndoManager.EditToRedo as GoUndoManagerCompoundEdit;
base.Redo();
if (edit != null) {
System.Diagnostics.Debug.WriteLine(edit.PresentationName);
foreach (GoChangedEventArgs ea in edit.AllEdits) {
if (ea.Hint == GoLayer.InsertedObject) {
IGoIdentifiablePart part = ea.Object as IGoIdentifiablePart;
if (part != null)
System.Diagnostics.Debug.WriteLine("redo insert of " + part.PartID.ToString());
} else if (ea.Hint == GoLayer.RemovedObject) {
IGoIdentifiablePart part = ea.Object as IGoIdentifiablePart;
if (part != null)
System.Diagnostics.Debug.WriteLine("redo remove of " + part.PartID.ToString());
}
}
}
}
}