// PageExport.cpp : implementation file // #include "stdafx.h" #include "NVAPIExample.h" #include "NVAPIExampleDlg.h" #include "PageExport.h" #include "PageData.h" #include "Sheet.h" #include #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // CPageExport dialog CPageExport::CPageExport(CSheet * pParent) : CPage(CPageExport::IDD, pParent) , m_bActiveState(false) , m_thread(0) { //{{AFX_DATA_INIT(CPageExport) //}}AFX_DATA_INIT } void CPageExport::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CPageExport) DDX_Control(pDX, IDC_STATIC_TOTAL_REMAINTIME, c_textTotalRemainTime); DDX_Control(pDX, IDC_STATIC_TOTAL_PROGRESS, c_textTotalProgress); DDX_Control(pDX, IDC_STATIC_CURRENT_REMAINTIME, c_textCurrentRemainTime); DDX_Control(pDX, IDC_STATIC_CURRENT_PROGRESS, m_textCurrentProgress); DDX_Control(pDX, IDC_PROGRESS_TOTAL, c_ProgressTotal); DDX_Control(pDX, IDC_PROGRESS_CURRENT, c_progressCurrent); //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CPageExport, CDialog) //{{AFX_MSG_MAP(CPageExport) // NOTE: the ClassWizard will add message map macros here //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CPageExport message handlers bool CPageExport::Create (void) { // This is a CPage virtual function. Just create the dialog and return // success. // return CDialog::Create (m_lpszTemplateName, m_pParentWnd) != FALSE; } bool CPageExport::OnBack (void) { // go back to first page CNVAPIExampleDlg * pParentSheet = (CNVAPIExampleDlg *) GetParent(); if (pParentSheet) pParentSheet->SwitchPage(0); return true; } bool CPageExport::OnNext (void) { // If we are in an active state, the button is used for abortion. So, // abort and eat the button click. // if (m_bActiveState) { m_IsAborting = true; return true; } else { CNVAPIExampleDlg * pParentSheet = (CNVAPIExampleDlg *) GetParent(); if (pParentSheet) pParentSheet->SwitchPage(0); return true; } } DWORD WINAPI CPageExport::BeginThreadFunc(void* p) { ASSERT(p); CPageExport* page = (CPageExport*)p; page->ExportProcess(); return 0; } void CPageExport::ExportProcess() { CoInitialize(0); try { // prepare the exporter NeroVisionAPI::IErrorPtr err; NeroVisionAPI::IMovieExporterPtr exporter; { if (FAILED(exporter.CreateInstance(__uuidof(NeroVisionAPI::MovieExporter)))) throw _bstr_t("CreateInstance failed"); err = exporter->LastError; if (err->ErrCode) throw err; } m_pageData->m_pProject->SetXMLString ((LPSTR)(LPCSTR) m_pageData->m_sXML); CString str; str.Format("t%d", m_pageData->m_selectedItemIndex + 1); wchar_t XMLID[100]; MultiByteToWideChar(CP_UTF8, 0, str, -1, XMLID, 100); if (!exporter->SetSource(m_pageData->m_pProject, XMLID)) throw err = exporter->LastError; __int64 s; if (!exporter->EstimateFileSize(&s)) throw err = exporter->LastError; if (!exporter->ExportMovie(m_exportFilename, this)) throw err = exporter->LastError; } catch (_bstr_t& errstr) { m_IsAborting = true; MessageBox(_T("Error occurred:\n") + errstr, 0, MB_OK | MB_ICONERROR); } catch (NeroVisionAPI::IErrorPtr& e) { m_IsAborting = true; if (e->ErrCode != NeroVisionAPI::Canceled) { _bstr_t s = "NeroVisionAPI error occurred:\n" + e->ErrText; _bstr_t s2 = e->XMLID; if (s2.length()) s += "\nXML-ID: " + s2; MessageBox(s , 0, MB_OK | MB_ICONERROR); } } catch (_com_error& e) { m_IsAborting = true; _bstr_t s = L"COM error occurred:\n"; if ((wchar_t*)e.Description()) s += e.Description(); if (e.ErrorMessage()) s += e.ErrorMessage(); MessageBox(s, 0, MB_OK | MB_ICONERROR); } CoUninitialize(); PostMessage(WM_COMMAND, MAKEWPARAM(IDC_START_PROCESSINGFINISHED, 0), 0); } void CPageExport::OnChangeState (bool bActivate, bool bForward) { if (bForward) { // let user select filename for export CString sAbort; sAbort.LoadString (IDS_BUTTON_ABORT); GetParent ()->GetDlgItem (IDOK)->SetWindowText (sAbort); GetParent ()->GetDlgItem (IDCANCEL)->EnableWindow (false); c_ProgressTotal.SetRange(0, 1000); c_ProgressTotal.SetPos(0); c_progressCurrent.SetRange(0, 1000); c_progressCurrent.SetPos(0); c_textTotalRemainTime.SetWindowText(""); c_textTotalProgress.SetWindowText(""); c_textCurrentRemainTime.SetWindowText(""); m_textCurrentProgress.SetWindowText(""); char fileBuffer[MAX_PATH]; *fileBuffer = 0; char filterBuffer[] = "MPEG files (*.mpg)\0*.mpg\0\0"; char extBuffer[] = ".mpg"; char titleBuffer[] = "Save as MPEG file"; OPENFILENAME ofn; ZeroMemory(&ofn, sizeof(ofn)); ofn.lStructSize = sizeof(ofn); ofn.hwndOwner = GetSafeHwnd(); ofn.lpstrFile = fileBuffer; ofn.nMaxFile = MAX_PATH; ofn.lpstrFilter = filterBuffer; ofn.lpstrDefExt = extBuffer; ofn.lpstrTitle = titleBuffer; ofn.Flags = OFN_ENABLESIZING | OFN_EXPLORER | OFN_OVERWRITEPROMPT | OFN_PATHMUSTEXIST | OFN_HIDEREADONLY; if (GetSaveFileName(&ofn) == IDOK) { m_exportFilename = fileBuffer; m_IsAborting = false; m_bActiveState = true; CString sAbort; sAbort.LoadString (IDS_BUTTON_ABORT); GetParent ()->GetDlgItem (IDOK)->SetWindowText (sAbort); GetParent ()->GetDlgItem (IDOK)->EnableWindow (true); GetParent ()->GetDlgItem (IDCANCEL)->EnableWindow (false); m_pageData = GetPageData(); // for use inside thread function m_thread = (HANDLE)CreateThread(0, 0, BeginThreadFunc, this, 0, 0); } else { PostMessage(WM_COMMAND, MAKEWPARAM(IDC_START_PROCESSINGFINISHED, 0), 0); } } } STDMETHODIMP CPageExport::raw_OnProgress (enum NeroVisionAPI::ProgressAction action, BSTR itemName, double currentRemain, double currentTotal, float currentFraction, double totalRemain, double totalTotal, float totalFraction) { // update progress controls SendDlgItemMessage(IDC_PROGRESS_CURRENT, PBM_SETPOS, WPARAM(currentFraction * 1000), 0); SendDlgItemMessage(IDC_PROGRESS_TOTAL, PBM_SETPOS, WPARAM(totalFraction * 1000), 0); // display current action _bstr_t actionText; switch (action) { case NeroVisionAPI::Estimating: actionText = _T("Estimating"); break; case NeroVisionAPI::Preparing: actionText = _T("Preparing"); break; case NeroVisionAPI::Transcoding: actionText = _T("Transcoding"); break; case NeroVisionAPI::Generating: actionText = _T("Generating"); break; case NeroVisionAPI::Analyzing: actionText = _T("Analyzing"); break; } if (_bstr_t(itemName).length() > 0) actionText += _T(": '") + _bstr_t(itemName) + _T("'"); SetDlgItemText(IDC_STATIC_PROGRESS, actionText); // display total times for current action and total process TCHAR text[2048]; FormatTimeString(currentTotal, _T("Time needed for current task: %ldh %02ldm %02lds"), text); SetDlgItemText(IDC_STATIC_CURRENT_PROGRESS, text); FormatTimeString(totalTotal, _T("Total time needed: %ldh %02ldm %02lds"), text); SetDlgItemText(IDC_STATIC_TOTAL_PROGRESS, text); // display times remaining for current action and total process TCHAR fmtRemain[] = _T("Remaining: %ldh %02ldm %02lds"); FormatTimeString(currentRemain, fmtRemain, text); SetDlgItemText(IDC_STATIC_CURRENT_REMAINTIME, text); FormatTimeString(totalRemain, fmtRemain, text); SetDlgItemText(IDC_STATIC_TOTAL_REMAINTIME, text); UpdateWindow(); return S_OK; } STDMETHODIMP CPageExport::raw_ShouldCancel(VARIANT_BOOL* pbCancel) { *pbCancel = (m_IsAborting ? VARIANT_TRUE : VARIANT_FALSE); return S_OK; } void CPageExport::FormatTimeString(double secs, const TCHAR* format, TCHAR* buffer) { unsigned int hours = unsigned int(secs / 3600); unsigned int minutes = (unsigned int(secs) % 3600) / 60; unsigned int seconds = unsigned int(secs) % 60; _stprintf(buffer, format, hours, minutes, seconds); } BOOL CPageExport::OnCommand(WPARAM wParam, LPARAM lParam) { // delay go on back to first page if (LOWORD(wParam) == IDC_START_PROCESSINGFINISHED) { if (m_thread) { CloseHandle(m_thread); m_thread = 0; } CNVAPIExampleDlg * pParentSheet = (CNVAPIExampleDlg *) GetParent(); if (pParentSheet) pParentSheet->SwitchPage(0); } return CDialog::OnCommand(wParam, lParam); }