unionsoft 发表于 2003-7-16 12:59:00

在AutoCAD中动态读取Excel数据

在AutoCAD中动态读取Excel数据

        在实际的工作中,我们经常要对一些表格数据进行处理,如果先把这些表格数据通过Excel处理,再导入到AutoCAD,
那绝对会起到事半功倍的效果。随着Automation编程技术的出现,我们可以很方便地实现这一点了,下面是个
ObjectARX的例子,其功能是动态关联Excel,然后读取其数据,并将这些数据打印在文本域中。

//动态从Excel读取数据
int DynamicReadFromExcel()
{
        //常用变量定义
        _Application app;   
        Workbooks books;
        _Workbook book;
        Worksheets sheets;
        _Worksheet sheet;
        Range range;
        Range iCell;

        LPDISPATCH lpDisp;   
        COleVariant
      covTrue((short)TRUE),
      covFalse((short)FALSE),
      covOptional((long)DISP_E_PARAMNOTFOUND, VT_ERROR);      
        COleVariant vResult;

        //采用MFC方式初始化COM库,程序结束时COM库会自动释放
        if(!AfxOleInit())
        {
                MessageBox(NULL,"初始化COM支持库失败!\n无法控制Excel!", \
                        "TrueTable",MB_ICONERROR | MB_OK);
                return RTERROR;
        }
               
        //关联已经运行的Excel实例
        CLSID clsid;
        CLSIDFromProgID(L"Excel.Application", &clsid);
        IUnknown *pUnk = NULL;
        IDispatch *pRunDisp = NULL;
       
        for(long i=1;i<=5;i++) //做5次尝试
        {
                HRESULT hr = GetActiveObject(clsid, NULL, (IUnknown**)&pUnk);
                if(SUCCEEDED(hr))
                {
                        hr = pUnk->QueryInterface(IID_IDispatch, (void **)&pRunDisp);
                        break;
                }
                ::Sleep(10);
        }
       
        if (!pRunDisp)
        {
                ::MessageBox(NULL, "没有发现Excel!", "TrueTable", MB_ICONHAND);
                return RTERROR;
        }

        if (pUnk)         pUnk->Release();
       
        //关联Excel
        app.AttachDispatch (pRunDisp);

        //得到当前活跃sheet
        //如果有单元格正处于编辑状态中,此操作不能返回,会一直等待
        lpDisp=app.GetActiveSheet();
        if(lpDisp==NULL)
        {
                MessageBox(NULL, "没有发现有效的表格!", \
                        "TrueTable",MB_ICONERROR | MB_OK);
                app.ReleaseDispatch ();       

                return RTERROR;
        }
        sheet.AttachDispatch(lpDisp);
       
        //已经使用的行数:
        long row_num;
        range.AttachDispatch(sheet.GetUsedRange());
        range.AttachDispatch(range.GetRows());
        row_num=range.GetCount();
               
       
        //已经使用的列数:
        long col_num;
        range.AttachDispatch(sheet.GetUsedRange());
        range.AttachDispatch(range.GetColumns());
        col_num=range.GetCount();

        //已经使用区域的起始行、列:
        range.AttachDispatch(sheet.GetUsedRange());
        long StartRow=range.GetRow();       //起始行
        long StartCol=range.GetColumn();    //起始列

        //读取sheet名
        CString SheetName=sheet.GetName();
        //ads_printf("\n%s",SheetName);
        if(col_num<2 && row_num<2)   //此sheet为空
        {
                MessageBox(NULL,"\n当前表格没有数据!", \
                        "TrueTable",MB_ICONERROR | MB_OK);
                app.ReleaseDispatch ();       

                return RTERROR;
               
        }
        else
        {
                ads_printf("\n表格%s共%d行,%d列",SheetName,row_num,col_num);
        }
               
       
               
        //得到全部Cells,此时,range是cells的集合
        range.AttachDispatch(sheet.GetCells());
               
               
        //读写数据了
        CString cstr;
        ads_printf("\n");
        for(long i=StartRow;i<StartRow+row_num;i++)
        {
                               
                for(long j=StartCol;j<StartCol+col_num;j++)
                {
                       
                        //读取单元格文本
                        iCell.AttachDispatch(range.GetItem (COleVariant(i),COleVariant(j)).pdispVal );
                        vResult =iCell.GetText();
                        cstr=vResult.bstrVal;
                       
                        //写单元格文本
                        ads_printf("%s    ",(LPTSTR)cstr);
                                               
                }
                ads_printf("\n");
        }

               
        //释放Dispatch
        iCell.ReleaseDispatch ();
        range.ReleaseDispatch ();
        sheet.ReleaseDispatch ();
        sheets.ReleaseDispatch ();
        book.ReleaseDispatch ();
        books.ReleaseDispatch ();
        app.ReleaseDispatch ();       

        return RTNORM;

}

        如果要输出到Excel的话,关键函数就是:
        iCell.SetItem(COleVariant(i),COleVariant(j),COleVariant(cstr));
       
        我利用Automation技术编了个在Excel和AotuCAD间互导表格的程序TrueTable,在明静通道上有下载,下载地址为:
        http://www.mjtd.com/mcdown/list.asp?id=375
       
                                                                       
                                                                                      龚敏
                                                                                unionsoft@163.com

muzi 发表于 2003-7-24 15:16:00

你会读出csv中的数据吗?就是文本文件,没行的数据用逗号隔开,每行最后没有逗号

unionsoft 发表于 2003-7-28 17:13:00

你可以用TrueTable来读取该文本文件,记得用逗号","作为“分列标记”,TrueTable可以将其表格化

success8879 发表于 2003-8-3 10:51:00

TrueTable在读取文件后绘出表格时,会出现有的表格不均等,文字不在表格线中央,请问“龚工”这是为什么?

unionsoft 发表于 2003-8-3 11:51:00

TrueTable会读取Excel中的对齐方式,如果在Excel中是靠左对齐方式,自然不在中间了
建议你好好看看帮助文档

success8879 发表于 2003-8-3 21:07:00

居中也是如此的!!!!(说的是文字不在上下表格线的中央)

unionsoft 发表于 2003-8-5 08:15:00

针对很多朋友不知道如何使用TrueTable,我特意做了个演示动画

TrueTable动画演示下载:http://www.szty.com.cn/gmsoft

unionsoft 发表于 2003-8-5 22:58:00

TrueTable9.0:
增强的更新模式,支持合并单元格,支持静态更新,不用打开Excel,表格也照样更新,即使表格全空,也照样更新
详见TrueTable全程演示动画:http://www.szty.com.cn/gmsoft

TrueTable9.0还增加材料表制做功能,绝对让让你的工作效率大大提高,详见材料表演示动画:http://www.szty.com.cn/gmsoft

liujiping 发表于 2003-8-8 22:23:00

unionsoft兄:
      能不能把CAD导入EXCEL的指定文件的指定位置(如SHEET1/A1开始),并且不覆盖原来的其他内容,(SHEET可选或自动的往后移)
      现在好象没这功能,能不能加上此功能?

unionsoft 发表于 2003-8-9 13:54:00

将多个表格输出到同一个Excel表格的功能在注册版本中才能享受,未注册版本做了限制。
页: [1] 2 3 4 5
查看完整版本: 在AutoCAD中动态读取Excel数据