unit MesView;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  ComCtrls, Buttons, ExtCtrls, StdCtrls, Db, Grids, DBGrids, frxClass,
  frxDBSet, DBGridEh, GridsEh;

Const
  MesLogErrMes = 'Ошибка чтения данных из архива сообщений!';

type
  TMesViewForm = class(TForm)
    Panel1: TPanel;
    Panel2: TPanel;
    btOnLine: TSpeedButton;
    btRefresh: TSpeedButton;
    DeltaPanel: TPanel;
    btSetDelta: TSpeedButton;
    DeltaTimePicker: TDateTimePicker;
    MoveToPanel: TPanel;
    btSetMoveTo: TSpeedButton;
    MoveToDatePicker: TDateTimePicker;
    MoveToTimePicker: TDateTimePicker;
    EmptyPanel: TPanel;
    Panel3: TPanel;
    btMoveTo: TSpeedButton;
    btForward: TSpeedButton;
    btBack: TSpeedButton;
    btDelta: TSpeedButton;
    DataSource: TDataSource;
    Timer: TTimer;
    DeltaDayEdit: TEdit;
    DateDeltaUpDown: TUpDown;
    btPrint: TSpeedButton;
    grid: TDBGridEh;
    Label1: TLabel;
    Label2: TLabel;
    CloseButton: TButton;
    procedure CloseButtonClick(Sender: TObject);
    procedure FormActivate(Sender: TObject);
    procedure FormCreate(Sender: TObject);
    procedure FormDeactivate(Sender: TObject);
    procedure btOnLineClick(Sender: TObject);
    procedure OnLineUpdateList(Sender: TObject);
    procedure UpdateList(Sender: TObject);
    procedure btBackClick(Sender: TObject);
    procedure btForwardClick(Sender: TObject);
    procedure btDeltaClick(Sender: TObject);
    procedure btSetDeltaClick(Sender: TObject);
    procedure btMoveToClick(Sender: TObject);
    procedure btSetMoveToClick(Sender: TObject);
    procedure btFiltOprClick(Sender: TObject);
    procedure btPrintClick(Sender: TObject);
    procedure gridDrawColumnCell(Sender: TObject; const Rect: TRect;
      DataCol: Integer; Column: TColumnEh; State: TGridDrawState);
    procedure gridApplyFilter(Sender: TObject);
    procedure FormClose(Sender: TObject; var Action: TCloseAction);
  private
    OnLineMode: boolean;

    FiltTags: array of integer;
    FiltMsgs: array of integer;
    FiltStr: string;
    DateBeg, DateEnd: TDateTime;
    DateDelta: TDateTime;
    DateOneDay: TDateTime;

    procedure CreateFilterStr;
    function getSelectSQL: string;
  public
    { Public declarations }
    procedure CreateList;
  end;

var
  MesViewForm: TMesViewForm = nil;

implementation
uses
  infodlg,
  connecting,
  IniFiles,
  HyperStr,
  DataMod,
  RpVisualGlobal;

{$R *.DFM}

procedure TMesViewForm.FormCreate(Sender: TObject);
begin
  DateOneDay := 1;

  DateDelta := DateOneDay;

  OnLineMode := true;

  DeltaPanel.Align := alClient;
  MoveToPanel.Align := alClient;
  DeltaPanel.Visible := false;
  MoveToPanel.Visible := false;


  FiltTags := nil;
  FiltMsgs := nil;
end;

procedure TMesViewForm.FormActivate(Sender: TObject);
begin
  CreateList;
  WindowState := wsMaximized;

  grid.Columns[1].Width := 70;
  grid.Columns[2].Width := 70;

  with TIniFile.Create(CurDir + RpVisualIniFile) do begin
    grid.Columns[3].Width := ReadInteger('MesView', 'GridColumn3', 200);
    grid.Columns[4].Width := ReadInteger('MesView', 'GridColumn4', 200);
    Free;
  end;
end;

procedure TMesViewForm.CloseButtonClick(Sender: TObject);
begin
  close;
end;

