BCDemo.c

//****************************************************************************************
// Brightness/Contrast Demo
//
// Written by Jack Fu, 09/1999
// Copyright 1999 by Apple Computer, Inc.
//----------------------------------------------------------------------------------------
 
//----------------------------------------------------------------------------------------
// Includes
//----------------------------------------------------------------------------------------
#include <AVComponents.h>
 
#include "BCEngine.h"
 
 
//----------------------------------------------------------------------------------------
// Includes
//----------------------------------------------------------------------------------------
#define SUPPORT_OLD_BC_ENGINES  1
 
 
//----------------------------------------------------------------------------------------
// Private Defines
//----------------------------------------------------------------------------------------
#define kSleepTime          10      // in ticks
 
#define kMBARResID          128
#define kAppleMenuResID     128
#define kFileMenuResID      129
#define kEditMenuResID      130
 
enum    // menu items for MENU kFileMenuResID
{
    kQuitMenuItem = 1
};
 
enum    // menu items for MENU kEditMenuResID
{
    kUndoMenuItem = 1
};
 
#define kDialogID               128
#define kComponentAlertID       129
#define kComponentOpenAlertID   130
#define kComponentTargetAlertID 131
#define kComponentMiscAlertID   132
#define kDMAlertID              133
 
enum    // dialog items for DITL (ID = kDialogID )
{
    kContrastTextItem = 1,
    kContrastSliderItem,
    kBrightnessTextItem,
    kBrightnessSliderItem,
    kContrast0PctTextItem,
    kContrast100PctTextItem,
    kBrightness0PctTextItem,
    kBrightness100PctTextItem
};
 
 
//----------------------------------------------------------------------------------------
// Private Prototypes
//----------------------------------------------------------------------------------------
typedef struct OurDMNotifyData 
{
    ComponentInstance   engine;
    DialogPtr           dp;
    ControlHandle       brightnessCtl;
    ControlHandle       contrastCtl;
} OurDMNotifyData, *OurDMNotifyDataPtr, **OurDMNotifyDataHdl;
 
 
//----------------------------------------------------------------------------------------
// Private Prototypes
//----------------------------------------------------------------------------------------
OSErr       InitializeApp               (void);
void        CleanUpApp                  (OurDMNotifyDataPtr dataP);
 
DialogPtr   SetupDialog                 (ComponentInstance engine, OurDMNotifyDataPtr dataP);
OSErr       RunEventLoop                (DialogPtr dp, ComponentInstance engine);
OSErr       HandleMouseDown             (EventRecord* theEvent, DialogPtr dp, ComponentInstance engine, Boolean *handled);
OSErr       HandleMenuSelect            (EventRecord* theEvent, ComponentInstance engine, Boolean *handled);
 
OSErr       OpenEngine                  (ComponentInstance *engine);
OSErr       FindBCEngine                (AVIDType displayID, Component *theEnginePtr);
OSErr       ResetSettings               (ComponentInstance engine, short brightness, short contrast);
OSErr       UpdateSliders               (OurDMNotifyDataPtr dataP);
static pascal void BCTargetIterator     (void* userData, DMListIndexType itemIndex, DMComponentListEntryPtr listInfo);
 
pascal OSErr AEOpenHandler              (AppleEvent *messagein, AppleEvent *reply, long refln);
pascal OSErr AEQuitHandler              (AppleEvent *messagein, AppleEvent *reply, long refIn);
 
