C++ Notifiers
by Dave Pomerantz


Listing One
class CTemperatureNotifier : public CNotifier
{
public:
   CTemperatureNotifier(void) : CNotifier(TEMPERATURE_NOTIFIER)
      { m_temperature = 0.0; }
public:
   float m_temperature;   // temperature is in degrees celsius
};
// convenience function to send the notifier immediately
inline HRESULT SendTemperatureNotifier(float temperature)
{
   HRESULT hr = E_OUTOFMEMORY;
   CTemperatureNotifier *pNotifier = new CTemperatureNotifier();
   if (pNotifier)
   {
      pNotifier->m_temperature = temperature;
      pNotifier->Send();
   }
   return hr;
}
// convenience function to queue the notifier for dispatching
inline HRESULT PostTemperatureNotifier(float temperature, 
    CNotifier::PRIORITY nPriority = CNotifier::PRIORITY_NORMAL)
{
   HRESULT hr = E_OUTOFMEMORY;
   CTemperatureNotifier *pNotifier = new CTemperatureNotifier();
   if (pNotifier)
   {
      pNotifier->m_temperature = temperature;
      pNotifier->Post(nPriority);
   }
   return hr;
}


Listing Two
class CSubscriber
{
public:
   enum SUBSCRIBER_PRIORITY
   {
      PRIORITY_HIGH,
      PRIORITY_NORMAL,
      PRIORITY_LOW
   };
public:     
// Constructors and destructors
   CSubscriber(void);
   CSubscriber(const CSubscriber &src);
   virtual ~CSubscriber(void);
   CSubscriber &operator=(const CSubscriber &src);
// Subscription Operations
      // GetSubscriberPriority: return relative priority of subscriber
   SUBSCRIBER_PRIORITY GetSubscriberPriority(void);
      // SetSubscriberPriority:  move this subscriber ahead or behind other
      //                         subscribers in the list
   void SetSubscriberPriority(const SUBSCRIBER_PRIORITY nPriority);
      // IsSubscribed: return true if a subscriber will be sent this notifier 
   bool IsSubscribed(UINT nSubscription);
      // Subscribe: add subscriber to the list that receives this notifier
   HRESULT Subscribe(UINT nSubscription);
      // Unsubscribe: no longer send this notifier type to the subscriber
   HRESULT Unsubscribe(UINT nSubscription);
// Notifier response functions, called by dispatcher
      // called when the temperature changes
   virtual void OnTemperatureNotifier(CTemperatureNotifier *pNotifier);
      // called when temperature units change
   virtual void OnUnitsNotifier(CUnitsNotifier *pNotifier);
      // called when thermostat setpoint changes
   virtual void OnSetPointNotifier(CSetPointNotifier *pNotifier);
      // called when another subscriber wants a notifier
   virtual void OnRequestNotifier(CRequestNotifier *pNotifier);
protected:  // Implementation
      // SetDispatcher: Called by CDispatcher
   static void SetDispatcher(CDispatcher *pDispatcher);
      // GetDispatcher: Get pointer to dispatcher
   static CDispatcher * GetDispatcher(void);
private:  // Data members
   static CDispatcher *m_pDispatcher;           // see SetDispatcher
   SUBSCRIBER_PRIORITY m_nSubscriberPriority;
   friend class CDispatcher;
};


Listing Three
HRESULT CThermometer::Init(void)
{
   ... other initialization ...
   Subscribe(TEMPERATURE_NOTIFIER);
   return result;
}
void CThermometer::OnTemperatureNotifier(CTemperatureNotifier *pNotifier)
{
   if ((GetSafeHwnd() != 0) && 
       (m_temperature != pNotifier->m_temperature))
   {
      m_temperature = pNotifier->m_temperature;
      RedrawThermometer();
   }
}





3


