/*
	Copyright (c) 2024 PTC Inc. and/or Its Subsidiary Companies. All Rights Reserved.
*/

/*-------------------------------------------------------------*\
    Pro/Toolkit includes
\*-------------------------------------------------------------*/
#include <ProToolkit.h>
#include <ProDrawing.h>
#include <ProDtlitem.h>
#include <ProDtlnote.h>
#include <ProDtlsymdef.h>
#include <ProDtlsyminst.h>
#include <ProDtlentity.h>
#include <ProSelection.h>
#include <ProMessage.h>
#include <ProMdl.h>
#include <ProMenu.h>
#include <ProWindows.h>
#include <ProGraphic.h>

/*-------------------------------------------------------------*\
    Application includes
\*-------------------------------------------------------------*/
#include "TestError.h"
#include "UtilMessage.h"
#include "UtilString.h"
#include "UtilNames.h"
#include "UtilMenu.h"
#include "UtilMath.h"
#include <ProTKRunTime.h>

/*-------------------------------------------------------------*\
    Declaration some functions.
\*-------------------------------------------------------------*/
ProError ProTestSymDefInfo();
ProError ProTestSymDefRetrieve(ProDrawing drawing);
ProError ProTestSymDefCreate(ProDrawing drawing);
ProError ProTestSymDefModify(ProDrawing drawing);
ProError ProTestSymDefDelete(ProDrawing drawing);
ProError ProTestSymDefGet(ProDrawing drawing, ProDtlsymdef *sym_def);

/*=========================================================================*\
    Function:	ProTestSymDefMenu()
    Purpose:	Make main menu for symdef test and demo.
    Returns:	PRO_TK_NO_ERROR if success;
\*=========================================================================*/
int ProTestSymDefMenu(ProDrawing drawing)
{
    ProError error;
    int menu_id;
/*-------------------------------------------------------------*\
    Create main menu for this test
\*-------------------------------------------------------------*/
    error = ProMenuFileRegister((char*)"Symdef",(char*)"tksymdef.mnu", &menu_id);
    TEST_CALL_REPORT ("ProMenuFileRegister()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);
    
    error = ProMenubuttonActionSet((char*)"Symdef",(char*)"Info", 
	    (ProMenubuttonAction)ProTestSymDefInfo, NULL, 0);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"Symdef",(char*)"Retrieve", 
	    (ProMenubuttonAction)ProTestSymDefRetrieve, drawing, 0);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"Symdef",(char*)"Create", 
	    (ProMenubuttonAction)ProTestSymDefCreate, drawing, 0);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"Symdef",(char*)"Delete", 
	    (ProMenubuttonAction)ProTestSymDefDelete, drawing, 0);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"Symdef",(char*)"Symdef", 
	    (ProMenubuttonAction)ProMenuDelete, NULL, 0);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    error = ProMenuCreate(PROMENUTYPE_MAIN,(char*) "Symdef", &menu_id);
    TEST_CALL_REPORT ("ProMenuCreate()",
	    "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    error = ProMenuProcess((char*)"", &menu_id);
    TEST_CALL_REPORT ("ProMenuProcess()",
            "ProTestSymDefMenu()", error, error != PRO_TK_NO_ERROR);

    return (PRO_TK_NO_ERROR);
}

