/* The original version of this program can be found at http://damb.dk */
#include <windows.h>
#include <string.h>

#define IDT_BEETLE_TIMER 1001

void DrawBeetle(HWND hwnd, HDC dc);
HFONT Font;
HINSTANCE hInst;        /* Instance handle */
unsigned int BeetleIdx;
LRESULT CALLBACK MainWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);

static BOOL InitApplication(void)
{
  WNDCLASS wc;

  memset(&wc, 0, sizeof(WNDCLASS));
  wc.style = CS_HREDRAW | CS_VREDRAW  | CS_DBLCLKS ;
  wc.lpfnWndProc = (WNDPROC )MainWndProc;
  wc.hInstance = hInst;
  wc.hbrBackground = (HBRUSH )(COLOR_WINDOW + 1);
  wc.lpszClassName = "WinBeetleWndClass";
  wc.lpszMenuName = 0;
  wc.hCursor = LoadCursor(NULL, IDC_ARROW);
  wc.hIcon = LoadIcon(NULL, IDI_APPLICATION);
  if (!RegisterClass(&wc))
    return 0;

  /* We need a fixed sized font */
  Font = CreateFont(12,                          /* nHeight */
                    0,                           /* nWidth */
                    0,                           /* nEscapement */
                    0,                           /* nOrientation */
                    FW_NORMAL,                   /* nWeight */
                    FALSE,                       /* bItalic */
                    FALSE,                       /* bUnderline */
                    0,                           /* cStrikeOut */
                    ANSI_CHARSET,                /* nCharSet */
                    OUT_DEFAULT_PRECIS,          /* nOutPrecision */
                    CLIP_DEFAULT_PRECIS,         /* nClipPrecision */
                    DEFAULT_QUALITY,             /* nQuality */
                    DEFAULT_PITCH | FF_SWISS,    /* nPitchAndFamily */
                    "Courier");                  /* lpszFacename */
  return 1;
}

HWND CreateWinBeetleWndClassWnd(void)
{
  return CreateWindow("WinBeetleWndClass","WinBeetle",
                      WS_MINIMIZEBOX | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_MAXIMIZEBOX |
                      WS_CAPTION | WS_BORDER | WS_SYSMENU | WS_THICKFRAME,
                      CW_USEDEFAULT, 0, CW_USEDEFAULT, 0,
                      NULL,
                      NULL,
                      hInst,
                      NULL);
}

LRESULT CALLBACK MainWndProc(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam)
{
  switch (msg)
  {
    case WM_DESTROY:
      PostQuitMessage(0);
      break;
    case WM_PAINT:
    {
      PAINTSTRUCT PaintStruct;
      HDC dc = BeginPaint(hwnd, &PaintStruct);
      DrawBeetle(hwnd, dc);
      EndPaint(hwnd, &PaintStruct);
      break;
    }

    case WM_TIMER:
    {
      HDC dc = GetDC(hwnd);
      DrawBeetle(hwnd, dc);
      ReleaseDC(hwnd, dc);
      BeetleIdx++;
      return 1;
    }
    default:
      return DefWindowProc(hwnd,msg,wParam,lParam);
  }
  return 0;
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, INT nCmdShow)
{
  MSG msg;
  HWND hwndMain;
  hInst = hInstance;

  if (!InitApplication())
    return 0;

  if ((hwndMain = CreateWinBeetleWndClassWnd()) == (HWND)0)
    return 0;
  ShowWindow(hwndMain,SW_SHOW);

  SetTimer(hwndMain, IDT_BEETLE_TIMER, 300, 0);

  while(GetMessage(&msg, NULL, 0, 0))
  {
    TranslateMessage(&msg);
    DispatchMessage(&msg);
  }
  return msg.wParam;
}

const char *const Leg[] =
{
  "  )))",
  "  |||",
  "  (((",
  "  |||"
};

const char * const Boddy = " -OOOO:";

void DrawBeetle(HWND hwnd, HDC dc)
{
  TEXTMETRIC TextMetric;

  HFONT OldFont = (HFONT )SelectObject(dc, Font);
  GetTextMetrics(dc, &TextMetric);
  TextOut(dc, BeetleIdx*TextMetric.tmAveCharWidth, 0*TextMetric.tmHeight, Leg[BeetleIdx%4], strlen(Leg[BeetleIdx%4]));
  TextOut(dc, BeetleIdx*TextMetric.tmAveCharWidth, 1*TextMetric.tmHeight, Boddy, strlen(Boddy));
  TextOut(dc, BeetleIdx*TextMetric.tmAveCharWidth, 2*TextMetric.tmHeight, Leg[BeetleIdx%4], strlen(Leg[BeetleIdx%4]));

  SelectObject(dc, OldFont);
  if(BeetleIdx == 40U)
    KillTimer(hwnd, IDT_BEETLE_TIMER);
}