/*===========================================================================*\
FILE :   ProTestDrwInfo.c
PURPOSE: Drawing - demo & ProTest
 
HISTORY:
DATE               AUTHOR      MODIFICATIONS
20-Oct-99 I-03-20   akh         $$1    Created
\*===========================================================================*/
#include <ProDrawing.h>
#include <ProMessage.h>
#include <ProMdl.h>
#include <ProModelitem.h>
#include <ProWindows.h>
#include <ProDwgtable.h>

#include "UtilString.h"
#include "UtilFiles.h"

/*--------------------------------------------------------------------*\
  Function prototypes
\*--------------------------------------------------------------------*/
typedef struct tag_TestViewVisitData
{
    FILE        *fp;
    ProDrawing  drawing;
    int         count;
}ProTestViewVisitData;

/*===========================================================================*\
  FUNCTION: ProTestViewFilterAction
  PURPOSE:  
\*===========================================================================*/
ProError ProTestViewFilterAction (
    ProDrawing  drawing,
    ProView     view,
    ProAppData  data)
{
    TEST_CALL_REPORT ("ProViewFilterAction()", "ProTestViewFilterAction()",
        PRO_TK_NO_ERROR, 0);
    return (PRO_TK_NO_ERROR);
}

/*===========================================================================*\
  FUNCTION: ProTestSolidFilterAction
  PURPOSE:  
\*===========================================================================*/
ProError ProTestSolidFilterAction (
    ProSolid    solid,
    ProAppData  data)
{
    TEST_CALL_REPORT ("ProSolidFilterAction()", "ProTestSolidFilterAction()",
        PRO_TK_NO_ERROR, 0);
    return(PRO_TK_NO_ERROR);
}

/*===========================================================================*\
  FUNCTION: ProTestDwgtableFilterAction
  PURPOSE:  
\*===========================================================================*/
ProError ProTestDwgtableFilterAction (
    ProDwgtable *table,
    ProAppData  data)
{
    TEST_CALL_REPORT ("ProDwgtableFilterAction()",
        "ProTestDwgtableFilterAction()", PRO_TK_NO_ERROR, 0);
    return(PRO_TK_NO_ERROR);
}

/*===========================================================================*\
  FUNCTION: ProTestViewVisitAction
  PURPOSE:  
\*===========================================================================*/
ProError ProTestViewVisitAction (
    ProDrawing  drawing,
    ProView     view, 
    ProError    filter_status, 
    ProAppData  data)
{
    int                     id;
    char                    c_name[PRO_LINE_SIZE];
    double                  scale;
    ProError                status;
    ProMdldata              mdldata;
    ProSolid                solid;
    ProTestViewVisitData   *data_ptr = (ProTestViewVisitData*)data;

    data_ptr->count++;

    status = ProDrawingViewScaleGet (drawing, view, &scale);
    TEST_CALL_REPORT ("ProDrawingViewScaleGet()",
        "ProTestViewVisitAction()", status, status!=PRO_TK_NO_ERROR);

    status = ProDrawingViewSolidGet (drawing, view, &solid);
    TEST_CALL_REPORT ("ProDrawingViewSolidGet()",
        "ProTestViewVisitAction()", status, status!=PRO_TK_NO_ERROR);

    status = ProMdlDataGet (solid, &mdldata);
    TEST_CALL_REPORT ("ProMdlDataGet()",
        "ProTestViewVisitAction()", status, status!=PRO_TK_NO_ERROR);

    status = ProMdlIdGet (solid, &id);
    TEST_CALL_REPORT ("ProMdlIdGet()",
        "ProTestViewVisitAction()", status, status!=PRO_TK_NO_ERROR);

    if (solid != NULL)
    {
        fprintf (data_ptr->fp,
            "[%d] Solid name: %s; solid type: %s;\n"
            "     solid id: %d; view scale: %3.3f;\n",
            data_ptr->count,
            ProWstringToString (c_name, mdldata.name),
            ProWstringToString (c_name, mdldata.type),
            id,
            scale);
    }
    else
    {
        fprintf(data_ptr->fp,
            "[%d] view scale: %3.3f;\n", data_ptr->count, scale);
    }
    return(PRO_TK_NO_ERROR);
}