/*=========================================================================*\
    Function:	ProTestSymDefRetrieve()
    Purpose:	Retrive symdef from disk.
    Returns:	PRO_TK_NO_ERROR if success;
\*=========================================================================*/
ProError ProTestSymDefRetrieve(ProDrawing drawing)
{
    ProError error;
    ProDtlsymdef symdef;
    ProLine buff;
    int version;
    ProCharLine line, str;
    ProPath *path_arr, sel_path, def_path;
    ProName *path_lab_arr;
	ProMdlName w_name;
	ProMdlExtension w_type;

/*-------------------------------------------------------------*\
    Check input
\*-------------------------------------------------------------*/
    if(drawing==NULL)
	return(PRO_TK_GENERAL_ERROR);

/*-------------------------------------------------------------*\
    Define mask for retrive symdef.
    By default symdef retrive from current directory.
\*-------------------------------------------------------------*/
    ProStringToWstring(buff,(char*) "*.sym");
    ProStringToWstring(def_path,(char*) ".");

/*-------------------------------------------------------------*\
    Allocate memory for path data
\*-------------------------------------------------------------*/

    error = ProArrayAlloc(0, sizeof(ProPath), 1, (ProArray*)&path_arr);
    TEST_CALL_REPORT("ProArrayAlloc()", "ProTestSymDefRetrieve()", 
	    error, error != PRO_TK_NO_ERROR);

    error = ProArrayAlloc(0, sizeof(ProPath), 1, (ProArray*)&path_lab_arr);
    TEST_CALL_REPORT("ProArrayAlloc()", "ProTestSymDefRetrieve()", 
	    error, error != PRO_TK_NO_ERROR);

/*-------------------------------------------------------------*\
    Call OpenFile dialog.
\*-------------------------------------------------------------*/
    error = ProFileMdlnameOpen(NULL, buff, path_arr, path_lab_arr, 
	def_path, NULL, sel_path);
    TEST_CALL_REPORT("ProFileMdlnameOpen()", "ProTestSymDefRetrieve()", 
	    error, error != PRO_TK_NO_ERROR);

    ProWstringToString(line, sel_path);

    if (error == PRO_TK_NO_ERROR)
    {

/*-------------------------------------------------------------*\
    Call OpenFile dialog.
\*-------------------------------------------------------------*/
	error = ProFileMdlnameParse(sel_path, def_path, w_name, w_type, &version);
	TEST_CALL_REPORT("ProFileMdlnameParse()", "ProTestSymDefRetrieve()", 
		error, error != PRO_TK_NO_ERROR);

	ProWstringToString(str, sel_path);

/*-------------------------------------------------------------*\
    Chect file type
\*-------------------------------------------------------------*/
	if(strcmp("sym", ProWstringToString(str, w_type))==0)
	{ 
	    ProStringToWstring(def_path,(char*)".");
	    error = ProDrawingDtlsymdefRetrieve(drawing, 
		def_path, w_name, version, PRO_B_TRUE, &symdef);
	    TEST_CALL_REPORT("ProDrawingDtlsymdefRetrieve()", 
		"ProTestSymDefRetrieve()", error, error != PRO_TK_NO_ERROR);
	} else ProTKPrintf("Bad inputs: %s, %s \n",str,line);
    }

/*-------------------------------------------------------------*\
    Free memory and refresh current window
\*-------------------------------------------------------------*/
    error = ProArrayFree((ProArray*)&path_arr);
    TEST_CALL_REPORT("ProArrayFree()", "ProTestSymDefRetrieve()", 
	    error, error != PRO_TK_NO_ERROR);

    error = ProArrayFree((ProArray*)&path_lab_arr);
    TEST_CALL_REPORT("ProArrayFree()", "ProTestSymDefRetrieve()", 
	    error, error != PRO_TK_NO_ERROR);

    error = ProWindowRepaint(PRO_VALUE_UNUSED);
    TEST_CALL_REPORT("ProWindowRepaint()", "ProTestSymDefRetrieve()", 
			error, error != PRO_TK_NO_ERROR);
    return (PRO_TK_NO_ERROR);
}

