/*************************************************
*           BK Emulator v3.9 for Windows         *
*************************************************/

/*
File: TapeManagerDlg.h
Version: 1.0.0
Written by: Yuriy Kalmykov <kalmykov@stoik.com>
    Copyright (c) 2002-2004 Yuriy Kalmykov

    BK Emulator is a program emulated hardware environment for running
code for BK 0010(01) in different configurations.

    This code may be used in compiled form in any way you desire.
This file or it's parts can't be redistributed without the authors
written consent, but can be modified for your private needs.
    Providing that this notice and the authors name and all copyright
notices remains intact.

    Please, an email me to know how you are using it and where. You can
ask me for any information about this below code or any attendant
knowledge.

    This file is provided "as is" with no expressed or implied warranty.
The author accepts no liability for any damage or loss of business that
this product may cause.
*/


#pragma once

// TapeManagerDlg.h : header file
//

#include <afxmt.h>
#include <Mmsystem.h>

#include "Defines.h"
#include "Tape.h"
#include "TapeUnit.h"

/////////////////////////////////////////////////////////////////////////////
// CTapeManagerDlg dialog

class CTapeManagerDlg : public CDialogEx
{
		enum                {CAPTURE_BUFFERS_NUM = 5};
		enum                {OUTSTRINGS_COUNT = 300};
		enum                {SILENCE_THRESHOLD = 128};
		enum                {COLUMN_TYPE = 0, COLUMN_NAME, COLUMN_ADDR, COLUMN_LEN,
		                     COLUMN_TIME, COLUMN_WAVELEN, COLUMN_CRC, COLUMN_PATH
		                    };
		enum                {COMBO_NONE = 0, COMBO_SAVE_AS_MSF, COMBO_SAVE_AS_WAV, COMBO_SAVE_AS_BIN};

		int                 m_nSilenceLength;

		CCriticalSection    m_csModifyBuffer;
		CList <BYTE *, BYTE *>m_captureBuffers;
		BYTE                *m_CurrentCaptureBuffer; //указатель на текущий буфер из m_captureBuffers

		bool                m_bRun;
		HWAVEIN             m_hWaveIn;
		WAVEHDR             m_WHDR[CAPTURE_BUFFERS_NUM];
		WAVEFORMATEX        m_wfx;

		int                 m_nOutStringsCount;
		CStringList         m_outStrings;

		bool                m_bCaptureMode;
		DWORD               m_nCaptureOffset;
		DWORD               m_nCaptureLength;
		CTape               m_headReader;
		CFile               m_captureFile;
		CString             m_strCaptureFileName;
		CList<CString, CString &> m_strCaptureFileNameList; //список временных файлов, которые надо удалить при закрытии диалога

		CImageList          m_imgList;
		CWinThread         *m_pStatusThread;
		HANDLE              m_hStatusExit;
		HANDLE              m_hStatusNew;
		CCriticalSection    m_csModifyStatus;

		int                 m_nTapePos;
		int                 m_nTapeCount;
		CTapeUnit          *m_pTapeUnit;

		CString             m_strCurrentFolder;

		// Capture methods
		UINT                FillDevices();
		bool                OpenDevice();
		void                CloseDevice();
		void                PrepareBuffers();
		void                UnPrepareBuffers();
		void                RemoveBuffers();
		void                InitBuffers();
		static void CALLBACK waveInProc(HWAVEIN hwi, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2);
		void                ProcessHeader(WAVEHDR *pHdr);

		static UINT         StatusThreadWrapper(CTapeManagerDlg *pThis);
		void                StatusThread();

		void                GetAllBuffers(BYTE *pBuffer);
		inline DWORD        GetBufferLength()
		{
			return m_wfx.nAvgBytesPerSec;
		}
		inline DWORD        GetAllBuffersLength()
		{
			return GetBufferLength() * CAPTURE_BUFFERS_NUM;
		}
		void                ClearBuffers();

		void                DebugDraw(BYTE *pBuffer, int nBufferLength);
		void                OutString(const CString &strOut);

		CString             GetTmpFilePath();
		bool                WriteBuffer(BYTE *pBuff, DWORD nSize);
		bool                IsCaptureEnd(BYTE *pBuff, DWORD nSize);

		// Get file status methods
		void                InitListCtrl();
		void                InitComboCtrl();
		void                InsertNewUnit(CTapeUnit *pUnit);
		void                RetrieveInfo(CTapeUnit *pUnit);
		void                FileListChanged(int nTapeCount);
		void                SetFolder(const CString &strFolder);
		void                DeleteUnits(bool bSelected);
		void                SaveUnitsAs(int type);

// Construction
	public:
		CTapeManagerDlg(CWnd *pParent = nullptr);   // standard constructor
		virtual ~CTapeManagerDlg();

// Dialog Data
		enum { IDD = IDD_TAPE_MANAGER };
		CListCtrl   m_list;


// Overrides
	protected:
		virtual void DoDataExchange(CDataExchange *pDX) override;    // DDX/DDV support

// Implementation
	protected:
		virtual BOOL OnInitDialog() override;
		virtual void OnCancel() override;
		afx_msg LRESULT OnBufferReady(WPARAM wParam, LPARAM lParam);
		afx_msg LRESULT OnInfoReady(WPARAM wParam, LPARAM lParam);
		afx_msg void OnTmLoad();
		afx_msg void OnGetdispinfoTmList(NMHDR *pNMHDR, LRESULT *pResult);
		afx_msg void OnTmBrowse();
		afx_msg void OnTmRemove();
		afx_msg void OnUpdateTmRemove(CCmdUI *pCmdUI);
		afx_msg void OnSelendokTmSaveAs();
		afx_msg void OnUpdateSelendokTmSaveAs(CCmdUI *pCmdUI);
		afx_msg void OnRclickTmList(NMHDR *pNMHDR, LRESULT *pResult);
		afx_msg void OnTmSelectall();
		DECLARE_MESSAGE_MAP()
};