pascal void ContrastActionProc          (ControlHandle theControl, short partCode);
pascal void BrightnessActionProc        (ControlHandle theControl, short partCode);
pascal void BrightnessContrastNotify    (void* userData, short theMessage, void* notifyData);
 
 
//----------------------------------------------------------------------------------------
// Globals
//----------------------------------------------------------------------------------------
Boolean                     gTimeToQuit             = false;
ControlActionUPP            gBrightnessSliderUPP    = NULL;     
ControlActionUPP            gContrastSliderUPP      = NULL;     
DMExtendedNotificationUPP   gDMNotifyUPP            = NULL;
DisplayIDType               gOurDisplayID;
short                       gInitialBrightness;
short                       gInitialContrast;
 
 
//****************************************************************************************
// main
//
//----------------------------------------------------------------------------------------
int main (void)
{
    OSErr               result      = noErr;
    DialogPtr           myDialog    = NULL;
    ComponentInstance   engine;
    OurDMNotifyData     data;
        
    result = InitializeApp();
    
    //--- First, we must be able to find a brightness/contrast engine ---
    if ( result == noErr )
        result = OpenEngine( &engine );
    
    //--- Store the initial engine settings in case we want to undo later ---
    if ( result == noErr )
    {
        result = ContrastEngineGetBrightness( engine, &gInitialBrightness );
        if ( result == noErr )
            result = ContrastEngineGetContrast( engine, &gInitialContrast );
    }
    
    if ( result == noErr )
    {
        //--- Bring up our dialog window ----------------------------------
        myDialog = SetupDialog( engine, &data );
            
        //--- Do the main loop -------------------------------------------
        if ( myDialog != NULL )
            result = RunEventLoop( myDialog, engine );
    }
    
    CleanUpApp( &data );
    
    return result;  
}
 
//****************************************************************************************
// InitializeApp
//
//----------------------------------------------------------------------------------------
OSErr InitializeApp (void)
{
    OSErr       result          = noErr;
    Handle      myMenu          = NULL;
    MenuHandle  appleMenuHandle = NULL; 
        
    //--- Initialize all needed managers ---------------------------------
    InitGraf(&qd.thePort);
    InitFonts();
    InitWindows();
    InitMenus();
    TEInit();
    InitDialogs(nil);
    InitCursor();
 
    //--- Required Suite -------------------------------------------------
    result = AEInstallEventHandler( kCoreEventClass, kAEOpenApplication, NewAEEventHandlerProc(AEOpenHandler), 0L, false );
    if ( result == noErr )
        result = AEInstallEventHandler( kCoreEventClass, kAEOpenDocuments, NewAEEventHandlerProc(AEOpenHandler), 0L, false );
    if ( result == noErr )
        result = AEInstallEventHandler( kCoreEventClass, kAEPrintDocuments, NewAEEventHandlerProc(AEOpenHandler), 0L, false );
    if ( result == noErr )
        result = AEInstallEventHandler( kCoreEventClass, kAEQuitApplication, NewAEEventHandlerProc(AEQuitHandler), 0L, false );
        
    //--- Initialize the Menu Bar ----------------------------------------
    if ( result == noErr )
    {
        myMenu = GetNewMBar( kMBARResID );
        SetMenuBar( myMenu );
        appleMenuHandle = GetMenuHandle( kAppleMenuResID );
        AppendResMenu( appleMenuHandle, 'DRVR' );   
        
        //--- When all is said and done, draw the menu ------------
        DrawMenuBar();
    }
    
    return result;
}
 
//****************************************************************************************
// CleanUpApp
//
//----------------------------------------------------------------------------------------
void CleanUpApp (OurDMNotifyDataPtr dataP)
{
    ProcessSerialNumber currentPSN;
 
    //--- Remove Display Manager's notification proc -------------
    GetCurrentProcess( &currentPSN );
    DMRemoveExtendedNotifyProc( gDMNotifyUPP, (void*) dataP, &currentPSN, (unsigned short) NULL);
    DisposeRoutineDescriptor( gDMNotifyUPP );
    
    //--- Dispose the other routine descriptors ------------------
    DisposeRoutineDescriptor( gBrightnessSliderUPP );
    DisposeRoutineDescriptor( gContrastSliderUPP );
    
    return;
}
 
//****************************************************************************************
// AEOpenHandler
//
//  - used to handle opendoc, openapp, and printdoc AE events
//----------------------------------------------------------------------------------------
pascal OSErr AEOpenHandler (AppleEvent *messagein, AppleEvent *reply, long refIn)
{
#pragma unused (messagein, refIn, reply)
            
    return noErr;
}
 