/*===========================================================================*\
  FUNCTION: ProTestSolidVisitAction
  PURPOSE:  
\*===========================================================================*/
ProError ProTestSolidVisitAction (
    ProSolid   solid,
    ProError   filter_status,  
    ProAppData data)
{
    int                     i, num, id;
    char                    c_name[PRO_LINE_SIZE];
    ProError                status;
    ProMdldata              mdl_data;
    ProTestViewVisitData   *data_ptr       = (ProTestViewVisitData*)data;
    ProSimprep             *simpreps       = NULL;
    
    data_ptr->count++;
        
    status = ProMdlDataGet (solid, &mdl_data);
    TEST_CALL_REPORT ("ProMdlDataGet()", "ProTestSolidVisitAction()",
        status, status!=PRO_TK_NO_ERROR);

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

    status = ProMdlIdGet(solid, &id);
    TEST_CALL_REPORT ("ProMdlIdGet()", "ProTestSolidVisitAction()",
        status, status!=PRO_TK_NO_ERROR);

    fprintf (data_ptr->fp,
        "[%d] Name: %s; type: %s; id: %d;\n",
        data_ptr->count,
        ProWstringToString (c_name, mdl_data.name),
        ProWstringToString (c_name, mdl_data.type),
        id);

/*--------------------------------------------------------------------*\
        Simp reps
\*--------------------------------------------------------------------*/
    status = ProDrawingSimprepsCollect (data_ptr->drawing,
        solid, &simpreps);
    TEST_CALL_REPORT ("ProDrawingSimprepsCollect()",
        "ProTestSolidVisitAction()", status, status!=PRO_TK_NO_ERROR);

    if (status == PRO_TK_NO_ERROR)
    {
        fprintf (data_ptr->fp, "\tSimpreps:\n");
        status = ProArraySizeGet ((ProArray)simpreps, &num);
        TEST_CALL_REPORT ("ProArraySizeGet()", "ProTestSolidVisitAction()",
            status, status!=PRO_TK_NO_ERROR);

        for (i=0; i<num; i++)
        {                    
            fprintf (data_ptr->fp, "\t[%d] Id: %d.\n",
                i+1, simpreps[i].id);
        }

        status = ProArrayFree ((ProArray*)&simpreps);
        TEST_CALL_REPORT ("ProArrayFree()", "ProTestSolidVisitAction()",
            status, status!=PRO_TK_NO_ERROR);
    }
    return(PRO_TK_NO_ERROR);
}

/*===========================================================================*\
  FUNCTION: ProTestDwgtableVisitAction
  PURPOSE:  
\*===========================================================================*/
ProError ProTestDwgtableVisitAction (
    ProDwgtable *table,
    ProError    filter_status,
    ProAppData  data)
{
    int                     n_col, n_row;
    ProError                status;
    ProBoolean              from_frm;
    ProTestViewVisitData   *data_ptr = (ProTestViewVisitData*)data;

    data_ptr->count++;
        
    status = ProDwgtableColumnsCount(table, &n_col);
    TEST_CALL_REPORT ("ProDwgtableColumnsCount()",
        "ProTestDwgtableVisitAction()", status, status!=PRO_TK_NO_ERROR);

    status = ProDwgtableRowsCount(table, &n_row);
    TEST_CALL_REPORT ("ProDwgtableRowsCount()",
        "ProTestDwgtableVisitAction()", status, status!=PRO_TK_NO_ERROR);

    status = ProDwgtableIsFromFormat(table, &from_frm);
    TEST_CALL_REPORT ("ProDwgtableIsFromFormat()",
        "ProTestDwgtableVisitAction()", status, status!=PRO_TK_NO_ERROR);

    fprintf (data_ptr->fp,
        "[%d] columns: %d; rows: %d;%s associated with the format.\n",
        data_ptr->count,
        n_col,
        n_row,
        (from_frm)?(""):("Not "));

    return(PRO_TK_NO_ERROR);
}

