/********************************************************************/
/* Copyright (c) 2019 System fugen G.K. and Yuzi Mizuno          */
/* All rights reserved.                                             */
/********************************************************************/
/********************************************************************/
#include "stdafx.h"
#include <dlgs.h> // psh2 等を参照したい場合はコメントアウトを解禁するべし。
#include "fugen.h"
#include "GLFileDialog.h"
#include "IO/GLFileManager.h"
#include "IO/GLFileExporter.h"
#include "VersionHelpers.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

BEGIN_MESSAGE_MAP(CGLFileDialog, CFileDialog)
	ON_BN_CLICKED(IDC_BUTTON_OPTION, OnBnClickedOption)
END_MESSAGE_MAP()

// コンストラクター
CGLFileDialog::CGLFileDialog(
	BOOL bOpenFileDialog,
	LPCTSTR lpszDefExt,
	LPCTSTR lpszFileName,
	DWORD dwFlags,
	LPCTSTR lpszFilter,
	CWnd* pParentWnd)
	 : CFileDialog(bOpenFileDialog, lpszDefExt, lpszFileName, dwFlags, lpszFilter, pParentWnd)
{
	if(!bOpenFileDialog){
		m_ofn.Flags |= OFN_EXPLORER | OFN_ENABLETEMPLATE;

		// OSの種類によってファイル選択ダイアログを分ける
		// vista以降はGetIFileDialogCustomize()を呼ぶ
		// XP以前の場合は、今まで通りSetTemplate(0, IDD_FILEDIALOG_OPTION)を呼ぶ
		// 内部バージョンが6以降のものが、vista以降のものになる
		if(IsWindowsXPOrGreater())
			GetIFileDialogCustomize();
		else
			SetTemplate(0, IDD_FILEDIALOG_OPTION);
	}
}

BOOL CGLFileDialog::OnInitDialog()
{
	if(!CFileDialog::OnInitDialog()){
		return FALSE;
	}

	SetIcon(::AfxGetApp()->LoadIcon(IDR_MGCLTYPE), FALSE);

	if(m_bOpenFileDialog){
		return TRUE;
	}

	// サイズ合わせ

	//CWnd* pWndLabel = GetParent()->GetDlgItem(stc2); // 「ファイルの種類」ラベル
	CWnd* pWndCancel = GetParent()->GetDlgItem(IDCANCEL);
	CWnd* pWndOpt = GetDlgItem(IDC_BUTTON_OPTION); // カスタム領域上の「オプション」ボタン
	CWnd* pWndPane = pWndOpt->GetParent(); // 何でしょう
	if(!pWndCancel || !pWndOpt || !pWndPane){
		// とりあえずダイアログを表示しよう
		return TRUE;
	}

	CRect rcLabel;
	pWndCancel->GetWindowRect(rcLabel);
	ScreenToClient(rcLabel);

	CRect rcOpt;
	pWndOpt->GetWindowRect(rcOpt);
	ScreenToClient(rcOpt);

	CRect rcPane;
	pWndOpt->GetWindowRect(rcPane);
	ScreenToClient(rcPane);

	// オプションボタンを動かす。

	//rcPane.InflateRect(0, 0, rcLabel.left - rcOpt.left, 0);
	rcOpt += CSize(rcLabel.left - rcOpt.left, 0);
	rcOpt.right = rcOpt.left + rcLabel.Width();

	pWndOpt->MoveWindow(rcOpt);
	//pWndPane->MoveWindow(rcPane);

	UpdateOptionButton();

	return TRUE;
}

// 入力パス名の検査に利用する。MSDN を参照。
BOOL CGLFileDialog::OnFileNameOK()
{
	if(GetFileExt().IsEmpty()){
		// 「すべて」だとタイプが分からないので終了
		if(m_ofn.nFilterIndex == m_ofn.nMaxCustFilter){
			AfxMessageBox(IDS_WARNING_EXTENSION);
			return TRUE;
		}
		else{
			// 拡張子を足してやって
			// すでに同名のファイルがないかどうか調べる
			// あれば上書きしてよいかどうか利用者にたずねる
			if(!m_bOpenFileDialog){ // 保存のときのみの処理

				// このパスはおそらく通らない。

				CGLFileManager& fm = CGLFileManager::GetInstance();
				CString ext = GetDesiredExt();
				ASSERT(!ext.IsEmpty());

				CString fileName = GetPathName();

				// 拡張子を付加
				::PathAddExtension(fileName.GetBuffer(MAX_PATH), ext);
				fileName.ReleaseBuffer();

				CFileFind ff;
				if(ff.FindFile(fileName)){
					CString strMessage;
					strMessage.Format(IDS_PROMPT_OVERWRITE, fileName);
					int nRet = AfxMessageBox(strMessage, MB_YESNO, MB_ICONQUESTION | MB_DEFBUTTON2);
					if(nRet != IDYES){
						return TRUE;
					}
				}
			}
		}
	}
	return FALSE;
}

// コンボボックスの選択が変化したときに呼ばれる。MSDN を参照。
void CGLFileDialog::OnTypeChange()
{
	UpdateOptionButton();
}

// オプションボタンのイベントハンドラー
void CGLFileDialog::OnBnClickedOption()
{
	if(m_bOpenFileDialog){
		return;
	}

	// ファイルを保存のオプション
	const OPENFILENAME& ofn = GetOFN();
	CWnd* pWndOpt = GetDlgItem(IDC_BUTTON_OPTION);

	CGLFileManager& mgr = CGLFileManager::GetInstance();
	CGLFileExporter* pHandler = mgr.GetExporterFromFilter(
		GetCurrentFilterText());
	ASSERT(pHandler);

	// 予定
	pHandler->OnSetOption();
}

void CGLFileDialog::UpdateOptionButton()
{
	if(m_bOpenFileDialog){
		return;
	}

	CWnd* pWndOpt = GetDlgItem(IDC_BUTTON_OPTION);
	if(!pWndOpt){
		return;
	}

	CGLFileManager& mgr = CGLFileManager::GetInstance();
	CGLFileExporter* pHandler = mgr.GetExporterFromFilter(
		GetCurrentFilterText());

	// 状況に応じてグレーアウト
	pWndOpt->EnableWindow(pHandler != 0 && pHandler->HasOption());
}

/// 選択されている "AG Files (*.ag)" 等のテキストを返す。
CString CGLFileDialog::GetCurrentFilterText() const
{
	const OPENFILENAME& ofn = GetOFN();
	const int nNullChar = 2 * (ofn.nFilterIndex - 1);
	const TCHAR* pChar = ofn.lpstrFilter;
	for(int nCount = 0; nCount < nNullChar; ++pChar){
		if(*pChar == TCHAR(0)){
			++nCount;
		}
	}
	return CString(pChar);
}

// Igesファイル(*.iges;*.igs)
// agファイル(*.ag)
CString CGLFileDialog::GetDesiredExt() const
{
	CString str(GetCurrentFilterText());
	int nStart = str.Find(_T("(*."));
	if(nStart == -1){
		return _T(".mgl");
	}
	// (* をスキップ。
	nStart += 2;

	// セミコロンを先にテストする。
	int nEnd = str.Find(_T(";"), nStart);
	if(nEnd != -1){
		return str.Mid(nStart, nEnd - nStart);
	}

	// 括弧終わりをテストする。
	nEnd = str.Find(_T(")"), nStart);
	if(nEnd != -1){
		return str.Mid(nStart, nEnd - nStart);
	}

	return _T(".mgl");
}
