色を数字にしよう

ランダムな色を表示しようRGB カラー を使って、表示されている色を数字に変換してみましょう。とりあえず、ここでは上記2つの内容を既に見たということで始めたいと思います。

まず初めに、以下のようにコンポーネントを配置してください。

ラベルの Name プロパティをそれぞれ表示されているのと同じように設定してください。Delphi では、Name プロパティを変更しますと、 Caption プロパティも自動的に変更されます。しかし、Caption プロパティを先に変更した後では、Name プロパティを変更しても Caption プロパティは変わらない仕組みになっています。

次に、スクロールバーを動かすと、パネルの色とラベルに数字を表示させるようにします。(スクロールバーの Min、 Max プロパティをそれぞれ 0、 255 にすることを忘れないで下さい。)詳しくは、RGB カラーを見てください。コードは以下のようになります。

procedure TForm1.ScrollBar1Change(Sender: TObject);
var
  r, g, b: string;
begin
  r := IntToStr(ScrollBar1.Position);
  g := IntToStr(ScrollBar2.Position);
  b := IntToStr(ScrollBar3.Position);

  lblR.Caption := r;
  lblG.Caption := g;
  lblB.Caption := b;

  Panel1.Color := RGB(StrToInt(r), StrToInt(g), StrToInt(b));

end;

ここまでは、前回と同じなので大丈夫だと思います。スクロールバーの状態に応じて、パネルの色と、ラベルに表示する数字を設定しているだけです。

色の表示について
Delphi では色を表示する場合、例えばフォームの色を変更する場合にはオブジェクトインスペクタで Color プロパティを変更することになります。これは実際には、TColor 型が使われていることになっています。そして、この TColor 型は、以下のような値をとることができます。
TColor = -$7FFFFFFF-1..$7FFFFFFF;

ですから、オブジェクトインスペクタで表示される clWhite や clBlue などは全てこの範囲の中で表されていることになります。

そして、この TColor 型は大きく分けて2つの型に分類されています。一つが RGB 型で、もう一つが System Color 型です。まず System Color 型についてですが、この System Color 型というのは、ボタンやスクロールバーなどに使われている色が、それに当たります。オブジェクトインスペクタで clBtnFace や clMenu などがそうです。簡単に言えば、ボタンは何色で表示するかということを定義しているだけです。

次に RGB 型ですが、これは以下のような値をとることになっています。

$00BBGGRR   // BB ( 青 )、GG ( 緑 )、RR ( 赤 )