/*=========================================================================*\
    Function:	ProTestSymDef_attach_add()
    Purpose:	Add new attache to symdef 
    Returns:	PRO_TK_NO_ERROR if success;
\*=========================================================================*/
ProError ProTestSymDef_attach_add(ProDrawing drawing, ProDtlsymdef *symdef,
			  ProDtlsymdefattachType type, int entity_id,   
			  double entity_param, ProVector pos)
{
    ProDtlsymdefdata entdata;
    ProDtlsymdefattach attach;
    ProError error;

/*-------------------------------------------------------------*\
    Allocate memory for symdef data.
    And setup data for add new attache.
\*-------------------------------------------------------------*/
    error = ProDtlsymdefdataAlloc(drawing, &entdata);
    TEST_CALL_REPORT ("ProDtlsymdefdataAlloc()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

    error = ProDtlsymdefDataGet(symdef, &entdata);
    TEST_CALL_REPORT ("ProDtlsymdefDataGet()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

    error = ProDtlsymdefattachAlloc(type, entity_id,
		entity_param, pos, &attach);
    TEST_CALL_REPORT ("ProDtlsymdefattachAlloc()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

    error = ProDtlsymdefdataAttachAdd(entdata, attach);
    TEST_CALL_REPORT ("ProDtlsymdefdataAttachAdd()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

/*-------------------------------------------------------------*\
    Post information to the symdef data and free memory.
\*-------------------------------------------------------------*/
    error = ProDtlsymdefModify(symdef, entdata);
    TEST_CALL_REPORT ("ProDtlsymdefModify()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

    error = ProDtlsymdefattachFree(attach);
    TEST_CALL_REPORT ("ProDtlsymdefattachFree()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

    error = ProDtlsymdefdataFree(entdata);
    TEST_CALL_REPORT ("ProDtlsymdefdataFree()",
	    "ProTestSymDef_attach_add()", error, error != PRO_TK_NO_ERROR);

    return(PRO_TK_NO_ERROR);
}

/*=========================================================================*\
    Function:	ProTestSymDef_AddItem()
    Purpose:	Copy entity or note from drawing to the symdef
    Returns:	PRO_TK_NO_ERROR if success; 
		out - handle to the new entity or note
\*=========================================================================*/
ProError ProTestSymDef_AddItem(ProDrawing drawing, ProDtlsymdef *symdef, 
			    ProDtlentity *entity, ProDtlentity *out)
{
    ProDtlentitydata data;
    ProDtlnotedata   ndata;
    ProColor color;
    ProError error;
	ProTextStyle nDataTextStyle;

/*-------------------------------------------------------------*\
    Check input
\*-------------------------------------------------------------*/
    if((symdef==NULL)||(entity==NULL))
	return(PRO_TK_GENERAL_ERROR);

/*-------------------------------------------------------------*\
    Add only entity or note
\*-------------------------------------------------------------*/
    if(((entity->type) == PRO_NOTE)||((entity->type) == PRO_DRAFT_ENTITY)) 
    {
/*-------------------------------------------------------------*\
    Add new entity to the symdef
\*-------------------------------------------------------------*/
	if((entity->type)  == PRO_DRAFT_ENTITY)
	{
	    error = ProDtlentityDataGet (entity, NULL, &data); 
	    TEST_CALL_REPORT("ProDtlentityDataGet()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);
	    if(error!=PRO_TK_NO_ERROR)
		return(PRO_TK_GENERAL_ERROR);
/*-------------------------------------------------------------*\
	    Setup entity color.
\*-------------------------------------------------------------*/
	    error = ProDtlentitydataColorGet(data, &color);
	    TEST_CALL_REPORT("ProDtlentitydataColorGet()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);

	    if (color.method == PRO_COLOR_METHOD_DEFAULT)
		color.value.type = PRO_COLOR_LETTER;

	    error = ProDtlentitydataColorSet(data, &color);
	    TEST_CALL_REPORT("ProDtlentitydataColorSet()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);
/*-------------------------------------------------------------*\
	    Create new entity
\*-------------------------------------------------------------*/
	    error = ProDtlentityCreate (drawing, symdef, data,  out);
	    TEST_CALL_REPORT("ProDtlentityCreate()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);

	    if(error!=PRO_TK_NO_ERROR)
		return(error);
/*-------------------------------------------------------------*\
	    if entity success create then show it.
\*-------------------------------------------------------------*/
#if 0
	    error = ProDtlentityShow(out);
	    TEST_CALL_REPORT("ProDtlentityShow()", "ProTestSymDef_AddItem()", 
		    error, error != PRO_TK_NO_ERROR);
#endif
	    error = ProDtlentitydataFree( data );
	    TEST_CALL_REPORT("ProDtlentitydataFree()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);
	}
    else 
	{
/*-------------------------------------------------------------*\
	    Add new note to the symdef
\*-------------------------------------------------------------*/
	    error = ProDtlnoteDataGet((ProDtlnote*)entity, NULL, PRODISPMODE_SYMBOLIC, &ndata);
	    TEST_CALL_REPORT("ProDtlnoteDataGet()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);

	    if(error!=PRO_TK_NO_ERROR)
		return(error);

/*-------------------------------------------------------------*\
	    Note color setup
\*-------------------------------------------------------------*/
		error = ProDtlnotedataTextStyleGet(ndata, &nDataTextStyle);
		TEST_CALL_REPORT("ProDtlnotedataTextStyleGet()", "ProTestSymDef_AddItem()",
			error, error != PRO_TK_NO_ERROR);

	    error = ProTextStyleColorGetWithDef(nDataTextStyle, &color);
	    TEST_CALL_REPORT("ProTextStyleColorGetWithDef()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);

	    if (color.method == PRO_COLOR_METHOD_DEFAULT)
		color.value.type =  PRO_COLOR_DRAWING;

	    error = ProTextStyleColorSetWithDef(nDataTextStyle, &color);
	    TEST_CALL_REPORT("ProTextStyleColorSetWithDef ()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);

/*-------------------------------------------------------------*\
	    Add new note to the symdef
\*-------------------------------------------------------------*/
	    error = ProDtlnoteCreate(drawing, symdef, ndata, (ProDtlnote*)out);
	    TEST_CALL_REPORT("ProDtlnoteCreate()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);
	    ProDtlnotedataFree( ndata );
	    TEST_CALL_REPORT("ProDtlnotedataFree()", "ProTestSymDef_AddItem()", 
		error, error != PRO_TK_NO_ERROR);
	}
	return(error);
    }
    return(PRO_TK_GENERAL_ERROR);
}

/*=========================================================================*\
    Function:	TestAttachType()
    Purpose:	Make menu for select symdef attache type
    Returns:	Attach Type;
\*=========================================================================*/
int TestAttachType()
{
    int menu_id, attach_type;
    ProError error;

/*-------------------------------------------------------------*\
    Make menu for select attache type 
\*-------------------------------------------------------------*/
    error = ProMenuFileRegister((char*)"AttachType",(char*)"tksymdefatac.mnu", &menu_id);
    TEST_CALL_REPORT ("ProMenuFileRegister()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);
    
    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"Free", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&attach_type, PROSYMDEFATTACHTYPE_FREE);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"Left Leader", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&attach_type, PROSYMDEFATTACHTYPE_LEFT_LEADER);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"Right Leader", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&attach_type, PROSYMDEFATTACHTYPE_RIGHT_LEADER);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"Radial Leader", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&attach_type, PROSYMDEFATTACHTYPE_RADIAL_LEADER);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"On item", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&attach_type, PROSYMDEFATTACHTYPE_ON_ITEM);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"Normal", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&attach_type, PROSYMDEFATTACHTYPE_NORM_ITEM);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"Done", 
	    (ProMenubuttonAction)ProMenuDelete, NULL, 1);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"AttachType",(char*)"AttachType", 
	    (ProMenubuttonAction)ProMenuDelete, NULL, 1);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenuCreate(PROMENUTYPE_MAIN,(char*) "AttachType", &menu_id);
    TEST_CALL_REPORT ("ProMenuCreate()",
	    "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonDeactivate((char*)"AttachType",(char*)"Done");
    TEST_CALL_REPORT ("ProMenubuttonDeactivate()",
            "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenuProcess((char*)"", &menu_id);
    TEST_CALL_REPORT ("ProMenuProcess()",
            "TestAttachType()", error, error != PRO_TK_NO_ERROR);

    return(attach_type);
}

/*=========================================================================*\
    Function:	TestHeightType()
    Purpose:	Make menu for select symdef height type
    Returns:	Height Type;
\*=========================================================================*/
int TestHeightType()
{
    ProError error;
    int menu_id, height_type; 

/*-------------------------------------------------------------*\
    Create menu for select symdef height type
\*-------------------------------------------------------------*/
    error = ProMenuFileRegister((char*)"HeightType",(char*)"tksymdefhgh.mnu", &menu_id);
    TEST_CALL_REPORT ("ProMenuFileRegister()",
	    "TestHeightType()", error, error != PRO_TK_NO_ERROR);
    
    error = ProMenubuttonActionSet((char*)"HeightType",(char*)"Fixed", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&height_type, PRODTLSYMDEFHGHTTYPE_FIXED);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	"TestHeightType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"HeightType",(char*)"Variable", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&height_type, PRODTLSYMDEFHGHTTYPE_VARIABLE);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	"TestHeightType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"HeightType",(char*)"Text related", 
	    (ProMenubuttonAction)ProUtilAssign, (ProAppData)&height_type, PRODTLSYMDEFHGHTTYPE_TEXTRELATED);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	"TestHeightType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenubuttonActionSet((char*)"HeightType",(char*)"HeightType", 
	    (ProMenubuttonAction)ProMenuDelete, (ProAppData)&height_type, PROSYMDEFATTACHTYPE_FREE);
    TEST_CALL_REPORT ("ProMenubuttonActionSet()",
	"TestHeightType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenuCreate(PROMENUTYPE_MAIN,(char*) "HeightType", &menu_id);
    TEST_CALL_REPORT ("ProMenuCreate()",
	    "TestHeightType()", error, error != PRO_TK_NO_ERROR);

    error = ProMenuProcess((char*)"", &menu_id);
    TEST_CALL_REPORT ("ProMenuProcess()",
            "TestHeightType()", error, error != PRO_TK_NO_ERROR);

    return(height_type);
}

/*=========================================================================*\
    Function:	ProTestSymDefCreate()
    Purpose:	Create new symdef, copy some notes and entity from current
                drawing, user select attache and symdef height type via menu. 
    Returns:	PRO_TK_NO_ERROR if success;
\*=========================================================================*/
ProError ProTestSymDefCreate(ProDrawing drawing)
{
    ProError error;
    ProDtlsymdef symdef;
    ProDtlsymdefdata entdata;
    ProDtlentity entity, *newent = NULL, *entitys = NULL, *p_entity;
    ProCharLine astr, astr2;
    ProPath symname;
    int n_sel, n, attach_type, dtype, height_type;
    ProPoint3d pos;
    ProMouseButton but;
    double param;
    ProSelection *p_sel;
    ProDtlentitydata dtl_entdata;
    int flg = 1;
    ProCurvedata curve;
    ProUvParam uv_param;

    ProUtilMsgPrint("gen", "TEST %0s","Symbol name [QUIT] : ");
/*-------------------------------------------------------------*\
    Prompt user for input symdef name
\*-------------------------------------------------------------*/
   if(ProMessageStringRead(PRO_PATH_SIZE, symname)!=PRO_TK_NO_ERROR)
	    return(PRO_TK_GENERAL_ERROR);    

    error = ProDtlsymdefdataAlloc(drawing, &entdata);
    TEST_CALL_REPORT("ProDtlsymdefdataAlloc()", "ProTestSymDefCreate()", 
	error, error != PRO_TK_NO_ERROR);

    if(error!=PRO_TK_NO_ERROR)
    	return(PRO_TK_GENERAL_ERROR);
#if 0
/*-------------------------------------------------------------*\
    Setup symdef name and create new symdef
\*-------------------------------------------------------------*/
    error = ProDtlsymdefdataPathSet(entdata,symname);
    TEST_CALL_REPORT("ProDtlsymdefdataPathSet()", "ProTestSymDefCreate()", 
	    error, error != PRO_TK_NO_ERROR);
#endif
    error = ProDtlsymdefCreate(drawing, entdata,  &symdef);
    TEST_CALL_REPORT("ProDtlsymdefCreate()", "ProTestSymDefCreate()", 
	error, error != PRO_TK_NO_ERROR);

    if(error!=PRO_TK_NO_ERROR)
    {
	     ProUtilMsgPrint("gen", "TEST %0s ", "Can't created symbol definition.");
	     if(entdata!=NULL)
	     {
	         error = ProDtlsymdefdataFree(entdata);
	         TEST_CALL_REPORT("ProDtlsymdefdataFree()", "ProTestSymDefCreate()", 
		     error, error != PRO_TK_NO_ERROR);
	     }
	     return(PRO_TK_GENERAL_ERROR);
    }

    ProTKSprintf(astr," Created symbol definition: %s", ProWstringToString(astr2, symname));
    ProUtilMsgPrint("gen", "TEST %0s ", astr);
    ProUtilMsgPrint("gen", "TEST %0s","Select items to be in the symbol definition");

/*-------------------------------------------------------------*\
    Copy some entity and note from drawing to the symdef.
\*-------------------------------------------------------------*/

    ProSelect((char*)"any_note,draft_ent",-1,  NULL, NULL, NULL, NULL, &p_sel, &n_sel);
    entitys = (ProDtlentity*)calloc(n_sel, sizeof(ProDtlentity));
    newent  = (ProDtlentity*)calloc(n_sel, sizeof(ProDtlentity));

/*-------------------------------------------------------------*\
    For all the selected items, remember the item type and id,
    add it to the symbol definition, and remember the id it
    has in the symbol.
\*-------------------------------------------------------------*/
    for(n=0;n<n_sel;n++)
    {
	error = ProSelectionModelitemGet(p_sel[n], (ProModelitem *)&entity);

	error = ProTestSymDef_AddItem(drawing, &symdef, &entity, &newent[n]);
	memcpy(&entitys[n], &entity, sizeof(ProDtlentity));  
    }

/*-------------------------------------------------------------*\
    Get attach type
\*-------------------------------------------------------------*/
    attach_type = TestAttachType();

    if (attach_type == -1)
    	attach_type = PROSYMDEFATTACHTYPE_FREE;

    switch(attach_type)
    {
    case PROSYMDEFATTACHTYPE_FREE :
/*-------------------------------------------------------------*\
	Just select the (free) origin of the symbol definition
\*-------------------------------------------------------------*/
	ProUtilMsgPrint("gen", "TEST %0s","Select symbol origin");

	error = ProMousePickGet(PRO_ANY_BUTTON, &but, pos);
        TEST_CALL_REPORT ("ProMousePickGet()",
	       "ProTestSymDef_attach()", error, error != PRO_TK_NO_ERROR);

        if(error!=PRO_TK_NO_ERROR)
	    return(PRO_TK_NO_ERROR);
/*-------------------------------------------------------------*\
	Add free attach 
\*-------------------------------------------------------------*/
        ProTestSymDef_attach_add(drawing, &symdef, (ProDtlsymdefattachType)attach_type, -1, 0.0, pos);
	break;

    case PROSYMDEFATTACHTYPE_LEFT_LEADER :
    case PROSYMDEFATTACHTYPE_RIGHT_LEADER :
    case PROSYMDEFATTACHTYPE_ON_ITEM :
    case PROSYMDEFATTACHTYPE_NORM_ITEM :
/*-------------------------------------------------------------*\
	Select the entity in the sym defn. that represents the
	attachment point.
\*-------------------------------------------------------------*/
	ProUtilMsgPrint("gen", "TEST %0s","Select attachment point");
	while(flg == 1)
	{
	    p_entity = NULL;
    	    
		if(ProSelect((char*)"draft_ent",1,NULL,NULL,NULL,NULL,&p_sel,&n_sel) < 1) 
			break;
		error = ProSelectionModelitemGet(p_sel[n], &entity);

		dtype = entity.type;

		for(n=0; n<n_sel; n++)
		{
			if((entity.id == entitys[n].id)&&(dtype == entitys[n].type))
			{
				p_entity = &newent[n];
				break;
			}

		}

	    if(p_entity == NULL)
	    	ProUtilMsgPrint("gen", "TEST %0s","That item is not part of the symbol");
	    else
		break;
	}
	if(p_entity == NULL)
	{
/*-------------------------------------------------------------*\
    Define all data for create new attach
\*-------------------------------------------------------------*/
		ProSelectionPoint3dGet(p_sel[0], pos);
		ProSelectionUvParamGet(p_sel[0], uv_param);
		param = uv_param[0];
	    ProTestSymDef_attach_add(drawing, &symdef, (ProDtlsymdefattachType)attach_type, 
		    p_entity->id, param, pos);
	}

	break;
    case PROSYMDEFATTACHTYPE_RADIAL_LEADER :
/*-------------------------------------------------------------*\
	The attachment type if RADIAL, so select a circle
\*-------------------------------------------------------------*/
	ProUtilMsgPrint("gen", "TEST %0s","Select circle");
	while(flg == 1)
	{
	    p_entity = NULL;

	    if(ProSelect((char*)"draft_ent",1,NULL,NULL,NULL,NULL,&p_sel,&n_sel) < 1) 
	    {
		ProUtilMsgPrint("gen", "TEST %0s","Have't selected entity");
		break;
	    }
	
		error = ProSelectionModelitemGet(p_sel[n], &entity);

		dtype = entity.type;
		
		for(n=0;n<n_sel;n++)
		{
			if((entity.id == entitys[n].id)&&(dtype == entitys[n].type))
			{
				p_entity = &newent[n];
				break;
			}

		}

	    if(p_entity == NULL)
	    	ProUtilMsgPrint("gen", "TEST %0s","That item is not part of the symbol");
	    else
	    {
			ProDtlentityDataGet(&entity, NULL, &dtl_entdata);
			ProDtlentitydataCurveGet(dtl_entdata, &curve);

/*-------------------------------------------------------------*\
    Check - selected entity must be circle
\*-------------------------------------------------------------*/
		if(curve.arc.type == PRO_ENT_ARC &&
		   curve.arc.start_angle <= EPSM10 &&
		   curve.arc.end_angle >= (TWOPI - EPSM10))
		    break;
		else
		    ProUtilMsgPrint("gen", "TEST %0s","That is not a circle");
	    }
	}
	if(p_entity!=NULL)
	{

/*-------------------------------------------------------------*\
    Define all data for create new attach
\*-------------------------------------------------------------*/

		ProSelectionPoint3dGet(p_sel[0], pos);
		ProSelectionUvParamGet(p_sel[0], uv_param);
		param = uv_param[0];

	    ProTestSymDef_attach_add(drawing, &symdef, (ProDtlsymdefattachType)attach_type, 
		    p_entity->id, param, pos);
	}

	break;
    } /* End of case statement */

    error = ProMenubuttonActivate((char*)"AttachType",(char*)"Done");
/*-------------------------------------------------------------*\
    Setup ELBOW property for created symdef
\*-------------------------------------------------------------*/
    if((attach_type == PROSYMDEFATTACHTYPE_RIGHT_LEADER)||(attach_type == PROSYMDEFATTACHTYPE_LEFT_LEADER))
    {
	ProUtilMsgPrint("gen", "TEST %0s", "Enable elbow (y/n)");
	error = ProDtlsymdefdataElbowSet(entdata, (ProBoolean)ProUtilYesnoGet((char*)"Y"));
	TEST_CALL_REPORT("ProDtlsymdefdataElbowSet()", "ProTestSymDefCreate()", 
		error, error != PRO_TK_NO_ERROR);
    }

/*-------------------------------------------------------------*\
    Select the type of height : FIXED, VARIABLE, or TEXT-RELATED
\*-------------------------------------------------------------*/
    height_type = TestHeightType();

    if (height_type == -1) height_type = PRODTLSYMDEFHGHTTYPE_FIXED;

    error = ProDtlsymdefDataGet(&symdef,&entdata);
    TEST_CALL_REPORT("ProDtlsymdefDataGet()", "ProTestSymDefCreate()", 
	error, error != PRO_TK_NO_ERROR);

/*-------------------------------------------------------------*\
    If the height type is TEXT_RELATED, select the text
\*-------------------------------------------------------------*/
    if(error==PRO_TK_NO_ERROR)
    {
	if(height_type == PRODTLSYMDEFHGHTTYPE_TEXTRELATED)
	{
	    ProUtilMsgPrint("gen", "TEST %0s","Select textl");
	    while(flg == 1)
	    {
		p_entity = NULL;
		
		if(ProSelect((char*)"any_note",1,NULL,NULL,NULL,NULL,&p_sel,&n_sel) < 1) 
			break;
/*-------------------------------------------------------------*\
    Check note, selected note must included in to the new symdef
\*-------------------------------------------------------------*/
		
		error = ProSelectionModelitemGet(p_sel[n], &entity);

		dtype = entity.type;

		for(n=0;n<n_sel;n++)
		{
			if((entity.id == entitys[n].id)&&(PRO_NOTE == entitys[n].type))
			{
				p_entity = &newent[n];
				break;
			}

		}

		/* for n*/
		if(p_entity == NULL)
		    ProUtilMsgPrint("gen", "TEST %0s","That note is not part of the symbol");
		else
		    break;

	    }/* while (1) */

	    if(p_entity!=NULL)
	    {
/*-------------------------------------------------------------*\
    Setup text reference to the first text string in selected note. 
\*-------------------------------------------------------------*/
		error = ProDtlsymdefdataTextrefSet(entdata, p_entity->id,0,0); 
		TEST_CALL_REPORT("ProDtlsymdefdataTextrefSet()", 
		"ProTestSymDefCreate()", error, error != PRO_TK_NO_ERROR);
	    } else 
	    {   
		ProUtilMsgPrint("gen", "TEST %0s","Set defaul height type: Fixed");
		height_type = PRODTLSYMDEFHGHTTYPE_FIXED;
	    }

	}/* if PRODTLSYMDEFHGHTTYPE_TEXTRELATED */

	error = ProDtlsymdefdataHeighttypeSet(entdata, (ProDtlsymdefdataHeighttype)height_type);
	TEST_CALL_REPORT("ProDtlsymdefdataHeighttypeSet()", "ProTestSymDefCreate()", 
	    error, error != PRO_TK_NO_ERROR);

/*-------------------------------------------------------------*\
    Post all chenges to the new symdef
\*-------------------------------------------------------------*/
	error = ProDtlsymdefModify(&symdef, entdata);
	TEST_CALL_REPORT("ProDtlsymdefModify()", "ProTestSymDefCreate()", 
	    error, error != PRO_TK_NO_ERROR);

    }/* if PRO_TK_NO_ERROR */

/*-------------------------------------------------------------*\
    Free all temporary variables
\*-------------------------------------------------------------*/
    if(entdata!=NULL)
    {
	error = ProDtlsymdefdataFree(entdata);
	TEST_CALL_REPORT("ProDtlsymdefdataFree()", "ProTestSymDefCreate()", 
	    error, error != PRO_TK_NO_ERROR);
    }

    if(entitys!=NULL)
    {
	free(entitys);
	entitys = NULL;
    }

    if(newent!=NULL)
    {
	free(newent);
	entitys = NULL;
    }

    return(PRO_TK_NO_ERROR);
}

/*=========================================================================*\
    Function:	ProTestSymDefDelete()
    Purpose:    Delete selected symdef from current drawing. 
    Returns:	PRO_TK_NO_ERROR if success;
\*=========================================================================*/
ProError ProTestSymDefDelete(ProDrawing drawing)
{
    ProError error;
    ProDtlsymdef sym_def;

    ProUtilMsgPrint("gen", "TEST %0s", "Not implemented" );

#if 0
    ProUtilMsgPrint("gen", "TEST %0s", "Select Symdef for delete.");

/*-------------------------------------------------------------*\
    Select symdef for delete.
\*-------------------------------------------------------------*/
    error = ProTestSymDefGet (drawing, &sym_def);

    if(error!=PRO_TK_NO_ERROR)
	return(PRO_TK_GENERAL_ERROR);

    ProUtilMsgPrint("gen", "TEST %0s", "Are you sure ? (y/n)");
    if (!ProUtilYesnoGet("N"))
		return(PRO_TK_NO_ERROR); 

/*-------------------------------------------------------------*\
    Delete selected symdef.
\*-------------------------------------------------------------*/
    error = ProDtlsymdefDelete(&sym_def);
    TEST_CALL_REPORT("ProDtlsymdefDelete()",
        "ProTestSymDefDelete()", error, error != PRO_TK_NO_ERROR);

    if(error==PRO_TK_NO_ERROR)
	    ProUtilMsgPrint("gen", "TEST %0s", "Symdef success deleted");
    else
	    ProUtilMsgPrint("gen", "TEST %0s", "Error ! ");
#endif

    return(PRO_TK_NO_ERROR);
}