#include "master.h" #include #include #include #include #include #include #include #include #include #include "mediadet.h" #include "stream.h" #include "menu.h" #include "misc.h" #include "gui.h" #include "systray.h" #include "playlist.h" #include "metaparse.h" #include "comfunct/comfunct.h" IGraphBuilder *pGraph = NULL; IMediaControl *pControl = NULL; IMediaSeeking *pSeek = NULL; IBasicAudio *pVolume = NULL; DWORD dwMaxSliderPos = 0, capable = AM_SEEKING_CanSeekAbsolute | AM_SEEKING_CanGetDuration; LPTSTR szVolume = NULL, lpSharedMem = NULL; bool bCanSeek = false; REFERENCE_TIME FileTimeinNanos = 0; HANDLE hMemMap = NULL, hInetStreamThread = NULL; HMODULE hAudioSE = NULL; bool GetMute(void) { signed long lVolume = 0L; pVolume->lpVtbl->get_Volume(pVolume, &lVolume); if(lVolume == VOLUME_MUTE) { return true; } else return false; } bool SetMute(bool bToMute) { extern signed long PlayVolume; if(bToMute == true) { long lVolume = 0L; pVolume->lpVtbl->get_Volume(pVolume, &lVolume); PlayVolume = lVolume; if(SUCCEEDED(pVolume->lpVtbl->put_Volume(pVolume, VOLUME_MUTE))) { return true; } else return false; } else { if(SUCCEEDED(pVolume->lpVtbl->put_Volume(pVolume, PlayVolume))) { return true; } else return false; } } bool DShowInit() { HRESULT hr = 0; hr = CoCreateInstance(&CLSID_FilterGraph, NULL, CLSCTX_INPROC_SERVER, &IID_IGraphBuilder, (void**)&pGraph); if(FAILED(hr)) { HRErrorInfo(hr); ErrorMessage(GetLocalText(55)); return false; } pGraph->lpVtbl->QueryInterface(pGraph, &IID_IMediaControl, (void **)&pControl); pGraph->lpVtbl->QueryInterface(pGraph, &IID_IBasicAudio, (void **)&pVolume); pGraph->lpVtbl->QueryInterface(pGraph, &IID_IMediaSeeking, (void **)&pSeek); return true; } void DShowRelease() { SAFE_RELEASE(pControl); SAFE_RELEASE(pSeek); SAFE_RELEASE(pGraph); SAFE_RELEASE(pVolume); return; } void GetOpenFile(HWND hwnd, const bool bTrayed) { OPENFILENAME ofn = {0}; unsigned long lFilesSelected = 1L; static bool bSuccess = false; TCHAR szFileName[MAX_PATH] = TEXT(""); TCHAR szMyMusic[MAX_PATH] = TEXT(""); LPCTSTR szFilter = GetLocalText(154); if(pGraph == NULL) { if(DShowInit() == false) { return; } } if(bSuccess == false) { GetMyMusicDir(hwnd, szMyMusic); bSuccess = true; } ofn.lStructSize = sizeof(OPENFILENAME); ofn.hwndOwner = hwnd; ofn.lpstrFilter = szFilter; ofn.lpstrFile = szFileName; ofn.nFilterIndex = 6; ofn.lpstrTitle = GetLocalText(56); ofn.nMaxFile = MAX_PATH; ofn.Flags = OFN_EXPLORER | OFN_FILEMUSTEXIST | OFN_PATHMUSTEXIST | OFN_HIDEREADONLY | OFN_NONETWORKBUTTON | OFN_ALLOWMULTISELECT; ofn.lpstrDefExt = TEXT("m3u"); if(bSuccess == true) { ofn.lpstrInitialDir = szMyMusic; } if(GetOpenFileName(&ofn)) { RAWDATA rd = {0}; TCHAR* szBufferPointer = _tcschr(szFileName, TEXT('\0')); while(*(szBufferPointer + sizeof(TCHAR)) != TEXT('\0')) { lFilesSelected++; szBufferPointer = _tcschr(szBufferPointer + sizeof(TCHAR), TEXT('\0')); } /* Find how many files have been selected */ if(lFilesSelected == 1L) /* if the while loop never gets entered only 1 file has been selected */ { ProcessFile(hwnd, bTrayed, szFileName, NULL); return; } else { lFilesSelected -= 1L; /* Take away the 1 provided in the initialisation */ rd.lNumFiles = lFilesSelected; rd.szPlaylist = szFileName; rd.hwnd = hwnd; SendMessage(hwnd, WM_MAKEPLAYLIST, (WPARAM)&rd, 0); return; } } else if(CommDlgExtendedError() == 0) { DShowRelease(); return; } } void ProcessFile(HWND hwnd, bool bTrayed, LPCTSTR szFileName, PLAYLISTDATA* pld) { WCHAR* szWideFileName = NULL; LPCTSTR szFileExt = PathFindExtension(szFileName); HRESULT hr = 0; if(pGraph == NULL) { DShowInit(); } if(CompareString(LOCALE_INVARIANT, NORM_IGNORECASE, szFileExt, -1, TEXT(".mid"), -1) != CSTR_EQUAL && CompareString(LOCALE_INVARIANT, NORM_IGNORECASE, szFileExt, -1, TEXT(".mod"), -1) != CSTR_EQUAL) { if(PathIsURL(szFileName) == TRUE) { SetDlgItemText(hwnd, IDI_FILENAME, szFileName); SetStatus(hwnd, IDI_STATUS, 0, GetLocalText(7)); SendMessage(hwnd, WM_COMMAND, MAKEWPARAM(IDI_CONT_PLAY, 0), (LPARAM)NULL); return; } if((_tcscmp(szFileName, TEXT("")) == 0) || IsFileAudio(szFileName) != true) { if(pld == NULL) { ErrorMessage(GetLocalText(57)); return; } else { PostMessage(hwnd, WM_COMMAND, MAKEWPARAM(IDI_PV_REMOVE_TRACK, pld->lCurrentPlayingFile), (LPARAM)0xDEAD); if(pld->bShuffle == true) { pld->lCurrentPlayingFile = GetRandomTrack(pld); return ProcessFile(hwnd, bTrayed, pld->PlaylistItems[pld->lCurrentPlayingFile], pld); } else { if(pld->lCurrentPlayingFile == (pld->lNumOfFilesinPlaylist - 1)) { pld->lCurrentPlayingFile = 0; } else pld->lCurrentPlayingFile += 1; return ProcessFile(hwnd, bTrayed, pld->PlaylistItems[pld->lCurrentPlayingFile], pld); } } } } /*end of midi 'if' */ #ifndef UNICODE /* more DirectShow conversion */ szWideFileName = UnicodeConversion(szFileName); hr = pGraph->lpVtbl->RenderFile(pGraph, szWideFileName, NULL); FreePointer(szWideFileName); #else hr = pGraph->lpVtbl->RenderFile(pGraph, szFileName, NULL); #endif if(FAILED(hr)) { HRErrorInfo(hr); ErrorMessage(GetLocalText(58)); return; } bCanSeek = (S_OK == pSeek->lpVtbl->CheckCapabilities(pSeek, &capable)); FileOpen(hwnd, szFileName, bCanSeek); if(pld != NULL) { HWND hPlaylistItems = GetDlgItem(hwnd, IDI_PLAYLIST_VIEW); ListView_SetItemState(hPlaylistItems, pld->lCurrentPlayingFile, LVIS_FOCUSED, 0); } Sleep(50); /* The next line seems to be ineffectual without this */ SendMessage(hwnd, WM_COMMAND, MAKEWPARAM(IDI_CONT_PLAY, 0), (LPARAM)NULL); if(bTrayed == true) { UpdateTrayToolTip(hwnd); } return; } void FileOpen(HWND hwnd, LPCTSTR szFileName, bool bSeekable) { extern signed long PlayVolume; HMENU hParentMenu = GetMenu(hwnd), hOpenMenu = NULL; LPCTSTR szFileTitle = PathFindFileName(szFileName); TCHAR* szArtistSong = NULL; IWMMetadataEditor* pWMEdit = NULL; WCHAR* wszFileName = NULL; SetDlgItemText(hwnd, IDI_FILENAME, szFileName); ToggleButton(hwnd, true, false); SetStatus(hwnd, IDI_STATUS, 0, GetLocalText(59)); #ifndef UNICODE wszFileName = UnicodeConversion(szFileName); pWMEdit = CreateReader(wszFileName); FreePointer(wszFileName); #else pWMEdit = CreateReader(szFileName); #endif if(pWMEdit != NULL) { bool bSuccess = false; WCHAR* wszArtist = NULL, *wszTitle = NULL; bSuccess = GetID3TagArtist(pWMEdit, &wszArtist); if(bSuccess == true) { size_t s_tAttrLength = wcslen(wszArtist) + 1; GetID3TagTitle(pWMEdit, &wszTitle); s_tAttrLength += wcslen(wszTitle) + 1; s_tAttrLength += sizeof(" - "); #ifdef UNICODE szArtistSong = malloc(s_tAttrLength * sizeof(WCHAR)); _snwprintf(szArtistSong, s_tAttrLength, L"%s - %s", wszArtist, wszTitle); #else szArtistSong = malloc(s_tAttrLength); { char* szArtist, *szTitle; szArtist = ASCIIConversion(wszArtist); szTitle = ASCIIConversion(wszTitle); _snprintf(szArtistSong, s_tAttrLength, "%s - %s", szArtist, szTitle); FreePointer(szArtist); FreePointer(szTitle); } #endif free(wszArtist); free(wszTitle); SetStatus(hwnd, IDI_STATUS, 1, szArtistSong); free(szArtistSong); } else SetStatus(hwnd, IDI_STATUS, 1, szFileTitle); // bSuccess == false } else SetStatus(hwnd, IDI_STATUS, 1, szFileTitle); // pWMEdit == NULL if(bSeekable == true) { HRESULT hr = 0; pSeek->lpVtbl->SetTimeFormat(pSeek, &TIME_FORMAT_MEDIA_TIME); hr = pSeek->lpVtbl->GetDuration(pSeek, &FileTimeinNanos); if(FAILED(hr)) { HRErrorInfo(hr); ErrorMessage(GetLocalText(60)); } SendDlgItemMessage(hwnd, IDI_SLIDER, TBM_SETRANGE, true, MAKELONG(0, 100)); dwMaxSliderPos = (DWORD)SendDlgItemMessage(hwnd, IDI_SLIDER, TBM_GETRANGEMAX, 0, 0); ShowWindow(GetDlgItem(hwnd, IDI_DIVIDE), SW_SHOW); TotalTimeUpdate(hwnd); ElapsedTimeUpdate(hwnd, 0); } else { EnableWindow(GetDlgItem(hwnd, IDI_SLIDER), false); } pVolume->lpVtbl->put_Volume(pVolume, PlayVolume); ChangeMenuState(hwnd, MF_ENABLED); hOpenMenu = GetSubMenu(hParentMenu, FILE_MENU); return; } void OpenMP3URL(HWND hwnd, LPCTSTR szUrl, bool IsMP3) { extern signed long PlayVolume; HMENU hParentMenu = GetMenu(hwnd), hControlMenu = NULL, hOpenMenu = NULL; if(IsMP3 == true) { ASEFUNC InetThread = NULL; DWORD dwNotNeeded = 0; size_t s_tUrlLen = (_tcslen(szUrl) * sizeof(TCHAR)); if(s_tUrlLen < (MAX_PATH * sizeof(TCHAR))) { s_tUrlLen = MAX_PATH * sizeof(TCHAR); } EnableWindow(GetDlgItem(hwnd, IDI_CONT_PLAY), false); hAudioSE = LoadLibrary(TEXT("AudioSE.dll")); InetThread = (ASEFUNC)GetProcAddress(hAudioSE, "ASEThread"); hMemMap = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, (DWORD)s_tUrlLen, TEXT("URLMap")); if(hMemMap == NULL || GetLastError() == ERROR_ALREADY_EXISTS) { ErrorInfo(); ErrorMessage(GetLocalText(61)); return; } lpSharedMem = (LPTSTR)MapViewOfFile(hMemMap, FILE_MAP_ALL_ACCESS, 0, 0, s_tUrlLen); if(lpSharedMem == NULL) { ErrorInfo(); ErrorMessage(GetLocalText(62)); return; } CopyMemory((LPVOID)lpSharedMem, szUrl, s_tUrlLen); ShowWindow(GetDlgItem(hwnd, IDI_DIVIDE), SW_SHOW); hInetStreamThread = CreateThread(NULL, 0, InetThread, (LPVOID)s_tUrlLen, 0, &dwNotNeeded); } if(pVolume == NULL) { DShowInit(); } bCanSeek = false; pVolume->lpVtbl->put_Volume(pVolume, PlayVolume); SendDlgItemMessage(hwnd, IDI_VOLUME, TBM_SETPOS, true, 0); szVolume = VolumeTextFromLong(0L, szVolume); SetStatus(hwnd, IDI_STATUS, 2, szVolume); hControlMenu = GetSubMenu(hParentMenu, CONTROL_MENU); if(IsMP3 == true) { ToggleButton(hwnd, true, true); EnableMenuItem(hControlMenu, IDI_CONT_PLAY, MF_BYCOMMAND | MF_GRAYED); EnableMenuItem(hControlMenu, IDI_CONT_PAUSE, MF_BYCOMMAND | MF_GRAYED); EnableWindow(GetDlgItem(hwnd, IDI_CONT_PAUSE), false); } else { ToggleButton(hwnd, true, false); } EnableWindow(GetDlgItem(hwnd, IDI_SLIDER), false); ChangeMenuState(hwnd, MF_ENABLED); hOpenMenu = GetSubMenu(hParentMenu, FILE_MENU); EnableMenuItem(hOpenMenu, IDI_FILE_OPEN, MF_BYCOMMAND | MF_GRAYED); DrawMenuBar(hwnd); return; } void CommandLineOpen(LPTSTR szFileName, HWND hwnd) { AP_DATACOPY adc = {0}; PathUnquoteSpaces(szFileName); adc.szFileName = szFileName; adc.hwnd = hwnd; if(CheckForOtherInstances(&adc) == true) return; if(GetPlaylistType(szFileName) != PLAYLIST_ERROR) { TCHAR szFileNameCopy[MAX_PATH] = TEXT(""); memcpy(szFileNameCopy, szFileName, ((_tcslen(szFileName) + 1) * sizeof(TCHAR))); PathRemoveFileSpec(szFileNameCopy); SetCurrentDirectory(szFileNameCopy); /* This helps to resolve relative file paths in playlists by using the playlist's path as the root */ SendMessage(hwnd, WM_COMMAND, MAKEWPARAM(IDI_PLAYLIST_COMMANDLINE, 0), (LPARAM)szFileName); return; } ProcessFile(hwnd, IsIconic(hwnd), szFileName, NULL); return; } void CloseStream(HWND hwnd, HANDLE* hDownloadedStream) { HMENU hParentMenu = GetMenu(hwnd), hOpenMenu = NULL; DShowRelease(); SetStatus(hwnd, IDI_STATUS, 0, GetLocalText(7)); SetStatus(hwnd, IDI_STATUS, 1, TEXT("")); SetDlgItemText(hwnd, IDI_CONT_PAUSE, GetLocalText(2)); ClearTimes(hwnd); ToggleButton(hwnd, false, false); ChangeMenuState(hwnd, MF_GRAYED); hOpenMenu = GetSubMenu(hParentMenu, FILE_MENU); EnableMenuItem(hOpenMenu, IDI_FILE_OPEN, MF_BYCOMMAND | MF_ENABLED); EnableMenuItem(hOpenMenu, IDI_FILE_SAVESTREAM, MF_BYCOMMAND | MF_GRAYED); DrawMenuBar(hwnd); if(hDownloadedStream != NULL) { CloseHandle(*hDownloadedStream); *hDownloadedStream = NULL; } return; } void StopInternetDownload() { STOPPROC StopDownloading = NULL; StopDownloading = (STOPPROC)GetProcAddress(hAudioSE, "StopDownloading"); StopDownloading(); return; } void SaveAudioStream(HANDLE hTempStream, LPTSTR szNewPath) { static HANDLE hTempAudioFile = NULL; if(hTempStream != NULL) { hTempAudioFile = hTempStream; } else { HANDLE hNewFile = NULL; DWORD dwFileSize = 0, dwBytesRead = 0, dwBytesWritten = 0; BYTE* byFileData = NULL; hNewFile = CreateFile(szNewPath, GENERIC_WRITE | DELETE, FILE_SHARE_WRITE, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); if(hNewFile == NULL || hNewFile == INVALID_HANDLE_VALUE) { ErrorInfo(); ErrorMessage(GetLocalText(63)); return; } dwFileSize = GetFileSize(hTempAudioFile, NULL); byFileData = malloc(dwFileSize); if(byFileData != NULL) { if(ReadFile(hTempAudioFile, &byFileData[0], dwFileSize, &dwBytesRead, NULL) != false) { WriteFile(hNewFile, &byFileData[0], dwBytesRead, &dwBytesWritten, NULL); } else { ErrorInfo(); ErrorMessage(GetLocalText(64)); DeleteFile(hNewFile); } } CloseHandle(hNewFile); CloseHandle(hTempAudioFile); free(byFileData); } return; }