/*
 * AddressBookLib.idl
 *
 * Automation API for an Address Book library
 */

import "oaidl.idl";     // standard Automation definitions
import "ocidl.idl";     // standard ActiveX Control definitions

/* First section defines interfaces:
 * marshalling code generated from these
 * definitions
 */

// forward declarations of interfaces
interface DIEnum;
interface Application;
interface AddressBooks;
interface AddressBook;
interface Address;

/*
 * DIEnum interface
 * Dual Interface for simple enumerations
 */
[
    object,
    uuid(4f9dfa90-32ef-11d1-b5ac-9e4a44000000),
    dual,
    pointer_default(unique),
    helpstring("DIEnum Interface")
]
interface DIEnum : IDispatch
{
    [
        id(DISPID_VALUE)
    ]
    HRESULT NextElement([out, retval] IDispatch ** val);

    HRESULT HasMoreElements([out,retval] VARIANT_BOOL* val);
}

/*
 * Application interface
 * top-level interface for the API
 */
[
    object,
    uuid(4f9dfa91-32ef-11d1-b5ac-9e4a44000000),
    dual,
    pointer_default(unique),
    helpstring("Application Interface")
]
interface Application : IDispatch
{
    /* for Application, this just returns
     * pointer to self
     */
    [
        propget,
        helpstring("Application property")
    ]
    HRESULT Application([out,retval] Application** val);

    /* Parent, i.e. containing object
     * for Application, returns pointer to itself
     */
    [
        propget,
        helpstring("Parent property")
    ]
    HRESULT Parent([out,retval] Application** val);

    /* name of the application
     */
    [
        propget,
        id(DISPID_VALUE),
        helpstring("Application Name")
    ]
    HRESULT Name([out,retval] BSTR* val);

    /* the collection of open AddressBooks
     */
    [
        propget,
        helpstring("AddressBooks property")
    ]
    HRESULT AddressBooks([out,retval] AddressBooks** val);
}

/*
 * AddressBooks interface
 * manages a collection of AddressBook objects
 */
[
    object,
    uuid(4f9dfa96-32ef-11d1-b5ac-9e4a44000000),
    dual,
    pointer_default(unique),
    helpstring("AddressBooks Interface")
]
interface AddressBooks : IDispatch
{
    [
        propget,
        helpstring("Application property")
    ]
    HRESULT Application([out,retval] Application** val);

    [
        propget,
        helpstring("Parent property")
    ]
    HRESULT Parent([out,retval] Application** val);

    [
        propget,
        helpstring("Returns number of open AddressBooks.")
    ]
    HRESULT Count([out, retval] long* retval);

    /* used by Visual Basic's "For Each" instruction
     */
    [
        propget, 
        restricted,     // should not be visible in object browser
        id(DISPID_NEWENUM),
        helpstring("returns an enumerator for the collection.")
    ]
    HRESULT _NewEnum([out, retval] IUnknown** ret); 

    [
        helpstring("Create an AddressBook.")
    ]
    HRESULT Add([in] BSTR filename, [out,retval] AddressBook** ret);

    [
        id(DISPID_VALUE), 
        helpstring(
        "Given an address book name, returns the AddressBook.")
    ]
    HRESULT Item([in] int index, [out, retval] AddressBook** ret);

    [
        propget, 
        helpstring("returns an enumerator for the collection.")
    ]
    HRESULT Enum([out, retval] DIEnum** ret);   

    [
        helpstring("Open an existing AddressBook")
    ]
    HRESULT Open([in] BSTR filename, [out,retval] AddressBook** val);

}

/*
 * AddressBook interface
 * An AddressBook is a collection of Address entries
 */
[
    object,
    uuid(4f9dfa92-32ef-11d1-b5ac-9e4a44000000),
    dual,
    pointer_default(unique),
    helpstring("AddressBook Interface")
]
interface AddressBook : IDispatch
{
    [
        propget,
        helpstring("Application property")
    ]
    HRESULT Application([out,retval] Application** val);

