// LexAPI.idl : IDL source for LexAPI.dll
//

// This file will be processed by the MIDL tool to
// produce the type library (LexAPI.tlb) and marshalling code.

//import "oaidl.idl";
import "ocidl.idl";

// Lexicon types supported
// Upto 32 lextypes
enum LEX_TYPE
{
   LEXTYPE_USER = 1,
   LEXTYPE_APP = 2,
   LEXTYPE_VENDOR = 4,
   LEXTYPE_GUESS = 8
}; // upto 32 lextypes

// Parts of speech currently supported
enum PART_OF_SPEECH 
{ 
	NOUN = 0,
	ADJ,
	ADV,
	VERB,
	PRPRN,
	FNME,
	DET,
	PREP,
	IJ,
	PRONOUN,
	CONJ,
	ANY,
	DEL
}; // upto 32k parts of speech

// WordInfo types currently supported
enum WORDINFOTYPE 
{ 
   PRON = 1, // includes SR_PRON and TTS_PRON
   SR_PRON = 2,
   TTS_PRON = 3,
   POS = 4
}; // upto 15 types

const LCID DONT_CARE_LCID = (LCID)-1;     // Matches with any Lcid

const DWORD MAX_STRING_LEN  = 128;        // Max length of word in lexicon in characters
const DWORD MAX_PRON_LEN = 384;           // Max length of pronunciation in lexicon in characters
const DWORD MAX_NUM_LEXINFO = 16;         // Max number of lexinfo units per word
const DWORD MAX_NUM_LANGS_SUPPORTED = 16; // Max number of LCIDs supported

// The Lex error and warning codes are derived from the following macros

//#define FACILITY_LEXICON   (FACILITY_ITF)
//#define LEXERROR(x)       MAKE_SCODE(SEVERITY_ERROR,   FACILITY_LEXICON, (x)+0x800)
//#define LEXWARNING(x)     MAKE_SCODE(SEVERITY_SUCCESS, FACILITY_LEXICON, (x)+0x800)

const DWORD LEXERR_INVALIDTEXTCHAR        = 0x80040801;   // LEXERROR(0x01);  
const DWORD LEXERR_NOTINLEX               = 0x80040803;   // LEXERROR(0x03);  
const DWORD LEXERR_LCIDNOTFOUND           = 0x8004080b;   // LEXERROR(0x0b);
const DWORD LEXERR_APPLEXNOTSET           = 0x8004080d;   // LEXERROR(0x0d);  
const DWORD LEXERR_VERYOUTOFSYNC          = 0x8004080e;   // LEXERROR(0x0e);  
const DWORD LEXERR_SETUSERLEXICON         = 0x8004080f;   // LEXERROR(0x0f);

const DWORD LEXERR_BADLCID                = 0x80040810;   // LEXERROR(0x10);
const DWORD LEXERR_BADINFOTYPE            = 0x80040811;   // LEXERROR(0x11);
const DWORD LEXERR_BADLEXTYPE             = 0x80040812;   // LEXERROR(0x12);
const DWORD LEXERR_BADINDEXBUFFER         = 0x80040813;   // LEXERROR(0x13);
const DWORD LEXERR_BADWORDINFOBUFFER      = 0x80040814;   // LEXERROR(0x14);
const DWORD LEXERR_BADWORDPRONBUFFER      = 0x80040815;   // LEXERROR(0x15);

// Holds the word-information
typedef [switch_type(short)] union _WORD_INFO_UNION
{
   [case(PRON)] 
      WCHAR wPronunciation[1];      // pronunciation - MIDL compiler does not allow for 0 length arrays in a union
   
   [case(POS)]         
      WORD POS;           // Part of Speech
   
   [default] 
      ;
} LEX_WORD_INFO_UNION;

// Holds the WordInformation and the Word Information Type
typedef struct 
{ 
   WORD Type;                                   // Type of information
   //[switch_is(Type)] LEX_WORD_INFO_UNION WI;    // Word information
   // The following union should be same as LEX_WORD_INFO_UNION above
   union
   {
      WCHAR wPronunciation[1];      // pronunciation - MIDL compiler does not allow for 0 length arrays in a union
      WORD POS;           // Part of Speech
   };
} LEX_WORD_INFO, *PLEX_WORD_INFO;