/*===========================================================================*\
  Function : ProTestDrwGetPlotSize
  Purpose  : To get size of sheet 
\*===========================================================================*/
char* ProTestDrwGetPlotSize (ProPlotPaperSize type)
{
    switch (type)
    {
       case A_SIZE_PLOT         : return "A";
       case B_SIZE_PLOT         : return "B";
       case C_SIZE_PLOT         : return "C";
       case D_SIZE_PLOT         : return "D";
       case E_SIZE_PLOT         : return "E";
       case A4_SIZE_PLOT        : return "A4";
       case A3_SIZE_PLOT        : return "A3";
       case A2_SIZE_PLOT        : return "A2";
       case A1_SIZE_PLOT        : return "A1";
       case A0_SIZE_PLOT        : return "A0";
       case F_SIZE_PLOT         : return "F";
       case VARIABLE_SIZE_PLOT  : return "VARIABLE SIZE";
       default                  : return "Unknown";
    }
}

/*===========================================================================*\
  Function : ProTestDrwGetSheetOrient
  Purpose  : To get orientation of sheet 
\*===========================================================================*/
char* ProTestDrwGetSheetOrient (int orient)
{
    switch (orient)
    {
       case -1  : return "Variable";
       case 0   : return "Landscape";
       case 1   : return "Portrait";
       default  : return "Unknown";
    }
}

