[Unity]NPOI2.0.1(beta 1)を使ってxlsとxlsxを読み込んでみた

パラメータ管理にエクセルを使おうかと思って探してみたところ
NPOIという.NETでエクセルの読み書きが出来るライブラリを見つけたので使ってみた。
※動作確認はWindows7で行っているため、それ以外の環境では動かないかも。その場合は、NPOIのMono DLLを自前で作る必要があるはず。

  • ダウンロード
    NPOIは現在2.0.1(beta 1)が最新版であり(Stableは1.2.5)、Excel2007以降のフォーマット(*.xlsx)にも対応しているとのこと。
    こちらからダウンロードできる。
    http://npoi.codeplex.com/

ダウンロードしたzipを解凍するとdotnet2フォルダなど、.NetのバージョンごとにDLLが用意されている。
Unityがサポートしているのは.Net2.0なのでとりあえずdotnet2を使ってみることにした。

  • UnityにDLLをインポート
    Assets以下の適当な場所にNPOIというフォルダを作って、dotnet2以下にあるファイルをそのままコピーした。
    もしかしたら不要なものもあるかもしれないが、とりあえず読み込めればOKなので気にしない気にしない。

ちなみに、読み込むエクセルファイルはAssetPostprocessor使って最終的にScriptableObjectにするつもりで、
Editor以外では必要ないのでExcelImporter/Editor/NPOIに置いて、出力する際の邪魔にならないようにした。
(Editor以下に置けばEditorからしか参照されないはず)

  • AssetPostprocessor使って読み込みテスト
    こんなコード書いみた

    using UnityEngine;
    using UnityEditor;
    using System.IO;
    using NPOI.HSSF.UserModel;
    using NPOI.XSSF.UserModel;
    using NPOI.SS.UserModel;
    
    public class TestExcelLoader : AssetPostprocessor
    {
    	static public void ReadBook( IWorkbook book )
    	{
    		int numberOfSheets = book.NumberOfSheets;
    
    		for( int sheetIndex = 0;sheetIndex < numberOfSheets;++sheetIndex )
    		{
    			ISheet sheet = book.GetSheetAt( sheetIndex );
    
    			int lastRowNum = sheet.LastRowNum;
    
    			Debug.Log ( "SheetName:"+sheet.SheetName+","+lastRowNum );
    
    			for( int rowIndex = sheet.FirstRowNum;rowIndex <= lastRowNum;++rowIndex )
    			{
    				IRow row = sheet.GetRow(rowIndex);
    
    				if( row==null )
    				{
    					continue;
    				}
    
    				Debug.Log( "Row"+rowIndex );
    
    				int lastCellNum = row.LastCellNum;
    				for( int cellIndex = row.FirstCellNum;cellIndex < lastCellNum;++cellIndex )
    				{
    					ICell cell = row.GetCell( cellIndex );
    
    					Debug.Log( "Cell"+cellIndex+":"+cell.CellType+","+cell );
    				}
    			}
    		}
    	}
    
    	static public void ReadXLS( string path )
    	{
    		using( FileStream fs = new FileStream( path,FileMode.Open,FileAccess.Read, FileShare.ReadWrite) )
    		{
    			Debug.Log("ReadXLS:"+path );
    
    			ReadBook( new HSSFWorkbook(fs) );
    		}
    	}
    
    	static public void ReadXLSX( string path )
    	{
    		using( FileStream fs = new FileStream( path,FileMode.Open,FileAccess.Read, FileShare.ReadWrite) )
    		{
    			Debug.Log("ReadXLSX:"+path );
    
    			ReadBook( new XSSFWorkbook(fs) );
    		}
    	}
    
    	static public void OnPostprocessAllAssets(
    		string[]	importedAssets,
    		string[]	deletedAssets,
    		string[]	movedAssets,
    		string[]	movedFromAssetPaths)
    	{
    		foreach( string importedAsset in importedAssets )
    		{
    			if( importedAsset.EndsWith(".xls") )
    			{
    				ReadXLS( importedAsset );
    			}
    			else if( importedAsset.EndsWith(".xlsx") )
    			{
    				ReadXLSX( importedAsset );
    			}
    		}
    	}
    }
    

自分の環境にはMicrosoft Officeがないので、
xlsxも対応しているLibreOfficeを使って、適当なテストデータを作った。
※LibreOfficeはこちらからhttp://ja.libreoffice.org/

テストデータのxls、xlsxをAssets以下の適当な場所に保存すると、Consoleにシート名や各セルの内容が出力できた。

あとは、各自ゲームの仕様にあわせて読み込んだエクセルデータをScriptableObjectなりにすればOK!

UnityはC#の資産がそのまま使えるっていうのもすばらしいですな。

Unityのアセット販売中!

ステートマシンの状態遷移やパラメータはエディタで編集でき、
ゲームロジックに依存するステートの挙動はスクリプトで記述可能なエディタ拡張。

詳細はこちら

RPGツクールVXやWOLF RPGエディターのオートタイルに準拠したエディタ拡張。

詳細はこちら

オススメ!