//****************************************************************************************
// AEQuitHandler
//
//  
//----------------------------------------------------------------------------------------
pascal OSErr AEQuitHandler (AppleEvent *messagein, AppleEvent *reply, long refIn)
{
#pragma unused (messagein, refIn, reply)
    
    gTimeToQuit = true;
    return noErr;
}
 
 
//****************************************************************************************
#pragma mark -
#pragma mark ¥ Event Handling Routines
#pragma mark -
//****************************************************************************************
 
//****************************************************************************************
// RunEventLoop
//
//  
//----------------------------------------------------------------------------------------
OSErr RunEventLoop (DialogPtr dp, ComponentInstance engine)
{
    OSErr           err         = noErr;
    Boolean         handled     = false;
    EventRecord     theEvent;
    short           itemHit;
    
    while ( err == noErr && !gTimeToQuit )
    {
        if ( WaitNextEvent(everyEvent, &theEvent, kSleepTime, NULL) )
        {
            //--- Handle events ------------------------------------
            switch (theEvent.what)
            {
                case updateEvt:         
                case activateEvt:               
                case mouseDown:         
                    if ( IsDialogEvent(&theEvent) )
                        DialogSelect(&theEvent, &dp, &itemHit);
                    else
                        err = HandleMouseDown( &theEvent, dp, engine, &handled );
                    break;
            
                case keyDown:
                case autoKey:
                    //--- We only care about Command-key shortcuts -----
                    if ( theEvent.modifiers & cmdKey )
                        err = HandleMenuSelect( &theEvent, engine, &handled );
                    break;
                                    
                case kHighLevelEvent:
                    err = AEProcessAppleEvent( &theEvent );
                    handled = true;
                    break;
                    
                case diskEvt:
                case osEvt:                 
                default:
                    break;
            }
        }
    }
        
    return err;
}
 
//****************************************************************************************
// HandleMouseDown
//
//----------------------------------------------------------------------------------------
OSErr HandleMouseDown (EventRecord* theEvent, DialogPtr dp, ComponentInstance engine, Boolean *handled)
{
    OSErr           result      = noErr;
    Boolean         wasActive   = true;
    WindowPtr       theWindow;
    short           partCode;
    
    //--- Figure out which window was hit -------------------------
    partCode = FindWindow( theEvent->where, &theWindow );
 
    //--- Figure out where the window was hit --------------------- 
    switch( partCode )
    {
        case inMenuBar:
            result = HandleMenuSelect( theEvent, engine, handled );
            break;
            
        case inSysWindow:
            SystemClick( theEvent, theWindow );
            *handled = true;
            break;
            
        case inDrag:
            {
                //--- Allow the user to drag our window around --------
                RgnHandle screenbounds = GetGrayRgn();
                DragWindow( (WindowPtr)dp, theEvent->where, &(*screenbounds)->rgnBBox );
            }
            break;
                    
        case inDesk:
        case inGrow:
        case inContent:
        case inGoAway:
        case inZoomIn:
        case inZoomOut:
            break;
            
    }
 
    return result;
}
 
//****************************************************************************************
// HandleMenuSelect
//
//----------------------------------------------------------------------------------------
OSErr HandleMenuSelect (EventRecord* theEvent, ComponentInstance engine, Boolean *handled)
{
    OSErr   result = noErr;
    long    menuVal;
    
    //--- Translate event to something useful -------------------
    if ( theEvent->modifiers & cmdKey )
        menuVal = MenuKey( theEvent->message & charCodeMask );
    else
        menuVal = MenuSelect( theEvent->where );
    
    if ( HiWord( menuVal ) == kFileMenuResID && LoWord( menuVal ) == kQuitMenuItem )
    {
        //--- The user has hit Command-Q -----------------------
        gTimeToQuit = true;
        *handled = true;
    }
    else if ( HiWord( menuVal ) == kEditMenuResID && LoWord( menuVal ) == kUndoMenuItem )
    {
        //--- The user has hit Command-Z to undo: reset the contrast/brightness 
        //--- settings to what we started with
        result = ResetSettings( engine, gInitialBrightness, gInitialContrast );
    }
 
    //--- Un-hilite the menu bar --------------------------------
    HiliteMenu( 0 );
        
    return result;
}
 
