bsColorCtrls.pas
上传用户:hylc_2004
上传日期:2014-01-23
资源大小:46800k
文件大小:52k
源码类别:

Delphi控件源码

开发平台:

Delphi

  1. {*******************************************************************}
  2. {                                                                   }
  3. {       Almediadev Visual Component Library                         }
  4. {       BusinessSkinForm                                            }
  5. {       Version 2.90                                                }
  6. {                                                                   }
  7. {       Copyright (c) 2000-2004 Almediadev                          }
  8. {       ALL RIGHTS RESERVED                                         }
  9. {                                                                   }
  10. {       Home:  http://www.almdev.com                                }
  11. {       Support: support@almdev.com                                 }
  12. {                                                                   }
  13. {*******************************************************************}
  14. unit bsColorCtrls;
  15. interface
  16. uses Windows, SysUtils, Messages, Classes, Graphics, Controls, Forms,
  17.      BusinessSkinForm, bsSkinData, bsSkinCtrls, bsSkinBoxCtrls, Dialogs,
  18.      StdCtrls, ExtCtrls, bsEffects;
  19. type
  20.   TbsCustomColorValues = array[1..12] of TColor;
  21.   TbsSkinCustomColorGrid = class(TbsSkinPanel)
  22.   private
  23.     FColorValue: TColor;
  24.     FOnChange: TNotifyEvent;
  25.     FColCount, FRowCount: Integer;
  26.     FColorIndex: Integer;
  27.     procedure SetColCount(Value: Integer);
  28.     procedure SetRowCount(Value: Integer);
  29.   protected
  30.     procedure DrawCursor(Cnvs: TCanvas; R: TRect; pmNotMode: Boolean);
  31.     procedure CreateControlDefaultImage(B: TBitMap); override;
  32.     procedure CreateControlSkinImage(B: TBitMap); override;
  33.     procedure PaintGrid(Cnvs: TCanvas);
  34.     procedure MouseDown(Button: TMouseButton; Shift: TShiftState;
  35.       X, Y: Integer); override;
  36.   public
  37.     CustomColorValues: TbsCustomColorValues;
  38.     FColorsCount: Integer;
  39.     constructor Create(AOwner: TComponent); override;
  40.     destructor Destroy; override;
  41.     procedure AddColor(AColor: TColor);
  42.   published
  43.     property RowCount: Integer read FRowCount write SetRowCount;
  44.     property ColCount: Integer read FColCount write SetColCount;
  45.     property ColorValue: TColor read FColorValue;
  46.     property OnChange: TNotifyEvent  read FOnChange write FOnChange;
  47.   end;
  48.   TbsEmptyControl = class(TCustomControl)
  49.   protected
  50.     procedure WMEraseBkgnd(var Msg: TWMEraseBkgnd); message WM_ERASEBKGND;
  51.   public
  52.     procedure Paint; override;
  53.   end;
  54.   TbsSkinColorGrid = class(TbsSkinPanel)
  55.   private
  56.     FColorValue: TColor;
  57.     FOnChange: TNotifyEvent;
  58.     FColCount, FRowCount: Integer;
  59.     procedure SetColCount(Value: Integer);
  60.     procedure SetRowCount(Value: Integer);
  61.     procedure SetColorValue(Value: TColor);
  62.   protected
  63.     procedure DrawCursor(Cnvs: TCanvas; R: TRect; pmNotMode: Boolean);
  64.     function CheckColor(Value: TColor): boolean;
  65.     procedure CreateControlDefaultImage(B: TBitMap); override;
  66.     procedure CreateControlSkinImage(B: TBitMap); override;
  67.     procedure PaintGrid(Cnvs: TCanvas);
  68.     procedure MouseDown(Button: TMouseButton; Shift: TShiftState;
  69.       X, Y: Integer); override;
  70.   public
  71.     constructor Create(AOwner: TComponent); override;
  72.     destructor Destroy; override;
  73.   published
  74.     property RowCount: Integer read FRowCount write SetRowCount;
  75.     property ColCount: Integer read FColCount write SetColCount;
  76.     property ColorValue: TColor read FColorValue write SetColorValue;
  77.     property OnChange: TNotifyEvent  read FOnChange write FOnChange;
  78.   end;
  79.   TbsColorViewer = class(TGraphicControl)
  80.   private
  81.     FColorValue: TColor;
  82.     procedure SetColorValue(Value: TColor);
  83.   public
  84.     constructor Create(AOwner: TComponent); override;
  85.     procedure Paint; override;
  86.   published
  87.     property ColorValue: TColor read FColorValue write SetColorValue;
  88.   end;
  89.   const
  90.     CalcEpsilon: Double = 1E-8;
  91.     CalcRadian: Double = 3.1415926536 / 180;
  92.     RectPSP: TRect = (Left:44; Top:44; Right:150; Bottom:150);
  93.     RectActCol: TRect = (Left:21; Top:20; Right:69; Bottom:70);
  94.     RectPreCol: TRect = (Left:21; Top:95; Right:69; Bottom:145);
  95.     PalettePSPCoord: TRect = (Left:0; Top:0; Right:195; Bottom:195);
  96.     MaxPixelCount = 32768;
  97.   type
  98.     THSL = record
  99.       H, S, L: Double;
  100.     end;
  101.     TRGB = record
  102.       R, G, B : byte;
  103.     end;
  104.     THSLPSP = record
  105.       H, S, L: Byte;
  106.     end;
  107.     TPSPColor = class
  108.     private
  109.       FRGB : TRGB;
  110.       FHSL : THSL;
  111.       FHSLPSP : THSLPSP;
  112.       function HSLToRGB (Value: THSL): TRGB;
  113.       function RGBToHSL (Value: TRGB): THSL;
  114.       function HSLToHSLPSP:THSLPSP;
  115.       function HSLPSPToHSL:THSL;
  116.       procedure SetRGB(const Value: TRGB);
  117.       procedure SeTHSL(const Value: THSL);
  118.       procedure SeTHSLPSP(const Value: THSLPSP);
  119.     public
  120.       constructor Create;
  121.       destructor Destroy;override;
  122.       procedure Assign(const Value : TPSPColor);
  123.       property RGB : TRGB read FRGB write SetRGB;
  124.       property HSL : THSL read FHSL write SeTHSL;
  125.       property HSLPSP : THSLPSP read FHSLPSP write SeTHSLPSP;
  126.     end;
  127.   TClickZonePSP = (czpspPnone, czpspPCircle, czpspPCar);
  128.   TLineB = array of Byte;
  129.   TLineI = array of Integer;
  130.   PRGBArray = ^TRGBArray;
  131.   TRGBArray = array[0..MaxPixelCount - 1] of TRGBTriple;
  132.   TbsSkinColorDialog = class(TComponent)
  133.   private
  134.     RGBStopCheck: Boolean;
  135.     HSLStopCheck: Boolean;
  136.     FromPSP: Boolean;
  137.   protected
  138.     FColor: TColor;
  139.     FCaption: String;
  140.     FSD: TbsSkinData;
  141.     FCtrlFSD: TbsSkinData;
  142.     FButtonSkinDataName: String;
  143.     FEditSkinDataName: String;
  144.     FLabelSkinDataName: String;
  145.     FDefaultLabelFont: TFont;
  146.     FDefaultEditFont: TFont;
  147.     FDefaultButtonFont: TFont;
  148.     FAlphaBlend: Boolean;
  149.     FAlphaBlendAnimation: Boolean;
  150.     FAlphaBlendValue: Byte;
  151.     FUseSkinFont: Boolean;
  152.     //
  153.     ColorGrid: TbsSkinColorGrid;
  154.     CustomColorGrid: TbsSkinCustomColorGrid;
  155.     OkButton, CancelButton, AddCustomColorButton: TbsSkinButton;
  156.     ColorViewer: TbsColorViewer;
  157.     REdit, GEdit, BEdit: TbsSkinTrackEdit;
  158.     RLabel, GLabel, BLabel, EQLabel: TbsSkinStdLabel;
  159.     HEdit, LEdit, SEdit: TbsSkinTrackEdit;
  160.     HLabel, LLabel, SLabel: TbsSkinStdLabel;
  161.     //
  162.     PalettePSPPanel: TbsEmptyControl;
  163.     PalettePSP: TImage;
  164.     PosCircle, PosCar: Integer;
  165.     ClickImg: TClickZonePSP;
  166.     PSPColor : TPSPColor;
  167.     CustomColorValues: TbsCustomColorValues;
  168.     CustomColorValuesCount: Integer;
  169.     function CalcAngle3Points(X1, Y1, Xc, Yc, X2, Y2: Double): Double;
  170.     function CalcAnglePoints(X1, Y1, X2, Y2: Double): Double;
  171.     procedure CalcAngle360(var Angle: Double);
  172.     function CalcDistancePoints(X1, Y1, X2, Y2: Double): Double;
  173.     function CalcArcCosRadians(CosAngle: Double): Double;
  174.     function CalcArcSinRadians(SinAngle: Double): Double;
  175.     procedure CalcRotationPoint(Xc, Yc: Double; Angle: Double; X1, Y1: Double; var X2, Y2: Double);
  176.     procedure CalcPointSurEllipse(Xc, Yc: Double; RayonX, RayonY: Double; Angle: Double; var X, Y: Double);
  177.     function CalcArcTan(TanAngle: Double): Double;
  178.     procedure InitPSPPalette;
  179.     procedure DrawPSPPalette;
  180.     procedure DrawCursor;
  181.     procedure PalettePSPMouseMove(Sender: TObject; Shift: TShiftState; X,
  182.       Y: Integer); 
  183.     procedure PalettePSPMouseUp(Sender: TObject; Button: TMouseButton;
  184.       Shift: TShiftState; X, Y: Integer);
  185.     procedure PalettePSPMouseDown(Sender: TObject; Button: TMouseButton;
  186.       Shift: TShiftState; X, Y: Integer);
  187.     //
  188.     procedure SetDefaultLabelFont(Value: TFont);
  189.     procedure SetDefaultButtonFont(Value: TFont);
  190.     procedure SetDefaultEditFont(Value: TFont);
  191.     procedure Notification(AComponent: TComponent;  Operation: TOperation); override;
  192.     procedure ColorGridChange(Sender: TObject);
  193.     procedure CustomColorGridChange(Sender: TObject);
  194.     procedure RGBEditChange(Sender: TObject);
  195.     procedure HSLEditChange(Sender: TObject);
  196.     procedure AddCustomColorButtonClick(Sender: TObject);
  197.     procedure ChangeEdits;
  198.   public
  199.     constructor Create(AOwner: TComponent); override;
  200.     destructor Destroy; override;
  201.     function Execute: Boolean;
  202.   published
  203.     property Color: TColor read FColor write FColor;
  204.     property Caption: String read FCaption write FCaption;
  205.     property AlphaBlend: Boolean read FAlphaBlend write FAlphaBlend;
  206.     property AlphaBlendValue: Byte read FAlphaBlendValue write FAlphaBlendValue;
  207.     property AlphaBlendAnimation: Boolean
  208.       read FAlphaBlendAnimation write FAlphaBlendAnimation;
  209.     property SkinData: TbsSkinData read FSD write FSD;
  210.     property CtrlSkinData: TbsSkinData read FCtrlFSD write FCtrlFSD;
  211.     property ButtonSkinDataName: String
  212.       read FButtonSkinDataName write FButtonSkinDataName;
  213.     property LabelSkinDataName: String
  214.       read FLabelSkinDataName write FLabelSkinDataName;
  215.     property EditSkinDataName: String
  216.      read FEditSkinDataName write FEditSkinDataName;
  217.     property DefaultLabelFont: TFont read FDefaultLabelFont write SetDefaultLabelFont;
  218.     property DefaultButtonFont: TFont read FDefaultButtonFont write SetDefaultButtonFont;
  219.     property DefaultEditFont: TFont read FDefaultEditFont write SetDefaultEditFont;
  220.     property UseSkinFont: Boolean read FUseSkinFont write FUseSkinFont;
  221.   end;
  222. implementation
  223. Uses bsUtils, Math, bsConst;
  224. const
  225.   ColorValues: array[1..48] of TColor =
  226.   (0, 64, 128, 4210816, 255, 8421631, 32896, 16512, 33023, 4227327, 65535, 8454143,
  227.    4227200, 16384, 32768, 65280, 65408, 8454016, 8421504, 4210688, 4227072, 8421376, 4259584, 8453888,
  228.    8421440, 8388608, 16711680, 8404992, 16776960, 16777088, 12632256, 4194304, 10485760, 16744576, 12615680, 16744448,
  229.    4194368, 5194368, 8388736, 4194432, 12615808, 12615935, 16777215, 8388672, 16711808, 8388863, 16711935, 16744703);
  230. procedure ColorToR_G_B(C: TColor; var R, G, B: Byte);
  231. begin
  232.   R := C and $FF;
  233.   G := (C shr 8) and $FF;
  234.   B := (C shr 16) and $FF;
  235. end;
  236. function R_G_BToColor(R, G, B: Byte): TColor;
  237. begin
  238.   Result := RGB(R, G, B);
  239. end;
  240. procedure RGBToHSL1(AR, AV, AB: Byte; var H, S, L: Double);
  241. var
  242.   R,
  243.   G,
  244.   B,
  245.   D,
  246.   Cmax,
  247.   Cmin: double;
  248. begin
  249.   R := AR / 255;
  250.   G := AV / 255;
  251.   B := AB / 255;
  252.   Cmax := Max (R, Max (G, B));
  253.   Cmin := Min (R, Min (G, B));
  254.   L := (Cmax + Cmin) / 2;
  255.   if Cmax = Cmin
  256.   then
  257.     begin
  258.       H := 0;
  259.       S := 0
  260.     end
  261.   else
  262.     begin
  263.       D := Cmax - Cmin;
  264.       if L < 0.5 then S := D / (Cmax + Cmin) else S := D / (2 - Cmax - Cmin);
  265.       if R = Cmax
  266.       then
  267.         H := (G - B) / D
  268.       else
  269.         if G = Cmax then H  := 2 + (B - R) /D else H := 4 + (R - G) / D;
  270.       H := H / 6;
  271.       if H < 0 then  H := H + 1;
  272.     end;
  273. end;
  274. procedure RGBToHSL2(AR, AG, AB: Byte; var H, S, L: Integer);
  275. var
  276.   RGB: array[0..2] of Double;
  277.   MinIndex, MaxIndex: Integer;
  278.   Range: Double;
  279.   H1 : Double;
  280. begin
  281.   RGB[0]:= AR;
  282.   RGB[1]:= AG;
  283.   RGB[2]:= AB;
  284.   MinIndex:= 0;
  285.   if AG < AR then MinIndex:= 1;
  286.   if AB < RGB[MinIndex] then MinIndex:= 2;
  287.   MaxIndex:= 0;
  288.   if AG > AR then MaxIndex:= 1;
  289.   if AB > RGB[MaxIndex] then MaxIndex:= 2;
  290.   Range:= RGB[MaxIndex] - RGB[MinIndex];
  291.   if Range = 0
  292.   then
  293.     begin
  294.       S := 0;
  295.       L := Round(100 * AR / 255); 
  296.     end
  297.   else
  298.     begin
  299.       H1 := MaxIndex * 2 + (AR - AG) / Range;
  300.       S := Round(Range / RGB[MaxIndex] * 100);
  301.       L :=  Round(100 * (RGB[MaxIndex] / 255));
  302.       H1 := H1 / 6;
  303.       if H1 < 0 then H1 := H1 + 1;
  304.       H := Round(H1 * 359);
  305.     end;
  306. end;
  307. procedure RGBToHSL(AR, AG, AB: Byte; var RH, RS, RL: Integer);
  308. var
  309.   H, S, L: Double;
  310. begin
  311.   RGBToHSL1(AR, AG, AB, H, S, L);
  312.   RGBToHSL2(AR, AG, AB, RH, RS, RL);
  313.   if RS <> 0 then RH := Round(H * 359);
  314. end;
  315. procedure HSLToRGB(var R, G, B: Byte; RH, RS, RL: Integer);
  316. const 
  317.   SectionSize = 60/360;
  318. var 
  319.   Section: Double; 
  320.   SectionIndex: Integer; 
  321.   f, p, q, t, H, S, L: Double;
  322. begin
  323.   H := RH / 360;
  324.   S := RS / 100;
  325.   L := (255 * RL / 100);
  326.   if S = 0
  327.   then
  328.     begin
  329.       R := Round(L);
  330.       G := R;
  331.       B := R;
  332.     end
  333.   else
  334.    begin
  335.      Section := H / SectionSize;
  336.      SectionIndex := Floor(Section);
  337.      f := Section - SectionIndex;
  338.      p := L * ( 1 - S );
  339.      q := L * ( 1 - S * f );
  340.      t := L * ( 1 - S * ( 1 - f ) );
  341.      case SectionIndex of
  342.       0:
  343.         begin
  344.           R := Round(L);
  345.           G := Round(t);
  346.           B := Round(p);
  347.         end;
  348.       1:
  349.         begin
  350.           R := Round(q);
  351.           G := Round(L);
  352.           B := Round(p);
  353.         end;
  354.       2:
  355.         begin
  356.           R := Round(p);
  357.           G := Round(L);
  358.           B := Round(t);
  359.         end;
  360.       3:
  361.         begin
  362.           R := Round(p);
  363.           G := Round(q);
  364.           B := Round(L);
  365.         end;
  366.       4:
  367.         begin
  368.           R := Round(t);
  369.           G := Round(p);
  370.           B := Round(L);
  371.         end;
  372.     else
  373.       R := Round(L);
  374.       G := Round(p);
  375.       B := Round(q);
  376.     end;
  377.   end;
  378. end;
  379. procedure TbsEmptyControl.WMEraseBkgnd;
  380. begin
  381.   Msg.Result := 1;
  382. end;
  383. procedure TbsEmptyControl.Paint;
  384. begin
  385. end;
  386. constructor TbsSkinColorGrid.Create(AOwner: TComponent);
  387. begin
  388.   inherited;
  389.   ControlStyle := ControlStyle - [csAcceptsControls];
  390.   CaptionMode := True;
  391.   Caption := BS_COLORGRID_CAP;
  392.   BorderStyle := bvFrame;
  393.   Width := 280;
  394.   Height := 115;
  395.   FColorValue := 0;
  396.   FColCount := 12;
  397.   FRowCount := 4;
  398. end;
  399. destructor TbsSkinColorGrid.Destroy;
  400. begin
  401.   inherited;
  402. end;
  403. procedure TbsSkinColorGrid.SetColCount(Value: Integer);
  404. begin
  405.   if Value < 1 then Exit;
  406.   FColCount := Value;
  407.   RePaint;
  408. end;
  409. procedure TbsSkinColorGrid.SetRowCount(Value: Integer);
  410. begin
  411.   FRowCount := Value;
  412.   RePaint;
  413. end;
  414. procedure TbsSkinColorGrid.DrawCursor;
  415. var
  416.   CX, CY, Rd: Integer;
  417. begin
  418.   CX := R.Left + RectWidth(R) div 2;
  419.   CY := R.Top + RectHeight(R) div 2;
  420.   if RectWidth(R) > RectHeight(R)
  421.   then
  422.     Rd := RectHeight(R) div 2 - 2
  423.   else
  424.     Rd := RectWidth(R) div 2 - 2;
  425.   with Cnvs do
  426.   begin
  427.     if pmNotMode then Pen.Mode := pmNot else Pen.Color := 0;
  428.     MoveTo(CX - rd, CY); LineTo(CX - 2, CY);
  429.     MoveTo(CX + 3, CY); LineTo(CX + rd + 1, CY);
  430.     MoveTo(CX, CY - rd); LineTo(CX, CY - 2);
  431.     MoveTo(CX, CY + 3); LineTo(CX, CY + rd);
  432.   end;
  433. end;
  434. procedure TbsSkinColorGrid.PaintGrid(Cnvs: TCanvas);
  435. var
  436.   X, Y, CW, CH, i, j, k: Integer;
  437.   R, Rct: TRect;
  438. begin
  439.   R := Rect(0, 0, Width, Height);
  440.   AdjustClientRect(R);
  441.   CW := (RectWidth(R) - ColCount * 2) div ColCount;
  442.   CH := (RectHeight(R) - RowCount * 2) div RowCount;
  443.   Y := R.Top + 1;
  444.   k := 0;
  445.   for i := 1 to RowCount do
  446.   begin
  447.     X := R.Left + 1;
  448.     for j := 1 to ColCount do
  449.     begin
  450.       Inc(k);
  451.       with Cnvs do
  452.       begin
  453.         Brush.Color := ColorValues[k];
  454.         Rct := Rect(X, Y, X + CW, Y + CH);
  455.         InflateRect(Rct, -1, -1);
  456.         FillRect(Rct);
  457.         InflateRect(Rct, 1, 1);
  458.         if FColorValue = ColorValues[k]
  459.         then
  460.           begin
  461.             if ColorValues[k] <> clGray
  462.             then
  463.               DrawCursor(Cnvs, Rct, True)
  464.             else
  465.               DrawCursor(Cnvs, Rct, False);
  466.           end
  467.       end;
  468.       Inc(X, CW + 2);
  469.     end;
  470.     Inc(Y, CH + 2);
  471.   end;
  472. end;
  473. procedure TbsSkinColorGrid.CreateControlDefaultImage;
  474. begin
  475.   inherited;
  476.   PaintGrid(B.Canvas);
  477. end;
  478. procedure TbsSkinColorGrid.CreateControlSkinImage;
  479. begin
  480.   inherited;
  481.   PaintGrid(B.Canvas);
  482. end;
  483. function TbsSkinColorGrid.CheckColor(Value: TColor): boolean;
  484. var
  485.   I: Integer;
  486. begin
  487.   Result := False;
  488.   for I := 1 to 48 do
  489.     if ColorValues[I] = Value
  490.     then
  491.       begin
  492.         Result := True;
  493.         Break;
  494.       end;
  495. end;
  496. procedure TbsSkinColorGrid.SetColorValue(Value: TColor);
  497. begin
  498.   FColorValue := Value;
  499.   if CheckColor(FColorValue)
  500.   then
  501.     begin
  502.       if Assigned(FOnChange) then FOnChange(Self);
  503.       RePaint;
  504.     end;
  505. end;
  506. procedure TbsSkinColorGrid.MouseDown(Button: TMouseButton; Shift: TShiftState;
  507.                                      X, Y: Integer);
  508. var
  509.   X1, Y1, CW, CH, i, j, k: Integer;
  510.   R, Rct: TRect;
  511. begin
  512.   inherited;
  513.   R := Rect(0, 0, Width, Height);
  514.   AdjustClientRect(R);
  515.   CW := (RectWidth(R) - ColCount * 2) div ColCount;
  516.   CH := (RectHeight(R) - RowCount * 2) div RowCount;
  517.   Y1 := R.Top + 1;
  518.   k := 0;
  519.   for i := 1 to RowCount do
  520.   begin
  521.     X1 := R.Left + 1;
  522.     for j := 1 to ColCount do
  523.     begin
  524.       Inc(k);
  525.       Rct := Rect(X1, Y1, X1 + CW, Y1 + CH);
  526.       if PtInRect(Rct, Point(X, Y))
  527.       then
  528.         begin
  529.           ColorValue := ColorValues[k];
  530.           Break;
  531.         end;
  532.       Inc(X1, CW + 2);
  533.     end;
  534.     Inc(Y1, CH + 2);
  535.   end;  
  536. end;
  537. constructor TbsColorViewer.Create(AOwner: TComponent);
  538. begin
  539.   inherited;
  540.   ControlStyle := ControlStyle + [csOpaque];
  541.   FColorValue := 0;
  542. end;
  543. procedure TbsColorViewer.Paint;
  544. var
  545.   B: TBitMap;
  546. begin
  547.   B := TBitMap.Create;
  548.   B.Width := Width;
  549.   B.Height := Height;
  550.   with B.Canvas do
  551.   begin
  552.     Pen.Color := clBlack;
  553.     Brush.Color := FColorValue;
  554.     Rectangle(0, 0, Width, Height);
  555.   end;
  556.   Canvas.Draw(0, 0, B);
  557.   B.Free;
  558. end;
  559. procedure TbsColorViewer.SetColorValue;
  560. begin
  561.   if FColorValue = Value then Exit;
  562.   FColorValue := Value;
  563.   RePaint;
  564. end;
  565. function TPSPColor.RGBToHSL(Value: TRGB): THSL;
  566. var
  567.   R,
  568.   G,
  569.   B,
  570.   D,
  571.   Cmax,
  572.   Cmin: double;
  573. begin
  574.   R := Value.R / 255;
  575.   G := Value.G / 255;
  576.   B := Value.B / 255;
  577.   Cmax := Max (R, Max (G, B));
  578.   Cmin := Min (R, Min (G, B));
  579. // calculate luminosity
  580.   Result.L := (Cmax + Cmin) / 2;
  581.   if Cmax = Cmin then
  582.   begin
  583.     Result.H := 0; 
  584.     Result.S := 0
  585.   end else begin
  586.     D := Cmax - Cmin;
  587. // calculate Saturation
  588.     if Result.L < 0.5 then
  589.       Result.S := D / (Cmax + Cmin)
  590.     else
  591.       Result.S := D / (2 - Cmax - Cmin);
  592. // calculate Hue
  593.     if R = Cmax then
  594.       Result.H := (G - B) / D
  595.     else
  596.       if G = Cmax then
  597.         Result.H  := 2 + (B - R) /D
  598.       else
  599.         Result.H := 4 + (R - G) / D;
  600.     Result.H := Result.H / 6;
  601.     if Result.H < 0 then
  602.       Result.H := Result.H + 1
  603.   end
  604. end;
  605. function TPSPColor.HSLToRGB(Value: THSL): TRGB;
  606. var
  607.   M1,
  608.   M2: double;
  609.   function HueToColourValue (Hue: double) : byte;
  610.   var
  611.     V : double;
  612.   begin
  613.     if Hue < 0 then
  614.       Hue := Hue + 1
  615.     else
  616.       if Hue > 1 then
  617.         Hue := Hue - 1;
  618.     if 6 * Hue < 1 then
  619.       V := M1 + (M2 - M1) * Hue * 6
  620.     else
  621.     if 2 * Hue < 1 then
  622.       V := M2
  623.     else
  624.     if 3 * Hue < 2 then
  625.       V := M1 + (M2 - M1) * (2/3 - Hue) * 6
  626.     else
  627.       V := M1;
  628.     Result := round (255 * V)
  629.   end;
  630. begin
  631.   if Value.S = 0 then
  632.   begin
  633.     Result.R := round (255 * Value.L);
  634.     Result.G := Result.R;
  635.     Result.B := Result.R
  636.   end else begin
  637.     if Value.L <= 0.5 then
  638.       M2 := Value.L * (1 + Value.S)
  639.     else
  640.       M2 := Value.L + Value.S - Value.L * Value.S;
  641.     M1 := 2 * Value.L - M2;
  642.     Result.R := HueToColourValue (Value.H + 1/3);
  643.     Result.G := HueToColourValue (Value.H);
  644.     Result.B := HueToColourValue (Value.H - 1/3)
  645.   end;
  646. end;
  647. function TPSPColor.HSLToHSLPSP: THSLPSP;
  648. begin
  649.   Result.H := round(FHSL.H*255);
  650.   Result.S := round(FHSL.S*255);
  651.   Result.L := round(FHSL.L*255);
  652. end;
  653. function TPSPColor.HSLPSPToHSL: THSL;
  654. begin
  655.   Result.H := FHSLPSP.H/255;
  656.   Result.S := FHSLPSP.S/255;
  657.   Result.L := FHSLPSP.L/255;
  658. end;
  659. constructor TPSPColor.Create;
  660. begin
  661.   inherited;
  662. end;
  663. destructor TPSPColor.Destroy;
  664. begin
  665.   inherited;
  666. end;
  667. procedure TPSPColor.SetRGB(const Value: TRGB);
  668. begin
  669.   FRGB := Value;
  670.   FHSL := RGBToHSL(FRGB);
  671.   FHSLPSP := HSLToHSLPSP();
  672. end;
  673. procedure TPSPColor.SeTHSL(const Value: THSL);
  674. begin
  675.   FHSL := Value;
  676.   FRGB := HSLToRGB(FHSL);
  677.   FHSLPSP := HSLToHSLPSP;
  678. end;
  679. procedure TPSPColor.SeTHSLPSP(const Value: THSLPSP);
  680. begin
  681.   FHSLPSP := Value;
  682.   FHSL := HSLPSPToHSL;
  683.   FRGB := HSLToRGB(FHSL);
  684. end;
  685. procedure TPSPColor.Assign(const Value: TPSPColor);
  686. begin
  687.   FRGB := Value.FRGB;
  688.   FHSL := Value.FHSL;
  689.   FHSLPSP := Value.FHSLPSP;
  690. end;
  691. constructor TbsSkinColorDialog.Create;
  692. var
  693.   I: Integer;
  694. begin
  695.   inherited Create(AOwner);
  696.   RGBStopCheck := False;
  697.   HSLStopCheck := False;
  698.   FromPSP := False;
  699.   FColor := 0;
  700.   PSPColor := TPSPColor.Create;
  701.   FAlphaBlend := False;
  702.   FAlphaBlendAnimation := False;
  703.   FAlphaBlendValue := 200;
  704.   FCaption := 'Set color';
  705.   FButtonSkinDataName := 'button';
  706.   FLabelSkinDataName := 'stdlabel';
  707.   FEditSkinDataName := 'edit';
  708.   FDefaultLabelFont := TFont.Create;
  709.   FDefaultButtonFont := TFont.Create;
  710.   FDefaultEditFont := TFont.Create;
  711.   FUseSkinFont := True;
  712.   with FDefaultLabelFont do
  713.   begin
  714.     Name := 'Arial';
  715.     Style := [];
  716.     Height := 14;
  717.   end;
  718.   with FDefaultButtonFont do
  719.   begin
  720.     Name := 'Arial';
  721.     Style := [];
  722.     Height := 14;
  723.   end;
  724.   with FDefaultEditFont do
  725.   begin
  726.     Name := 'Arial';
  727.     Style := [];
  728.     Height := 14;
  729.   end;
  730.   for I := 1 to 12 do CustomColorValues[I] := clWhite;
  731.   CustomColorValuesCount := 0;
  732. end;
  733. destructor TbsSkinColorDialog.Destroy;
  734. begin
  735.   PSPColor.Free;
  736.   FDefaultLabelFont.Free;
  737.   FDefaultButtonFont.Free;
  738.   FDefaultEditFont.Free;
  739.   inherited;
  740. end;
  741. procedure TbsSkinColorDialog.ChangeEdits;
  742. var
  743.   R, G, B: Byte;
  744. begin
  745.   FromPSP := True;
  746.   R := PSPColor.FRGB.R;
  747.   G := PSPColor.FRGB.G;
  748.   B := PSPColor.FRGB.B;
  749.   REdit.Value := R;
  750.   GEdit.Value := G;
  751.   BEdit.Value := B;
  752.   FromPSP := False;
  753. end;
  754. procedure TbsSkinColorDialog.HSLEditChange(Sender: TObject);
  755. var
  756.   R, G, B: Byte;
  757.   RGB: TRGB;
  758. begin
  759.   if HSLStopCheck then Exit;
  760.   HSLTORGB(R, G, B, HEdit.Value, SEdit.Value, LEdit.Value);
  761.   ColorViewer.ColorValue := R_G_BToColor(R, G, B);
  762.   RGBStopCheck := True;
  763.   //
  764.   REdit.Value := R;
  765.   GEdit.Value := G;
  766.   BEdit.Value := B;
  767.   //
  768.   if not FromPSP
  769.   then
  770.     begin
  771.       DrawCursor;
  772.       RGB.R := R;
  773.       RGB.G := G;
  774.       RGB.B := B;
  775.       PSPColor.SetRGB(RGB);
  776.       DrawPSPPalette;
  777.     end;  
  778.   //
  779.   RGBStopCheck := False;
  780. end;
  781. procedure TbsSkinColorDialog.AddCustomColorButtonClick(Sender: TObject);
  782. begin
  783.   CustomColorGrid.AddColor(ColorViewer.ColorValue);
  784. end;
  785. procedure TbsSkinColorDialog.RGBEditChange(Sender: TObject);
  786. var
  787.   R, G, B: Byte;
  788.   H, S, L: Integer;
  789.   RGB: TRGB;
  790. begin
  791.   if RGBStopCheck then Exit;
  792.   ColorViewer.ColorValue := R_G_BToColor(REdit.Value, GEdit.Value, BEdit.Value);
  793.   ColorToR_G_B(ColorViewer.ColorValue, R, G, B);
  794.   HSLStopCheck := True;
  795.   RGBToHSL(R, G, B, H, S, L);
  796.   HEdit.Value := H;
  797.   SEdit.Value := S;
  798.   LEdit.Value := L;
  799.   //
  800.   if not FromPSP
  801.   then
  802.     begin
  803.       DrawCursor;
  804.       RGB.R := R;
  805.       RGB.G := G;
  806.       RGB.B := B;
  807.       PSPColor.SetRGB(RGB);
  808.       DrawPSPPalette;
  809.     end;  
  810.   //
  811.   HSLStopCheck := False;
  812. end;
  813. procedure TbsSkinColorDialog.CustomColorGridChange(Sender: TObject);
  814. var
  815.   R, G, B: Byte;
  816.   H, S, L: Integer;
  817.   RGB: TRGB;
  818. begin
  819.   ColorToR_G_B(CustomColorGrid.ColorValue, R, G, B);
  820.   RGBStopCheck := True;
  821.   REdit.Value := R;
  822.   GEdit.Value := G;
  823.   BEdit.Value := B;
  824.   RGBStopCheck := False;
  825.   ColorViewer.ColorValue := CustomColorGrid.ColorValue;
  826.   RGBToHSL(R, G, B, H, S, L);
  827.   HSLStopCheck := True;
  828.   HEdit.Value := H;
  829.   SEdit.Value := S;
  830.   LEdit.Value := L;
  831.   if not FromPSP
  832.   then
  833.     begin
  834.       DrawCursor;
  835.       RGB.R := R;
  836.       RGB.G := G;
  837.       RGB.B := B;
  838.       PSPColor.SetRGB(RGB);
  839.       DrawPSPPalette;
  840.     end;  
  841.   HSLStopCheck := False;
  842. end;
  843. procedure TbsSkinColorDialog.ColorGridChange(Sender: TObject);
  844. var
  845.   R, G, B: Byte;
  846.   H, S, L: Integer;
  847.   RGB: TRGB;
  848. begin
  849.   ColorToR_G_B(ColorGrid.ColorValue, R, G, B);
  850.   RGBStopCheck := True;
  851.   REdit.Value := R;
  852.   GEdit.Value := G;
  853.   BEdit.Value := B;
  854.   RGBStopCheck := False;
  855.   ColorViewer.ColorValue := ColorGrid.ColorValue;
  856.   RGBToHSL(R, G, B, H, S, L);
  857.   HSLStopCheck := True;
  858.   HEdit.Value := H;
  859.   SEdit.Value := S;
  860.   LEdit.Value := L;
  861.   if not FromPSP
  862.   then
  863.     begin
  864.       DrawCursor;
  865.       RGB.R := R;
  866.       RGB.G := G;
  867.       RGB.B := B;
  868.       PSPColor.SetRGB(RGB);
  869.       DrawPSPPalette;
  870.     end;  
  871.   HSLStopCheck := False;
  872. end;
  873. procedure TbsSkinColorDialog.SetDefaultLabelFont;
  874. begin
  875.   FDefaultLabelFont.Assign(Value);
  876. end;
  877. procedure TbsSkinColorDialog.SetDefaultEditFont;
  878. begin
  879.   FDefaultEditFont.Assign(Value);
  880. end;
  881. procedure TbsSkinColorDialog.SetDefaultButtonFont;
  882. begin
  883.   FDefaultButtonFont.Assign(Value);
  884. end;
  885. procedure TbsSkinColorDialog.Notification;
  886. begin
  887.   inherited Notification(AComponent, Operation);
  888.   if (Operation = opRemove) and (AComponent = FSD) then FSD := nil;
  889.   if (Operation = opRemove) and (AComponent = FCtrlFSD) then FCtrlFSD := nil;
  890. end;
  891. function TbsSkinColorDialog.Execute: Boolean;
  892. var
  893.   Form: TForm;
  894.   BSF: TbsBusinessSkinForm;
  895.   ButtonTop, ButtonWidth, ButtonHeight: Integer;
  896.   R, G, B: Byte;
  897.   Temp : TRGB;
  898.   I: Integer;
  899.   PSPBGColor: TColor;
  900. begin
  901.   Form := TForm.Create(Application);
  902.   Form.BorderStyle := bsDialog;
  903.   Form.Caption := FCaption;
  904.   Form.Position := poScreenCenter;
  905.   BSF := TbsBusinessSkinForm.Create(Form);
  906.   BSF.BorderIcons := [];
  907.   BSF.SkinData := SkinData;
  908.   BSF.MenusSkinData := CtrlSkinData;
  909.   BSF.AlphaBlend := AlphaBlend;
  910.   BSF.AlphaBlendAnimation := AlphaBlendAnimation;
  911.   BSF.AlphaBlendValue := AlphaBlendValue;
  912.   try
  913.   Form.ClientWidth := 378;
  914.   ColorGrid := TbsSkinColorGrid.Create(Form);
  915.   with ColorGrid do
  916.   begin
  917.     Parent := Form;
  918.     CaptionMode := True;
  919.     RowCount := 8;
  920.     ColCount := 6;
  921.     Left := 5;
  922.     Top := 5;
  923.     Width := 167;
  924.     Height := 195;
  925.     SkinDataName := 'groupbox';
  926.     SkinData := CtrlSkinData;
  927.     OnChange := ColorGridChange;
  928.   end;
  929.   CustomColorGrid := TbsSkinCustomColorGrid.Create(Form);
  930.   with CustomColorGrid  do
  931.   begin
  932.     Parent := Form;
  933.     CaptionMode := True;
  934.     Left := 5;
  935.     Top := ColorGrid.Top + ColorGrid.Height + 10;
  936.     Width := 167;
  937.     Height := 68;
  938.     SkinDataName := 'groupbox';
  939.     SkinData := CtrlSkinData;
  940.     OnChange := CustomColorGridChange;
  941.   end;
  942.   for I := 1 to 12 do
  943.     CustomColorGrid.CustomColorValues[I] := Self.CustomColorValues[I];
  944.   CustomColorGrid.FColorsCount := CustomColorValuesCount;
  945.   //
  946.   PalettePSPPanel:= TbsEmptyControl.Create(Form);
  947.   with PalettePSPPanel do
  948.   begin
  949.     Parent := Form;
  950.     Top := 5;
  951.     Left := ColorGrid.Left + ColorGrid.Width + 5;
  952.     Width := 195;
  953.     Height := 195;
  954.   end;
  955.   PalettePSP := TImage.Create(Form);
  956.   with PalettePSP do
  957.   begin
  958.     Parent := PalettePSPPanel;
  959.     Top := 0;
  960.     Left := 0;
  961.     Width := 195;
  962.     Height := 195;
  963.     OnMouseMove := PalettePSPMouseMove;
  964.     OnMouseUp := PalettePSPMouseUp;
  965.     OnMouseDown := PalettePSPMouseDown;
  966.     Picture.Bitmap.PixelFormat := pf32bit;
  967.     Picture.Bitmap.width := PalettePSP.width;
  968.     Picture.Bitmap.height := PalettePSP.Height;
  969.   end;
  970.   ClickImg := czpspPnone;
  971.   Temp.R := 0;
  972.   Temp.G := 0;
  973.   Temp.B := 0;
  974.   PSPColor.RGB := Temp;
  975.   PosCircle := (PalettePSP.Width-PalettePSPCoord.Right)div 2;
  976.   PosCar := PosCircle;
  977.   InitPSPPalette;
  978.   //
  979.   RLabel := TbsSkinStdLabel.Create(Form);
  980.   with RLabel do
  981.   begin
  982.     Parent := Form;
  983.     Left := PalettePSPPanel.Left;
  984.     Top := ColorGrid.Top + ColorGrid.Height + 12;
  985.     DefaultFont := DefaultLabelFont;
  986.     UseSkinFont := Self.UseSkinFont;
  987.     SkinData := CtrlSkinData;
  988.     Caption := 'R:';
  989.   end;
  990.    REdit := TbsSkinTrackEdit.Create(Self);
  991.    with REdit do
  992.    begin
  993.      Parent := Form;
  994.      PopupKind := tbpLeft;
  995.      SetBounds(RLabel.Left + RLabel.Width + 5, ColorGrid.Top + ColorGrid.Height + 10, 50, 21);
  996.      TrackBarWidth := 200;
  997.      MinValue := 0;
  998.      MaxValue := 255;
  999.      Value := 0;
  1000.      SkinData := CtrlSkinData;
  1001.      JumpWhenClick := True;
  1002.      OnChange := RGBEditChange;
  1003.    end;
  1004.   GLabel := TbsSkinStdLabel.Create(Form);
  1005.   with GLabel do
  1006.   begin
  1007.     Parent := Form;
  1008.     Left := PalettePSPPanel.Left;
  1009.     Top := REdit.Top + REdit.Height + 12;
  1010.     DefaultFont := DefaultLabelFont;
  1011.     UseSkinFont := Self.UseSkinFont;
  1012.     SkinData := CtrlSkinData;
  1013.     Caption := 'G:';
  1014.   end;
  1015.    GEdit := TbsSkinTrackEdit.Create(Self);
  1016.    with GEdit do
  1017.    begin
  1018.      Parent := Form;
  1019.      PopupKind := tbpLeft;
  1020.      SetBounds(REdit.Left, REdit.Top + REdit.Height + 10, 50, 21);
  1021.      TrackBarWidth := 200;
  1022.      MinValue := 0;
  1023.      MaxValue := 255;
  1024.      Value := 0;
  1025.      SkinData := CtrlSkinData;
  1026.      JumpWhenClick := True;
  1027.      OnChange := RGBEditChange;
  1028.    end;
  1029.   BLabel := TbsSkinStdLabel.Create(Form);
  1030.   with BLabel do
  1031.   begin
  1032.     Parent := Form;
  1033.     Left := PalettePSPPanel.Left;
  1034.     Top := GEdit.Top + GEdit.Height + 12;
  1035.     DefaultFont := DefaultLabelFont;
  1036.     UseSkinFont := Self.UseSkinFont;
  1037.     SkinData := CtrlSkinData;
  1038.     Caption := 'B:';
  1039.   end;
  1040.    BEdit := TbsSkinTrackEdit.Create(Self);
  1041.    with BEdit do
  1042.    begin
  1043.      Parent := Form;
  1044.      PopupKind := tbpLeft;
  1045.      SetBounds(REdit.Left, GEdit.Top + GEdit.Height + 10, 50, 21);
  1046.      TrackBarWidth := 200;
  1047.      MinValue := 0;
  1048.      MaxValue := 255;
  1049.      Value := 0;
  1050.      SkinData := CtrlSkinData;
  1051.      JumpWhenClick := True;
  1052.      OnChange := RGBEditChange;
  1053.    end;
  1054.   HLabel := TbsSkinStdLabel.Create(Form);
  1055.   with HLabel do
  1056.   begin
  1057.     Parent := Form;
  1058.     Left := REdit.Left + REdit.Width + 5;
  1059.     Top := ColorGrid.Top + ColorGrid.Height + 12;
  1060.     DefaultFont := DefaultLabelFont;
  1061.     UseSkinFont := Self.UseSkinFont;
  1062.     SkinData := CtrlSkinData;
  1063.     Caption := 'H:';
  1064.   end;
  1065.   HEdit := TbsSkinTrackEdit.Create(Self);
  1066.   with HEdit do
  1067.   begin
  1068.     Parent := Form;
  1069.     PopupKind := tbpLeft;
  1070.     SetBounds(HLabel.Left + HLabel.Width + 5, ColorGrid.Top + ColorGrid.Height + 10, 50, 21);
  1071.     TrackBarWidth := 250;
  1072.     MinValue := 0;
  1073.     MaxValue := 359;
  1074.     Value := 0;
  1075.     SkinData := CtrlSkinData;
  1076.     JumpWhenClick := True;
  1077.     OnChange := HSLEditChange;
  1078.   end;
  1079.   SLabel := TbsSkinStdLabel.Create(Form);
  1080.   with SLabel do
  1081.   begin
  1082.     Parent := Form;
  1083.     Left := REdit.Left + REdit.Width + 5;
  1084.     Top := HEdit.Top + HEdit.Height + 12;
  1085.     DefaultFont := DefaultLabelFont;
  1086.     UseSkinFont := Self.UseSkinFont;
  1087.     SkinData := CtrlSkinData;
  1088.     Caption := 'S:';
  1089.   end;
  1090.   SEdit := TbsSkinTrackEdit.Create(Self);
  1091.   with SEdit do
  1092.   begin
  1093.     Parent := Form;
  1094.     PopupKind := tbpLeft;
  1095.     SetBounds(HEdit.Left, HEdit.Top + HEdit.Height + 10, 50, 21);
  1096.     TrackBarWidth := 120;
  1097.     MinValue := 0;
  1098.     MaxValue := 100;
  1099.     Value := 0;
  1100.     SkinData := CtrlSkinData;
  1101.     JumpWhenClick := True;
  1102.     OnChange := HSLEditChange;
  1103.   end;
  1104.   LLabel := TbsSkinStdLabel.Create(Form);
  1105.   with LLabel do
  1106.   begin
  1107.     Parent := Form;
  1108.     Left := REdit.Left + REdit.Width + 5;
  1109.     Top := SEdit.Top + SEdit.Height + 12;
  1110.     DefaultFont := DefaultLabelFont;
  1111.     UseSkinFont := Self.UseSkinFont;
  1112.     SkinData := CtrlSkinData;
  1113.     Caption := 'L:';
  1114.   end;
  1115.   LEdit := TbsSkinTrackEdit.Create(Self);
  1116.   with LEdit do
  1117.   begin
  1118.     Parent := Form;
  1119.     PopupKind := tbpLeft;
  1120.     SetBounds(HEdit.Left, SEdit.Top + SEdit.Height + 10, 50, 21);
  1121.     TrackBarWidth := 120;
  1122.     MinValue := 0;
  1123.     MaxValue := 100;
  1124.     Value := 0;
  1125.     SkinData := CtrlSkinData;
  1126.     JumpWhenClick := True;
  1127.     OnChange := HSLEditChange;
  1128.   end;
  1129.   ColorViewer := TbsColorViewer.Create(Form);
  1130.   with ColorViewer do
  1131.   begin
  1132.     Parent := Form;
  1133.     SetBounds(HEdit.Left + HEdit.Width + 5,
  1134.               PalettePSPPanel.Top + PalettePSPPanel.Height + 10,
  1135.               PalettePSPPanel.Left + PalettePSPPanel.Width - (HEdit.Left + HEdit.Width + 5),
  1136.               PalettePSPPanel.Left + PalettePSPPanel.Width - (HEdit.Left + HEdit.Width + 5));
  1137.   end;
  1138.   ButtonTop := LEdit.Top + LEdit.Height + 15;
  1139.   ButtonWidth := 70;
  1140.   ButtonHeight := 25;
  1141.   OkButton := TbsSkinButton.Create(Form);
  1142.   with OkButton do
  1143.    begin
  1144.      Parent := Form;
  1145.      DefaultFont := DefaultButtonFont;
  1146.      UseSkinFont := Self.UseSkinFont;
  1147.      if (CtrlSkinData <> nil) and (CtrlSkinData.ResourceStrData <> nil)
  1148.      then
  1149.        Caption := CtrlSkinData.ResourceStrData.GetResStr('MSG_BTN_OK')
  1150.      else
  1151.        Caption := BS_MSG_BTN_OK;
  1152.      ModalResult := mrOk;
  1153.      Default := True;
  1154.      SetBounds(5, ButtonTop, ButtonWidth, ButtonHeight);
  1155.      DefaultHeight := ButtonHeight;
  1156.      SkinDataName := FButtonSkinDataName;
  1157.      SkinData := CtrlSkinData;
  1158.    end;
  1159.   CancelButton := TbsSkinButton.Create(Form);
  1160.   with CancelButton do
  1161.   begin
  1162.     Parent := Form;
  1163.     DefaultFont := DefaultButtonFont;
  1164.     UseSkinFont := Self.UseSkinFont;
  1165.      if (CtrlSkinData <> nil) and (CtrlSkinData.ResourceStrData <> nil)
  1166.      then
  1167.        Caption := CtrlSkinData.ResourceStrData.GetResStr('MSG_BTN_CANCEL')
  1168.      else
  1169.        Caption := BS_MSG_BTN_CANCEL;
  1170.     ModalResult := mrCancel;
  1171.     Cancel := True;
  1172.     SetBounds(90, ButtonTop, ButtonWidth,
  1173.               ButtonHeight);
  1174.     DefaultHeight := ButtonHeight;
  1175.     SkinDataName := FButtonSkinDataName;
  1176.     SkinData := CtrlSkinData;
  1177.   end;
  1178.   AddCustomColorButton := TbsSkinButton.Create(Form);
  1179.   with AddCustomColorButton do
  1180.    begin
  1181.      Parent := Form;
  1182.      DefaultFont := DefaultButtonFont;
  1183.      UseSkinFont := Self.UseSkinFont;
  1184.      if (CtrlSkinData <> nil) and (CtrlSkinData.ResourceStrData <> nil)
  1185.      then
  1186.        Caption := CtrlSkinData.ResourceStrData.GetResStr('ADDCUSTOMCOLORBUTTON_CAP')
  1187.      else
  1188.        Caption := BS_ADDCUSTOMCOLORBUTTON_CAP;
  1189.      SetBounds(PalettePSPPanel.Left, ButtonTop, PalettePSPPanel.Width, ButtonHeight);
  1190.      DefaultHeight := ButtonHeight;
  1191.      SkinDataName := FButtonSkinDataName;
  1192.      SkinData := CtrlSkinData;
  1193.      OnClick := AddCustomColorButtonClick;
  1194.    end;
  1195.   Form.ClientHeight := AddCustomColorButton.Top + AddCustomColorButton.Height + 10;
  1196.   ColorViewer.ColorValue := Color;
  1197.   ColorGrid.ColorValue := Color;
  1198.   ColorToR_G_B(Color, R, G, B);
  1199.   REdit.Value := R;
  1200.   GEdit.Value := G;
  1201.   BEdit.Value := B;
  1202.     if Form.ShowModal = mrOk
  1203.     then
  1204.       begin
  1205.         Color := ColorViewer.ColorValue;
  1206.         for I := 1 to 12 do
  1207.           Self.CustomColorValues[I] := CustomColorGrid.CustomColorValues[I];
  1208.         CustomColorValuesCount := CustomColorGrid.FColorsCount;  
  1209.         Result := True;
  1210.       end
  1211.     else
  1212.       Result := False;
  1213.   finally
  1214.     Form.Free;
  1215.   end;
  1216. end;
  1217. procedure TbsSkinColorDialog.CalcAngle360(var Angle: Double);
  1218. begin
  1219.   while (Angle < 0) do Angle := Angle + 360;
  1220.   while (Angle >= 360) do Angle:=Angle - 360;
  1221. end;
  1222. function TbsSkinColorDialog.CalcAngle3Points(X1, Y1, Xc, Yc, X2, Y2: Double): Double;
  1223. var
  1224.   Angle1, Angle2, Angle: Double;
  1225. begin
  1226.   Angle1 := CalcAnglePoints(Xc, Yc, X1, Y1);
  1227.   Angle2 := CalcAnglePoints(Xc, Yc, X2, Y2);
  1228.   Angle := Angle2-Angle1;
  1229.   CalcAngle360(Angle);
  1230.   CalcAngle3Points := Angle;
  1231. end;
  1232. procedure TbsSkinColorDialog.CalcRotationPoint(Xc, Yc, Angle, X1, Y1: Double; var X2,Y2: Double);
  1233. var
  1234.   Angle0: Double;
  1235.   Distance: Double;
  1236. begin
  1237.   Angle0 := CalcAnglePoints(Xc, Yc, X1, Y1);
  1238.   Distance := CalcDistancePoints(Xc, Yc, X1, Y1);
  1239.   CalcPointSurEllipse(Xc, Yc, Distance, Distance, Angle0 + Angle, X2, Y2);
  1240. end;
  1241. procedure TbsSkinColorDialog.CalcPointSurEllipse(Xc, Yc, RayonX, RayonY, Angle: Double;
  1242.   var X, Y: Double);
  1243. var
  1244.   Angle1, AngleA: Double;
  1245.   A, B: Double;
  1246. begin
  1247.   CalcAngle360(Angle);
  1248.   Angle1 := 90 - Angle;
  1249.   A := Cos(Angle1 * CalcRadian) * RayonX;
  1250.   B := Sin(Angle1 * CalcRadian) * RayonY;
  1251.   if (Abs(B) < CalcEpsilon)
  1252.   then
  1253.     if (Abs(Angle - 90) < 1E-7)
  1254.     then
  1255.       AngleA := 90
  1256.     else
  1257.       AngleA := 270
  1258.   else
  1259.   begin
  1260.     AngleA := CalcArcTan(A/B);
  1261.     if (Angle < 90)
  1262.     then
  1263.     else
  1264.       if (Angle < 270)
  1265.       then
  1266.         AngleA := AngleA + 180
  1267.       else
  1268.         AngleA := AngleA + 0;
  1269.   end;
  1270.   Y := Yc + Sin(AngleA * CalcRadian) * RayonY;
  1271.   X := Xc + Cos(AngleA * CalcRadian) * RayonX;
  1272. end;
  1273. function TbsSkinColorDialog.CalcArcTan(TanAngle: Double): Double;
  1274. begin
  1275.   CalcArcTan := Arctan(TanAngle) / CalcRadian;
  1276. end;
  1277. function TbsSkinColorDialog.CalcAnglePoints(X1, Y1, X2, Y2: Double): Double;
  1278. var
  1279.   Distance, CosAngle, Angle: Double;
  1280. begin
  1281.   Distance := CalcDistancePoints(X1, Y1, X2, Y2);
  1282.   if (Abs(Distance) < CalcEpsilon)
  1283.   then
  1284.     Angle := 0
  1285.   else
  1286.   begin
  1287.     CosAngle := Abs(X1 - X2) / Distance;
  1288.     Angle := CalcArcCosRadians(CosAngle);
  1289.     if (Abs(Y1 - Y2) >= CalcEpsilon) and (Y2 < Y1) then Angle := -Angle;
  1290.     if (Abs(X1-X2) >= CalcEpsilon) and (X2 < X1) then Angle := Pi-Angle;
  1291.     if (Abs(Angle) < CalcEpsilon) then Angle:=0;
  1292.     if (Angle < 0) then Angle := Angle + 2 * Pi;
  1293.     Angle := Angle / CalcRadian;
  1294.   end;
  1295.   CalcAnglePoints := Angle;
  1296. end;
  1297. function TbsSkinColorDialog.CalcArcCosRadians(CosAngle: Double): Double;
  1298. var
  1299.   Angle: Double;
  1300. begin
  1301.   Angle := Pi/2 - CalcArcSinRadians(CosAngle);
  1302.   CalcArcCosRadians := Angle;
  1303. end;
  1304. function TbsSkinColorDialog.CalcArcSinRadians(SinAngle: Double): Double;
  1305. var
  1306.   Diviseur, Angle: Double;
  1307. begin
  1308.   Diviseur := Sqrt(1 - Sqr(SinAngle));
  1309.   if (Abs(Diviseur) < CalcEpsilon)
  1310.   then
  1311.     if (SinAngle > 0)
  1312.     then
  1313.       Angle := Pi/2
  1314.     else
  1315.       Angle := -Pi/2
  1316.   else
  1317.     Angle := ArcTan(SinAngle / Diviseur);
  1318.   CalcArcSinRadians := Angle;
  1319. end;
  1320. function TbsSkinColorDialog.CalcDistancePoints(X1, Y1, X2, Y2: Double): Double;
  1321. begin
  1322.   CalcDistancePoints := Sqrt(Sqr(Y2 - Y1) + Sqr(X2 - X1));
  1323. end;
  1324. procedure TbsSkinColorDialog.InitPSPPalette;
  1325. var
  1326.   GCircle, PCircle, Disque: HRGN;
  1327.   PLigneCircle: pointer;
  1328.   I, J : Integer;
  1329.   C_X, C_Y: Integer;
  1330.   Col: TPSPColor;
  1331.   Col2: THSL;
  1332.   Val: THSL;
  1333.   TabCol: array[0..359]of TRGB;
  1334.   Angle: Integer;
  1335.   PanelData: TbsDataSkinPanelControl;
  1336.   PanelDataIndex: Integer;
  1337.   NewClRect: TRect;
  1338.   w, h, rw, rh, X, Y, XCnt, YCnt, XO, YO: Integer;
  1339.   SB: TBitMap;
  1340. begin
  1341.   Col := TPSPColor.Create;
  1342.   GCircle := CreateEllipticRgn(PalettePSPCoord.Left, PalettePSPCoord.Top,
  1343.     PalettePSPCoord.Right, PalettePSPCoord.Bottom);
  1344.   PCircle := CreateEllipticRgn((PalettePSPCoord.Left + 20),
  1345.     (PalettePSPCoord.Top + 20), (PalettePSPCoord.Right - 20), (PalettePSPCoord.Bottom - 20));
  1346.   Disque := CreateRectRgn(0, 0, 2, 2);
  1347.   CombineRgn(Disque, GCircle, PCircle, RGN_DIFF);
  1348.   Val.S := 1;
  1349.   Val.L := 0.47;
  1350.   for I := 0 to 359 do
  1351.   begin
  1352.     Val.H := I/359;
  1353.     Col.HSL := Val;
  1354.     TabCol[I] := Col.RGB;
  1355.   end;
  1356.   C_X := PalettePSPCoord.Left + 98;
  1357.   C_Y := PalettePSPCoord.Left + 98;
  1358.   Val.S := 0.93;
  1359.   Val.L := 0.47;
  1360.   // Draw background
  1361.   if (FCtrlFSD <> nil) and not FCtrlFSD.Empty and
  1362.      (FCtrlFSD.GetControlIndex('panel') <> -1)
  1363.   then
  1364.     begin
  1365.       PanelDataIndex := FCtrlFSD.GetControlIndex('panel');
  1366.       PanelData := TbsDataSkinPanelControl(FCtrlFSD.CtrlList.Items[PanelDataIndex]);
  1367.       SB := TBitMap(FCtrlFSD.FActivePictures.Items[PanelData.PictureIndex]);
  1368.       NewClRect := Rect(0, 0, PalettePSP.Width, PalettePSP.Height);
  1369.       w := RectWidth(PanelData.ClRect);
  1370.       h := RectHeight(PanelData.ClRect);
  1371.       rw := RectWidth(NewClRect);
  1372.       rh := RectHeight(NewClRect);
  1373.       XCnt := rw div w;
  1374.       YCnt := rh div h;
  1375.       for X := 0 to XCnt do
  1376.       for Y := 0 to YCnt do
  1377.         begin
  1378.           if X * w + w > rw then XO := X * W + W - rw else XO := 0;
  1379.           if Y * h + h > rh then YO := Y * h + h - rh else YO := 0;
  1380.           PalettePSP.Canvas.CopyRect(
  1381.              Rect(NewClRect.Left + X * w, NewClRect.Top + Y * h,
  1382.                   NewClRect.Left + X * w + w - XO, NewClRect.Top + Y * h + h - YO),
  1383.              SB.Canvas,
  1384.              Rect(PanelData.SkinRect.Left + PanelData.ClRect.Left,
  1385.                   PanelData.SkinRect.Top + PanelData.ClRect.Top,
  1386.              PanelData.SkinRect.Left + PanelData.ClRect.Right - XO,
  1387.              PanelData.SkinRect.Top + PanelData.ClRect.Bottom - YO));
  1388.          end;
  1389.      end
  1390.   else
  1391.     begin
  1392.       PalettePSP.Canvas.Pen.Color := ColorToRGB(clBtnFace);
  1393.       PalettePSP.Canvas.Brush.Color := ColorToRGB(clBtnFace);
  1394.       Rectangle(PalettePSP.Canvas.Handle, 0, 0, PalettePSP.Width, PalettePSP.Height);
  1395.     end;
  1396.   //
  1397.   for J := 0 to PalettePSPCoord.Bottom - 1 do
  1398.   begin
  1399.     PLigneCircle := PalettePSP.Picture.Bitmap.ScanLine[PalettePSPCoord.Top+J];
  1400.     for I := 0 to PalettePSPCoord.Bottom - 1 do
  1401.       if PtInRegion(Disque,PalettePSPCoord.Left+I,PalettePSPCoord.Top+J) then
  1402.       begin
  1403.         Angle := Round(CalcAngle3Points(C_X, 0, C_X, C_Y, I, J));
  1404.         if Angle = 360 then Angle := 0;
  1405.         Angle := 359 - Angle;
  1406.         TLineB(PLigneCircle)[(PosCircle+I)*4 + 0] := TabCol[Angle].B;
  1407.         TLineB(PLigneCircle)[(PosCircle+I)*4 + 1] := TabCol[Angle].G;
  1408.         TLineB(PLigneCircle)[(PosCircle+I)*4 + 2] := TabCol[Angle].R;
  1409.       end;
  1410.   end;
  1411.   Col.Assign(PSPColor);
  1412.   Col2 := Col.HSL;
  1413.   for J :=RectPSP.Top to RectPSP.Bottom do
  1414.   begin
  1415.     PLigneCircle := PalettePSP.Picture.Bitmap.ScanLine[J];
  1416.     Col2.L := (J-RectPSP.Top)/(RectPSP.Bottom-RectPSP.Top);
  1417.     for I := RectPSP.Left to (RectPSP.Right) do
  1418.       begin
  1419.         Col2.S := (I-RectPSP.Left)/(RectPSP.Right-RectPSP.Left);
  1420.         Col.HSL := Col2;
  1421.         TLineB(PLigneCircle)[(I+PosCar)*4    ] := Col.RGB.B;
  1422.         TLineB(PLigneCircle)[(I+PosCar)*4 + 1] := Col.RGB.G;
  1423.         TLineB(PLigneCircle)[(I+PosCar)*4 + 2] := Col.RGB.R;
  1424.       end;
  1425.   end;
  1426.   PalettePSP.Canvas.Pen.Color := $FFFFFF;
  1427.   PalettePSP.Canvas.Pen.Mode := pmXor;
  1428.   PalettePSP.Canvas.Brush.Style := bsClear;
  1429.   DrawCursor;
  1430.   PalettePSP.Picture.Bitmap.modified := true;
  1431.   Col.Free;
  1432. end;
  1433. procedure TbsSkinColorDialog.DrawPSPPalette;
  1434.   procedure DrawRect;
  1435.   var
  1436.     PLigneCircle : pointer;
  1437.     I, J : Integer;
  1438.     Col : TPSPColor;
  1439.     Col2 : THSL;
  1440.   begin
  1441.     Col := TPSPColor.Create;
  1442.     Col.Assign(PSPColor);
  1443.     Col2 := Col.HSL;
  1444.     for J :=RectPSP.Top to RectPSP.Bottom do
  1445.     begin
  1446.       PLigneCircle := PalettePSP.Picture.Bitmap.ScanLine[J];
  1447.       Col2.L := (J-RectPSP.Top)/(RectPSP.Bottom-RectPSP.Top);
  1448.       for I := RectPSP.Left to (RectPSP.Right) do
  1449.         begin
  1450.           Col2.S := (I-RectPSP.Left)/(RectPSP.Right-RectPSP.Left);
  1451.           Col.HSL := Col2;
  1452.           TLineB(PLigneCircle)[(I+PosCar)*4    ] := Col.RGB.B;
  1453.           TLineB(PLigneCircle)[(I+PosCar)*4 + 1] := Col.RGB.G;
  1454.           TLineB(PLigneCircle)[(I+PosCar)*4 + 2] := Col.RGB.R;
  1455.         end;
  1456.     end;
  1457.     Col.free;
  1458.   end;
  1459. begin
  1460.   DrawRect;
  1461.   DrawCursor;
  1462.   PalettePSP.Picture.Bitmap.Modified := true;
  1463. end;
  1464. procedure TbsSkinColorDialog.DrawCursor;
  1465.   procedure DrawCircle(X,Y,R:Integer);
  1466.   begin
  1467.     Ellipse(PalettePSP.Canvas.Handle,X - R, Y - R,X + R, Y + R);
  1468.   end;
  1469. var
  1470.   Angle: Integer;
  1471.   X,Y: Double;
  1472.   C_X,C_Y:  Integer;
  1473. begin
  1474.   X := round((PSPColor.HSL.S * (RectPSP.Right-RectPSP.Left)) + (PosCar + RectPSP.Left));
  1475.   Y := round((PSPColor.HSL.L * (RectPSP.Bottom-RectPSP.Top)) + RectPSP.Top);
  1476.   DrawCircle(Round(X), Round(Y),5);
  1477.   C_X := PosCar + RectPSP.Left + (RectPSP.Right-RectPSP.Left)div 2;
  1478.   C_Y := RectPSP.Top + (RectPSP.Bottom - RectPSP.Top)div 2;
  1479.   Angle := Round(PSPColor.HSL.H * 360);
  1480.   CalcRotationPoint(C_X, C_Y, -Angle, C_X, C_Y-((PalettePSPCoord.Bottom-20) div 2), X,Y);
  1481.   DrawCircle(Round(X),Round(Y),5);
  1482. end;
  1483. procedure TbsSkinColorDialog.PalettePSPMouseDown(Sender: TObject;
  1484.   Button: TMouseButton; Shift: TShiftState; X, Y: Integer);
  1485. var
  1486.   GCircle, PCircle, Disque, Car: HRGN;
  1487.   HSLPSP: THSLPSP;
  1488.   C_X,C_Y: Integer;
  1489.   Angle: Integer;
  1490. begin
  1491.   GCircle := CreateEllipticRgn(PosCircle+PalettePSPCoord.Left,PalettePSPCoord.Top,PosCircle+PalettePSPCoord.Right,PalettePSPCoord.Bottom);
  1492.   PCircle := CreateEllipticRgn(PosCircle+PalettePSPCoord.Left+20,PalettePSPCoord.Top+20,PosCircle+PalettePSPCoord.Right-21,PalettePSPCoord.Bottom-21);
  1493.   Disque := CreateRectRgn(0,0,2,2);
  1494.   CombineRgn(Disque,GCircle,PCircle,RGN_DIFF);
  1495.   Car := CreateRectRgn(PosCar+RectPSP.Left,RectPSP.Top,PosCar+RectPSP.Right,RectPSP.Bottom);
  1496.   if PtInRegion(Car,X,Y)
  1497.   then
  1498.     ClickImg := czpspPCar
  1499.   else
  1500.   if PtInRegion(Disque,X,Y)
  1501.   then
  1502.     ClickImg := czpspPCircle
  1503.   else
  1504.     ClickImg := czpspPnone;
  1505.   if mbLeft = Button then
  1506.   case ClickImg of
  1507.     czpspPCircle :
  1508.     begin
  1509.       C_X := PosCar+RectPSP.Left+(RectPSP.Right-RectPSP.Left)div 2;
  1510.       C_Y := RectPSP.Top+(RectPSP.Bottom-RectPSP.Top)div 2;;
  1511.       Angle := Round(CalcAngle3Points(C_X, 0, C_X, C_Y, X, Y));
  1512.       if Angle = 360 then Angle := 0;
  1513.       Angle := 359 - Angle;
  1514.       HSLPSP := PSPColor.HSLPSP;
  1515.       HSLPSP.H := Round(255 * (Angle / 359));
  1516.       if HSLPSP.H <> PSPColor.HSLPSP.H
  1517.       then
  1518.         begin
  1519.           DrawCursor;
  1520.           PSPColor.HSLPSP := HSLPSP;
  1521.           ChangeEdits;
  1522.           DrawPSPPalette;
  1523.         end;
  1524.     end;
  1525.     czpspPCar :
  1526.     begin
  1527.       C_X := X;
  1528.       C_Y := Y;
  1529.       if C_X<PosCar+RectPSP.Left
  1530.       then
  1531.         C_X:= PosCar+RectPSP.Left
  1532.       else
  1533.       if C_X>PosCar+RectPSP.Right
  1534.       then
  1535.         C_X:= PosCar+RectPSP.Right;
  1536.       if C_Y<RectPSP.Top
  1537.       then
  1538.         C_Y:= RectPSP.Top
  1539.       else
  1540.       if C_Y>RectPSP.Bottom
  1541.       then
  1542.         C_Y:= RectPSP.Bottom;
  1543.       HSLPSP := PSPColor.HSLPSP;
  1544.       HSLPSP.S := Round(255 * ((C_X - (PosCar+RectPSP.Left)) / (RectPSP.Right-RectPSP.Left)));
  1545.       HSLPSP.L := Round(255 * ((C_Y - RectPSP.Top)/(RectPSP.Bottom - RectPSP.Top)));
  1546.       DrawCursor;
  1547.       PSPColor.HSLPSP := HSLPSP;
  1548.       ChangeEdits;
  1549.       DrawCursor;
  1550.       PalettePSP.Repaint;
  1551.     end;
  1552.   end;
  1553.    
  1554. end;
  1555. procedure TbsSkinColorDialog.PalettePSPMouseMove(Sender: TObject; Shift: TShiftState;
  1556.   X, Y: Integer);
  1557. var
  1558.   HSLPSP : THSLPSP;
  1559.   C_X,C_Y : Integer;
  1560.   Angle : Integer;
  1561. begin
  1562.   if ssLeft in Shift then
  1563.   case ClickImg of
  1564.     czpspPCircle:
  1565.     begin
  1566.       C_X := PosCar + RectPSP.Left + (RectPSP.Right - RectPSP.Left)div 2;
  1567.       C_Y := RectPSP.Top + (RectPSP.Bottom - RectPSP.Top) div 2;
  1568.       Angle := Round(CalcAngle3Points(C_X, 0, C_X, C_Y, X, Y));
  1569.       if Angle = 360 then Angle := 0;
  1570.       Angle := 359 - Angle;
  1571.       HSLPSP := PSPColor.HSLPSP;
  1572.       HSLPSP.H := Round(255*(Angle/359));
  1573.       if HSLPSP.H <> PSPColor.HSLPSP.H
  1574.       then
  1575.         begin
  1576.           DrawCursor;
  1577.           PSPColor.HSLPSP := HSLPSP;
  1578.           ChangeEdits;
  1579.           DrawPSPPalette;
  1580.         end;
  1581.     end;
  1582.     czpspPCar :
  1583.     begin
  1584.       C_X := X;
  1585.       C_Y := Y;
  1586.       if C_X < PosCar+RectPSP.Left
  1587.       then
  1588.         C_X := PosCar+RectPSP.Left
  1589.       else
  1590.       if C_X > PosCar+RectPSP.Right
  1591.       then
  1592.         C_X := PosCar+RectPSP.Right;
  1593.       if C_Y < RectPSP.Top
  1594.       then
  1595.         C_Y := RectPSP.Top
  1596.       else
  1597.       if C_Y > RectPSP.Bottom
  1598.       then
  1599.         C_Y := RectPSP.Bottom;
  1600.       HSLPSP := PSPColor.HSLPSP;
  1601.       HSLPSP.S := Round(255 * ((C_X-(PosCar+RectPSP.Left)) / (RectPSP.Right-RectPSP.Left)));
  1602.       HSLPSP.L := Round(255 * ((C_Y-RectPSP.Top) / (RectPSP.Bottom-RectPSP.Top)));
  1603.       DrawCursor;
  1604.       PSPColor.HSLPSP := HSLPSP;
  1605.       ChangeEdits;
  1606.       DrawCursor;
  1607.       PalettePSP.Repaint;
  1608.     end;
  1609.   end;
  1610. end;
  1611. procedure TbsSkinColorDialog.PalettePSPMouseUp(Sender: TObject; Button: TMouseButton;
  1612.   Shift: TShiftState; X, Y: Integer);
  1613. var
  1614.   HSLPSP : THSLPSP;
  1615.   C_X,C_Y : Integer;
  1616.   Angle : Integer;
  1617. begin
  1618.   if mbLeft=Button then
  1619.   case ClickImg of
  1620.     czpspPCircle :
  1621.     begin
  1622.       C_X := PosCar+RectPSP.Left+(RectPSP.Right-RectPSP.Left)div 2;
  1623.       C_Y := RectPSP.Top+(RectPSP.Bottom-RectPSP.Top)div 2;;
  1624.       Angle := Round(CalcAngle3Points(C_X, 0, C_X, C_Y, X,Y));
  1625.       if Angle = 360 then Angle := 0;
  1626.       Angle := 359 - Angle;
  1627.       HSLPSP := PSPColor.HSLPSP;
  1628.       HSLPSP.H := Round(255 * (Angle / 359));
  1629.       if HSLPSP.H <> PSPColor.HSLPSP.H
  1630.       then
  1631.         begin
  1632.           DrawCursor;
  1633.           PSPColor.HSLPSP := HSLPSP;
  1634.           ChangeEdits;
  1635.           DrawPSPPalette;
  1636.         end;
  1637.     end;
  1638.     czpspPCar :
  1639.     begin
  1640.       C_X := X;
  1641.       C_Y := Y;
  1642.       if C_X<PosCar+RectPSP.Left
  1643.       then
  1644.         C_X:= PosCar+RectPSP.Left
  1645.       else
  1646.       if C_X>PosCar+RectPSP.Right
  1647.       then
  1648.         C_X:= PosCar+RectPSP.Right;
  1649.       if C_Y<RectPSP.Top
  1650.       then
  1651.         C_Y:= RectPSP.Top
  1652.       else
  1653.       if C_Y>RectPSP.Bottom
  1654.       then
  1655.         C_Y:= RectPSP.Bottom;
  1656.       HSLPSP := PSPColor.HSLPSP;
  1657.       HSLPSP.S := Round(255 * ((C_X - (PosCar + RectPSP.Left)) / (RectPSP.Right - RectPSP.Left)));
  1658.       HSLPSP.L := Round(255 * ((C_Y - RectPSP.Top) / (RectPSP.Bottom-RectPSP.Top)));
  1659.       DrawCursor;
  1660.       PSPColor.HSLPSP := HSLPSP;
  1661.       ChangeEdits;
  1662.       DrawCursor;
  1663.       PalettePSP.Repaint;
  1664.     end;
  1665.   end;
  1666.   ClickImg := czpspPnone;
  1667. end;
  1668. constructor TbsSkinCustomColorGrid.Create(AOwner: TComponent);
  1669. var
  1670.   i: Integer;
  1671. begin
  1672.   inherited;
  1673.   ControlStyle := ControlStyle - [csAcceptsControls];
  1674.   CaptionMode := True;
  1675.   Caption := BS_CUSTOMCOLORGRID_CAP;
  1676.   BorderStyle := bvFrame;
  1677.   Width := 280;
  1678.   Height := 115;
  1679.   FColorValue := 0;
  1680.   FColCount := 6;
  1681.   FRowCount := 2;
  1682.   for i := 1 to 12 do CustomColorValues[I] := clWhite;
  1683.   FColorsCount := 0;
  1684.   FColorIndex := 0;
  1685. end;
  1686. destructor TbsSkinCustomColorGrid.Destroy;
  1687. begin
  1688.   inherited;
  1689. end;
  1690. procedure TbsSkinCustomColorGrid.AddColor(AColor: TColor);
  1691. begin
  1692.   if FColorsCount = 12 then FColorsCount := 0;
  1693.   Inc(FColorsCount);
  1694.   CustomColorValues[FColorsCount] := AColor;
  1695.   RePaint;
  1696. end;
  1697. procedure TbsSkinCustomColorGrid.SetColCount(Value: Integer);
  1698. begin
  1699.   if Value < 1 then Exit;
  1700.   FColCount := Value;
  1701.   RePaint;
  1702. end;
  1703. procedure TbsSkinCustomColorGrid.SetRowCount(Value: Integer);
  1704. begin
  1705.   FRowCount := Value;
  1706.   RePaint;
  1707. end;
  1708. procedure TbsSkinCustomColorGrid.DrawCursor;
  1709. var
  1710.   CX, CY, Rd: Integer;
  1711. begin
  1712.   CX := R.Left + RectWidth(R) div 2;
  1713.   CY := R.Top + RectHeight(R) div 2;
  1714.   if RectWidth(R) > RectHeight(R)
  1715.   then
  1716.     Rd := RectHeight(R) div 2 - 2
  1717.   else
  1718.     Rd := RectWidth(R) div 2 - 2;
  1719.   with Cnvs do
  1720.   begin
  1721.     if pmNotMode then Pen.Mode := pmNot else Pen.Color := 0;
  1722.     MoveTo(CX - rd, CY); LineTo(CX - 2, CY);
  1723.     MoveTo(CX + 3, CY); LineTo(CX + rd + 1, CY);
  1724.     MoveTo(CX, CY - rd); LineTo(CX, CY - 2);
  1725.     MoveTo(CX, CY + 3); LineTo(CX, CY + rd);
  1726.   end;
  1727. end;
  1728. procedure TbsSkinCustomColorGrid.PaintGrid(Cnvs: TCanvas);
  1729. var
  1730.   X, Y, CW, CH, i, j, k: Integer;
  1731.   R, Rct: TRect;
  1732. begin
  1733.   R := Rect(0, 0, Width, Height);
  1734.   AdjustClientRect(R);
  1735.   CW := (RectWidth(R) - ColCount * 2) div ColCount;
  1736.   CH := (RectHeight(R) - RowCount * 2) div RowCount;
  1737.   Y := R.Top + 1;
  1738.   k := 0;
  1739.   for i := 1 to RowCount do
  1740.   begin
  1741.     X := R.Left + 1;
  1742.     for j := 1 to ColCount do
  1743.     begin
  1744.       Inc(k);
  1745.       with Cnvs do
  1746.       begin
  1747.         Brush.Color := CustomColorValues[k];
  1748.         Rct := Rect(X, Y, X + CW, Y + CH);
  1749.         InflateRect(Rct, -1, -1);
  1750.         FillRect(Rct);
  1751.         InflateRect(Rct, 1, 1);
  1752.         if k = FColorIndex  
  1753.         then
  1754.           begin
  1755.             if CustomColorValues[k] <> clGray
  1756.             then
  1757.               DrawCursor(Cnvs, Rct, True)
  1758.             else
  1759.               DrawCursor(Cnvs, Rct, False);
  1760.           end
  1761.       end;
  1762.       Inc(X, CW + 2);
  1763.     end;
  1764.     Inc(Y, CH + 2);
  1765.   end;
  1766. end;
  1767. procedure TbsSkinCustomColorGrid.CreateControlDefaultImage;
  1768. begin
  1769.   inherited;
  1770.   PaintGrid(B.Canvas);
  1771. end;
  1772. procedure TbsSkinCustomColorGrid.CreateControlSkinImage;
  1773. begin
  1774.   inherited;
  1775.   PaintGrid(B.Canvas);
  1776. end;
  1777. procedure TbsSkinCustomColorGrid.MouseDown(Button: TMouseButton; Shift: TShiftState;
  1778.                                      X, Y: Integer);
  1779. var
  1780.   X1, Y1, CW, CH, i, j, k: Integer;
  1781.   R, Rct: TRect;
  1782. begin
  1783.   inherited;
  1784.   R := Rect(0, 0, Width, Height);
  1785.   AdjustClientRect(R);
  1786.   CW := (RectWidth(R) - ColCount * 2) div ColCount;
  1787.   CH := (RectHeight(R) - RowCount * 2) div RowCount;
  1788.   Y1 := R.Top + 1;
  1789.   k := 0;
  1790.   for i := 1 to RowCount do
  1791.   begin
  1792.     X1 := R.Left + 1;
  1793.     for j := 1 to ColCount do
  1794.     begin
  1795.       Inc(k);
  1796.       Rct := Rect(X1, Y1, X1 + CW, Y1 + CH);
  1797.       if PtInRect(Rct, Point(X, Y))
  1798.       then
  1799.         begin
  1800.           FColorValue := CustomColorValues[k];
  1801.           FColorIndex := k;
  1802.           RePaint;
  1803.           if Assigned(FOnChange) then FOnChange(Self);
  1804.           Break;
  1805.         end;
  1806.       Inc(X1, CW + 2);
  1807.     end;
  1808.     Inc(Y1, CH + 2);
  1809.   end;  
  1810. end;
  1811. end.