2017. 5. 2.
石立 喬

Visual Studio Community 2017の使い方(3)

―― 水平Sliderを使用してRGB値から色を作成し、HSVに変換する ――

 コントロール部品のSliderを使ってマウスで数値を入力し、計算を行う例を示す。具体的には、3個のSliderでRGBの値を設定して、色をRectangleで表示し、Buttponをクリックすると、RGB値がHSVに変換されて値が表示される。

Slider
 Sliderは、マウスを使って、外部からアナログ感覚で数値を設定できるコントロールで、そのValue(値はdouble型)プロパティを読み取って使用する。図1にSliderの「プロパティ」ウィンドウの一例を示す。左は設定前のデフォルト値で、Orientation(方向)はHorizontal(水平)である。これをVertical(垂直)にも変更できるので、垂直の例も示す。図1の右は、ここで使用する目的に沿って変更した後の状態である。
 イベントハンドラーには、ValueChangedを使用する。


図1 Sliderの「プロパティ」ウィンドウ(左はデフォルト、右は設定後)


RGB表色系とHSV表色系
 表示デバイスや画像処理には、R(Red、赤)、G(Green、緑)、B(Blue、青)のRGB表色系が用いられる。一方、デザイナー側からは、H(Hue、色相)、S(Saturation、彩度)、V(Value、明度)で色を表現するHSV表色系が好まれる。HSV表色系と同じものにHSB系、似たものにHSL、HSIがある。
 RGB系からHSV系への変換、その逆変換の計算式は、多くの資料にあるが、ここでは「Visual C++ 2010 Expressを用いた易しい画像処理(3)」のものを使用した。

使用したクラス、メソッドの説明
◎ColorHelperクラスとFromArgbメソッド
 C++/CXでは、Color構造体を設定するためにColorクラスを使うことができない。C#とVisual BasicでのColorクラスに対応する、C++/CX用のColorHelperクラスがある。唯一のメソッドとして、Windows RTのColor構造体を生成する
   FromArgb(byte A, byte R, byte G, byte B)
がある。FromRgbは無いので、A(透明度)を必ず入れなくてはならない。
◎SolidColorBrushクラス
 UIコントロール部品のBackground、Foreground、Flllなどのプロパティとして広く使われるBrushのタイプで、コンストラクタの
   SolidCororBrush(Color)
により、指定した色のブラシが得られる。ここでは、RectangleのFillプロパティの設定に用いている。
 namespaceは、System::Windows::Mediaで、これはデフォルトで設定されているので、新たに設定する必要はない。
 あらかじめ定義された色(Red、Greenなど)またはargbの16進数もこのクラスの値として使用できる。他に、LinearGradientBrush、ImageBrushなどがある。

XAMLによるコントロール部品の設定
 新たに使用した部品(SliderとRectangle)と、設定を追加した部品(TextBlock)のXAMLコードを下記に示し、説明する。
◎slider
 マウスで値を入力できるコントロールで、水平Sliderがデフォルトとなっていて、垂直の場合のみ、Orientation="Vertical"が入る。
   <Slider x:Name="sliderR" ------- プログラムで値を読み取るために名前を付けておく
         HorizontalAlignment="Left" ---- デフォルト
         Margin="100, 50, 0,0”
         VerticalAlignment="Top" ------ デフォルト
         Width="200"
         TickFrequency="16" --------- 刻みを16ごとにする
         TickPlacement="BottomRight" --- trackの下(水平の場合)または右(垂直の場合)に刻みを入れる
         Value="0" --------- Rの最小値
         Maximum="255" ---- Rの最大値
         LargeChange="16"
         ValueChanged="sliderR_ValueChanged"
   />
◎Rectangle
 FillプロパティにBrushを設定することにより、色を表示することができる。
   <Rectangle x:Name="rectangle1" -------- Fillをプログラムで与えるので、命名しておく
          Fill="Black" ----------------- 初期状態は、R = 0, G = 0, B = 0のため、Blackを指定
          HorizontalAlignment="Left" ---- デフォルト
          Height="146"
          Margin="400, 45, 0, 0"
          Stroke="Black" -------------- 周辺の線色(デフォルト)
          VerticalAlignment="Top"------- デフォルト
          Width="120" 
          RenderTransformOrigin="0.5, 0.5" --- ドラッグで配置すると値が不統一なので、編集するか削除する
   />