// Buffer holding indexes into word information
// The client passes in the address of a structure allocated by client with all members set to zero.
// LexAPI allocates the buffer pwIndex and sets the other members. The client can pass in this
// structure repeatedly to LexAPI. When the client is done with this structure it should 
// CoTaskMemFree pwIndex.
// When used with WORD_PRONS_BUFFER pwIndex holds indexes into WORD_PRONS_BUFFER.pwProns where the
// pronunciations start.
// When used with WORD_INFO_BUFFER pwIndex holds indexes into WORD_INFO_BUFFER.pInfo where the
// next LEX_WORD_INFO starts.
typedef struct
{
   DWORD cIndexes;            // Count of indexes used
   DWORD cWordsAllocated;     // Count of indexes allocated
   [size_is(cWordsAllocated), length_is(cIndexes)] WORD *pwIndex; // Indexes

} INDEXES_BUFFER, *PINDEXES_BUFFER;

// Buffer used to return one or more pronunciations (used with INDEXES_BUFFER)
// The client passes in the address of a structure allocated by client with all members set to zero.
// LexAPI allocates the buffer pwProns and sets the other members. The client can pass in this
// structure repeatedly to LexAPI. When the client is done with this structure it should 
// CoTaskMemFree pwProns.
typedef struct
{
   DWORD cProns;              // Count of pronunciations
   DWORD cWcharsUsed;         // Count of WCHARs used
   DWORD cWcharsAllocated;    // Count of WCHARs allocated
   [size_is(cWcharsAllocated), length_is(cWcharsUsed)] WCHAR *pwProns; // NULL separated pronunciations

} WORD_PRONS_BUFFER, *PWORD_PRONS_BUFFER;

// Buffer used to return one or more word informations (used with INDEXES_BUFFER)
// The client passes in the address of a structure allocated by client with all members set to zero.
// LexAPI allocates the buffer pInfo and sets the other members. The client can pass in this
// structure repeatedly to LexAPI. When the client is done with this structure it should 
// CoTaskMemFree pInfo.
typedef struct
{
   DWORD cInfoBlocks;         // Count of info blocks
   ULONG cBytesUsed;          // Count of bytes used in pInfo
   ULONG cBytesAllocated;     // Count of bytes allocated in pInfo

   // pInfo is an array of (variable lengthed) LEX_WORD_INFO
   // pInfo is a BYTE * rather than a PLEX_WORD_INFO because standard marshalling cannot
   // accomodate the variable lengthed LEX_WORD_INFO
   // When the client gets back this buffer it should cast pInfo to PLEX_WORD_INFO and tehn use
   // the indexes buffer to index into pInfo
   [size_is(cBytesAllocated), length_is(cBytesUsed)] BYTE * pInfo;

} WORD_INFO_BUFFER, *PWORD_INFO_BUFFER;

// Buffer in which all the changed words are returned
typedef struct
{
   DWORD cWords;                 // Count of words
   
   DWORD cWordsBytesUsed;        // Count of bytes used in pWords
   DWORD cWordsBytesAllocated;   // Count of bytes allocated in pWords
   // pWords is an array of NULL separated words
   // pInfo is a BYTE * rather than a WCHAR * because standard marshalling cannot
   // accomodate the a WCHAR * with NULLS in the string
   [size_is(cWordsBytesAllocated), length_is(cWordsBytesUsed)] BYTE *pWords;
   
   DWORD cBoolsUsed;             // Count of bools used == cWords?
   DWORD cBoolsAllocated;        // Count of bools allocated
   [size_is(cBoolsAllocated), length_is(cBoolsUsed)] BOOL *pfAdd; // array of BOOLS - TRUE for an added word

} WORD_SYNCH_BUFFER, *PWORD_SYNCH_BUFFER;

// Vendor Lexicons CLSID and LCIDs it supports
typedef struct
{
   CLSID CLSID;               // CLSID of the vendor lexicon
   DWORD cLcids;              // count of LCIDs this vendor lexicon supports
   LCID aLcidsSupported[20];  // array of LCIDs this vendor lexicon supports

} VENDOR_CLSID_LCID_HDR, *PVENDOR_CLSID_LCID_HDR;

// Vendor Lexicon Header
typedef struct
{
   VENDOR_CLSID_LCID_HDR LcidHdr;
   WCHAR wszManufacturer [128];     // Name of Manufacturer
   WCHAR wszDescription [256];      // Description

} LEX_HDR, *PLEX_HDR;

// Search state in the lexicon set by LexAPI and passed in to the low level API
// This structure is allocated by the client. All members except Lcid and dwLex should be initialized to zero.
// The Lcid should be set to specific Lcid or to a dont care Lcid and dwLex should be set to the lexicon type 
// for which the state is to be queried.
// The API will fill the rest of members when called and the result is set in hResult. When the client is done with
// this structure it should CoTaskMemFree pwWordNodes and pdwNodePositions
typedef struct
{
   LCID  Lcid;                      // The Lcid for which this info applies. Set by caller the first time API is called
   DWORD dwLex;                     // The lex flag for which this info applies. Set by caller the first time API is called
   HRESULT hResult;                 // Return code of calling the low-level API on this dwLex

   // the state   
   DWORD cUsed;                     // number of used units (WCHARs or DWORDs) in pwWordNodes/pdwNodePositions
   DWORD cAllocated;                // number of alloced units (WCHARs or DWORDs) in pwWordNodes/pdwNodePositions
   WCHAR *pwWordNodes;              // Concatentation of individual lexicon states
   DWORD *pdwNodePositions;         // positions of nodes in the lexicon states

   // the returned node if hResult is not an error
   WCHAR wNodeChar;                 // The new node - returned on calls to GetSibling() and GetChild()
   BOOL fEndofWord;                 // Does the new node mark end of word

} SEARCH_STATE, *PSEARCH_STATE;

// WORD_TOKEN is the unique word token for each word. It is the combination of lexicon id and word id.
typedef struct
{
   GUID gLexId;                     // Lexicon Id
   DWORD dwWordId;                  // Word Id

} WORD_TOKEN, *PWORD_TOKEN;

[
	object,
	uuid(4FAF16F6-F75B-11D2-9C24-00C04F8EF87C),

	helpstring("ILxLexicon Interface"),
	pointer_default(unique)
]

// ILxLexicon - Implemented by LexAPI
// Primary high level interface supported by the API to get/add/remove words and 
// their information from lexicons
interface ILxLexicon : IUnknown
{
   // Changes the user context
   // If this function is not called the 'DefaultUser" context is set
	[helpstring("method SetUser")] HRESULT SetUser(
   [in] WCHAR *pwUserName,                      // user name to set
   [in] DWORD cLcids,                           // count of Lcids
   [out, size_is(cLcids)] LCID *pLcidsSupported // the Lcids this user is interested in
   );
   
   // Gets the current user name
	[helpstring("method GetUser")] HRESULT GetUser(
   [out] WCHAR **pwUserName                     // user name to set - If the call succeeds the 
                                                // client should CoTaskMemFree *pwUserName
   );

   // Sets the application lexicon - it is not necessary for an application to set the app lexicon
   [helpstring("method SetAppLexicon")] 
   HRESULT SetAppLexicon(
   [in] WCHAR *pwPathFileName // app lexicon file name
   );
	
   // Gets the pronunciations of the word - Is a special case of GetWordInformation
   [helpstring("method GetWordPronunciations")] HRESULT GetWordPronunciations(
   [in] const WCHAR *pwWord,              // Word string
   [in] LCID lcid,                        // Lcid on which to search this word - can be DONT_CARE_LCID
   [in] DWORD dwLex,                      // OR of the LEXTYPES
   [in, out] PWORD_PRONS_BUFFER pProns,   // Buffer in which prons are returned
   [in, out] PINDEXES_BUFFER pIndexes,    // Buffer holding indexes to pronunciations
   [in, out] DWORD *pdwLexTypeFound,      // The lex type in which the word and its prons were found - can be NULL if client does not want this info
   [in, out] GUID *pGuidLexFound          // The lex GUID in which the word and its prons were found - can be NULL if client does not want this info
   );
	
