Click here to Skip to main content
15,893,622 members
Articles / Desktop Programming / MFC
Article

CFileChangeEvent Class

Rate me:
Please Sign up or sign in to vote.
3.69/5 (9 votes)
30 Nov 19992 min read 97.5K   2.5K   48   15
An article about how we can notify our application that a file has been changed by another application.

Introduction

This article is about how we can notify our application that a file has been changed by another application.

I've created the CFileChangeEvent-class for it. It has the following methods:

void addFile(const std::string &sFileName)
Use this method when you want to be notified of changes of a file. When the notification thread is running, it will be stopped and restarted.
void removeFile(const std::string &sFileName)
Use this method when you don't want to be notified anymore. When the notification thread is running, it will be stopped and restarted.
void startWatch(void)
This method starts the notification thread.
void stopWatch(void)
This method stops the notification thread. It's also called in the destructor, so you know the thread will always stop.
virtual void OnFileAlarm(FileAlarm nAlarm, const std::string &sFileName)

Override this method. This method is called when a file is changed or deleted. FileAlarm is an enum with following attributes: FA_CHANGED, FA_REMOVED, FA_CREATED.

How to use this class ?

Derive a class (for example your CDocument-class) from CFileChangeEvent and override the OnFileAlarm. That's all.

Warning: You can't call the method UpdateAllViews in the OnFileAlarm. This is why:

A thread can access only MFC objects that it created. This is because temporary and permanent Windows handle maps are kept in thread local storage to ensure protection from simultaneous access from multiple threads.

How can we solve this?

  1. Pass the individual handles (like HWND) rather than C++ objects, to the worker thread. The thread then adds these objects to its temporary map by calling the appropriate FromHandle member function.
  2. You can use a new user-defined message corresponding to the different tasks your worker threads will be performing and post these messages to the application's windows/views using PostMessage.
    1. Create a user-defined message with ::RegisterWindowMessage like this:
      const UINT msgFileChange = ::RegisterWindowMessage("FILECHANGE");

      Put this in the application's header file so that you can use this everywhere in your application

    2. In your document-class, create a member-variable to hold a pointer to the window you want to process the message.
      CView *m_pView;
      // This variable must be initialized in your view-class.
    3. In the method called by the thread, post the message to the processing window.
      // You can pass wparam, lparam if you wish
      m_pView->PostMessage(msgFileChange);
    4. In the processing view header file, add the following in the message map functions:
      // when you pass wparam, lparam add parameters to this function
      afx_msg void OnFileChange();
    5. In the processing view source file, add the following in the message map:
      ON_REGISTERED_MESSAGE(msgFileChange, OnFileChange)
    6. Add the source code for OnFileChange in the processing view source file.
      void CProcessView::OnFileChange()
      {
          CMyDocument *pDoc = GetDocument();
          pDoc->UpdateAllViews();
      }

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here


Written By
Web Developer
Belgium Belgium
Programmer since 1991 using C/C++/Visual Basic and Java. Playing with wxWindows at home.

Comments and Discussions

 
Generalwhat about Copy Event? Pin
batsword5-May-11 19:21
batsword5-May-11 19:21 
Generalusage in CDialog Pin
picazo5-Oct-05 9:45
picazo5-Oct-05 9:45 
GeneralImportant Fix in CFileChangeEvent::addFile Pin
David Lantsman24-Mar-05 10:15
David Lantsman24-Mar-05 10:15 
GeneralRegsitry Change Notification Pin
RoyceF14-Aug-04 14:14
RoyceF14-Aug-04 14:14 
GeneralFile Removed Event Pin
Paul-T13-Dec-03 23:12
Paul-T13-Dec-03 23:12 
GeneralRe: File Removed Event Pin
Member 126028330-Jul-04 10:21
Member 126028330-Jul-04 10:21 
GeneralPrevent a file from being deleted Pin
ja1618817-Dec-02 22:32
ja1618817-Dec-02 22:32 
GeneralProblem with removeFile Pin
Vinicius Pontes31-Jul-02 4:18
Vinicius Pontes31-Jul-02 4:18 
Hi,

I put your code in my application, and I'm having some problems to remove files from the list of files to watch.

My code is like below:

<br />
.<br />
.<br />
m_FileChangeEvent.removeFile( (const char *)lpszStr );<br />
.<br />
.<br />
.<br />
m_FileChangeEvent.addFile( (const char *)lpszPathName );<br />
if ( !m_FileChangeEvent.isWatching() ) m_FileChangeEvent.startWatch();<br />
.<br />
.<br />


Can you see anything wrong?

Thanks,

Vinicius
Generalcan't call the method UpdateAllViews - Simple Solution Pin
Amit Gefen29-Nov-01 15:11
Amit Gefen29-Nov-01 15:11 
QuestionWatching remote files (not mapped)??? Pin
Dan Madden10-Nov-01 6:59
Dan Madden10-Nov-01 6:59 
GeneralIncorrect notifications fired. Pin
Rob Wainwright19-Oct-00 2:59
Rob Wainwright19-Oct-00 2:59 
GeneralChange notifcations between 95/98 and NT Pin
Dean Wyant2-Apr-00 10:36
Dean Wyant2-Apr-00 10:36 
GeneralRe: Change notifcations between 95/98 and NT Pin
6-Apr-01 18:18
suss6-Apr-01 18:18 
GeneralMissing Project File Pin
nn7-Feb-00 6:56
nn7-Feb-00 6:56 
GeneralRe: Missing Project File Pin
8-Dec-01 3:08
suss8-Dec-01 3:08 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.