/*===========================================================================*\
  FUNCTION: ProTestDrawingInfo
  PURPOSE:  
\*===========================================================================*/
ProError ProTestDrawingInfo ()
{
    char                    file_name [PRO_PATH_SIZE+1];
    int                     n_sheets, i, num;
    ProError                status;
    ProTestViewVisitData    visit_data ={NULL, 0};
    FILE                   *info_file  = NULL;
    ProPath                 w_path;
    ProDrawing              drawing;
    ProDrawingSheetInfo     sheet_info;
#if 1
    ProSolid                *solids    = NULL;
    ProView                 *views     = NULL;
    ProDwgtable             *tables    = NULL;
#endif

    status = ProMdlCurrentGet ((ProMdl*)&drawing);

    ProUtilMsgPrint ("gen", "TEST %0s", "Enter name of file:");
    status = ProMessageStringRead (PRO_PATH_SIZE, w_path);
    
    if (status != PRO_TK_NO_ERROR)
        return -1;
    
    ProWstringToString (file_name, w_path);

    if ((info_file=fopen(file_name, "w")) == NULL)
    {
        printf ("Cannot open output file.\n");
        return (-1);
    }
    
    visit_data.fp = info_file;
    visit_data.drawing = drawing;

    fprintf (info_file,
        "-------------------Drawing information------------------\n\n");

/*--------------------------------------------------------------------*\
    Sheets
\*--------------------------------------------------------------------*/
    fprintf(info_file, "Sheets:\n");
    status = ProDrawingSheetsCount (drawing, &n_sheets);
    TEST_CALL_REPORT ("ProDrawingSheetsCount()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR);
    
    for (i=0; i<n_sheets; i++)
    {
        status = ProDrawingSheetInfoGet (drawing, i, &sheet_info);
        TEST_CALL_REPORT ("ProDrawingSheetInfoGet()",
            "ProTestDrawingInfo()", status, status != PRO_TK_NO_ERROR);
    
        fprintf(info_file, 
            "[%d] DwgSize: %s; width:%d; height:%d; units:%d; orientation: %s\n",
            i+1, 
            ProTestDrwGetPlotSize (sheet_info.type),
            sheet_info.width, 
            sheet_info.height, 
            sheet_info.units, 
            ProTestDrwGetSheetOrient (sheet_info.orientation));
    }

/*--------------------------------------------------------------------*\
    Solids
\*--------------------------------------------------------------------*/
    fprintf(info_file, "Solids:\n");
    visit_data.count = 0;
#if 0
    status = ProDrawingSolidsVisit (drawing,
                (ProSolidVisitAction)ProTestSolidVisitAction,
                (ProSolidFilterAction)ProTestSolidFilterAction,
                (ProAppData)&visit_data);
    TEST_CALL_REPORT ("ProDrawingSolidsVisit()",
        "ProTestDrawingInfo()", status, status!=PRO_TK_NO_ERROR);
#else
    status = ProDrawingSolidsCollect (drawing, &solids);
    TEST_CALL_REPORT ("ProDrawingSolidsCollect()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR);
        
    if (status == PRO_TK_NO_ERROR)
    {
        /*status!=PRO_TK_GENERAL_ERROR until solids cotrrupt.*/
        
        status = ProArraySizeGet ((ProArray)solids, &num);
        TEST_CALL_REPORT ("ProArraySizeGet()", "ProTestDrawingInfo()",
            status, status!=PRO_TK_NO_ERROR && status!=PRO_TK_BAD_INPUTS);
            
        for (i=0; i<num; i++)
        {
            status = ProTestSolidVisitAction (
                        solids[i], PRO_TK_NO_ERROR, &visit_data);
        }
        
        status = ProArrayFree ((ProArray*)&solids);
        TEST_CALL_REPORT ("ProArrayFree()", "ProTestDrawingInfo()",
            status, status!=PRO_TK_NO_ERROR && status!=PRO_TK_BAD_INPUTS);
    }
#endif
    
/*--------------------------------------------------------------------*\
    Views
\*--------------------------------------------------------------------*/
    fprintf(info_file, "Views:\n");

    visit_data.count = 0;
#if 0
    status = ProDrawingViewVisit (drawing,
                (ProViewVisitAction)ProTestViewVisitAction,
                (ProViewFilterAction)ProTestViewFilterAction,
                (ProAppData)&visit_data);
    TEST_CALL_REPORT ("ProDrawingViewVisit()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR);
#else
    status = ProDrawingViewsCollect (drawing, &views);
    TEST_CALL_REPORT ("ProDrawingViewsCollect()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR);
        
    if (status == PRO_TK_NO_ERROR)
    {
        status = ProArraySizeGet ((ProArray)views, &num);
        TEST_CALL_REPORT ("ProArraySizeGet()", "ProTestDrawingInfo()",
            status, status!=PRO_TK_NO_ERROR);
            
        for (i=0; i<num; i++)
        {
            status = ProTestViewVisitAction (drawing,
                        views[i], PRO_TK_NO_ERROR, &visit_data);
        }
        
        status = ProArrayFree ((ProArray*)&views);
        TEST_CALL_REPORT ("ProArrayFree()", "ProTestDrawingInfo()",
            status, status!=PRO_TK_NO_ERROR);
    }
#endif

/*--------------------------------------------------------------------*\
    Tables
\*--------------------------------------------------------------------*/
    fprintf(info_file,"Tables:\n");
    visit_data.count = 0;
#if 0
    status = ProDrawingTableVisit (drawing,
                (ProDwgtableVisitAction)ProTestDwgtableVisitAction,
                (ProDwgtableFilterAction)ProTestDwgtableFilterAction,
                (ProAppData)&visit_data);
    TEST_CALL_REPORT ("ProDrawingTableVisit()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR);
#else
    status = ProDrawingTablesCollect (drawing, &tables);
    TEST_CALL_REPORT ("ProDrawingTablesCollect()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR && status!=PRO_TK_E_NOT_FOUND);
        
    if (status == PRO_TK_NO_ERROR)
    {
        status = ProArraySizeGet ((ProArray)tables, &num);
        TEST_CALL_REPORT ("ProArraySizeGet()", "ProTestDrawingInfo()",
            status, status!=PRO_TK_NO_ERROR);
            
        for (i=0; i<num; i++)
        {
            status = ProTestDwgtableVisitAction (
                        &tables[i], PRO_TK_NO_ERROR, &visit_data);
        }
        
        status = ProArrayFree ((ProArray*)&tables);
        TEST_CALL_REPORT ("ProArrayFree()", "ProTestDrawingInfo()",
            status, status!=PRO_TK_NO_ERROR);
    }
#endif
    fprintf (info_file,
        "--------------------------------------------------------\n");

    fclose(info_file);

#if 0
    status = ProInfoWindowDisplay (
                ProStringToWstring(wstr, file_name), NULL, NULL);
    TEST_CALL_REPORT ("ProInfoWindowDisplay()", "ProTestDrawingInfo()",
        status, status!=PRO_TK_NO_ERROR);
#endif
    return(PRO_TK_NO_ERROR);
}