   // Get the information of a word
   [helpstring("method GetWordInformation")] HRESULT GetWordInformation(
   [in] const WCHAR *pwWord,              // Word string                                              
   [in] LCID lcid,                        // Lcid on which to search this word - can be DONT_CARE_LCID
   [in] DWORD dwTypes,                    // OR of types of word information to retrieve
   [in] DWORD dwLex,                      // OR of the LEXTYPES                              
   [in, out] PWORD_INFO_BUFFER pInfo,     // Buffer in which word info are returned
   [in, out] PINDEXES_BUFFER pIndexes,    // Buffer holding indexes to pronunciations
   [in, out] DWORD *pdwLexTypeFound,      // The lex type in which the word and its prons were found - can be NULL if client does not want this info
   [in, out] GUID *pGuidLexFound          // The lex GUID in which the word and its prons were found - can be NULL if client does not want this info
   );

	// Add a word and its pronunciations
   [helpstring("method AddWordPronunciations")] HRESULT AddWordPronunciations(
   [in] const WCHAR * pwWord,             // Word to add
   [in] LCID lcid,                        // LCID of this word
   [in] PWORD_PRONS_BUFFER pProns         // Pronunciation(s) for this word
   );

   // Add a word and its information
	[helpstring("method AddWordInformation")] HRESULT AddWordInformation(
   [in] const WCHAR * pwWord,             // Word to add                   
   [in] LCID lcid,                        // LCID of this word             
   [in] PWORD_INFO_BUFFER pInfo           // Information(s) for this word
   );

   // Remove  word
	[helpstring("method RemoveWord")] HRESULT RemoveWord(
   const WCHAR* pwWord,                   // Word to remove
   LCID lcid                              // LCID of this word
   );

   // Invoke the custom (if the custom UI sink is set). If not invoke the default LexAPI UI
   [helpstring("method InvokeLexiconUI")] HRESULT InvokeLexiconUI(void);
};
	
typedef ILxLexicon *PILXLEXICON;

[
	object,
	uuid(85A9C6FE-1490-11d3-9C25-00C04F8EF87C),

	helpstring("ILxWalkStates Interface"),
	pointer_default(unique)
]

// ILxWalkStates - Implemented by API and optionally by app and vendor lexicons
// This is the low level interface to walk intra-words in the lexicons. This is supported by the API
// to walk the states of user lexicon and may optionally be supported by the app and vendor lexicons.
// This interface differs  from ILxLexicon in that while ILxLexicon works on a lexicon stack - stopping 
// the querying of lexicons on the first hit, ILxWalkStates queries all the lexicons for which 
// SEARCH_STATEs have been passed in.
// This interface is used by the Speller.
interface ILxWalkStates : IUnknown
{
   // Get the number of user, app and vendor lexicons
   // This is called by the client to get the total number of lexicons and then to allocate
   // that many SEARCH_STATEs if it wants to call the low level API on eanh of the lexicons
   [helpstring("method GetLexCount")] HRESULT GetLexCount(
   [out]DWORD *dwNumUserLex,          // number of user lexicons
   [out]DWORD *dwNumAppLex,           // number of app lexicons
   [out]DWORD *dwNumVendorLex         // number of vendor lexicons
   );

   // Get the next sibling
   // The client allocates as many SEARCH_STATEs as the number of lexicons it wants to query.
   // The client initializes all members of each SEARCH_STATE to be zero except the dwLex which
   // the clients sets to the lexicon for which this SEARCH_STATE is to be queried
   // For a lexicon type for which there is more than one lexicon like the vendor lexicon the
   // dwLex should be set to vendor lexicon for that many SEARCH_STATEs and the API will go to
   // that many vendor lexicons and gets their states
	[helpstring("method GetSibling")] HRESULT GetSibling(
   [in]DWORD dwNumSearchStates,                                // number of SEARCH_STATEs
   [in, out, size_is(dwNumSearchStates)]SEARCH_STATE *pState   // array of SEARCH_STATEs
   );

