Link to home
Start Free TrialLog in
Avatar of PMH4514
PMH4514

asked on

Critique this approach and provide appropriate alternative if needed please

(this might be an MFC question, but I think it's more a C++ design question)

I'm Using VC++ 6.0 and MFC.

I have a class CMoviePage which is derived from CPropertyPage. This contains graphical controls and what not (it's an AVI player embedded in an application). I also have a class CMovieView which contains all of the filter graph and direct draw related stuff. CMovieView also has a message map setup, containing among others, this:

    ON_MESSAGE( WM_GRAPHNOTIFY, HandleGraphEvent )

which is defined in the header:
    #define WM_GRAPHNOTIFY  WM_USER+13

protected:
    afx_msg void HandleGraphEvent(WPARAM wParam, LPARAM lParam);

which my MediaEvent instance is told to watch:
    g_pMediaEvent->SetNotifyWindow((OAHWND)m_hWnd, WM_GRAPHNOTIFY, 0);


HandleGraphEvent looks like this:

void CMovieView::HandleGraphEvent(WPARAM wParam, LPARAM lParam)
{
LONG evCode, evParam1, evParam2;

HRESULT hr;
// Make sure that we don't access the media event interface
// after it has already been released.
if (g_pMediaEvent)
{
   // Process all queued events
   while(SUCCEEDED(g_pMediaEvent->GetEvent(&evCode, (LONG_PTR *) &evParam1, (LONG_PTR *) &evParam2, 0)))
   {

      hr = g_pMediaEvent->FreeEventParams(evCode, evParam1, evParam2);

      switch (evCode)
      {
          case EC_COMPLETE:
             // when done playing, rewind and pause.
             RewindClip();
           XXXXXXX -> UpdateVideoControlUI();

                break;

             // there are others, not relevant..

          }
      }
   }
}


So - what's that XXXXX? for? This is sorta the guts of the question. HandleGraphEvent() is a method within CMovieView.  CMovieView is contained by CMoviePage, which references it via private a member variable:
    CMovieView* pMovieView;

My UpdateVideoControlUI() is implemented by CMoviePage - as that is a UI related function.

So - the question is, I need CMovieView to be able to call "up into it's containing class", the UpdateVideoControlUI() method. My initial thought was to add a private member variable to CMovieView -- CMoviePage* m_pMoviePage  and then have CMovieView pass a 'this' reference into CMoviePage when it's instantiated or apply it via a non constructor method. That way when CMovieView::HandleGraphEvent() executes, it can execute m_pMovePage->UpdateVideoControlUI(), effectively calling a method in it's containing class.

That is in fact what I did, and yes, it works. But I'm not entirely comfortable with this for the following reasons:

1. I don't really like the idea of a class needing to be hard-wired to a specific containing class. While not doing so I believe is a sound design decision in theory for reuse and what not, I'm not sure how relevant it is in this particular situation.

2. I'm not yet fully comfortable enough with C++ to know if there is not a more appropriate mechanism to accomplish this (some kind of callback or MFC mechanism that I just don't know about.)

thougths?

thanks!
-Paul
Avatar of jkr
jkr
Flag of Germany image

>>I don't really like the idea of a class needing to be hard-wired to a specific containing class

Why not? This is a widely used approach. Just think of e.g. modeling a file system where you need to keep a pointer to the containing directory. If you don't like it, you could still send a message to the main window (available via 'AfxGetMainWnd()') to have it update the UI.
Avatar of PMH4514
PMH4514

ASKER

>>Why not? This is a widely used approach.

good 'nuff! If somebody with your expertise sees nothing wrong with it, then I guess I'm ok with it :-)
ASKER CERTIFIED SOLUTION
Avatar of Jaime Olivares
Jaime Olivares
Flag of Peru image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of PMH4514

ASKER

jamie - yeah, that's more along the lines of what I was thinking would be appropriate. Either or I guess, both perfectly valid it seems given appropriate arguments pro or con.  it's all in context I guess.

Like you, I don't like to make a class dependant from other, because I have troubles when I want to reuse it, since I have many year working for the same contractor, I face this dilemma every day, so I have developed many tricks. The first is the callback, like explained, others are "windows message driven" and even "socket message driven" when working distributed apps.
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial