UNIT SOURCE: Control Panel Unit

        Folks,
        Recently I had to write a control panel for Win95.  The new Win32
help file contains all of the details that you need (except for being a
bit vague on the registry keys...), but the D2 "windows.dcu" doesn't define
some of the necessary structures and constants.  With a bit of research
(and the MSVC++ cpl.h header file) I have constructed a "cpl.pas" which
defines the necessary stuff to make a Delphi D2 DLL work as a Win95
control panel.  Enjoy.

                                                        Fritz
unit cpl;

interface

uses
    messages, windows;

{  CPL.PAS 96.06.18 Fritz Lowrey

        The following was ported straight from CPL.H by me.  The original
        copyright follows.

        Disclaimer: Don't blame me, I just ported it.

*****************************************************************************\
*
*
* cpl.h -       Control panel extension DLL definitions
*
*
*
*               Version 3.10
*
*
*
*               Copyright (c) 1992, Microsoft Corp.  All rights reserved
*
*
*
******************************************************************************
*  General rules for being installed in the Control Panel:
*
*      1) The DLL must export a function named CPlApplet which will handle
*         the messages discussed below.
*      2) If the applet needs to save information in CONTROL.INI minimize
*         clutter by using the application name [MMCPL.appletname].
*      2) If the applet is refrenced in CONTROL.INI under [MMCPL] use
*         the following form:
*              ...
*              [MMCPL]
*              uniqueName=c:\mydir\myapplet.dll
*              ...
*
*
*  The order applet DLL's are loaded by CONTROL.EXE is:
*
*      1) MAIN.CPL is loaded from the windows system directory.
*
*      2) Installable drivers that are loaded and export the
*         CplApplet() routine.
*
*      3) DLL's specified in the [MMCPL] section of CONTROL.INI.
*
*      4) DLL's named *.CPL from windows system directory.
*
*

Quote
}

{*
 * CONTROL.EXE will answer this message and launch an applet
 *
 * WM_CPL_LAUNCH
 *
 *      wParam      - window handle of calling app
 *      lParam      - LPSTR of name of applet to launch
 *
 * WM_CPL_LAUNCHED
 *
 *      wParam      - TRUE/FALSE if applet was launched
 *      lParam      - NULL
 *
 * CONTROL.EXE will post this message to the caller when the applet returns
 * (ie., when wParam is a valid window handle)
 *
 *}

const

     WM_CPL_LAUNCH =  (WM_USER+1000);
     WM_CPL_LAUNCHED = (WM_USER+1001);

{ A function prototype for CPlApplet() }

{
typedef LRESULT (CALLBACK *APPLET_PROC)(HWND hwndCpl, UINT msg, LPARAM
lParam1, LPARAM lParam2);

Quote
}

{ The data structure CPlApplet() must fill in. }

type
    TCPLINFO = record
             idIcon   :integer; {icon resource id, provided by CPlApplet()}
             idName   :integer; {name string res. id, provided by
CPlApplet() }
             idInfo   :integer; {info string res. id, provided by
CPlApplet() }
             lData    :longint; {user defined data }
    end;

    TPCPLINFO = ^TCPLINFO;

    TNEWCPLINFO = record
                dwSize   :longint;         { similar to the commdlg }
                dwFlags  :longint;
                dwHelpContext :longint;  { help context to use }
                lData       :longint;          {user defined data }
                hIcon       :hIcon;          { icon to use, this is owned
by CONTROL.EXE (may be deleted) }
                szName :array[0..31] of char;     { short name }
                szInfo :array[0..63] of char;     { long name (status line)

Quote
}

                szHelpFile :array[0..127] of char;{ path to help file to
use }
    end;

    TPNEWCPLINFO = ^TNEWCPLINFO;

{ The messages CPlApplet() must handle: }

const

     CPL_INIT = 1;
{  This message is sent to indicate CPlApplet() was found. */
/*  lParam1 and lParam2 are not defined. */
/*  Return TRUE or FALSE indicating whether the control panel should
proceed. }

    CPL_GETCOUNT = 2;
{  This message is sent to determine the number of applets to be displayed.
*/
/*  lParam1 and lParam2 are not defined. */
/*  Return the number of applets you wish to display in the control */
/*  panel window. }

    CPL_INQUIRE  = 3;
{  This message is sent for information about each applet. */
/*  lParam1 is the applet number to register, a value from 0 to */
/*  (CPL_GETCOUNT - 1).  lParam2 is a far ptr to a CPLINFO structure. */
/*  Fill in CPL_INFO's idIcon, idName, idInfo and lData fields with */
/*  the resource id for an icon to display, name and description string
ids, */
/*  and a long data item associated with applet #lParam1. }

    CPL_SELECT  = 4;
{  This message is sent when the applet's icon has been clicked upon. */
/*  lParam1 is the applet number which was selected.  lParam2 is the */
/*  applet's lData value. }

    CPL_DBLCLK  = 5;
{  This message is sent when the applet's icon has been double-clicked */
/*  upon.  lParam1 is the applet number which was selected.  lParam2 is the
*/
/*  applet's lData value. */
/*  This message should initiate the applet's dialog box. }

    CPL_STOP    = 6;
{  This message is sent for each applet when the control panel is exiting.
*/
/*  lParam1 is the applet number.  lParam2 is the applet's lData  value. */
/*  Do applet specific cleaning up here. }

    CPL_EXIT    = 7;
{  This message is sent just before the control panel calls FreeLibrary. */
/*  lParam1 and lParam2 are not defined. */
/*  Do non-applet specific cleaning up here. }

    CPL_NEWINQUIRE = 8;
{ this is the same as CPL_INQUIRE execpt lParam2 is a pointer to a */
/* NEWCPLINFO structure.  this will be sent before the CPL_INQUIRE */
/* and if it is responed to (return != 0) CPL_INQUIRE will not be sent}

implementation

end.

"I'll gently raise and softly call,    | Fritz Lowrey
 Goodnight my friends, and joy to all."| Internet: jlow...@ucs.usc.edu
   "A Parting Glass", Irish Traditional|