SimpleWorkItemActivationService

Topics: CAB & Smart Client Software Factory
Jun 22, 2006 at 11:01 PM
originally posted by: juemue

Hi, all.

When you browse the code of the SimpleWorkItemActivationService you can read this service will ensure 'that only one WorkItem is active at one time'.
This fails if a WorkItem is activated and another WorkItem, which has subscribed to the OnDeactivating event, sets the Cancel property of the CancelEventArgs to true (maybe the data of it's SmartPart is not saved).
So I tried to write my own implementation of IWorkItemActivationService and use it instead, but I didn't succeed.

I want to ensure, that a WorkItem doesn't become activated when another WorkItem sets Cancel to false in it's Deactivating event.

Any ideas?

Or did I miss a thing or am I misunderstanding how the activating/deactivating stuff and the IWorkItemActivationService works?

Regards


Jürgen
Jun 28, 2006 at 8:00 AM
originally posted by: AndrePiwoni

Jurgen,

That was my undertsanding of how WorkItemActivation service should work. It seems that when you Activate work item ActivationService checks for cancelling work item's Activation, sets work item's status to Active if not cancelled, and then calls Deactivate which if cancelled would leave both WorkItems in active state. As a result, when you come back to activate work item with previously cancelled deactivate no activation/deactivation events occur making this functionality useless.

It worked for me prevoiusly since I called Deactivate on currently active work item and then checked its status for possible cancellation before showing/activating new work item.

What needs to happen when work item is activated is status has to be set to Active after ActivationService successfully deactivated currently active work item.

I have made a comment in WorkItem's code below where I think things go wrong below.

private void ChangeStatus(WorkItemStatus newStatus)
{
ThrowIfWorkItemTerminated();

WorkItemStatus oldStatus = status;

if (oldStatus != newStatus)
{
CancelEventArgs args = new CancelEventArgs();
FireIfActivating(newStatus, args);
FireIfDeactivating(newStatus, args);
FireIfTerminating(newStatus);
if (args.Cancel == false)
{
status = newStatus; // INCORRECT
if (ActivationService != null)
{
ActivationService.ChangeStatus(this);
}
FireStatusEvents();
}
}
}

If you happen to get to the bottom of this problem before I do please let me know. I need a solution for detecting when work item's views go away so I could possibly prompt for save or cancellation. I may have to opt for vetoable Close on workitem instead of activation service since I don't like activation being tied to focusing system as well. When two work items show views at the same time going from one to another may trigger activate/deactivate at whihc time I don't want save/cancel prompt.

Sincerely,

Andre Piwoni
Jun 29, 2006 at 2:19 AM
originally posted by: juemue

Hi, Andre.

Thanks for your answer.

What you describe is what I found out browsing the code, too.

At the moment I'm using the 'Validating' event of the UserControls (my SmartParts) to prevent Deactivation. This seems to work so far, but maybe there are scenarios this will not work anymore.

When I started evaluating the CAB I expected the WorkItem/SmartPart architecture to provide some kind of 'vetoable ActivationStatusChanging' event. This event should be thrown and be caught by instances of the WorkItem class, because a WorkItem represents a certain usecase, and it should be sent to all existing WorkItems of the application (maybe except the terminated) so each WorkItem is able to decide wheather to cancel or not. If cancelled, no changes must happen to the UI - this means, no activation/deactivation of WorkItems etc and the focus must still remain in the control it was before...
I think this must be done in a special service and, of course, it is tied to the Focus stuff, too. Maybe the ControlActivationService has to be modified, too.

At the moment I'm not working on this problem, because the use of the Validating events will fit for my needs.
But when I come to an edge and find some other solution I will let you know.

Regards

Jürgen