   // Get the child
   // Rest of comments as above
   [helpstring("method GetChild")] HRESULT GetChild(
   [in]DWORD dwNumSearchStates,                                // number of SEARCH_STATEs
   [in, out, size_is(dwNumSearchStates)]SEARCH_STATE *pState   // array of SEARCH_STATEs  
   );

   // Find a sibling
   [helpstring("method FindSibling")] HRESULT FindSibling(
   [in]DWORD dwNumSearchStates,                                // number of SEARCH_STATEs
   [in]WCHAR wNodeChar,                                        // the node to find
   [in, out, size_is(dwNumSearchStates)]SEARCH_STATE *pState); // array of SEARCH_STATEs 
};
	
typedef ILxWalkStates *PILXWALKSTATES;

[
    object,
    uuid(0639403D-17DF-11d3-9C25-00C04F8EF87C),
    helpstring("ILxAdvanced Interface"),
    pointer_default(unique)
]

// ILxAdvanced - Implemented by LexAPI and optionally by the app and vendor lexicons
// This interface is called by Handwriting
interface ILxAdvanced : IUnknown
{
   // Adds a word with LM probabilities distributed over the chars of the word
   HRESULT AddWordProbabilities(
   [in]WCHAR *pwWord,                              // Word to add
   [in]DWORD dwNumChars,                           // Number of characters
   [in, size_is(dwNumChars)]float *pflProb         // array of float probabilities for characters
   );
   
   // Given a string is there a word >= minimum len
   HRESULT GetWordInString(
   [in]WCHAR *pwString,                            // string of NULL terminated characters
   [in]DWORD dwMinLen,                             // minimum length of word to be found
   [out]DWORD *pdwStartChar                        // Start position (0 based) of the word in string. -1 if no word is found.
   );

   // Given a word return its token - every word has a unique ID which isa combination of Lex GUID and and a DWORD
   // This api walks down the lexicon stack querying the lexicon types specified in dwLex and stops at the first hit
   HRESULT GetWordToken(
   [in]DWORD dwLex,                                // OR of LEXTYPEs
   [in]WCHAR *pwWord,                              // Word
   [in, out]WORD_TOKEN *pWordToken                 // Word token returned
   );

   // Given a token return the word
   HRESULT GetWordFromToken(
   [in]WORD_TOKEN *pWordToken,                     // Word token
   [out]WCHAR **ppwWord                            // Returned word - should be CoTaskMemFreed by the caller
   );

   // Takes the input lattice with probabilities, adds to it the LM probabilities from lexicon and returns the best path
   // BUGBUG: Get the args right
   HRESULT GetBestPath(
   [in] BYTE *pLattice,                            // Lattice with probabilities
   [in, out] BYTE *pBestPath                       // Returned best path
   );
}

typedef ILxAdvanced *PILXADVANCED;

[
	object,
	uuid(4FAF16FD-F75B-11D2-9C24-00C04F8EF87C),
	helpstring("ILexiconObject Interface"),
	pointer_default(unique)
]

// ILxLexiconObject - Implemented by ILxLexiconObject
// ILxLexiconObject is the primary high-level interface supported by the vendor lexicon. Most of its members
// are similar to those of ILxLexicon interface
interface ILxLexiconObject : IUnknown
{
   // Get the header. This may be stored in the registry
	[helpstring("method GetHeader")] HRESULT GetHeader([out] LEX_HDR *pLexHdr);

   // Takes in a client Id. If the vendor lexicon wants to be used by this client it returns a LexId 
   // (which could be specific to a client) and marks itself as authenticated. The client subsequently
   // examines the LexId to see if it wants to use this lexicon and then communicates to LexAPI its intent
   // to use this vendor lexicon. If the LexAPI sees that a client wants to use a vendor lexicon it then calls
   // into the vendor lexicon IsAuthenticated(). If that returns TRUE the client is cleared to use the vendor lexicon
	[helpstring("method Authenticate")] HRESULT Authenticate([in] GUID ClientId, [out] GUID *LexId);

   // Returns true if this vendor lexicon is marked authenticated
	[helpstring("method IsAuthenticated")] HRESULT IsAuthenticated(BOOL *pfAuthenticated);
	