//****************************************************************************************
// UpdateSliders
//
//  
//----------------------------------------------------------------------------------------
OSErr UpdateSliders (OurDMNotifyDataPtr dataP)
{
    OSErr   result = noErr;
    short   value;
 
    //--- Get the current brightness and set the brightness slider control ----
    result = ContrastEngineGetBrightness( dataP->engine, &value );
    if ( result == noErr )
    {
        SetControlValue( dataP->brightnessCtl, value );
        
        //--- Get the current contrast and set the contrast slider control -----
        result = ContrastEngineGetContrast( dataP->engine, &value );
        if ( result == noErr )
            SetControlValue( dataP->contrastCtl, value );   
    }
            
    return result;
}
 
 
//****************************************************************************************
#pragma mark -
#pragma mark ¥ Engine Routines
#pragma mark -
//****************************************************************************************
 
//****************************************************************************************
// OpenEngine
//
//  
//----------------------------------------------------------------------------------------
OSErr OpenEngine (ComponentInstance *engine)
{
    OSErr           result      = noErr;
    GDHandle        aGDevice    = NULL;
    DisplayIDType   displayID   = kInvalidDisplayID;
    Component       bcEngine;
    
    //--- In the demo, we only mess with the main GDevice. In general, one could
    //--- use a combination of DMGetFirstScreenDevice and DMGetNextScreenDevice
    //--- (see Displays.h) to go through the exhaustive list of displays.
    aGDevice = GetMainDevice();
    if ( aGDevice != NULL )
    {
        //--- Get the DisplayID for this GDevice --------------------
        result = DMGetDisplayIDByGDevice( aGDevice, &displayID, false );
    }
    
    //--- Check for Display Manager errors
    if ( aGDevice == NULL || result != noErr )
    {
        StopAlert( kDMAlertID, NULL );
        return -1;
    }   
 
    //--- Find an engine for this DisplayID -------------------------------
    gOurDisplayID = displayID;
    result = FindBCEngine( displayID, &bcEngine );
    if ( result != noErr )
    {
        StopAlert( kComponentAlertID, NULL );
        return -2;
    }
    
    //--- Open the engine --------------------------------------------------
    *engine = OpenComponent( bcEngine );
    if ( *engine == NULL )
    {
        StopAlert( kComponentOpenAlertID, NULL );
        return -3;
    }
    
    //--- Tell the engine which display device we want it to control ----------
    result = AVEngineComponentTargetDevice( *engine, displayID );
    if ( result != noErr )
    {
        StopAlert( kComponentTargetAlertID, NULL );
        return -4;
    }   
            
    return result;  
}
 
