XLSXを読み込む

 

XLSXを読み込む

説明

エクセルファイル(.xlsx)を読み込んでArchicadに取り込む方法を紹介します。

プロジェクトに必要なインクルードディレクトリとライブラリを追加する

追加インクルードディレクトリ

  • Support\Modules\GSXML
  • Support\Modules\GSXMLUtils
  • Support\Modules\LibXL

追加ライブラリ

  • Support\Modules\LibXL\Win\LibXLImp.LIB
 
#include	"LibXL/libxl.h"
#include	"DGModule.hpp"
#include	"xercesc/dom/DOM.hpp"
#include	"GSXMLDOMUtilsEx.hpp"


#define UNISTR_TO_LIBXLSTR(str) ((str).ToUStr ())
#define LIBXLSTR_TO_UNISTR(str) (GS::UniString (str))


GSErrCode ReadXLSX()
{
	GSErrCode err = NoError;

	// Set xlsx extension
	FTM::FileTypeManager xmlTypeManager("xlsx");
	FTM::FileType fileType("xlsx", "xlsx", 0, 0, 0);
	FTM::TypeID typeID = xmlTypeManager.AddType(fileType);

	// File Open Dialog
	DG::FileDialog dlg(DG::FileDialog::OpenFile);
	dlg.EnablePreview();
	dlg.AddFilter(typeID);

	// Open Dialog
	bool bRet = dlg.Invoke();
	xmlTypeManager.RemoveType(typeID);

	if (!bRet)
		return APIERR_CANCEL;

	// Read xlsx file
	libxl::Book* book = nullptr;
	IO::Location fileLoc = dlg.GetSelectedFile();
	book = xlCreateXMLBook();

#ifdef macintosh
	book->setLocale("UTF-8");
#endif

	GS::UniString path;
	fileLoc.ToPath(&path);
	bRet = book->load(UNISTR_TO_LIBXLSTR(path));
	if (!bRet) {
		book->release();
	}

	if (book == nullptr) {
		return GS::ErrRead;
	}

	if (DBVERIFY(book->sheetCount() > 0))
	{
		Int32 nameInd = -1;
		Int32 typeInd = -1;
		Int32 sizeInd = -1;

		// Check format
		libxl::Sheet* sheet = book->getSheet(0);
		for (Int32 i = sheet->firstCol(); i < sheet->lastCol(); i++) {
			if (sheet->cellType(sheet->firstRow(), i) == libxl::CELLTYPE_STRING)
			{
				GS::UniString str = LIBXLSTR_TO_UNISTR(sheet->readStr(sheet->firstRow(), i));
				if (str == "Name")
					nameInd = i;
				else if (str == "Type")
					typeInd = i;
				else if (str == "Size")
					sizeInd = i;
			}
		}

		// xlsx format does not match
		if (nameInd != sheet->firstCol() || typeInd != nameInd+1 || sizeInd != nameInd+2) {
			book->release();
			return APIERR_CANCEL;
		}

		struct XLSXData
		{
			XLSXData() :name(""), type(0), size(0.0) {}
			GS::UniString name;
			int type;
			double size;
		};


		// Read all cells
		for (Int32 j = sheet->firstRow() + 1; j < sheet->lastRow(); j++)
		{
			XLSXData data;

			// Read name
			if (sheet->cellType(j, nameInd) == libxl::CELLTYPE_STRING){
				data.name = sheet->readStr(j, nameInd);
			}

			// Read type
			if (sheet->cellType(j, typeInd) == libxl::CELLTYPE_NUMBER ) {
				data.type = (int)sheet->readNum(j, typeInd);
			}

			// Read size
			if (sheet->cellType(j, sizeInd) == libxl::CELLTYPE_NUMBER) {
				data.size = sheet->readNum(j, sizeInd);
			}

			ACAPI_WriteReport("{%s, %d, %lf}", false, data.name.ToCStr().Get(), data.type, data.size);
		}
	}

	book->release();

	ACAPI_WriteReport("completed", true);

	return err;

}