| /********************************************************************* |
| * * |
| * rolex.c: Windows clock application for WINE (by Jim Peterson) * |
| * * |
| * This is a translation of a Turbo Pascal OWL application I made * |
| * once, so it's a little flaky (tons of globals, functions that * |
| * could have been in-lined, etc.). The source code should easily * |
| * compile with a standard Win32 C compiler. * |
| * * |
| * To try it out, type 'make rolex'. * |
| * * |
| *********************************************************************/ |
| |
| #include <math.h> |
| #include <string.h> |
| #include "windows.h" |
| |
| char AppName[] = "Rolex"; |
| char WindowName[] = "Rolex"; |
| int WindowWidth = 100; |
| int WindowHeight = 121; |
| COLORREF FaceColor = RGB(192,192,192); |
| COLORREF HandColor = RGB(0,0,0); |
| COLORREF EtchColor = RGB(0,0,0); |
| |
| float Pi=3.1415926; |
| |
| typedef struct |
| { |
| int StartX,StartY,EndX,EndY; |
| } HandData; |
| |
| int MaxX,MaxY; |
| HandData OldSecond,OldHour,OldMinute; |
| |
| HWND HWindow; |
| |
| void DrawFace(HDC dc) |
| { |
| int MidX, MidY, t; |
| |
| MidX=MaxX/2; |
| MidY=MaxY/2; |
| SelectObject(dc,CreateSolidBrush(FaceColor)); |
| SelectObject(dc,CreatePen(PS_SOLID,1,EtchColor)); |
| Ellipse(dc,0,0,MaxX,MaxY); |
| |
| for(t=0; t<12; t++) |
| { |
| MoveToEx(dc,MidX+sin(t*Pi/6)*0.9*MidX,MidY-cos(t*Pi/6)*0.9*MidY,NULL); |
| LineTo(dc,MidX+sin(t*Pi/6)*0.8*MidX,MidY-cos(t*Pi/6)*0.8*MidY); |
| } |
| if(MaxX>64 && MaxY>64) |
| for(t=0; t<60; t++) |
| SetPixel(dc,MidX+sin(t*Pi/30)*0.9*MidX,MidY-cos(t*Pi/30)*0.9*MidY |
| ,EtchColor); |
| DeleteObject(SelectObject(dc,GetStockObject(NULL_BRUSH))); |
| DeleteObject(SelectObject(dc,GetStockObject(NULL_PEN))); |
| memset(&OldSecond,0,sizeof(OldSecond)); |
| memset(&OldMinute,0,sizeof(OldMinute)); |
| memset(&OldHour,0,sizeof(OldHour)); |
| } |
| |
| void DrawHourHand(HDC dc) |
| { |
| MoveToEx(dc, OldHour.StartX, OldHour.StartY, NULL); |
| LineTo(dc, OldHour.EndX, OldHour.EndY); |
| } |
| |
| void DrawMinuteHand(HDC dc) |
| { |
| MoveToEx(dc, OldMinute.StartX, OldMinute.StartY, NULL); |
| LineTo(dc, OldMinute.EndX, OldMinute.EndY); |
| } |
| |
| void DrawSecondHand(HDC dc) |
| { |
| MoveToEx(dc, OldSecond.StartX, OldSecond.StartY, NULL); |
| LineTo(dc, OldSecond.EndX, OldSecond.EndY); |
| } |
| |
| BOOL UpdateHourHand(HDC dc,int MidX,int MidY,int XExt,int YExt,WORD Pos) |
| { |
| int Sx, Sy, Ex, Ey; |
| BOOL rv; |
| |
| rv = FALSE; |
| Sx = MidX; Sy = MidY; |
| Ex = MidX+sin(Pos*Pi/6000)*XExt; |
| Ey = MidY-cos(Pos*Pi/6000)*YExt; |
| rv = ( Sx!=OldHour.StartX || Ex!=OldHour.EndX || |
| Sy!=OldHour.StartY || Ey!=OldHour.EndY ); |
| if(rv)DrawHourHand(dc); |
| OldHour.StartX = Sx; OldHour.EndX = Ex; |
| OldHour.StartY = Sy; OldHour.EndY = Ey; |
| return rv; |
| } |
| |
| BOOL UpdateMinuteHand(HDC dc,int MidX,int MidY,int XExt,int YExt,WORD Pos) |
| { |
| int Sx, Sy, Ex, Ey; |
| BOOL rv; |
| |
| rv = FALSE; |
| Sx = MidX; Sy = MidY; |
| Ex = MidX+sin(Pos*Pi/30000)*XExt; |
| Ey = MidY-cos(Pos*Pi/30000)*YExt; |
| rv = ( Sx!=OldMinute.StartX || Ex!=OldMinute.EndX || |
| Sy!=OldMinute.StartY || Ey!=OldMinute.EndY ); |
| if(rv)DrawMinuteHand(dc); |
| OldMinute.StartX = Sx; OldMinute.EndX = Ex; |
| OldMinute.StartY = Sy; OldMinute.EndY = Ey; |
| return rv; |
| } |
| |
| BOOL UpdateSecondHand(HDC dc,int MidX,int MidY,int XExt,int YExt,WORD Pos) |
| { |
| int Sx, Sy, Ex, Ey; |
| BOOL rv; |
| |
| rv = FALSE; |
| Sx = MidX; Sy = MidY; |
| Ex = MidX+sin(Pos*Pi/3000)*XExt; |
| Ey = MidY-cos(Pos*Pi/3000)*YExt; |
| rv = ( Sx!=OldSecond.StartX || Ex!=OldSecond.EndX || |
| Sy!=OldSecond.StartY || Ey!=OldSecond.EndY ); |
| if(rv)DrawSecondHand(dc); |
| OldSecond.StartX = Sx; OldSecond.EndX = Ex; |
| OldSecond.StartY = Sy; OldSecond.EndY = Ey; |
| return rv; |
| } |
| |
| void Idle(HDC idc) |
| { |
| SYSTEMTIME st; |
| WORD H, M, S, F; |
| int MidX, MidY; |
| HDC dc; |
| BOOL Redraw; |
| |
| if(idc) |
| dc=idc; |
| else |
| dc=GetDC(HWindow); |
| if(!dc)return; |
| |
| GetLocalTime(&st); |
| H = st.wHour; |
| M = st.wMinute; |
| S = st.wSecond; |
| F = st.wMilliseconds / 10; |
| F = F + S*100; |
| M = M*1000+F/6; |
| H = H*1000+M/60; |
| MidX = MaxX/2; |
| MidY = MaxY/2; |
| SelectObject(dc,CreatePen(PS_SOLID,1,FaceColor)); |
| Redraw = FALSE; |
| if(UpdateHourHand(dc,MidX,MidY,MidX*0.5,MidY*0.5,H)) Redraw = TRUE; |
| if(UpdateMinuteHand(dc,MidX,MidY,MidX*0.65,MidY*0.65,M)) Redraw = TRUE; |
| if(UpdateSecondHand(dc,MidX,MidY,MidX*0.79,MidY*0.79,F)) Redraw = TRUE; |
| DeleteObject(SelectObject(dc,CreatePen(PS_SOLID,1,HandColor))); |
| if(Redraw) |
| { |
| DrawSecondHand(dc); |
| DrawMinuteHand(dc); |
| DrawHourHand(dc); |
| } |
| DeleteObject(SelectObject(dc,GetStockObject(NULL_PEN))); |
| if(!idc) ReleaseDC(HWindow,dc); |
| } |
| |
| LRESULT CALLBACK ProcessAppMsg(HWND wnd,UINT msg,WPARAM w,LPARAM l) |
| { |
| PAINTSTRUCT PaintInfo; |
| HDC dc; |
| |
| switch(msg) |
| { |
| case WM_PAINT: |
| if(GetUpdateRect(wnd,NULL,FALSE)) |
| { |
| dc=BeginPaint(wnd,&PaintInfo); |
| DrawFace(dc); |
| Idle(dc); |
| EndPaint(wnd,&PaintInfo); |
| } |
| break; |
| |
| case WM_SIZE: |
| MaxX = LOWORD(l); |
| MaxY = HIWORD(l); |
| break; |
| |
| case WM_DESTROY: |
| PostQuitMessage (0); |
| break; |
| |
| default: |
| return DefWindowProc (wnd, msg, w, l); |
| } |
| return 0l; |
| } |
| |
| WPARAM MessageLoop() |
| { |
| MSG msg; |
| |
| while(1) |
| { |
| Sleep(1); /* sleep 1 millisecond */ |
| if(PeekMessage(&msg,0,0,0,PM_REMOVE)) |
| { |
| if(msg.message == WM_QUIT) return msg.wParam; |
| TranslateMessage(&msg); |
| DispatchMessage(&msg); |
| } |
| else |
| Idle(NULL); |
| } |
| } |
| |
| int PASCAL WinMain (HANDLE inst, HANDLE prev, LPSTR cmdline, int show) |
| { |
| WNDCLASS class; |
| if(!prev) |
| { |
| class.style = CS_HREDRAW | CS_VREDRAW; |
| class.lpfnWndProc = ProcessAppMsg; |
| class.cbClsExtra = 0; |
| class.cbWndExtra = 0; |
| class.hInstance = inst; |
| class.hIcon = 0; /* Draw my own icon */ |
| class.hCursor = LoadCursor (0, IDC_ARROW); |
| class.hbrBackground = (HBRUSH)(COLOR_BACKGROUND + 1); |
| class.lpszMenuName = 0; |
| class.lpszClassName = AppName; |
| } |
| if (!RegisterClass (&class)) return -1; |
| |
| HWindow=CreateWindowEx(WS_EX_TOPMOST,AppName,WindowName,WS_OVERLAPPEDWINDOW, |
| CW_USEDEFAULT,CW_USEDEFAULT,WindowWidth,WindowHeight, |
| 0,0,inst,0); |
| memset(&OldSecond,0,sizeof(OldSecond)); |
| memset(&OldMinute,0,sizeof(OldMinute)); |
| memset(&OldHour,0,sizeof(OldHour)); |
| MaxX = WindowWidth; |
| MaxY = WindowHeight; |
| |
| ShowWindow (HWindow, show); |
| UpdateWindow (HWindow); |
| |
| return MessageLoop(); |
| } |