//****************************************************************************************
// SetupDialog
//
//  
//----------------------------------------------------------------------------------------
DialogPtr SetupDialog (ComponentInstance engine, OurDMNotifyDataPtr dataP)
{
    OSErr                   result                  = noErr;
    DialogPtr               dp                      = NULL;
    ControlHandle           brightnessSliderCtl;
    ControlHandle           contrastSliderCtl;
    ProcessSerialNumber     currentPSN;
 
    //--- Grab our dialog from resource -------------------------
    dp = GetNewDialog( kDialogID, NULL, (WindowPtr) -1 );
    
    if ( ResError() == noErr && dp != NULL )
    {
        short           itemType;
        Rect            itemRect;
        Handle          itemHdl;
        short           min, max, value;
    
        SetPort( (GrafPtr) dp );
 
        //--- Set up contrast slider ------------------------------
        gContrastSliderUPP = NewControlActionProc( ContrastActionProc );
 
        GetDialogItem( dp, kContrastSliderItem, &itemType, &itemHdl, &itemRect );
        result = ContrastEngineGetContrastRange( engine, &min, &max );
        if ( result == noErr )
        {
            result = ContrastEngineGetContrast( engine, &value);
            if ( result == noErr )
            {               
                //--- Get and use the system slider procs - this is for 8.0 and later only.
                contrastSliderCtl = NewControl ( dp, 
                                                 &itemRect, 
                                                 "\p", 
                                                 false, 
                                                 value,
                                                 min, 
                                                 max, 
                                                 kControlSliderProc + kControlSliderLiveFeedback + kControlSliderNonDirectional, 
                                                 0);
        
                //--- Associate this control with our dialog and set up the control action proc
                SetDialogItem( dp, kContrastSliderItem, ctrlItem, (Handle) contrastSliderCtl, &itemRect );
                SetControlReference( contrastSliderCtl, (long) engine );
                SetControlAction( contrastSliderCtl, gContrastSliderUPP );
                ShowControl( contrastSliderCtl );
            }
        }
        if ( result != noErr )
        {
            StopAlert( kComponentMiscAlertID, NULL );
            return NULL;
        }
        
        //--- Set up brightness slider ------------------------------
        gBrightnessSliderUPP = NewControlActionProc( BrightnessActionProc );
 
        GetDialogItem( dp, kBrightnessSliderItem, &itemType, &itemHdl, &itemRect );
        result = ContrastEngineGetBrightnessRange( engine, &min, &max );
        if ( result == noErr )
        {
            result = ContrastEngineGetBrightness( engine, &value);
            if ( result == noErr )
            {               
                //--- Get and use the system slider procs - this is for 8.0 and later only.
                brightnessSliderCtl = NewControl ( dp, 
                                                   &itemRect, 
                                                   "\p", 
                                                   false, 
                                                   value,
                                                   min, 
                                                   max, 
                                                   kControlSliderProc + kControlSliderLiveFeedback + kControlSliderNonDirectional, 
                                                   0);
        
                //--- Associate this control with our dialog and set up the control action proc
                SetDialogItem( dp, kBrightnessSliderItem, ctrlItem, (Handle) brightnessSliderCtl, &itemRect);
                SetControlReference( brightnessSliderCtl, (long) engine );
                SetControlAction( brightnessSliderCtl, gBrightnessSliderUPP );
                ShowControl( brightnessSliderCtl );
            }
        }
        if ( result != noErr )
        {
            StopAlert( kComponentMiscAlertID, NULL );
            return NULL;
        }
        
        //--- Set up some stuff used by the notification function (i.e. when Display Mgr calls us)
        dataP->engine           = engine;
        dataP->dp               = dp;
        dataP->brightnessCtl    = brightnessSliderCtl;
        dataP->contrastCtl      = contrastSliderCtl;
 
        //----------------------------------------------------------------------
        // Register for notification with the Display Manager so we can update
        // the sliders if brightness or contrast changes outside of our demo app.
        // Display Mgr will call us whenever brightness or contrast change so
        // we can update our sliders to reflect the actual values.
        //----------------------------------------------------------------------
        GetCurrentProcess( &currentPSN );
        gDMNotifyUPP = NewDMExtendedNotificationProc( BrightnessContrastNotify );
        DMRegisterExtendedNotifyProc( gDMNotifyUPP, (void*) dataP, (unsigned short) NULL, &currentPSN );
        
        //--- show our dialog box ---------------------------------
        ShowWindow( (WindowPtr) dp );       
    }
    
    return dp;
}
 
//****************************************************************************************
// ResetSettings
//
//  
//----------------------------------------------------------------------------------------
OSErr ResetSettings (ComponentInstance engine, short brightness, short contrast)
{
    OSErr   result = noErr;
    
    //--- Call the engine to reset the values for brightness and contrast.
    //--- We won't redraw the sliders here: Display Mgr will notify us later
    //--- so we can update the sliders later.
    result = ContrastEngineSetBrightness( engine, brightness );
    if ( result == noErr )
        result = ContrastEngineSetContrast( engine, contrast );
        
    if ( result != noErr )
        StopAlert( kComponentMiscAlertID, NULL );
        
    return result;
}
 