function TMesViewForm.getSelectSQL: string;
begin
  Result :=
    'select m.idm, m.dt, l.name, t.descr, m.data, u.name uname, p.name pname, m.clb, m.clf, m.act from messages m ' +
    'inner join meslist l on (m.idmsg = l.idmsg) ' +
    'inner join mestags t on (m.idtag = t.idtag) ' +
    'left outer join users u on (u.iduser = m.iduser) ' +
    'left outer join places p on (m.idplace = p.id) ' +
    'where ' +
    'm.dt>''' + DateTimeToStr(DateBeg) + ''' and ' +
    'm.dt<''' + DateTimeToStr(DateEnd) + ''' ' +
    FiltStr +
    'order by dt desc';
end;


//============================================================================
// Создание списка
//============================================================================
procedure TMesViewForm.CreateList;
begin

  if not isMesloggingConnected then exit;

  try

    if OnLineMode then DateEnd := now;
    DateBeg := DateEnd - DateDelta;

    CreateFilterStr;

    dm.dsRead.Close;
    dm.dsRead.SelectSQL.Text := getSelectSQL;
//          'select m.idm, m.dt, l.name, t.descr, m.data, u.name uname, p.name pname, m.clb, m.clf, m.act from messages m ' +
//          'inner join meslist l on (m.idmsg = l.idmsg) ' +
//          'inner join mestags t on (m.idtag = t.idtag) ' +
//          'left outer join users u on (u.iduser = m.iduser) ' +
//          'left outer join places p on (m.idplace = p.id) ' +
//          'where ' +
//          'm.dt>''' + DateTimeToStr(DateBeg) + ''' and ' +
//          'm.dt<''' + DateTimeToStr(DateEnd) + ''' ' +
//          FiltStr +
//          'order by dt desc';

    dm.dsRead.Open;

    DataSource.DataSet := dm.dsRead;

    btOnLine.Down := OnLineMode;
    btOnLineClick(nil);

  except
    dm.dsRead.Transaction.Active := false;
    showInfoDlg(MesLogErrMes, mtError, [mbOk], 0);
  end;

end;



//============================================================================
// Обновление списка
//============================================================================
procedure TMesViewForm.UpdateList(Sender: TObject);
begin
  if not isMesloggingConnected then exit;

  if dm.dsRead.Active then 
  try
    DateBeg := DateEnd - DateDelta;

    CreateFilterStr;
    
    dm.dsRead.Close;
    dm.dsRead.SelectSQL.Text := getSelectSQL;
    
//        'select m.idm, m.dt, l.name, t.descr, m.clb, m.clf, m.data, m.act ' +
//        'from messages m, meslist l, mestags t where '+
//        'm.idmsg=l.idmsg and ' +
//        'm.idtag=t.idtag and ' +
//        'm.dt>''' + DateTimeToStr(DateBeg) + ''' and ' +
//        'm.dt<''' + DateTimeToStr(DateEnd) + ''' ' +
//        FiltStr +
//        'order by dt desc';

    dm.dsRead.Open;
  except
    dm.dsRead.Transaction.Active := false;
  end;
end;



procedure TMesViewForm.OnLineUpdateList(Sender: TObject);
var
  flag: boolean;
  v: integer;
begin
  if not isMesloggingConnected then exit;

  if not Active then exit;
  flag := false;

  if dm.dsRead.Active then 
  try

    try
      v := dm.dsRead.Fields[0].AsInteger;
      dm.QueryMes.Transaction.StartTransaction;


      dm.QueryMes.SQL.Text := getSelectSQL;
//        'select count(*) ' +
//        'from messages m, meslist l, mestags t where '+
//        'm.idmsg=l.idmsg and ' +
//        'm.idtag=t.idtag and ' +
//        'm.dt>''' + DateTimeToStr(DateBeg) + ''' and ' +
//        'm.dt<''' + DateTimeToStr(DateEnd) + ''' ' +
//        FiltStr +
//        ' and idm>' + IntToStr(v);

      dm.QueryMes.ExecQuery;
      flag := (dm.QueryMes.Fields[0].AsInteger <> v);
      dm.QueryMes.Transaction.Commit;
    except
      dm.QueryMes.Transaction.Active := false;
    end;

  except
  end;


  if flag then begin
    DateEnd := now;
    UpdateList(nil);
  end;

end;


//============================================================================
// Закрытие журнала
//============================================================================
procedure TMesViewForm.FormDeactivate(Sender: TObject);
begin
  DataSource.DataSet := nil;
  dm.dsRead.Active := false;
  dm.dsRead.Transaction.Active := false;
end;



//============================================================================
// Создание строки фильтра
//============================================================================
procedure TMesViewForm.CreateFilterStr;
var
  s: string;
  i: integer;
begin
  FiltStr := '';

  for i:=0 to 5 do
    if trim(grid.Columns[i].STFilter.ExpressionStr) <> '' then begin

      s := grid.Columns[i].FieldName;
      if s = 'UNAME'  then s := 'U.NAME' else
      if s = 'PNAME'  then s := 'P.NAME' else
      if s = 'NAME'   then s := 'L.NAME' else
      if s = 'DESCR'  then s := 'T.DESCR' else
      if s = 'DATA'   then s := 'M.DATA' else
        Exit;

      FiltStr := FiltStr + ' AND ' + s + ' CONTAINING '''+trim(grid.Columns[i].STFilter.ExpressionStr)+''' ';
    end;


//  Translate(FiltStr, '''', '"');
end;



