module yamalib.auxil.appassist;

debug {

private import SDL;

private import std.string;
private import std.path;
private import std.utf;
private import std.stream;

private import std.file;
private import std.thread;

private import y4d;
private import y4d_aux.filesys;
private import y4d_aux.direnumerator;
private import y4d_aux.widestring;
private import y4d_timer.timer;
private import y4d_math.rand;

private import yamalib.auxil.list2scenario;
private import yamalib.log.log;
private import yamalib.log.performancelog;

private import kyojintati4d.val.kyojinconst;

// test用
private import yamalib.draw.textdraw;
private import yamalib.dict.dictdata;


/// プログラミング補助クラス
/// プログラムするときにあると便利な環境関数を詰め込んだクラス
/// ぼちぼちつくりかけ...
class AppAssist {

public:

	/// 描画パフォーマンス測定
	static void openGLParformance(Screen screen) {
		// 15秒
		static const int LIMIT_TIME = 15 * 1000;
		
		// メインスレッド設定
		Texture.setMainThreadId(cast(uint) Thread.getThis().hdl);
		Texture t = new Texture();
		t.load(cast(char[]) "test/test.png");

		Timer timer = new Timer();
		Rand rand = new Rand();
		rand.randomize();
		uint count = 0;
		
		screen.blendSrcAlpha();
		int maxW = cast(int) (screen.getWidth() - t.getWidth());
		int maxH = cast(int) (screen.getHeight() - t.getHeight());
	
		screen.setClearColor(0,0,0);
		screen.clear();
		screen.update(); 

		
		// 走らせる前に一時休憩
		SDL_Delay(10000);
		
		timer.reset();
		while (true) {
			screen.setColor( rand.get(255), rand.get(255), rand.get(255) );
			screen.blt( t, rand.get(maxW), rand.get(maxH) );
			screen.update(); 
			count++;
			if ( timer.get() >= LIMIT_TIME ) {
				break;
			}
		}
		
		Log.print("[DRAW PAFORMANCE] %s", count);
		
	}

	/// 事典データモデル単体テスト
	static void test001() {
		
		char[] buf;
		
		TextDrawContext tdc = new TextDrawContext();
		tdc.setText( toWCS( cast(char[]) FileSys.read(
				cast(char[]) "./data/dict/contents/test_data.txt") ) ); 
		DictData data = new DictData();
		
//		data.getFontRepository().setLoader(null,1);
//		data.getFontRepository().setMax(500);

		data.setTextDrawContext(tdc);
		data.updateText();
		
		buf ~= data.toString();
		
		data.nextPage();
		
		buf ~= "\r\n" ~ data.toString();
		
		data.prevPage();
		
		buf ~= "\r\n" ~ data.toString();
		
		FileSys.write( cast(char[]) "DATA_DUMP.txt", buf );
	}

	/// リソースファイルを検索してファイル名を外部ストリング化する
	static bool fileEnum(char[] topDir) {
		assert ( !(topDir is null) );
		
		DirEnumerator dir = new DirEnumerator();
		dir.setDir( topDir );
		
		char[] fullname;
		char[] fullnameUp;
		char[] buffer;
		
		foreach ( filename; dir ) {
			if ( isResouceFile( filename ) ) {
				fullname = FileSys.makeFullName( cast(char[]) filename );
				fullnameUp = cast(char[]) std.string.toupper( cast(char[]) fullname );
				
				fullnameUp = cast(char[]) std.string.replace( fullnameUp, "\\", "__" );
				fullnameUp = cast(char[]) std.string.replace( fullnameUp, "/", "__" );
				fullnameUp = cast(char[]) std.string.replace( fullnameUp, ".", "_" );
				
				buffer ~= "\t" ~ SENGEN ~ fullnameUp ~ " = " ~ "\"" ~ fullname ~ "\";" ~ "\n";
			}
		}
		
		// テンプレート読み込み
		wchar[] tmp = toWCS( cast(char[]) FileSys.read(cast(char[]) TEMPLATE_KYOJINCONST) );
		char[] tmp2 = cast(char[]) std.string.replace( toUTF8(tmp), TEMPLATE_KYOJINCONST_KEY, buffer );
		
		// ファイル書き出し
		std.file.remove(SRC_KYOJINCONST);
		std.file.write( SRC_KYOJINCONST, tmp2 );
		
		return true;
	}
	
	/// 指定したインデックスのシナリオファイルをコンバートする
	static bool createScenarioScript(int[] indexs) {
		
		static const char[][] INPUT_CSV = [
			"S-01.csv",
			"S-02.0.csv",
			"S-02.1.csv",
			"S-02.2.csv",
			"S-03.csv",
			"S-04.csv",
			"S-05.csv",
			"S-06.csv",
			"S-07.csv",
			"S-08.0.csv",
			"S-08.1.csv",
			"S-08.2.csv",
			"S-08.3.csv",
			"S-09.csv",
			"S-10.csv",
			"S-11.csv",
			"S-12.csv",
			"S-13.csv"
		];

		static const char[][] VOICE_DIR_ID = [
			"s01",
			"s02",
			"s02_1",
			"s02_2",
			"s03",
			"s04",
			"s05",
			"s06",
			"s07",
			"s08",
			"s08_1",
			"s08_2",
			"s08_3",
			"s09",
			"s10",
			"s11",
			"s12",
			"s13",
		];
				
		for (int i; i < indexs.length; ++i ) {
			if (indexs[i] >= KyojinConst.scenarioFileName.length) {
				continue;
			}
			
//			(new List2Script(VOICE_DIR_ID[i])).convert(SCENARIO_CSV_PATH~INPUT_CSV[i], KyojinConst.scenarioFileName[i]);
		}
				
		return true;
	}
	
private:
	static const char[] SCENARIO_CSV_PATH = "data/csv/";
	static const char[] SCENARIO_OUT_PATH = "data/out/";


	static const char[] TEMPLATE_KYOJINCONST = "template/PicNameConst.tpl";
	static const char[] TEMPLATE_KYOJINCONST_KEY = "$$$PicNameConst$$$";
	static const char[] SRC_KYOJINCONST = "kyojintati4d/val/kyojinconst.d";
	
	static const char[][] EXT_LIST = [
		"lst", "sdf", "bmp", "png", "jpg", "png"
	];
	static const char[][] EXT_PIC = [
		"bmp", "png", "jpg", "png"
	];
	
	static final const char[] SENGEN = "static final const char[] ";

	/// 対象拡張子がリソースファイルかどうか	
	static bool isResouceFile(char[] filename) {
		foreach ( ext; EXT_PIC) {
			if (std.string.tolower(std.path.getExt(filename)) == ext) {
				return true;
			}
		}
		return false;
	}
	
	/// 画像リソースファイル列挙
	static char[][] getFileNames(char[] topDir) {
		DirEnumerator dir = new DirEnumerator();
		dir.setDir( topDir );
		
		char[][] ret;
				
		foreach ( char[] filename; dir ) {
			if ( isResouceFile( filename ) ) {
				ret ~= filename;
			}
		}
		
		return ret;
	}
	
}

}