//****************************************************************************************
// FindBCEngine
//
//  
//----------------------------------------------------------------------------------------
OSErr FindBCEngine (AVIDType displayID, Component *theEnginePtr)
{
    ComponentResult             result;
    DMListType                  engineList          = NULL;
    DMListIndexType             engineCount         = 0;
    DMComponentListIteratorUPP  theListIteratorUPP;
 
    //--- Pre-init the returned engine ptr ------------------------------
    *theEnginePtr = NULL;
    
#if SUPPORT_OLD_BC_ENGINES
 
    //-------------------------------------------------------------------
    // Currently, there are two types of brightness/contrast engines:
    //
    //   kContrastEngineComponentSubType
    //   kOldContrastEngineComponentSubType
    //
    // The first engine type is more general and can handle all apple
    // displays. The second engine type is meant to be used only with 
    // macs that have built-in displays (like the iMac or the all-in-one
    // PowerMac G3). Currently, the former engine type cannot control
    // brightness/contrast on the built-in monitors.
    //
    // However, the latter is being phased out, and in a little while
    // we will provide a single engine type (i.e. kContrastEngineComponentSubType)
    // that can handle all apple displays -- built-in or otherwise. At that
    // point in time, one would only need to ask for and use one single
    // engine type.
    //
    // In the meantime, we can find an appropriate engine to use with
    // any given GDevice by looking for kOldContrastEngineComponentSubType
    // first. If an engine is returned by DMNewAVEngineList, we'll know
    // that the given GDevice is a built-in display. If no engines are
    // returned, then we know that we need to look for the more general
    // kContrastEngineComponentSubType engine type. 
    //
    // Note that Apple's brightness/contrast engines do not work with
    // third-party displays.
    //-------------------------------------------------------------------
 
    result = DMNewAVEngineList( displayID,                          
                                kOldContrastEngineComponentSubType,
                                kMinimumFidelity,                   
                                0,
                                0,
                                &engineCount,
                                &engineList );
#endif
 
    //-------------------------------------------------------------------
    // DMNewAVEngineList()
    //
    //   DMNewAVEngineList is a Display Manager call that can be used to
    //   find engines that will work with a particular display. For example,
    //   in this demo app we are interested in finding a brightness/contrast
    //   engine that will work with the main GDevice. 
    //
    //   Display Manager will only return engines matching the caller's
    //   requirements. Here are some brief descriptions of each parameter:
    //
    //
    //  DMNewAVEngineList ( DisplayIDType       displayID,
    //                      ResType             engineType,
    //                      DMFidelityType      minimumFidelity,
    //                      unsigned long       engineListFlags,
    //                      unsigned long       reserved,
    //                      DMListIndexType *   engineCount,
    //                      DMListType *        engineList )
    //
    //
    //  displayID - the display ID of the display that we want an engine for.
    //
    //  engineType - the type of engine that we are interested in. For
    //               brightness/contrast engines, use the constant
    //               "kContrastEngineComponentSubType", which will return
    //               engines that can talk to Apple's displays. Currently,
    //               you'll need to specify "kOldContrastEngineComponentSubType"
    //               if you want an engine to control built-in displays like
    //               on the iMac or the all-in-one PowerMac G3. In the near
    //               future, one will be able to specify just one constant
    //               (kContrastEngineComponentSubType) and get the best 
    //               brightness/contrast engine that'll work with the given
    //               display ID without using two constants.
    //
    //  minimumFidelity - an arbitrary number used by engines to tell Display
    //                    Manager how well each engine works with the given
    //                    display. Display Manager will not return any engine
    //                    that has a lower fidelity than specified in this
    //                    parameter. In general, use "kMinimumFidelity".
    //
    //  engineListFlags - set to 0.
    //
    //  reserved - set to 0.
    //
    //  engineCount - returns the number of engines found.
    //
    //  engineList - a list of engines that match the requirements. The first
    //               engine will be the best one to use. See code below for
    //               grabbing the first engine.
    //
    //-------------------------------------------------------------------
    
    if ( engineCount <= 0 )
    {   
        //--- We couldn't find any old brightness/contrast engines. So
        //--- we'll just look for and use the normal one.
 
        //--- Clean up the engine list if necessary
        if ( engineList != NULL )
            DMDisposeList( engineList );
        
        //--- Ask DisplayMgr for a list of brightness/contrast engines ------
        //--- NOTE: DM _only_ returns engines for the given displayID -------
        result = DMNewAVEngineList( displayID, 
                                    kContrastEngineComponentSubType,
                                    kMinimumFidelity, 
                                    0, 
                                    0, 
                                    &engineCount, 
                                    &engineList);
    }
 
    //--- Did we get an engine? -----------------------------------------
    if ( result == noErr && engineCount > 0 )
    {
        theListIteratorUPP = NewDMComponentListIteratorProc(BCTargetIterator);
        
        //--- Get the first engine in list ------------------------------
        result = DMGetIndexedComponentFromList( engineList, 0, 0, theListIteratorUPP, theEnginePtr );
 
        //--- Get rid of the list routine descriptor
        DisposeRoutineDescriptor(theListIteratorUPP);
    }
    else
    {
        result = -1;
    }
 
    //--- Dispose of the list --------------------------------------------
    if ( engineList != NULL )
        DMDisposeList( engineList );
 
    return result;
}
 