//============================================================================
// OnLine
//============================================================================
procedure TMesViewForm.btOnLineClick(Sender: TObject);
begin
  OnLineMode := btOnLine.Down;
  btBack.Enabled := not OnLineMode;
  btForward.Enabled := not OnLineMode;
  btMoveTo.Enabled := not OnLineMode;
  Timer.Enabled := OnLineMode;
  Grid.Enabled := not OnLineMode;
  Grid.STFilter.Visible := not OnLineMode;
  Grid.VertScrollBar.Visible := not OnLineMode;
end;



//============================================================================
// Навигация
//============================================================================
procedure TMesViewForm.btBackClick(Sender: TObject);
begin
  DateEnd := DateEnd - DateDelta;
  UpdateList(nil);
end;

procedure TMesViewForm.btForwardClick(Sender: TObject);
begin
  DateEnd := DateEnd + DateDelta;
  UpdateList(nil);
end;



//============================================================================
// Установка DELTA
//============================================================================
procedure TMesViewForm.btDeltaClick(Sender: TObject);
begin
  DateDeltaUpDown.Position := trunc(DateDelta);
  DeltaTimePicker.DateTime := DateDelta;
  DeltaPanel.Visible := true;
end;

procedure TMesViewForm.btSetDeltaClick(Sender: TObject);
begin
  DateDelta := DateDeltaUpDown.Position;
  ReplaceTime(DateDelta, DeltaTimePicker.DateTime);
  DeltaPanel.Visible := false;
  UpdateList(nil);
end;



//============================================================================
// Переход к моменту
//============================================================================
procedure TMesViewForm.btMoveToClick(Sender: TObject);
begin
  MoveToDatePicker.DateTime := DateEnd;
  MoveToTimePicker.DateTime := DateEnd;
  MoveToPanel.Visible := true;
end;

procedure TMesViewForm.btSetMoveToClick(Sender: TObject);
begin
  DateEnd := MoveToDatePicker.DateTime;
  ReplaceTime(DateEnd, MoveToTimePicker.DateTime);
  DateEnd := DateEnd;
  MoveToPanel.Visible := false;
  UpdateList(nil);
end;

procedure TMesViewForm.btFiltOprClick(Sender: TObject);
begin
  CreateFilterStr;
  UpdateList(nil);
end;



//============================================================================
// Фильтр по имени
//============================================================================
procedure TMesViewForm.btPrintClick(Sender: TObject);
var
  flag: boolean;
begin
  DataSource.DataSet := nil;
  flag := Timer.Enabled;
  Timer.Enabled := false;

  dm.frxReport.LoadFromFile(ReportDirStd + 'MesView.fr3');
  dm.frxReport.PrepareReport;
  dm.frxReport.ShowPreparedReport;

  Timer.Enabled := flag;
  dm.dsRead.Close;
  DataSource.DataSet := dm.dsRead;
  CreateList;
end;

procedure TMesViewForm.gridDrawColumnCell(Sender: TObject;
  const Rect: TRect; DataCol: Integer; Column: TColumnEh;
  State: TGridDrawState);
begin
  if (dm.dsRead.Active) then
    if not ((dm.dsRead.Eof) and (dm.dsRead.Bof)) then begin
      Grid.Canvas.Brush.Color := dm.dsRead.FieldByName('CLB').AsInteger;
      Grid.Canvas.Font.Color := dm.dsRead.FieldByName('CLF').AsInteger;
      Grid.DefaultDrawColumnCell(Rect,DataCol,Column,State);
    end;
end;

procedure TMesViewForm.gridApplyFilter(Sender: TObject);
begin
  UpdateList(nil);
end;

procedure TMesViewForm.FormClose(Sender: TObject;
  var Action: TCloseAction);
begin
  with TIniFile.Create(CurDir + RpVisualIniFile) do begin
    WriteInteger('MesView', 'GridColumn3', grid.Columns[3].Width);
    WriteInteger('MesView', 'GridColumn4', grid.Columns[4].Width);
    Free;
  end;
end;

end.
