How to apply observer pattern if observers are also subjects - oop

I have a container panel.
In the container I have n other panels. The user can change the information in any panel. When a panel changes, all other containers should be updated and refresh the information they present.
In a normal situation the observer patter has a single subject and a bunch of observers. In this case the observers are also subjects.
Is this something design patterns can address ? How should I build the interaction between these objects in a good OOP style ?

the http://en.wikipedia.org/wiki/Mediator_pattern might be useful here.

Sounds more like the pub/sub pattern than the observer pattern.
Panel A, B and C subscribes on topic X.
Panel B generates topic Z when it have received hand handled topic X

You can tweak the idea of the observer pattern by just making it many-to-many. The only difference is that the observer needs to know WHAT subject changed state rather than ANY subject has changed state.

Say you have a container class instance C1 and Observer class instance ob1, ob2, ob3 all observing Subject class instance s1. When an event occurs on ob1 you could trigger an event in class S1 and ensure the event handler function in S1 notfies observer ob1, ob2, ob3
Hope this helps. Please let me know if it does :)
Thanks!

Related

How to Subscribe to a single Event from multiple classes?

I am creating a Draft Room for a football game I am making and have several classes involved with it.
The DraftPick Class will be responsible for raising an Event once the current team has made their selection. However, there are multiple other classes that need to "know" when this event has been fired as well. The Draft Class needs to know so it can remove the player from the list of available players, restart the clock and update the current team on the clock. The DraftNews Class needs to know about this event so it can update the in-draft ListView with the Pick information, and the DraftTicker class needs to know about the event to add the selection that was just made to the scrolling draft ticker at the bottom of the screen.
I'm working in VB.Net, so its not as straightforward as it would be in C#. However, I am thinking the easiest way would be to make the PickMade Event shared so the other classes would be able to simply access the event via DraftPick.PickMade() and simply use an AddHandler. I was wondering if there is an established "method" for doing this, or if what I am considering doing would be OK.
Any advice would be appreciated, first time I've had the need for multiple classes to be listening to an event...

How do I record a player's response?

Basically what I am trying to do is have the player respond to a message in which they are required to input numbers only. From that point, I could parse the String into an int and use it towards the rest of my code. Also, I am trying to make it so this occurs in my event method. Any help is greatly appreciated!
What you essentially want to do is store the player in a container until the next time they talk, then remove them. This, represented in pseudocode, would look like the following:
on your condition:
add player to collection
on player chat:
does the player exist in the collection?
yes: is input a valid number?
yes: proceed with execution, remove player from collection after
no: print error
no: ignore, let event pass
Since the MineCraft protocol does not allow input verifying, there will be cases where the user may submit non-numerical characters. Integer.parseInt, or its sibling valueOf will throw an exception if this is the case.
To prevent memory leaks, you should remove the player from the collection when they log off. Alternatively, you could store them in a weak reference container. A good one for this scenario would be a WeakSet, which you can essentially obtain via Collections.newSetFromMap(new WeakHashMap()). Weak references get garbage-collected if all other references are eliminated, so this reduces the risk of a memory leak.
You should look into the bukkit conversation API. It for doing exactly this. You can find tutorials online, but basically to set it up you do this.
Build a conversation with the ConversationFactory
ConversationFactory HudConvo = new ConversationFactory(plugin)
.withModality(true)
.withEscapeSequence("exit")
.withFirstPrompt(new HudConversationMain(plugin, player, 0))
.withLocalEcho(false);
Conversation conversation = HudConvo.buildConversation((Conversable) player);
Begin the conversation
conversation.begin();
Make the first prompt as a class that either extends one of the input type prompts (i.e. StringPrompt) or implements the Prompt abstract class.
Fill in the methods getPromptText() and acceptInput(). getPromptText() constructs the message to be displayed to the player and acceptInput() takes what the player types and reacts to it with a new prompt.
I hope this helped. If you have questions, feel free to ask.

Use Dojo's Publish Subscribe Model