//****************************************************************************************
// BCTargetIterator
//
//  
//----------------------------------------------------------------------------------------
static pascal void BCTargetIterator (void* userData, DMListIndexType itemIndex, DMComponentListEntryPtr listInfo)
{
    #pragma unused(itemIndex)
    
    *(Component *)userData = listInfo->itemComponent;
}
 
//****************************************************************************************
// BrightnessActionProc
//
//  
//----------------------------------------------------------------------------------------
pascal void BrightnessActionProc (ControlHandle theControl, short partCode)
{
#pragma unused (partCode)
 
    ComponentInstance   engine      = (ComponentInstance) GetControlReference( theControl);
    short               brightness  = GetControlValue( theControl );
    
    //--- Set the brightness. Since we can't pass back errors, just ignore any error
    ContrastEngineSetBrightness( engine, brightness );
    
    return;
}
 
//****************************************************************************************
// ContrastActionProc
//
//  
//----------------------------------------------------------------------------------------
pascal void ContrastActionProc (ControlHandle theControl, short partCode)
{
#pragma unused (partCode)
 
    ComponentInstance   engine      = (ComponentInstance) GetControlReference( theControl);
    short               contrast    = GetControlValue( theControl );
    
    //--- Set the contrast. Since we can't pass back errors, just ignore any error
    ContrastEngineSetContrast( engine, contrast );
    
    return;
}
                                                         
//****************************************************************************************
// BrightnessContrastNotify
//
//  This function is registered with Display Mgr (see SetupDialog) and is called
//  by Display Mgr whenever the contrast or the brightness changes on any display.
//  All we have to do is update our brightness and contrast sliders to
//  reflect this change. This way, if some other app changes the brightness/contrast
//  behind our backs (e.g. Monitors control panel), our sliders will pick up these
//  changes while the demo app is running.
//
//----------------------------------------------------------------------------------------
pascal void BrightnessContrastNotify (void* userData, short theMessage, void* notifyData)
{
    OurDMNotifyDataPtr      dataP = (OurDMNotifyDataPtr) userData;
    DependentNotifyPtr      dependentNotifyData = NULL;
    
    //--- If it's not a dependent notification, we don't care ------------
    if ( theMessage != kDMNotifyDependents )
        return;
    
    //--- We need the notification data for further analysis -------------
    dependentNotifyData = (DependentNotifyPtr)notifyData;
    if ( dependentNotifyData == NULL )
        return;
    
    //--- If it's not the display that we are interested in, we don't care
    if ( dependentNotifyData->notifyPortID != gOurDisplayID )
        return;
 
    //--- If it's not a brightness/contrast change or device reset, we don't care
    if ( dependentNotifyData->notifyType != kContrastChanged && 
         dependentNotifyData->notifyType != kBrightnessChanged &&
         dependentNotifyData->notifyType != kAVNotifyDeviceReset )
    {
        return;
    }
    
    //--- Update the sliders to reflect any changes. We have enough information
    //--- to only update either the brightness or the contrast slider, but
    //--- we'll be lazy and update both.
    UpdateSliders( dataP );
    
    return;
}