◎Sliderの値を表示するために設けた文字列表示用で、Bindingにより、自動的に値を取得する。
   <TextBlock x:Name="textBlockR" ------- プログラム上は必要ないが、念のために付けた
          HorizontalAlignment="Left" ---- デフォルト
          Margin="320, 58, 0, 0"
          TextWrapping="Wrap" --------- デフォルト
          Text="{Binding Value, ElementName=sliderR}"---- sliderRのValueプロパティを入れるように設定する
          VerticalAlignment="Top" ------ デフォルト
          Width="30"
          TextAlignment="Right" ------- 右詰めに配置する(デフォルトはLeft)、「プロパティ」ウィンドウに見当たらなかった
    />

「デザイン」画面による部品の配置と「XAML」エディタによる詳細設定
 「ツールボックス」から大体の位置にコントロール部品を持ってきて並べ、「プロパティ」ウィンドウで名前や表示、サイズを設定し、さらに「XAML」エディタを直接編集して最終的に得られた結果を以下に示す。
 図2は「デザイン」画面で、初期設定で、各SliderのValueが0に、RectangleのFillがBlackになっていることが分かる。
 図3は「XAML」エディタの左側部分で、「R成分」などのTextBlock3個、対応するsliderRなどのSlider3個(値を読み取るために名前は必要)、各Sliderの値を表示するTextBlock3個(これはBindingで値を表示させるので、名前は不要であるが、念のために付けた)、色を表示するためのRectangle、「H =」などのTextBlock3個、「RGB→HSV」のButton、HSVを表示するためのTextBlock3個が記述されている(「ツールボックス」から自動生成されたものを詳細編集)。図4はXAMLコードの右側部分で、設定の詳細が分かる。


図2 コントロール部品を配置した「デザイン」画面



図3 コントロール部品の配置と設定を終わったXAMLコード(左半分)



図4 コントロール部品の配置と設定を終わったXAMLコード(右半分)


プログラムの作成
 このプログラムは、イベントドリブン方式で、コントロールに何らかの変化があった場合に処理を行う。したがって、コードの記述は、イベントハンドラーのメソッド内が中心となる。
1) プログラムの最初の部分で、Windows::UIのnamespaceを宣言しておく。これは、ColorクラスとColorHelperクラスのためである(図5参照)。C++/CXでは、RGBからColor構造体を生成するのに、ColorHelperクラスを使用することに注意を要する。
2)Sliderの設定が変化した場合には、そのSliderのValueを読み取り、Color構造体のcolor1を生成し、さらにSolidColorBrushクラスのオブジェクトに変換して、RectangleのFillプロパティに設定する(図6参照)。Fillプロパティには、Color構造体ではなく、Brush系のクラスを用いることに注意を要する。
3) Buttonがクリックされた場合には、RGBからHSVへの変換を行い、各HSV値を文字列に変換してから、それぞれ、textBlockHなどのTextプロパティに入れる(図7参照)。


図5 プログラムの最初の部分でnamespaceとグローバル変数を追加する



図6 各Sliderのイベントハンドラーは、各Valueでcolor1を生成し、Brush化してrectangle1のFillに渡す



図7 button1をクリックした時のイベントハンドラーで、RGB値をHSV値に変換し表示する


得られた結果
 図8は、このプログラムの起動直後の画面を示したもので、デバッグの際の便利のために、上方中央部にデバッグツールが表示されている。デバッグ時以外では表示されないものであるが、邪魔であるので、メニューから「デバッグ」→「オプション」と選択して、図9のように「XAMLのUIデバッグツールを有効にする」のチェックを外す。
 図9は、プログラムを起動後、3個のSliderを動かして色を作成し、「RGB→HSV」をクリックしてHSV値に変換・表示した結果である。


図8 デフォルトでは、画面上方中央部にUIデバッグツールが表示される



図9 デバッグ時にデフォルトツールを表示させないようにする



図10 3個のSliderで色を作成し、ButtonをクリックしてHSV値を表示


垂直Sliderを使用した例
 Sliderの「プロパティ」ウィンドウで、OrientationをVerticalに変更し、サイズと関連部品の配置を変更して得た結果を図11に示す。IsDirectionReversedにチェックを付けなくても、上に行くほど値が大きくなり、TickPlacementもそのままでよかった。


図11 垂直Sliderを使用した例、Slider関連以外の位置はそのままにしてある








「Visual C++の勉強部屋」(目次)