I agree that you misunderstood. :) Events abstract things that
just as tightly as by other class members. The coupling is determined
by what types are shared, and how much one class depends on the specific
interface and implementation of another. Adding events does not help
reduce coupling, it is just a different way to look at how object interact.
Well, there is a "supposed to", but it is more of a higher level goal
than focusing on specific implementation details.
In any case, it seems to me that again, it is important to stay focused
and not try to learn too many things at once. Frankly, a lot of the
higher-level design techniques just do not make as much sense until
you have seen enough of the lower-level implementation details.
it is a bit like "kndg" posting the explicit "listener/observer" pattern
implementation. it is not that you would write code like that in C#, but it
_is_ useful to understand the more explicit way to implement those kinds
of patterns before using language features that abstract and hide
implementation details for those patterns.
As far as the question of events go, it is useful to understand the
difference between polling and interrupt- (or event-) driven
programming. Start with the fundamental goal: you want to know when the
state of something changes. This could be a value changing, or the user
performing an action, or some data arriving, or whatever.
There are two basic ways to accomplish that goal: keep checking the
state to see if it is changed since the last time you looked; or register
yourself in some way so that the thing controlling the state can just
let you know when it happens.
This distinction has existed essentially since the beginning of
computers in one form or another, but it usually comes down to the same
basic issue: checking (or "polling") is wasteful, while waiting for an
interrupt costs nothing but a little bit of memory to store the
In C#, this distinction roughly comes down to some code repeatedly
examining the state of some other object's property, or subscribing to
an event and "waiting" for the event to be raised (where by "waiting" I
simply mean that the code to handle the event is not executed until the
event is raised; it is not like the object is literally sitting there
actively waiting???after all, that is the whole point of interrupt-driven
So, when thinking about how to design your code, the question mostly
becomes one of how the information needs to move between objects. In
general, there is no reason to use an event unless it is something that
the code that is interested in it will not already know it is time to access
For example: the presenter has no way to automatically know when the
user's interacted with the view object. It _could_ just keep looking
for some state to change in the view object, but that is wasteful. So
instead, an event is appropriate.
On the other hand, once that event is raised, the rest of the logic is
completely deterministic and sequential. The presenter knows that it
needs to retrieve some data from the model, and then pass it to the view
(possibly reformatting it to suit the view's needs). There is nothing in
that flow of data that would require any of the actors to wait for
something to happen or otherwise repeatedly poll; it knows it can get
everything it needs on the first try, and so it simply should.
That's a completely different question from the one of whether to use an
event or not. it is true that _each_ of the objects in the design
pattern should be "dumb". The less any one object knows about any other
object, the better. Encapsulation, information hiding, etc. these all
relate to isolating functionality and having well-defined ways for what
information is shared to flow between objects.
it is kind of like your brain. Our biology _could_ have been implemented
such that we had no division of hemispheres, with everything in the
brain connected to everything else. And granted, science is still
learning the whys and wherefores about why the brain is organized the
way it is. But I think it is safe to assume that the division of labor,
with specific links between areas (such as the corpus callossum that
connects the hemispheres) is an important feature that helps the brain
work more efficiently and, probably more importantly, helps the brain
evolve and _develop_ in a more efficient way.
Likewise, in your program, you _could_ make everything in every class
public, and just have one type fiddle directly with whatever's in the
other type, with each type having intimate knowledge of the
implementation details of every other type. But to maintain such a
program means that you have to remember how _everything_ works all at
once, because no matter what part of the program you are working on, you
cannot afford to not know how changes to it might affect other parts of
But if you keep things isolated, and require each part of the program to
expose their features in ways that are well-defined and change very
little, you have the freedom to modify the internal implementation
details without disturbing the other parts of the code.
All of that is important. But it has little or nothing to do with
whether some feature is to be exposed as an event or not.
A ListView control is just that: a view of a list. So fundamentally,
you need for the presenter to deliver a list of data to it. The first
question is what data will actually be in the list. Then your view
needs to have some kind of mechanism that the controller can use to
deliver that data to it.
If you expect the data to flow only into the view, to be shown to the
user, then passing a list from the controller to the view is probably
best. If the list data will flow both ways, then it is possible you will
prefer a property. If you want to get really fancy, then you can
abstract the ListView object as an interface that allows list-like
operations, perhaps even as an IList<T>. Then your IList<T>
implementation can update the ListView directly as the controller
modifies it, and retrieve data directly from the ListView if the
controller tries to get things from the IList<T>.
Of course, you also need some data type that represents a single item in
the list. This might as simple as a string, or it could be a more
complex data type. It just depends on what you are using the ListView to
show the user.
However, you do it, the important thing is that the controller should
not have any need to know about the ListView type, nor even that a
ListView object is being used to present the data to the user.
Hope that helps!