2010年1月4日月曜日

C# カラーピッカーのスライダーを作ってみた その2

C#たんかわいいよC#たん もでりんぐしたい><


先日から引き続きカラーピッカー用のスライダーを作ってみた。
変更点は色選択を配列で渡すように変更して、2色以上のグラデーションに対応。

これでHSVのHのスライダーが作れるようになった^^



using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;
using System.Drawing.Drawing2D;

public partial class GradationSlider : Control
{

    // イベントの宣言
    [Description("コントロールの値が変更するとき発生します。")]
    [Category("アクション")]
    public event EventHandler ValueChanged;

    // プロパティ
    private int _maximum = 100;
    public int Maximum
    {
        set
        {
            this._maximum = value;
        }
        get
        {
            return this._maximum;
        }
    }

    public int Minimum { get; set; }

    private int _value;
    public int Value
    {
        set
        {
            this._value = value;
            if (ValueChanged != null && Value >= Minimum && Value <= Maximum) ValueChanged(this, new EventArgs());
            this.Refresh();
        }
        get
        {
            return this._value;
        }
    }

    private Color[] _gradationColor;
    public Color[] GradationColor
    {
        set
        {
            this._gradationColor = value;
            drawGradation();
            this.Refresh();
        }
        get
        {

            return this._gradationColor;
        }
    }

    public GradationSlider()
    {
        InitializeComponent();

        this.SetStyle(ControlStyles.ResizeRedraw, true);
        this.SetStyle(ControlStyles.DoubleBuffer, true);
        this.SetStyle(ControlStyles.UserPaint, true);
        this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);

        this.Resize += new System.EventHandler(this.CSlider_Resize);
        this.MouseMove += new System.Windows.Forms.MouseEventHandler(this.CSlider_MouseMove);
        this.MouseDown += new System.Windows.Forms.MouseEventHandler(this.CSlider_MouseDown);
        this.MouseUp += new System.Windows.Forms.MouseEventHandler(this.CSlider_MouseUp);
        this.MouseLeave += new System.EventHandler(this.CSlider_MouseLeave);
        this.MouseEnter += new System.EventHandler(this.CSlider_MouseEnter);

        drawTick();
    }

    // 描画
    //針の描画
    private Bitmap tick;
    private void drawTick()
    {
        tick = new Bitmap(10, 10);

        Graphics g = Graphics.FromImage(tick);
        g.SmoothingMode = SmoothingMode.HighQuality;
        Point[] point = {   new Point(5,1), new Point(9,5),
                                new Point(9,7), new Point(8,8),
                                new Point(2,8), new Point(1,7),
                                new Point(1,5), new Point(5,1) };
        Brush b = new SolidBrush(Color.White);
        g.FillPolygon(b, point);
        Pen p = new Pen(Color.Black, 1);
        if (activeFlag == true)
        {
            p = new Pen(Color.Brown, 1);
        }
        g.DrawLines(p, point);
        g.Dispose();
    }

    protected override void OnPaint(PaintEventArgs pe)
    {
        base.OnPaint(pe);
        drawGradation();
        pe.Graphics.DrawImage(gradation, 5, 0, gradation.Width, gradation.Height);
        pe.Graphics.DrawImage(tick, (Value * gradation.Width) / (Maximum - Minimum), gradation.Height);

    }

    //グラデーションの描画
    private Bitmap gradation;
    private void drawGradation()
    {
        if (this.Width > 10 && this.Height > 10)
        {
            Size gradationSize = new Size(this.Width - 10, this.Height - 10);

            gradation = new Bitmap(gradationSize.Width, gradationSize.Height);
            Graphics g = Graphics.FromImage(gradation);
            LinearGradientBrush lgb =
                new LinearGradientBrush(new Rectangle(0, 0, gradationSize.Width, gradationSize.Height),
                    Color.Black, Color.White, LinearGradientMode.Horizontal);

            //多色用


            if (GradationColor != null && GradationColor.Length >= 2)
            {
                // ColorBlendクラスを生成 
                ColorBlend cb = new ColorBlend();
                cb.Colors = GradationColor;
                float[] Position = new float[GradationColor.Length];
                for (int i = 0; i < GradationColor.Length; i++)
                {
                    Position[i] = (1.0f / (GradationColor.Length - 1)) * (i);
                }

                cb.Positions = Position;
                // ブラシのInterpolationColorsに設定 
                lgb.InterpolationColors = cb;
            }


            g.FillRectangle(lgb, new Rectangle(0, 0, gradationSize.Width, gradationSize.Height));

            //枠線
            Pen p = new Pen(Color.Black, 1);
            if (activeFlag == true)
            {
                p = new Pen(Color.Brown, 1);
            }

            g.DrawRectangle(p, 0, 0, gradationSize.Width - 1, gradationSize.Height - 1);
            lgb.Dispose();
            g.Dispose();
        }

    }


    //リサイズ時、グラデーションの再描画
    private void CSlider_Resize(object sender, EventArgs e)
    {
        drawGradation();
        this.Refresh();
    }


    //プロパティ
    private bool mouseDown = false;
    private void CSlider_MouseDown(object sender, MouseEventArgs e)
    {
        Value = (int)(((float)(e.X - 5) / (this.Width - 10)) * (Maximum - Minimum));
        if (Value <= Minimum) Value = Minimum;
        if (Value >= Maximum) Value = Maximum;

        if (ValueChanged != null) ValueChanged(this, new EventArgs());

        mouseDown = true;
    }

    private void CSlider_MouseMove(object sender, MouseEventArgs e)
    {
        if (mouseDown == true)
        {
            Value = (int)(((float)(e.X - 5) / (this.Width - 10)) * (Maximum - Minimum));
            if (Value <= Minimum) Value = Minimum;
            if (Value >= Maximum) Value = Maximum;

            if (ValueChanged != null) ValueChanged(this, new EventArgs());
        }
    }

    private void CSlider_MouseUp(object sender, MouseEventArgs e)
    {
        mouseDown = false;
    }


    private bool activeFlag = false;
    private void CSlider_MouseEnter(object sender, EventArgs e)
    {
        activeFlag = true;

        drawGradation();
        drawTick();
        this.Refresh();
    }

    private void CSlider_MouseLeave(object sender, EventArgs e)
    {
        activeFlag = false;

        drawGradation();
        drawTick();
        this.Refresh();
    }
}

0 件のコメント:

コメントを投稿