    [
        propget,
        helpstring("Parent property")
    ]
    HRESULT Parent([out,retval] AddressBooks** val);

    [
        propget,
        helpstring("The file name with path for this AddressBook")
    ]
    HRESULT FullName([out,retval] BSTR* val);

    [
        propget,
        helpstring("The file name (without path) for this AddressBook")
    ]
    HRESULT Name([out,retval] BSTR* val);

    [
        propget,
        helpstring("The path (without file name) for this AddressBook")
    ]
    HRESULT Path([out,retval] BSTR* val);

    [
        propget,
        helpstring(
         "Whether the file has been saved since the last changes")
    ]
    HRESULT Saved([out,retval] VARIANT_BOOL *val);

    [
        helpstring("close the Address Book")
    ]
    HRESULT Close();

    [
        helpstring("Save changes to Address Book")
    ]
    HRESULT Save();

    [
        propget,
        helpstring("Returns number of entries.")
    ]
    HRESULT Count([out, retval] long* retval);

    [
        propget, 
        restricted, 
        id(DISPID_NEWENUM),
        helpstring("returns an enumerator for the collection.")
    ]
    HRESULT _NewEnum([out, retval] IUnknown** ret); 

    [
        helpstring("Add a new Address entry.")
    ]
    HRESULT Add([in] BSTR name, [out,retval] Address** ret);

    [
        id(DISPID_VALUE), 
        helpstring("Given a name, returns the Address entry.")
    ]
    HRESULT Item([in] BSTR name, [out, retval] Address** ret);

    [
        helpstring("Remove an Address from the collection.")
    ]
    HRESULT Remove([in] BSTR name);

    [
        propget, 
        helpstring("returns an enumerator for the collection.")
    ]
    HRESULT Enum([out, retval] DIEnum** ret);   

}

/*
 * Address Interface
 * represents a single entry in the Address Book
 */
[
    object,
    uuid(4f9dfa93-32ef-11d1-b5ac-9e4a44000000),
    dual,
    pointer_default(unique),
    helpstring("Address entry Interface")
]
interface Address : IDispatch
{
    [
        propget,
        helpstring("Application property")
    ]
    HRESULT Application([out,retval] Application** val);

    [
        propget,
        helpstring("Parent property")
    ]
    HRESULT Parent([out,retval] AddressBook** val);

    [
        propget, 
        helpstring("Name Property")
    ]
    HRESULT Name([out, retval] BSTR * val);

    [
        propput, 
        helpstring("Name Property")
    ]
    HRESULT Name([in] BSTR newval);

    [
        propget,
        helpstring("Address Property")
    ]
    HRESULT Address([out,retval] BSTR * val);

    [
        propput,
        helpstring("Address Property")
    ]
    HRESULT Address([in] BSTR newval);

    [
        propget,
        helpstring("City Property")
    ]
    HRESULT City([out,retval] BSTR * val);

    [
        propput,
        helpstring("City Property")
    ]
    HRESULT City([in] BSTR newval);

    [
        propget,
        helpstring("State Property")
    ]
    HRESULT State([out,retval] BSTR * val);

    [
        propput,
        helpstring("State Property")
    ]
    HRESULT State([in] BSTR newval);


    [
        propget,
        helpstring("Zip Property")
    ]
    HRESULT Zip([out,retval] BSTR * val);

    [
        propput,
        helpstring("Zip Property")
    ]
    HRESULT Zip([in] BSTR newval);

    [
        propget,
        helpstring("Phone Property")
    ]
    HRESULT Phone([out,retval] BSTR * val);

    [
        propput,
        helpstring("Phone Property")
    ]
    HRESULT Phone([in] BSTR newval);
}

/* The next section generates the type library.  All and only
 * those interfaces declared within the library section are
 * described in the type library.
 */