We are working on a portal environment. On one of our page we have two portlets. When some action happens on one portlet, we have to minimize the other portlet and viceversa.
So we feel that this is a suitable situation where we can use Dojo's publish/subscribe model. But I'm a bit confused if I need to use different topics [One when some action happens on Portlet A, and the second topic when some action occurs on PortletB] or one topic [something like minimize]. Can someone please guide me.
This is really up to you, and depends on your needs.
Topics are free-form texts, so you can arrange it in any text format you like.
My own experiences have been to treat a topic as an "event". Therefore, one topic, one event.
My experience has also been that it is tremendous beneficial to implement "commands" in the same system as events -- so you have a universal command/event system.
Events (therefore topics) do not have to correspond to your portlets. For instance, one portlet can have multiple events (if they make sense), or one event can be shared by multiple portlets (for shared functionalities or for cross-portlet communcations).
Parameters and data can be passed with the event (i.e. topic) as arguments.
Now, a good trick I've learnt is to have "sub-topics" -- i.e. topics that are prefixed with an parent topic, when things want to subscribe to a particular instance of event.
Example: Assume we have an event called "/portlets/showhide" which is published by any portlet when it is shown or hidden, together with the id of the portlet and a boolean variable indicating whether it is shown or hidden.
Now, assume that a portlet will also publish topics called "/portlets/showhide/{id}" (with true/false argument) and "/portlets/showhide/{id}/show" (no arguments) when shown, together with the generic "/portlets/showhide" topic (event).
Now assume some handler object is really only interested when the "xyz" portlet is hidden. It doesn't have to subscribe to "/portlets/showhide" and listen to all those events of other portlets that it is not interested in. It can simply subscribe to "/portlets/showhide/xyz/hide". When number of subscriptions increase in a large system, this kind of optimizations can come in quite handy.
You can use one topic in which pass additional parameters. Something like this:
// PortletA
dojo.publish("onPortletAction", [{sender: "PortletA"}]);
// PortletB
dojo.publish("onPortletAction", [{sender: "PortletB"}]);
....
dojo.subscribe("onPortletAction", dojo.hitch(window, window.processAction));
window.processAction = function(data) {
if (data.sender == "PortletA"){
//to do something
}
if (data.sender == "PortletB") {
//to do something
}
}

Help me name my class

Okay, first, here's my rather poor diagram...
It's worth noting the "Name Me" class may be listening to more than one RequestNotifier
It's safe to assume all Work Items that are put on the Work Queue are taken off the work queue by something else not shown and are processed exactly the same.
The only difference between the work items is the name (or id, but the name is my id in this) of the WorkItem that's being requested.
Name Me listens to Requests to work on a specific WorkItem, it then asks (a repository or some other data access class) for a WorkItem with that name, if one exists, submits it to the Work Queue. If none is found it ignores it and it's safe to do so.
Any ideas for a name, or if not a name, a better design that would make naming easier?
NotificationBroker gets my vote.
The primary responsibility of that class seems to be listening to notifiers and Brokering those Notifications to multiple Worker Queues.
KISS Principle
class Listener
RequestListener
WorkRequester
WorkManager
WorkItemSubmitter
Most of the suggestions done so far make sense to me.

Notifications in wxWidgets?

I'm working on a small application using C++/wxWidgets, where several parts of the GUI need to be updated based on e.g. received UDP datagrams. More specifically, a secondary thread tries to keep a list of available "clients" in the network (which may come and go away) and e.g. corresponding comboboxes in the UI need to be updated to reflect the changes.
The documentation mentions that for this kind of thing EVT_UPDATE_UI would be a good choice. As far as I can understand from the sparse documentation, this event is sent automatically by the system and provides some support for assisted UI change.
However, I'd feel more comfortable using a more direct approach, i.e. where e.g. a window object could register/subscribe to receive notifications (either events or callbacks) upon particular events and another part of the code is sending out these notifications when required. I could do this in C++ using my own code, however I guess if wxWidgets already supports something like that, I should make use of it. However I haven't found anything in that regards.
So, the question is: does wxWidgets support this kind of notification system (or similar alternatives) or would I be best served coding my own?
AFAIK there is nothing directly usable in wxWidgets, but doing it on your own seems easy.
What I would do:
Create a wxEvtHandler-descendent class to hold the list of available "clients" in the network. Let this class have a wxCriticalSection, and use a wxCriticalSectionLocker for that in all methods that add or delete "clients".
Create a worker thread class by inheriting wxThread to handle your UDP datagrams, using blocking calls. The thread should directly call methods of the client list object whenever a client has to be added or removed. In these methods update the list of clients, and ::wxPostEvent() an event to itself (this will execute the whole notification calls in the main GUI thread).
Handle the event in the client list class, and notify all listeners that the list of clients has changed. The observer pattern seems to me a good fit. You could either call a method of all registered listeners directly, or send a wxCommandEvent to them.
Have you tried calling Update() on the widget(s) that change? Once you update the contents of the combo box, call Update(), and the contents should update.