   // Similar to ILxLexicon:GetWordInformation
   [helpstring("method GetWordInformation")] HRESULT GetWordInformation([in] const WCHAR *pwWord, [in] LCID lcid, [in] DWORD dwTypes,
                                                                  [in] DWORD dwLex, [in, out] PWORD_INFO_BUFFER pInfo, [in, out] PINDEXES_BUFFER pIndexes,
                                                                  [in, out] DWORD *pdwLexTypeFound, [in, out] GUID *pGuidLexFound);
	
   // Similar to ILxLexicon:AddWordInformation - May not be supported
   [helpstring("method AddWordInformation")] HRESULT AddWordInformation([in] const WCHAR * pwWord, [in] LCID lcid, [in] PWORD_INFO_BUFFER pInfo);
	
   // Similar to ILxLexicon:RemoveWord - May not be supported
   [helpstring("method RemoveWord")] HRESULT RemoveWord([in] const WCHAR *pwWord, [in] LCID lcid);
};

typedef ILxLexiconObject *PILXLEXICONOBJECT;

[
	object,
	uuid(32C5378E-04CD-11d3-9C24-00C04F8EF87C),
	helpstring("ILxNotifySink Interface"),
	pointer_default(unique)
]

// ILxNotifySink - Implemented by the LexAPI client 
// This interface is implemented by the client which wants to be notified of changes to user and app lexicons.
// In the implementation of these functions the client sets flags and callas back into the API's ILxSynchWithLexicon
// to get the changes
interface ILxNotifySink : IUnknown
{
   // An app lexicon has been loaded
   [helpstring("method NotifyAppLexiconChange")] HRESULT NotifyAppLexiconChange(void);

   // The user lexicon has been modified
   [helpstring("method NotifyUserLexiconChange")] HRESULT NotifyUserLexiconChange(void);
}

typedef ILxNotifySink *PILXNOTIFYSINK;

[
	object,
	uuid(E8C668C2-1C7A-11d3-9C25-00C04F8EF87C),
	helpstring("ILxCustomUISink Interface"),
	pointer_default(unique)
]

// ILxNotifySink - Implemented by the LexAPI client 
// This interface is implemented by the client which wants to be to implement its own custom UI to add/modify
// words. However the client should call AddWord/RemoveWord on ILxLexicon so that the other LexAPI clients
// know of the changes
interface ILxCustomUISink : IUnknown
{
   // An app lexicon has been loaded
   [helpstring("method InvokeCustomUI")] HRESULT InvokeCustomUI(void);
}

typedef ILxCustomUISink *PILXCUSTOMUISINK;

[
	object,
	uuid(F7E615A8-1231-11d3-9C24-00C04F8EF87C),
	helpstring("ILxAuthenticateSink Interface"),
	pointer_default(unique)
]

// ILxAuthenticateSink - Implemented by the LexAPI client
// The LexAPI calls this interface to authenticate a list of vendor lexicons that the user wants to use
interface ILxAuthenticateSink : IUnknown
{
   // Checks if a client wants to use a set of vendor lexicons and vice-versa
   [helpstring("method AuthenticateVendorLexicons")] HRESULT AuthenticateVendorLexicons(
   [in] DWORD dwNumLexiconObjects,                                            // Number of lexicon objects
   [in, size_is (dwNumLexiconObjects, )] ILxLexiconObject **ppLexiconObjects, // Array of pointers to vendor lexicons
   [out, size_is (dwNumLexiconObjects)] BOOL *pbAuthenticated                 // An element of this array is set to TRUE if
                                                                              // the client wants to use the corresponding vendor lex
   );
}

typedef ILxAuthenticateSink *PILXAUTHENTICATESINK;

[
	object,
	uuid(F67C2FF9-1232-11d3-9C24-00C04F8EF87C),
	helpstring("ILxHookLexiconObject Interface"),
	pointer_default(unique)
]

