
/****************************************************************************
 * 
 * VRML 2.0 to RW3.0 Converter
 * Copyright (C) 1997 Criterion Technologies
 *
 * Author  : Damian Scallan 
 *
 * Module  : LLinkList.h
 *                                                                         
 * Purpose : Polymorphic doubly linked list + methods
 *                                                                         
 ****************************************************************************/

#ifndef LLINKLIST_H
#define LLINKLIST_H

/****************************************************************************
 Includes
 */

#include <stdlib.h>

#include "_rpvrml.h"
#include "types.h"
#include "utilities.h"

/****************************************************************************
 Defines
 */

/* callback used to destroy the link lists data */
#define DESTROYCALLBACK(func)	(void (*)(void *))(func)

/****************************************************************************
 Global Types
 */

typedef struct LLLink LLLink;
struct LLLink 
{
    LLLink *Next;
    LLLink *Prev;
    void *Data;
};

typedef struct LLinkList LLinkList;
struct LLinkList
{
    LLLink Link;
    LLLink *Iterator;
    int Items;
};



typedef void (*linkCallback) (void *);
typedef RwBool(*linkCallbackII) (LLinkList *, LLLink *);
typedef RwBool(*linkCallbackIII) (void *linkData, void *inout);
typedef void *(*copyCallBack) (void *dst, void *src);

/****************************************************************************
 Function prototypes
 */

#ifdef    __cplusplus
extern "C"
{
#endif         /* __cplusplus */

extern VRMLBool LLinkListOpen(void);
extern void LLinkListClose(void);
extern void LLLink_Init(LLLink * link);
extern LLLink *LLLink_Create(void *Data);
extern void LLLink_Destroy(LLLink * link);
extern LLLink *LLLink_GetNext(LLLink * link);
extern LLLink *LLLink_GetPrev(LLLink * link);
extern void *LLLink_GetData(LLLink * link);
extern void LLinkList_Init(LLinkList * llist);
extern VRMLBool LLinkList_IsEmpty(LLinkList * llist);
extern void LLinkList_AddLink(LLinkList * llist,
                              LLLink * link);
extern VRMLBool LLinkList_AddData(LLinkList * llist,
                                  void *data);
extern void LLinkList_RemoveLink(LLinkList * llist,
                                 LLLink * link);
extern LLLink *LLinkList_GetFirst(LLinkList * llist);
extern LLLink *LLinkList_GetLast(LLinkList * llist);
extern VRMLBool LLinkList_IsTerminator(LLinkList * llist,
                                       LLLink * link);
extern VRMLBool LLinkList_Destroy(LLinkList * list,
                                  linkCallback destroy);
extern int LLinkList_NumItems(LLinkList * list);
extern void LLinkList_Reset(LLinkList * llist);
extern VRMLBool LLinkList_ForAllLinks(LLinkList * list,
                                      linkCallback callback);
extern RwBool LLinkList_ForAllLinksII(LLinkList * list,
                                      linkCallbackII callback);
extern RwBool LLinkList_ForAllLinkData(LLinkList * list,
                                       linkCallbackIII callback,
                                       void *inout);
extern LLLink *LLinkList_IteratorReset(LLinkList * list);
extern void LLinkList_IteratorRestore(LLinkList * list,
                                      LLLink * link);
extern void *LLinkList_IteratorNext(LLinkList * list);
extern RwBool LLinkList_IteratorNextII(LLinkList * list,
                                       void *data);
extern void *LLinkList_IteratorPrev(LLinkList * list);
extern void *LLinkList_GetItem(LLinkList * list,
                               int Item);

#ifdef    __cplusplus
}
#endif         /* __cplusplus */

#endif         /* LLINKLIST_H */
