#include #include "ijl.h"//add ijl15.lib to Project -Settings -Link #include //for sprintf #include "resource.h" #define FULL 0 #define HALF 1 #define QUARTER 2 int CmdLineLen, Next; char CmdLine[9000]; char Start[3]; BOOL gotsize = FALSE; int x, y, Files = 0, ptr, FilenameStart = 0, Width, Height, padBytes, Resolution, Response, Quality = 90; int FilenamePtr[100]; DWORD fileSize, OutFileSize, dwBytesRead, dwBytesWritten; char Filename[MAX_PATH]; char ShortFilename[MAX_PATH]; char OutFile[MAX_PATH]; char ShortOutFile[MAX_PATH]; char JFile[1000]; char Directory[MAX_PATH]; char ErrorMsg[200]; BYTE *Buf, *pixel_buf; HWND hwnd, hDlgModeless = NULL, hwndDlg; HINSTANCE hInst; HANDLE hFile, hFile2; HCURSOR hCursor, hWaitingCursor; OPENFILENAME ofn; HDC hdcMem, hdc; HBITMAP hBitmap; PAINTSTRUCT ps; RECT rect; HGDIOBJ hObject; BITMAPINFO bmi, *pbmi = &bmi; BITMAPINFOHEADER bmih, *pbmih = &bmih; JPEG_CORE_PROPERTIES jcprops; IJLERR jerr; WIN32_FIND_DATA fd; char Version[] = "Version 1.3 by Doug Cox Dec 29, 2006"; int CALLBACK SizeProc(HWND hwndDlg, UINT message, WPARAM wParam, LPARAM lParam); int CALLBACK QualityProc(HWND, UINT, WPARAM, LPARAM); LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow) { MSG msg; WNDCLASS wndclass; char szAppName[] = "ReducePhotoSize"; hInst = hInstance; wndclass.style = CS_HREDRAW | CS_VREDRAW; wndclass.lpfnWndProc = WndProc; wndclass.cbClsExtra = 0; wndclass.cbWndExtra = 0; wndclass.hInstance = hInstance; wndclass.hIcon = LoadIcon (NULL, IDI_APPLICATION); wndclass.hCursor = LoadCursor (NULL, IDC_ARROW); wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH); wndclass.lpszMenuName = NULL; wndclass.lpszClassName = szAppName; if (!RegisterClass (&wndclass)) return 0; if (szCmdLine[0] != 0) { for (x = 0, CmdLineLen = 0; szCmdLine[x] != 0; x++) if (szCmdLine[x] != '"') CmdLine[CmdLineLen++] = szCmdLine[x]; CmdLine[CmdLineLen] = 0; } hwnd = CreateWindow (szAppName, szAppName, WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN, // WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX, // CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, 0,0,0,0, NULL, NULL, hInstance, NULL); ShowWindow (hwnd, iCmdShow); UpdateWindow (hwnd); while (GetMessage (&msg, NULL, 0, 0)) { // if (hDlgModeless == 0 || !IsDialogMessage (hDlgModeless, &msg)) { TranslateMessage (&msg); DispatchMessage (&msg); } } return msg.wParam; } LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_CREATE: Start[0] = CmdLine[0]; Start[1] = CmdLine[1]; Start[2] = CmdLine[2]; ptr = 0; if (CmdLineLen == 0) { ofn.lpstrFile = JFile; ofn.lStructSize = sizeof(OPENFILENAME); ofn.hwndOwner = hwnd; ofn.hInstance = hInst; ofn.lpstrFilter = "*.jpg\x0*.jpg\x0\x0"; ofn.lpstrCustomFilter = NULL; ofn.nMaxCustFilter = 0; ofn.nFilterIndex = 0; ofn.nMaxFile = 1000; ofn.lpstrFileTitle = ShortFilename; ofn.nMaxFileTitle = MAX_PATH; ofn.lpstrInitialDir = Directory; ofn.lpstrTitle = "Select file[s]"; ofn.Flags = OFN_HIDEREADONLY|OFN_CREATEPROMPT|OFN_ALLOWMULTISELECT|OFN_EXPLORER; ofn.nFileOffset = 0; ofn.nFileExtension = 0; ofn.lpstrDefExt = "jpg"; ofn.lCustData = 0; ofn.lpfnHook = NULL; ofn.lpTemplateName = NULL; ofn.lpstrDefExt =".jpg"; if (0 == GetOpenFileName(&ofn)) { SendMessage(hwnd, WM_DESTROY, 0, 0); return 0; } for (x = 0; (JFile[x] != 0) || (JFile[x+1] != 0); x++) { if (Files == 0) Filename[x] = JFile[x]; if (JFile[x] == 0) { if (Files == 0) FilenameStart = x; FilenamePtr[Files] = x+1; Files++; } } if (Files == 0) Files = 1; for (ptr = 0 ; Files > 0; Files--, ptr++) { if (FilenameStart != 0) { y = FilenameStart; Filename[y++] = '\\'; for (x = FilenamePtr[ptr]; JFile[x] != 0; x++, y++) Filename[y] = JFile[x]; Filename[y] = 0; } hFile = CreateFile(Filename, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL); if (hFile != INVALID_HANDLE_VALUE) fileSize = GetFileSize(hFile, NULL); else { FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM|FORMAT_MESSAGE_IGNORE_INSERTS, NULL, GetLastError(), MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), ErrorMsg, 200, NULL); MessageBox(hwnd, ErrorMsg, ERROR, MB_OK); return 0; } if (fileSize == 0) { MessageBox(hwnd, "File is empty", NULL, MB_OK); SendMessage(hwnd, WM_DESTROY, 0, 0); return 0; } else { Buf = (BYTE*)VirtualAlloc(NULL, fileSize, MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE); ReadFile(hFile, Buf, fileSize, &dwBytesRead, NULL) ; if ((Buf[0] != 0xFF) || (Buf[1] != 0xD8) || (Buf[2] != 0xFF)) {//if not a jpeg file VirtualFree(Buf, 0, MEM_RELEASE); MessageBox(hwnd, "That's not a jpeg file.", ERROR, MB_OK); DestroyWindow(hwnd); return 0; } if (FALSE == DialogBox(hInst, "SIZE", NULL, SizeProc)) { VirtualFree(Buf, 0, MEM_RELEASE); ijlFree(&jcprops); DestroyWindow(hwnd); return 0; } } CloseHandle(hFile); for (x = 0, y = 0; (Filename[x] != '.') && (Filename[x] != 0); x++, y++) OutFile[y] = Filename[x]; OutFile[y++] = 'X'; for ( ; Filename[x] != 0; x++, y++) OutFile[y] = Filename[x]; OutFile[y] = 0; for (x = 0, y = 0; ShortFilename[x] != '.'; x++, y++) ShortOutFile[y] = ShortFilename[x]; ShortOutFile[y++] = 'X'; for ( ; ShortFilename[x] != 0; x++, y++) ShortOutFile[y] = ShortFilename[x]; ShortOutFile[y] = 0; Buf = (BYTE*)VirtualAlloc(NULL, (Width + padBytes) * Height * 3, MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE); retry: Response = DialogBox(hInst, "QUALITY", hwnd, QualityProc); if (Response == 96) goto retry; if (Response != 69) { if (Response) { hFile = CreateFile(OutFile, GENERIC_READ|GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL); if (hFile != INVALID_HANDLE_VALUE) { WriteFile(hFile, Buf, OutFileSize, &dwBytesWritten, NULL); SetFileTime(hFile, NULL, NULL, &fd.ftLastWriteTime); } CloseHandle(hFile); } else goto retry; } VirtualFree(Buf, 0, MEM_RELEASE); VirtualFree(pixel_buf, 0, MEM_RELEASE); } } else while (ptr < CmdLineLen) { for (Next = ptr+1; Next < CmdLineLen; Next++) { if ((CmdLine[Next] == Start[0]) && (CmdLine[Next+1] == Start[1]) && (CmdLine[Next+2] == Start[2])) { CmdLine[Next-1] = 0;//end of that filename break; } } hFile = CreateFile(&CmdLine[ptr], GENERIC_READ|GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL); fileSize = GetFileSize(hFile, NULL); if (fileSize) { Buf = (BYTE*)VirtualAlloc(NULL, fileSize, MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE); ReadFile(hFile, Buf, fileSize, &dwBytesRead, NULL) ; if ((Buf[0] != 0xFF) || (Buf[1] != 0xD8) || (Buf[2] != 0xFF)) {//if not a jpeg file VirtualFree(Buf, 0, MEM_RELEASE); CloseHandle(hFile); MessageBox(hwnd, "That's not a jpeg file.", ERROR, MB_OK); DestroyWindow(hwnd); return 0; } // hDlgModeless = CreateDialog(hInst, "SIZE", hwnd, SizeProc); if (FALSE == DialogBox(hInst, "SIZE", NULL, SizeProc)) { CloseHandle(hFile); VirtualFree(Buf, 0, MEM_RELEASE); ijlFree(&jcprops); DestroyWindow(hwnd); return 0; } } else { ptr = Next; CloseHandle(hFile); continue; } CloseHandle(hFile); for (x = ptr, y = 0; (CmdLine[x] != '.') && (CmdLine[x] != 0); x++, y++) OutFile[y] = CmdLine[x]; OutFile[y++] = 'X'; for ( ; CmdLine[x] != 0; x++, y++) OutFile[y] = CmdLine[x]; OutFile[y] = 0; for ( ; (OutFile[y] != '\\') && (y); y--) ; if (y) y++; for (x = 0; (OutFile[y] != '.') && (OutFile[y] != 0); x++, y++) ShortOutFile[x] = OutFile[y]; ShortOutFile[x++] = 'X'; for ( ; OutFile[y] != 0; x++, y++) ShortOutFile[x] = OutFile[y]; ShortOutFile[x] = 0; Buf = (BYTE*)VirtualAlloc(NULL, (Width + padBytes) * Height * 3, MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE); retry2: Response = DialogBox(hInst, "QUALITY", hwnd, QualityProc); if (Response == 96) goto retry2; if (Response != 69) { if (Response) { hFile = CreateFile(OutFile, GENERIC_READ|GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL); if (hFile != INVALID_HANDLE_VALUE) { WriteFile(hFile, Buf, OutFileSize, &dwBytesWritten, NULL); SetFileTime(hFile, NULL, NULL, &fd.ftLastWriteTime); } CloseHandle(hFile); } else goto retry2; } VirtualFree(Buf, 0, MEM_RELEASE); VirtualFree(pixel_buf, 0, MEM_RELEASE); ptr = Next; }//end of while (TRUE) DestroyWindow(hwnd); return 0; case WM_DESTROY: // DestroyWindow(hwndDlg); // hDlgModeless = NULL; PostQuitMessage(0); return 0; } return DefWindowProc (hwnd, message, wParam, lParam); } int CALLBACK SizeProc(HWND hwndDlg, UINT message, WPARAM wParam, LPARAM lParam) { char Res[50]; static HWND hwndFull, hwndHalf, hwndQuarter; switch (message) { case WM_INITDIALOG: hWaitingCursor = LoadCursor(NULL, IDC_WAIT); jerr = ijlInit (&jcprops);//use Intel's ijl15.dll to convert JPEG files jcprops.JPGBytes = Buf;//source jcprops.JPGSizeBytes = fileSize; jcprops.JPGFile = NULL; jerr = ijlRead(&jcprops, IJL_JBUFF_READPARAMS); Width = jcprops.JPGWidth; Height = jcprops.JPGHeight; hwndFull = GetDlgItem(hwndDlg, IDC_RADIO1); hwndHalf = GetDlgItem(hwndDlg, IDC_RADIO2); hwndQuarter = GetDlgItem(hwndDlg, IDC_RADIO3); sprintf(Res, "%d by %d", Width, Height); SetWindowText(hwndFull, Res); sprintf(Res, "%d by %d", Width/2, Height/2); SetWindowText(hwndHalf, Res); sprintf(Res, "%d by %d", Width/4, Height/4); SetWindowText(hwndQuarter, Res); if (Resolution == FULL) CheckRadioButton(hwndDlg, IDC_RADIO1, IDC_RADIO3, IDC_RADIO1); else if (Resolution == HALF) CheckRadioButton(hwndDlg, IDC_RADIO1, IDC_RADIO3, IDC_RADIO2); else if (Resolution == QUARTER) CheckRadioButton(hwndDlg, IDC_RADIO1, IDC_RADIO3, IDC_RADIO3); break; case WM_COMMAND: switch (LOWORD(wParam)) { case IDC_RADIO1: Resolution = FULL; break; case IDC_RADIO2: Resolution = HALF; break; case IDC_RADIO3: Resolution = QUARTER; break; case IDOK: if (Resolution == HALF) { Width /= 2; Height /= 2; } else if (Resolution == QUARTER) { Width /= 4; Height /= 4; } SetCursor(hWaitingCursor); jcprops.DIBWidth = Width; jcprops.DIBHeight = Height; padBytes = IJL_DIB_PAD_BYTES(Width, 3); jcprops.DIBPadBytes = padBytes; pixel_buf = (BYTE*)VirtualAlloc(NULL, (Width + jcprops.DIBPadBytes) * Height * 3, MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE); jcprops.DIBBytes = pixel_buf;//destination jcprops.DIBChannels = 3; jcprops.DIBColor = IJL_BGR; if (Resolution == FULL) jerr = ijlRead (&jcprops, IJL_JBUFF_READWHOLEIMAGE); else if (Resolution == HALF) jerr = ijlRead (&jcprops, IJL_JBUFF_READONEHALF); else jerr = ijlRead (&jcprops, IJL_JBUFF_READONEQUARTER); ijlFree(&jcprops); VirtualFree(Buf, 0, MEM_RELEASE); bmih.biSize = sizeof(BITMAPINFOHEADER); bmih.biWidth = Width; bmih.biHeight = -(Height);// - for right-side-up picture bmih.biPlanes = 1; bmih.biBitCount = 24; bmih.biCompression = BI_RGB; bmih.biSizeImage = 0; bmih.biXPelsPerMeter = 0; bmih.biYPelsPerMeter = 0; bmih.biClrUsed = 0; bmih.biClrImportant = 0; bmi.bmiHeader = *pbmih; SetCursor(hCursor); EndDialog (hwndDlg, TRUE); return TRUE; break; case IDCANCEL: EndDialog (hwndDlg, FALSE); return FALSE; } } return FALSE; } int CALLBACK QualityProc(HWND hwndDlg, UINT message, WPARAM wParam, LPARAM lParam) { int x; char asdf[10]; char fdsa[15]; static HWND hwndQuality, hwndInputSize, hwndOutputSize; switch (message) { case WM_INITDIALOG: SetCursor(hWaitingCursor); jerr = ijlInit (&jcprops);//use Intel's ijl15.dll to convert JPEG files jcprops.DIBWidth = Width; jcprops.DIBHeight = Height; jcprops.DIBPadBytes = IJL_DIB_PAD_BYTES(Width, 3); jcprops.DIBChannels = 3; jcprops.DIBColor = IJL_BGR; jcprops.DIBBytes = pixel_buf;//input buffer jcprops.JPGColor = IJL_YCBCR; jcprops.JPGWidth = Width; jcprops.JPGHeight = Height; jcprops.jquality = Quality; jcprops.JPGSubsampling = IJL_422; // 4:2:2 subsampling. jcprops.JPGBytes = Buf;//output buffer jcprops.JPGSizeBytes = (Width + padBytes) * Height * 3;//estimate jcprops.JPGFile = NULL; jerr = ijlWrite(&jcprops,IJL_JBUFF_WRITEWHOLEIMAGE); OutFileSize = jcprops.JPGSizeBytes;//re-computed by ijl15.dll ijlFree(&jcprops); SetCursor(hCursor); sprintf(fdsa, "%i by %i", Width, Height); SetWindowText(GetDlgItem(hwndDlg, IDC_EDIT4), fdsa); hwndQuality = GetDlgItem(hwndDlg, IDC_EDIT1); hwndInputSize = GetDlgItem(hwndDlg, IDC_EDIT2); hwndOutputSize = GetDlgItem(hwndDlg, IDC_EDIT3); _itoa(Quality, asdf, 10); SetWindowText(hwndQuality, asdf); _itoa(fileSize/1024, asdf, 10); for (x = 0; asdf[x] != 0; x++) ; asdf[x++] = ' '; asdf[x++] = 'K'; asdf[x++] = 'B'; asdf[x++] = 0; SetWindowText(hwndInputSize, asdf); _itoa(OutFileSize/1024, asdf, 10); for (x = 0; asdf[x] != 0; x++) ; asdf[x++] = ' '; asdf[x++] = 'K'; asdf[x++] = 'B'; asdf[x++] = 0; SetWindowText(hwndOutputSize, asdf); SetWindowText(GetDlgItem(hwndDlg, IDC_EDIT5), ShortOutFile); SetFocus(hwndQuality); break; case WM_COMMAND: switch (LOWORD(wParam)) { case IDOK://Continue GetWindowText(hwndQuality, asdf, 10); x = atoi(asdf); if (x != Quality) { Quality = x; x = 96; } else x = TRUE; EndDialog (hwndDlg, x); return TRUE; case IDC_BUTTON1://Retry with new JPEG quality GetWindowText(hwndQuality, asdf, 10); Quality = atoi(asdf); EndDialog (hwndDlg, FALSE); return FALSE; case IDCANCEL: EndDialog (hwndDlg, 69); return 69; } } return FALSE; }