[
    uuid(4f9dfa94-32ef-11d1-b5ac-9e4a44000000),
    helpstring("AddressBook Type Library"),
    version(1.0)
]
library AddressBookLib
{
    importlib("stdole32.tlb");

    /* declaring these interfaces here forces them
     * to be described in the type library
     */
    interface Application;
    interface AddressBook;
    interface Address;
    interface DIEnum;

    /*
     * Standard Error Values
     * defined in COM
     */
    enum StdErrors
    {
        [helpstring("Unexpected failure")]
        E_UNEXPECTED = 0x8000FFFF,

        [helpstring("Not implemented")]
        E_NOTIMPL = 0x80004001,

        [helpstring("Ran out of memory")]
        E_OUTOFMEMORY = 0x8007000E,

        [helpstring("One or more arguments are invalid")]
        E_INVALIDARG = 0x80070057,

        [helpstring("No such interface supported")]
        E_NOINTERFACE = 0x80004002,

        [helpstring("Invalid pointer")]
        E_POINTER = 0x80004003,

        [helpstring("Invalid handle")]
        E_HANDLE = 0x80070006,

        [helpstring("Operation aborted")]
        E_ABORT = 0x80004004,

        [helpstring("Unspecified error")]
        E_FAIL = 0x80004005,

        [helpstring("General access denied error")]
        E_ACCESSDENIED = 0x80070005,

        [helpstring("Unknown interface")]
        DISP_E_UNKNOWNINTERFACE = 0x80020001,

        [helpstring("Member not found")]
        DISP_E_MEMBERNOTFOUND = 0x80020003,

        [helpstring("Parameter not found")]
        DISP_E_PARAMNOTFOUND = 0x80020004,

        [helpstring("Type mismatch")]
        DISP_E_TYPEMISMATCH = 0x80020005,

        [helpstring("Unknown name")]
        DISP_E_UNKNOWNNAME = 0x80020006,

        [helpstring("No named arguments")]
        DISP_E_NONAMEDARGS = 0x80020007,

        [helpstring("Bad variable type")]
        DISP_E_BADVARTYPE = 0x80020008,

        [helpstring("Exception occurred")]
        DISP_E_EXCEPTION = 0x80020009,

        [helpstring("Out of present range")]
        DISP_E_OVERFLOW = 0x8002000A,

        [helpstring("Invalid index")]
        DISP_E_BADINDEX = 0x8002000B,

        [helpstring("Unknown Locale Id")]
        DISP_E_UNKNOWNLCID = 0x8002000C,

        [helpstring("Memory is locked")]
        DISP_E_ARRAYISLOCKED = 0x8002000D,

        [helpstring("Invalid number of parameters")]
        DISP_E_BADPARAMCOUNT = 0x8002000E,

        [helpstring("Parameter not optional")]
        DISP_E_PARAMNOTOPTIONAL = 0x8002000F,

        [helpstring("Invalid callee")]
        DISP_E_BADCALLEE = 0x80020010,

        [helpstring("Does not support a collection")]
        DISP_E_NOTACOLLECTION = 0x80020011,
    };

    /*
     * Error Values:
     * These are custom HRESULT codes that can be returned
     * by the interfaces defined here
     */
    enum Errors
    {
        E_FIRST = 0x80040200,
    
        [helpstring("Index not valid for collection")]
        E_OUTOFBOUNDS,

        [helpstring("Specified Item not Found")]
        E_ITEMNOTFOUND,

        [helpstring("Error Occurred Saving File")]
        E_SAVEFAILED,

        [helpstring("File Already Exists - Can't Create it")]
        E_FILEEXISTS,

        [helpstring("File Not Found")]
        E_FILENOTFOUND,

        [helpstring("Error Occurred Loading File")]
        E_LOADFAILED
    };

    /* A COM Class (coclass) can be created via the COM
     * API.  Top-level objects are coclasses.
     */
    [
        uuid(4f9dfa95-32ef-11d1-b5ac-9e4a44000000),
        appobject,  // the Application object
        helpstring("The Application Object for the AddressBook API")
    ]
    coclass CApplication
    {
        interface Application;
    };
};