// ILxHookLexiconObject - Implemented by LexAPI
// This interface enables a client to bypass parts of lexAPI functionality.
interface ILxHookLexiconObject : IUnknown
{
   // Set the hook pointer and set the scope of bypass of LexAPI functionality
   [helpstring("method SetHook")] HRESULT SetHook(
   [in] ILxLexiconObject *pLexiconObject, // The ILxLexiconObject interface to which the Get/Add/Remove calls are rerouted to by the lexAPI
   [in] BOOL fTopVendor                   // This values s considered if fExclusive is FALSE. if fTopVendor is TRUE the passed in
                                          // ILxLexiconObject* is called before calling other registered vendor lexicons. If this is FALSE
                                          // then the passed in ILxLexiconObject* is called after calling all other vendor lexicons
   );
}

typedef ILxHookLexiconObject *PILXHOOKLEXICONOBJECT;

[
   object,
   uuid(CA1C3C72-04CD-11d3-9C24-00C04F8EF87C),
   helpstring("ILxNotifySource Interface"),
   pointer_default(unique)
]

// ILxNotifySource - Implemented by LexAPI
// This interface enables a client to set the sink interface address that is set by the client
interface ILxNotifySource : IUnknown
{
   // Set the notification sink pointers
   HRESULT SetNotifySink(
   [in] ILxNotifySink *pNotifySink,             // Notification pointer to an ILxNotifySink
   [in] ILxAuthenticateSink *pAuthenticateSink, // Notification pointer to an ILxAuthenticateSink
   [in] ILxCustomUISink *pCustomUISink          // Notification pointer to an ILxCustomUISink
   );
}

typedef ILxNotifySource *PILXNOTIFYSOURCE;

[
    object,
    uuid(FCDAACEE-0954-11d3-9C24-00C04F8EF87C),
    helpstring("ILxSynchWithLexicon Interface"),
    pointer_default(unique)
]

// ILxSynchWithLexicon - Implemented by LexAPI
// This interface enables a client to synch with app lexicon and with the changes that have been made to the user lexicon
interface ILxSynchWithLexicon : IUnknown
{
    // Get the app lex id - can be used by the client to check if it has already syned to this app lexicon
    [helpstring("method GetAppLexiconID")] HRESULT GetAppLexiconID(
    [out] GUID *ID                                 // Id of the app lexicon
    );

    // Get the app lexicon's words - The client should call ILxLexicon (and set dwLex to LEXTYPE_APP) to get the words's info
    [helpstring("method GetAppLexicon")] HRESULT GetAppLexicon(
    [in] LCID Lcid,                                // LCID of the words to retrieve
    [in] GUID AppId,                               // App Lex id
    [in, out] WORD_SYNCH_BUFFER *pWordSynchBuffer  // buffer to get back the app lexicon's words
    );

    // Get the changed user lexicon's words - The client should call ILxLexicon (and set dwLex to LEXTYPE_USER) to get the words's info
    [helpstring("method GetChangedUserWords")] HRESULT GetChangedUserWords(
    [in] LCID Lcid,                                // LCID of the words to retrieve
    [in] DWORD dwAddGenerationId,                  // The current AddGenId of the client
    [in] DWORD dwDelGenerationId,                  // The current DelGenId of the client
    [out] DWORD *dwNewAddGenerationId,             // The new AddGenId of the client
    [out] DWORD *dwNewDelGenerationId,             // The new DelGenId of the client
    [in, out] WORD_SYNCH_BUFFER *pWordSynchBuffer  // The buffer to return the changed user words
    );
}

typedef ILxSynchWithLexicon *PILXSYNCHWITHLEXICON;

[
	uuid(4FAF16E8-F75B-11D2-9C24-00C04F8EF87C),
	version(1.0),
	helpstring("LexAPI 1.0 Type Library")
]
library LEXAPILib
{
	importlib("stdole32.tlb");
	importlib("stdole2.tlb");

	[
		uuid(4FAF16E7-F75B-11D2-9C24-00C04F8EF87C),
		helpstring("Lexicon Class")
	]
	coclass Lexicon
	{
		interface ILxLexicon;
      interface ILxWalkStates;
      interface ILxAdvanced;
		interface ILxLexiconObject;
		interface ILxNotifySink;
      interface ILxAuthenticateSink;
      interface ILxHookLexiconObject;
		interface ILxNotifySource;
      interface ILxSynchWithLexicon;
	};
};