$ は、この値が 16 進数であることを示しています。その後に続く 00 ですが、これは気にしないで下さい。(^^;
そして、その後に続く BBGGRR で、それぞれ青、緑、赤の設定をします。これで、それぞれの色( 青、緑、赤 )は、いくつの数字を持っているか分かると思います。この数字は、16 進数であるから、それぞれ $00 〜 $FF、つまり 0 〜 255 の値を取ることが出来ることになります。その為に、スクロールバーの Min、Max を 0、255 に設定したわけです。

ここでの目的は、色を数字にすることです。パネルに表示されている色を具体的な数値として表示させたいと思います。なんだか難しいようにみえますが、実は Delphi には、このための便利な関数があり、とても簡単に出来てしまいます。早速やってみましょう。

まず、パネルに表示された色を RGB 値として表示するには、ColorToRGB 関数を使ってやります。この名前は、わかりやすいですよね。IntToStr が分かる人なら誰でも理解することが出来て、さらに記憶しやすいと思います。

それでは、早速やってみましょう。以下のコードを書いてください。

type
  TForm1 = class(TForm)
    
    ............
    procedure ScrollBar1Change(Sender: TObject);
    procedure Button3Click(Sender: TObject);
  private
    { Private 宣言 }
  public
    { Public 宣言 }
    procedure ChangeColor; // 追加
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.ScrollBar1Change(Sender: TObject);
var
  r, g, b: string;
begin
  // それぞれの値(R, G, B)を取得
  r := IntToStr(ScrollBar1.Position);
  g := IntToStr(ScrollBar2.Position);
  b := IntToStr(ScrollBar3.Position);

  lblR.Caption := r;
  lblG.Caption := g;
  lblB.Caption := b;
 
  Panel1.Color := RGB(StrToInt(r), StrToInt(g), StrToInt(b));

  ChangeColor;
end;

procedure TForm1.ChangeColor;
begin
  lblTen.Caption := IntToStr(ColorToRGB(Panel1.Color));
end;

出来ましたら、実行してみて、スクロールバーを動かして見てください。
試してみて分かると思いますが、なんだか期待していたものではないような感じがしているのではないでしょうか?実は、これは数値は数値でも10進数で表示された数値なのです。ですからこれを16進数に変換しなければなりません。この変換も大変そうに見えますが、Delphi がちゃんと用意してくれているので、これもあっさり変換することが出来ます。

コードは以下のようになります。

procedure TForm1.ScrollBar1Change(Sender: TObject);
var
  r, g, b: string;
begin
  r := IntToStr(ScrollBar1.Position);
  g := IntToStr(ScrollBar2.Position);
  b := IntToStr(ScrollBar3.Position);

  lblR.Caption := r;
  lblG.Caption := g;
  lblB.Caption := b;

  Panel1.Color := RGB(StrToInt(r), StrToInt(g), StrToInt(b));

  ChangeColor;
end;

procedure TForm1.ChangeColor;
begin
  lblTen.Caption := IntToStr(ColorToRGB(Panel1.Color));
  lblRGB.Caption := '$' + IntToHex(ColorToRGB(Panel1.Color), 8);
  
end;

これで期待するものが出来ました。IntToHex が16進数に変換をしてくれています。

一応、これで出来たのですけれども、何か色の一覧表から任意の色を選んで、そしてその色の値を得られたらいいですよね。それには、まさに ColorDialog がその役目を果たしてくれます。それでは、フォームに ColorDialog を貼り付けて、以下のようにします。

procedure TForm1.Button1Click(Sender: TObject);
var
  r, g, b: string;
begin
  if ColorDialog1.Execute then
    Panel1.Color := ColorDialog1.Color;

  ChangeColor;
  
  // それぞれの値を取得
  r := format('%d', [GetRValue(Panel1.Color)]);
  g := format('%d', [GetGValue(Panel1.Color)]);
  b := format('%d', [GetBValue(Panel1.Color)]);

  lblR.Caption := r;
  lblG.Caption := g;
  lblB.Caption := b;

  ScrollBar1.Position := StrToInt(r);
  ScrollBar2.Position := StrToInt(g);
  ScrollBar3.Position := StrToInt(b);
end;

また、ついでに HTML で使用する色の値をとるようにもしてみます。

function ColorToHTML(AColor: TColor): string;  // 追加
begin
  Result := format('#%.2x%.2x%.2x',
    [GetRValue(AColor), GetGValue(AColor), GetBValue(AColor)]);
end;

procedure TForm1.ScrollBar1Change(Sender: TObject);
var
  r, g, b: string;
begin
  r := IntToStr(ScrollBar1.Position);
  g := IntToStr(ScrollBar2.Position);
  b := IntToStr(ScrollBar3.Position);

  lblR.Caption := r;
  lblG.Caption := g;
  lblB.Caption := b;

  Panel1.Color := RGB(StrToInt(r), StrToInt(g), StrToInt(b));

  ChangeColor;
end;

procedure TForm1.Button3Click(Sender: TObject);
var
  r, g, b: string;
begin
  if ColorDialog1.Execute then
    Panel1.Color := ColorDialog1.Color;

  ChangeColor;

  r := format('%d', [GetRValue(Panel1.Color)]);
  g := format('%d', [GetGValue(Panel1.Color)]);
  b := format('%d', [GetBValue(Panel1.Color)]);

  lblR.Caption := r;
  lblG.Caption := g;
  lblB.Caption := b;

  ScrollBar1.Position := StrToInt(r);
  ScrollBar2.Position := StrToInt(g);
  ScrollBar3.Position := StrToInt(b);
end;

procedure TForm1.ChangeColor;
begin
  lblHTML.Caption := ColorToHTML(Panel1.Color);  // 追加
  lblTen.Caption := IntToStr(ColorToRGB(Panel1.Color));
  lblRGB.Caption := '$' + IntToHex(ColorToRGB(Panel1.Color), 8);
end;

見やすくするためのラベルも貼り付けてあります。


up next
Last update: 2002/6/10