unit Main;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  Menus, RxMenus, RXShell, AppEvent, ExtCtrls, imglist;

const
  FrameColor = clBlue;
  DigitColor = clNavy;

type
  TfrmMain = class(TForm)
    Tray1: TRxTrayIcon;
    Menu: TRxPopupMenu;
    Close1: TMenuItem;
    AppEvents: TAppEvents;
    Timer: TTimer;
    Tray2: TRxTrayIcon;
    ImageHour: TImageList;
    Tray3: TRxTrayIcon;
    ImageMin: TImageList;
    N1: TMenuItem;
    N3: TMenuItem;
    procedure AppEventsMinimize(Sender: TObject);
    procedure Tray1DblClick(Sender: TObject);
    procedure AppEventsRestore(Sender: TObject);
    procedure Tray1Click(Sender: TObject; Button: TMouseButton;
      Shift: TShiftState; X, Y: Integer);
    procedure FormCreate(Sender: TObject);
    procedure FormDestroy(Sender: TObject);
    procedure TimerTimer(Sender: TObject);
    procedure Close1Click(Sender: TObject);
    procedure FormCloseQuery(Sender: TObject; var CanClose: Boolean);
    procedure N3Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
    pc  : Integer;
    ico : TIcon;
    bmp : TBitmap;
    msk : TBitmap;
    tit : String;
    hou : Integer;
    neg : Boolean;
    { procedures }
    procedure SetupTime;
    procedure FillImageList;
    procedure SetDelimeter(img : TBitmap);
    procedure SetDots(img : TBitmap; left, right : Boolean; off : Integer);
  end;

var
  frmMain: TfrmMain;

implementation

uses About;

{$R *.DFM}

procedure TfrmMain.AppEventsMinimize(Sender: TObject);
begin
  if NewStyleControls then ShowWindow(Application.Handle, SW_HIDE);
  Tray1.Active := true;
end;

procedure TfrmMain.Tray1DblClick(Sender: TObject);
begin
//  Application.Restore;
//  Application.BringToFront;
end;

procedure TfrmMain.AppEventsRestore(Sender: TObject);
begin
  if NewStyleControls then ShowWindow(Application.Handle, SW_SHOW);
  Tray1.Active := false;
end;

