3. RGB 與HSI 色彩空間互換

namespace Q3
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            foreach (var item in new List<TextBox>()
            {
                r,
                g,
                b
            })
            {
                item.TextChanged += rgb2hsi;
            };

            foreach (var item in new List<TextBox>()
            {
                h,
                s,
                i
            })
            {
                item.TextChanged += hsi2rgb;
            };
        }

        private void tc(object sender, EventArgs e)
        {

        }

        private void rgb2hsi(object sender, EventArgs e)
        {
            if (ignore || r.Text == "" || g.Text == "" || b.Text == "") return;
            double vr = int.Parse(r.Text);
            double vg = int.Parse(g.Text);
            double vb = int.Parse(b.Text);
            var sum = vr + vg + vb;
         
            if (sum == 255 * 3)
            {
                ignore = true;
                h.Text = "0";
                s.Text = "0";
                i.Text = "255";
                ignore = false;
                return;
            }


            if (sum == 0)
            {
                ignore = true;
                h.Text = "0";
                s.Text = "0";
                i.Text = "0";
                ignore = false;
                return;
            }
            vr /= sum;
            vg /= sum;
            vb /= sum;

            double vh, vs, vi;

            vh = Math.Acos(0.5 * ((vr - vg) + (vr - vb)) / Math.Pow(
                ((vr - vg) * (vr - vg) + (vr - vb) * (vg - vb))
                , 0.5));
            if (vb > vg)
            {
                vh = 2 * Math.PI - vh;
            }

            vs = 1 - 3 * Math.Min(Math.Min(vr, vg), vb);
            vi = sum / (3 * 255);

            ignore = true;
            h.Text = ((int)Math.Round(vh * 180 / Math.PI)).ToString();
            s.Text = ((int)Math.Round(vs * 255)).ToString();
            i.Text = ((int)Math.Round(vi * 255)).ToString();
            ignore = false;
        }

        bool ignore = false;

        private void hsi2rgb(object sender, EventArgs e)
        {
            if (ignore) return;
            if (h.Text == "" || s.Text == "" || i.Text == "") return;
            var H = int.Parse(h.Text) * Math.PI / 180;
            var vs = int.Parse(s.Text) / 255.0;
            var vi = int.Parse(i.Text) / 255.0;
            double vh = -1;

            vh = H;
            if (2 * Math.PI / 3 <= H && H < 4 * Math.PI / 3)
            {
                vh = H - 2 * Math.PI / 3;
            }
            else if (4 * Math.PI / 3 <= H && H < 2 * Math.PI)
            {
                vh = H - 4 * Math.PI / 3;
            }

            var x = vi * (1 - vs);
            var y = vi * (1 + vs * Math.Cos(vh) / Math.Cos(Math.PI / 3 - vh));
            var z = 3 * vi - (x + y);

            double vr = 0, vg = 0, vb = 0;
            if (H < Math.PI * 2 / 3)
            {
                vb = x;
                vr = y;
                vg = z;
            }
            if (2 * Math.PI / 3 <= H && H < 4 * Math.PI / 3)
            {
                vr = x;
                vg = y;
                vb = z;
            }
            if (4 * Math.PI / 3 <= H && H < 2 * Math.PI)
            {
                vg = x;
                vb = y;
                vr = z;
            }

            ignore = true;
            r.Text = ((int)Math.Round(vr * 255)).ToString();
            g.Text = ((int)Math.Round(vg * 255)).ToString();
            b.Text = ((int)Math.Round(vb * 255)).ToString();
            ignore = false;
        }
    }
}

Last updated