procedure TfrmMain.Tray1Click(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
//  Application.Restore;
//  Application.BringToFront;
end;

procedure TfrmMain.FormCreate(Sender: TObject);
var
  str : string;
begin
  pc  := ParamCount;
  if pc = 2 then begin
     str := ParamStr(1);
     if (str[1] = '+') or (str[1] = '-') then begin
        try
          hou := StrToInt(str);
        except
          hou := -5;
        end;
        neg := false;
        if hou < 0 then begin
           neg := true;
           hou := -hou;     
        end;
     end
     else begin
        hou := 5;
        neg := true;
     end;
     tit := ' ' + ParamStr(2) + ' - ';
  end
  else begin
     tit := ' Московское время - ';
     neg := true;
     hou := 5;
  end;
  ico := TIcon.Create;
  bmp := TBitmap.Create;
  bmp.Width  := 16;
  bmp.Height := 16;
  bmp.Canvas.Font.Name := 'MS Sans Serif';
  bmp.Canvas.Font.Height := 8;
  msk := TBitmap.Create;
  msk.Width  := 16;
  msk.Height := 16;
  msk.Canvas.Font.Name := 'MS Sans Serif';
  msk.Canvas.Font.Height := 8;
  FillImageList;
  SetupTime;
end;

procedure TfrmMain.FormDestroy(Sender: TObject);
begin
  ico.Free;
  bmp.Free;
  msk.Free;
end;

procedure TfrmMain.TimerTimer(Sender: TObject);
begin
  SetupTime;
end;

procedure TfrmMain.Close1Click(Sender: TObject);
begin
  Close;
end;

procedure TfrmMain.FormCloseQuery(Sender: TObject; var CanClose: Boolean);
begin
  CanClose := true;
end;

procedure TfrmMain.FillImageList;
var
  i : integer;
  s : string;
begin
  { fill hour settings }
  bmp.Canvas.Font.Color := DigitColor;
  msk.Canvas.Font.Color := DigitColor;
  for i := 0 to 23 do begin
      bmp.Canvas.brush.Color := clWhite;
      bmp.Canvas.FillRect(Rect(0, 0, 16, 16));
      msk.Canvas.brush.Color := clBlack;
      msk.Canvas.FillRect(Rect(0, 0, 16, 16));
      if (i div 10) = 0 then s := '0'
                        else s := IntToStr(i div 10);
      if (i mod 10) = 0 then s := s + '0'
                        else s := s + IntToStr(i mod 10);
      bmp.Canvas.TextOut(1, 2, s);
      msk.Canvas.TextOut(1, 2, s);
      SetDots(bmp, false, false, 1);
      SetDots(msk, false, false, 1);
      SetDelimeter(bmp);
      SetDelimeter(msk);
      ImageHour.Add(msk, bmp);
  end;
  { fill min settings }
  bmp.Canvas.Font.Color := DigitColor;
  msk.Canvas.Font.Color := DigitColor;
  for i := 0 to 59 do begin
      bmp.Canvas.brush.Color := clWhite;
      bmp.Canvas.FillRect(Rect(0, 0, 16, 16));
      msk.Canvas.brush.Color := clBlack;
      msk.Canvas.FillRect(Rect(0, 0, 16, 16));
      if (i div 10) = 0 then s := '0'
                        else s := IntToStr(i div 10);
      if (i mod 10) = 0 then s := s + '0'
                        else s := s + IntToStr(i mod 10);
      bmp.Canvas.TextOut(0, 2, s);
      msk.Canvas.TextOut(0, 2, s);
      SetDots(bmp, false, true, 0);
      SetDots(msk, false, true, 0);
      ImageMin.Add(msk, bmp);
  end;
end;

procedure TfrmMain.SetDots(img : TBitmap; left, right : Boolean; off : Integer);
var
  i : integer;
begin
  img.canvas.pen.color := FrameColor;
  i := off;
  while i <= 15 do begin
     img.canvas.MoveTo(i, 0);
     img.canvas.LineTo(i+2, 0);
     img.canvas.MoveTo(i, 15);
     img.canvas.LineTo(i+2, 15);
     Inc(i, 4);
  end;
  i := 1;
  while i <= 15 do begin
     if left then begin
        img.canvas.MoveTo(0, i);
        img.canvas.LineTo(0, i+2);
     end;
     if right then begin
        img.canvas.MoveTo(15, i);
        img.canvas.LineTo(15, i+2);
     end;
     Inc(i, 4);
  end;
  if left then begin
     img.canvas.MoveTo(1, 0);
     img.canvas.LineTo(2, 0);
     img.canvas.MoveTo(1, 15);
     img.canvas.LineTo(2, 15);
  end;
  if right then begin
     img.canvas.MoveTo(14, 0);
     img.canvas.LineTo(15, 0);
     img.canvas.MoveTo(14, 15);
     img.canvas.LineTo(15, 15);
  end;
end;

procedure TfrmMain.SetDelimeter(img : TBitmap);
begin
  img.canvas.pen.color := DigitColor;
  img.canvas.MoveTo(15, 6);
  img.canvas.LineTo(15, 8);
  img.canvas.MoveTo(15, 10);
  img.canvas.LineTo(15, 12);
end;

procedure TfrmMain.SetupTime;
var
  curr : TDateTime;
  hour : Word;
  min  : Word;
  sec  : Word;
  msec : Word;
  str  : String;
begin
  str  := IntToStr(hou) + ':00:00';
  if neg then
     curr := Now - StrToTime(str)
  else
     curr := Now + StrToTime(str);
  DecodeTime(curr, hour, min, sec, msec);
  ImageHour.GetIcon(hour, ico);
  Tray2.Icon.Assign(ico);
  ImageMin.GetIcon(min, ico);
  Tray3.Icon.Assign(ico);
  Tray1.Hint := tit + TimeToStr(curr) + ' ';
  Tray2.Hint := Tray1.Hint;
  Tray3.Hint := Tray1.Hint;
end;

procedure TfrmMain.N3Click(Sender: TObject);
begin
  frmAbout.ShowModal;
end;

end.
