Пример #1
0
        public void Test_DecodeRune_Extension()
        {
            ustring     us    = "Hello, 世界";
            List <Rune> runes = new List <Rune>();
            int         tSize = 0;

            for (int i = 0; i < us.RuneCount; i++)
            {
                (Rune rune, int size) = Rune.DecodeRune(us.RuneSubstring(i, 1));
                runes.Add(rune);
                tSize += size;
            }
            ustring result = ustring.Make(runes);

            Assert.AreEqual("Hello, 世界", result);
            Assert.AreEqual(13, tSize);
        }
Пример #2
0
        public void Test_IsNonSpacingChar()
        {
            Rune l = '\u0370';

            Assert.False(Rune.IsNonSpacingChar(l, out _));
            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual(1, ustring.Make(l).ConsoleWidth);
            Rune ns = '\u302a';

            Assert.True(Rune.IsNonSpacingChar(ns, out _));
            Assert.AreEqual(2, Rune.ColumnWidth(ns));
            Assert.AreEqual(2, ustring.Make(ns).ConsoleWidth);
            l  = '\u006f';
            ns = '\u0302';
            var s = "\u006f\u0302";

            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual(0, Rune.ColumnWidth(ns));
            var ul = ustring.Make(l);

            Assert.AreEqual("o", ul);
            var uns = ustring.Make(ns);

            Assert.AreEqual("̂", uns);
            var f = ustring.Make($"{l}{ns}");

            Assert.AreEqual("ô", f);
            Assert.AreEqual(f, s);
            Assert.AreEqual(1, f.ConsoleWidth);
            Assert.AreEqual(1, s.Sum(c => Rune.ColumnWidth(c)));
            Assert.AreEqual(2, s.Length);
            (var rune, var size) = Rune.DecodeRune(f);
            Assert.AreEqual(rune, l);
            Assert.AreEqual(1, size);
            l  = '\u0041';
            ns = '\u0305';
            s  = "\u0041\u0305";
            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual(0, Rune.ColumnWidth(ns));
            ul = ustring.Make(l);
            Assert.AreEqual("A", ul);
            uns = ustring.Make(ns);
            Assert.AreEqual("̅", uns);
            f = ustring.Make($"{l}{ns}");
            Assert.AreEqual("A̅", f);
            Assert.AreEqual(f, s);
            Assert.AreEqual(1, f.ConsoleWidth);
            Assert.AreEqual(1, s.Sum(c => Rune.ColumnWidth(c)));
            Assert.AreEqual(2, s.Length);
            (rune, size) = Rune.DecodeRune(f);
            Assert.AreEqual(rune, l);
            Assert.AreEqual(1, size);
            l  = '\u0061';
            ns = '\u0308';
            s  = "\u0061\u0308";
            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual(0, Rune.ColumnWidth(ns));
            ul = ustring.Make(l);
            Assert.AreEqual("a", ul);
            uns = ustring.Make(ns);
            Assert.AreEqual("̈", uns);
            f = ustring.Make($"{l}{ns}");
            Assert.AreEqual("ä", f);
            Assert.AreEqual(f, s);
            Assert.AreEqual(1, f.ConsoleWidth);
            Assert.AreEqual(1, s.Sum(c => Rune.ColumnWidth(c)));
            Assert.AreEqual(2, s.Length);
            (rune, size) = Rune.DecodeRune(f);
            Assert.AreEqual(rune, l);
            Assert.AreEqual(1, size);
            l  = '\u4f00';
            ns = '\u302a';
            s  = "\u4f00\u302a";
            Assert.AreEqual(2, Rune.ColumnWidth(l));
            Assert.AreEqual(2, Rune.ColumnWidth(ns));
            ul = ustring.Make(l);
            Assert.AreEqual("伀", ul);
            uns = ustring.Make(ns);
            Assert.AreEqual("〪", uns);
            f = ustring.Make($"{l}{ns}");
            Assert.AreEqual("伀〪", f);             // Occupies 4 columns.
            Assert.AreEqual(f, s);
            Assert.AreEqual(4, f.ConsoleWidth);
            Assert.AreEqual(4, s.Sum(c => Rune.ColumnWidth(c)));
            Assert.AreEqual(2, s.Length);
            (rune, size) = Rune.DecodeRune(f);
            Assert.AreEqual(rune, l);
            Assert.AreEqual(3, size);
        }
Пример #3
0
        public void TestColumnWidth()
        {
            Rune   a = 'a';
            Rune   b = 'b';
            Rune   c = 123;
            Rune   d = '\u1150';        // 0x1150	ᅐ	Unicode Technical Report #11
            Rune   e = '\u1161';        // 0x1161	ᅡ	null character with column equal to 0
            Rune   f = 31;              // non printable character
            Rune   g = 127;             // non printable character
            string h = "\U0001fa01";
            string i = "\U000e0fe1";
            Rune   j = '\u20D0';
            Rune   k = '\u25a0';
            Rune   l = '\u25a1';
            Rune   m = '\uf61e';

            byte[] n = new byte[4] {
                0xf0, 0x9f, 0x8d, 0x95
            };                                       // UTF-8 Encoding
            Rune   o = new Rune('\ud83c', '\udf55'); // UTF-16 Encoding;
            string p = "\U0001F355";                 // UTF-32 Encoding
            Rune   q = '\u2103';
            Rune   r = '\u1100';
            Rune   s = '\u2501';

            Assert.AreEqual(1, Rune.ColumnWidth(a));
            Assert.AreEqual("a", a.ToString());
            Assert.AreEqual(1, a.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(a));
            Assert.AreEqual(1, Rune.ColumnWidth(b));
            Assert.AreEqual("b", b.ToString());
            Assert.AreEqual(1, b.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(b));
            var rl = a < b;

            Assert.IsTrue(rl);
            Assert.AreEqual(1, Rune.ColumnWidth(c));
            Assert.AreEqual("{", c.ToString());
            Assert.AreEqual(1, c.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(c));
            Assert.AreEqual(2, Rune.ColumnWidth(d));
            Assert.AreEqual("ᅐ", d.ToString());
            Assert.AreEqual(1, d.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(d));
            Assert.AreEqual(2, Rune.ColumnWidth(e));
            string join = "\u1104\u1161";

            Assert.AreEqual("따", join);
            Assert.AreEqual(4, join.Sum(x => Rune.ColumnWidth(x)));
            Assert.IsFalse(Rune.DecodeSurrogatePair(join, out _));
            Assert.AreEqual("ᅡ", e.ToString());
            Assert.AreEqual(1, e.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(e));
            Assert.AreEqual(-1, Rune.ColumnWidth(f));
            Assert.AreEqual(1, f.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(f));
            Assert.AreEqual(-1, Rune.ColumnWidth(g));
            Assert.AreEqual(1, g.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(g));
            var uh = ustring.Make(h);

            (var runeh, var sizeh) = Rune.DecodeRune(uh);
            Assert.AreEqual(2, Rune.ColumnWidth(runeh));
            Assert.AreEqual("🨁", h);
            Assert.AreEqual(2, runeh.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runeh));
            Assert.AreEqual(sizeh, Rune.RuneLen(runeh));
            for (int x = 0; x < uh.Length - 1; x++)
            {
                Assert.False(Rune.EncodeSurrogatePair(uh[x], uh[x + 1], out _));
            }
            Assert.IsTrue(Rune.ValidRune(runeh));
            Assert.True(Rune.Valid(uh.ToByteArray()));
            Assert.True(Rune.FullRune(uh.ToByteArray()));
            Assert.AreEqual(1, Rune.RuneCount(uh));
            (var runelh, var sizelh) = Rune.DecodeLastRune(uh);

            Assert.AreEqual(2, Rune.ColumnWidth(runelh));
            Assert.AreEqual(2, runelh.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runelh));
            Assert.AreEqual(sizelh, Rune.RuneLen(runelh));
            Assert.IsTrue(Rune.ValidRune(runelh));

            var ui = ustring.Make(i);

            (var runei, var sizei) = Rune.DecodeRune(ui);
            Assert.AreEqual(1, Rune.ColumnWidth(runei));
            Assert.AreEqual("󠿡", i);
            Assert.AreEqual(2, runei.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runei));
            Assert.AreEqual(sizei, Rune.RuneLen(runei));
            for (int x = 0; x < ui.Length - 1; x++)
            {
                Assert.False(Rune.EncodeSurrogatePair(ui[x], ui[x + 1], out _));
            }
            Assert.IsTrue(Rune.ValidRune(runei));
            Assert.True(Rune.Valid(ui.ToByteArray()));
            Assert.True(Rune.FullRune(ui.ToByteArray()));
            (var runeli, var sizeli) = Rune.DecodeLastRune(ui);
            Assert.AreEqual(1, Rune.ColumnWidth(runeli));
            Assert.AreEqual(2, runeli.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runeli));
            Assert.AreEqual(sizeli, Rune.RuneLen(runeli));
            Assert.IsTrue(Rune.ValidRune(runeli));

            Assert.AreNotEqual(Rune.ColumnWidth(runeh), Rune.ColumnWidth(runei));
            Assert.AreNotEqual(h, i);
            Assert.AreEqual(runeh.ToString().Length, runei.ToString().Length);
            Assert.AreEqual(Rune.RuneLen(runeh), Rune.RuneLen(runei));
            Assert.AreEqual(Rune.RuneLen(runeh), Rune.RuneLen(runei));
            var uj = ustring.Make(j);

            (var runej, var sizej) = Rune.DecodeRune(uj);
            Assert.AreEqual(0, Rune.ColumnWidth(j));
            Assert.AreEqual(0, Rune.ColumnWidth(uj.RuneAt(0)));
            Assert.AreEqual(j, uj.RuneAt(0));
            Assert.AreEqual("⃐", j.ToString());
            Assert.AreEqual("⃐", uj.ToString());
            Assert.AreEqual(1, j.ToString().Length);
            Assert.AreEqual(1, runej.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(j));
            Assert.AreEqual(sizej, Rune.RuneLen(runej));
            Assert.AreEqual(1, Rune.ColumnWidth(k));
            Assert.AreEqual("■", k.ToString());
            Assert.AreEqual(1, k.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(k));
            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual("□", l.ToString());
            Assert.AreEqual(1, l.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(l));
            Assert.AreEqual(1, Rune.ColumnWidth(m));
            Assert.AreEqual("", m.ToString());
            Assert.AreEqual(1, m.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(m));
            var rn = Rune.DecodeRune(ustring.Make(n)).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(rn));
            Assert.AreEqual("🍕", rn.ToString());
            Assert.AreEqual(2, rn.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(rn));
            Assert.AreEqual(1, Rune.ColumnWidth(o));
            Assert.AreEqual("🍕", o.ToString());
            Assert.AreEqual(2, o.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(o));
            var rp = Rune.DecodeRune(ustring.Make(p)).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(rp));
            Assert.AreEqual("🍕", p);
            Assert.AreEqual(2, p.Length);
            Assert.AreEqual(4, Rune.RuneLen(rp));
            Assert.AreEqual(1, Rune.ColumnWidth(q));
            Assert.AreEqual("℃", q.ToString());
            Assert.AreEqual(1, q.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(q));
            var rq = Rune.DecodeRune(ustring.Make(q)).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(rq));
            Assert.AreEqual("℃", rq.ToString());
            Assert.AreEqual(1, rq.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(rq));
            Assert.AreEqual(2, Rune.ColumnWidth(r));
            Assert.AreEqual("ᄀ", r.ToString());
            Assert.AreEqual(1, r.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(r));
            Assert.AreEqual(1, Rune.ColumnWidth(s));
            Assert.AreEqual("━", s.ToString());
            Assert.AreEqual(1, s.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(s));
            var buff = new byte[4];
            var sb   = Rune.EncodeRune('\u2503', buff);

            Assert.AreEqual(1, Rune.ColumnWidth('\u2503'));
            (var rune, var size) = Rune.DecodeRune(ustring.Make('\u2503'));
            Assert.AreEqual(sb, size);
            Assert.AreEqual('\u2503', (uint)rune);
            var scb = char.ConvertToUtf32("℃", 0);
            var scr = '℃'.ToString().Length;

            Assert.AreEqual(scr, Rune.ColumnWidth((uint)scb));
            buff = new byte[4];
            sb   = Rune.EncodeRune('\u1100', buff);
            Assert.AreEqual(2, Rune.ColumnWidth('\u1100'));
            Assert.AreEqual(2, ustring.Make('\u1100').ConsoleWidth);
            Assert.AreEqual(1, '\u1100'.ToString().Length);             // Length as string returns 1 but in reality it occupies 2 columns.
            (rune, size) = Rune.DecodeRune(ustring.Make('\u1100'));
            Assert.AreEqual(sb, size);
            Assert.AreEqual('\u1100', (uint)rune);
            string str = "\u2615";

            Assert.AreEqual("☕", str);
            Assert.AreEqual(1, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(1, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));
            Assert.AreEqual(1, str.Length);
            str = "\u2615\ufe0f";             // Identical but \ufe0f forces it to be rendered as a colorful image as compared to a monochrome text variant.
            Assert.AreEqual("☕️", str);
            Assert.AreEqual(1, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(1, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(2, Rune.RuneCount(str));
            Assert.AreEqual(2, str.Length);
            str = "\u231a";
            Assert.AreEqual("⌚", str);
            Assert.AreEqual(2, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(2, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));
            Assert.AreEqual(1, str.Length);
            str = "\u231b";
            Assert.AreEqual("⌛", str);
            Assert.AreEqual(2, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(2, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));
            Assert.AreEqual(1, str.Length);
            str = "\u231c";
            Assert.AreEqual("⌜", str);
            Assert.AreEqual(1, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(1, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));
            Assert.AreEqual(1, str.Length);
            str = "\u1dc0";
            Assert.AreEqual("᷀", str);
            Assert.AreEqual(0, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(0, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));
            Assert.AreEqual(1, str.Length);
            str = "\ud83e\udd16";
            Assert.AreEqual("🤖", str);
            Assert.AreEqual(2, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(2, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));    // Here returns 1 because is a valid surrogate pair resulting in only rune >=U+10000..U+10FFFF
            Assert.AreEqual(2, str.Length);             // String always preserves the originals values of each surrogate pair
            str = "\U0001f9e0";
            Assert.AreEqual("🧠", str);
            Assert.AreEqual(2, str.Sum(x => Rune.ColumnWidth(x)));
            Assert.AreEqual(2, ((ustring)str).ConsoleWidth);
            Assert.AreEqual(1, Rune.RuneCount(str));
            Assert.AreEqual(2, str.Length);
        }
Пример #4
0
        public void TestRune()
        {
            Rune a = new Rune('a');

            Assert.AreEqual(1, Rune.ColumnWidth(a));
            Assert.AreEqual(1, a.ToString().Length);
            Assert.AreEqual("a", a.ToString());
            Rune b = new Rune(0x0061);

            Assert.AreEqual(1, Rune.ColumnWidth(b));
            Assert.AreEqual(1, b.ToString().Length);
            Assert.AreEqual("a", b.ToString());
            Rune c = new Rune('\u0061');

            Assert.AreEqual(1, Rune.ColumnWidth(c));
            Assert.AreEqual(1, c.ToString().Length);
            Assert.AreEqual("a", c.ToString());
            Rune d = new Rune(0x10421);

            Assert.AreEqual(1, Rune.ColumnWidth(d));
            Assert.AreEqual(2, d.ToString().Length);
            Assert.AreEqual("𐐡", d.ToString());
            Assert.False(Rune.EncodeSurrogatePair('\ud799', '\udc21', out _));
            Assert.Throws <ArgumentOutOfRangeException>(() => new Rune('\ud799', '\udc21'));
            Rune e = new Rune('\ud801', '\udc21');

            Assert.AreEqual(1, Rune.ColumnWidth(e));
            Assert.AreEqual(2, e.ToString().Length);
            Assert.AreEqual("𐐡", e.ToString());
            Assert.False(new Rune('\ud801').IsValid);
            Rune f = new Rune('\ud83c', '\udf39');

            Assert.AreEqual(1, Rune.ColumnWidth(f));
            Assert.AreEqual(2, f.ToString().Length);
            Assert.AreEqual("🌹", f.ToString());
            Assert.DoesNotThrow(() => new Rune(0x10ffff));
            Rune   g = new Rune(0x10ffff);
            string s = "\U0010ffff";

            Assert.AreEqual(1, Rune.ColumnWidth(g));
            Assert.AreEqual(1, ustring.Make(s).ConsoleWidth);
            Assert.AreEqual(2, g.ToString().Length);
            Assert.AreEqual(2, s.Length);
            Assert.AreEqual("􏿿", g.ToString());
            Assert.AreEqual("􏿿", s);
            Assert.AreEqual(g.ToString(), s);
            Assert.Throws <ArgumentOutOfRangeException>(() => new Rune(0x12345678));
            var h = new Rune('\u1150');

            Assert.AreEqual(2, Rune.ColumnWidth(h));
            Assert.AreEqual(1, h.ToString().Length);
            Assert.AreEqual("ᅐ", h.ToString());
            var i = new Rune('\u4F60');

            Assert.AreEqual(2, Rune.ColumnWidth(i));
            Assert.AreEqual(1, i.ToString().Length);
            Assert.AreEqual("你", i.ToString());
            var j = new Rune('\u597D');

            Assert.AreEqual(2, Rune.ColumnWidth(j));
            Assert.AreEqual(1, j.ToString().Length);
            Assert.AreEqual("好", j.ToString());
            var k = new Rune('\ud83d', '\udc02');

            Assert.AreEqual(1, Rune.ColumnWidth(k));
            Assert.AreEqual(2, k.ToString().Length);
            Assert.AreEqual("🐂", k.ToString());
            var l = new Rune('\ud801', '\udcbb');

            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual(2, l.ToString().Length);
            Assert.AreEqual("𐒻", l.ToString());
            var m = new Rune('\ud801', '\udccf');

            Assert.AreEqual(1, Rune.ColumnWidth(m));
            Assert.AreEqual(2, m.ToString().Length);
            Assert.AreEqual("𐓏", m.ToString());
            var n = new Rune('\u00e1');

            Assert.AreEqual(1, Rune.ColumnWidth(n));
            Assert.AreEqual(1, n.ToString().Length);
            Assert.AreEqual("á", n.ToString());
            var o = new Rune('\ud83d', '\udd2e');

            Assert.AreEqual(1, Rune.ColumnWidth(o));
            Assert.AreEqual(2, o.ToString().Length);
            Assert.AreEqual("🔮", o.ToString());
            var p = new Rune('\u2329');

            Assert.AreEqual(1, Rune.ColumnWidth(p));
            Assert.AreEqual(1, p.ToString().Length);
            Assert.AreEqual("〈", p.ToString());
            var q = new Rune('\u232a');

            Assert.AreEqual(1, Rune.ColumnWidth(q));
            Assert.AreEqual(1, q.ToString().Length);
            Assert.AreEqual("〉", q.ToString());
            var r = Rune.DecodeRune(ustring.Make("\U0000232a")).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(r));
            Assert.AreEqual(1, r.ToString().Length);
            Assert.AreEqual("〉", r.ToString());

            PrintTextElementCount(ustring.Make('\u00e1'), "á", 1, 1, 1, 1);
            PrintTextElementCount(ustring.Make('\u0061', '\u0301'), "á", 1, 2, 2, 1);
            PrintTextElementCount(ustring.Make('\u0065', '\u0301'), "é", 1, 2, 2, 1);
            PrintTextElementCount(ustring.Make(new Rune[] { new Rune(0x1f469), new Rune(0x1f3fd), new Rune('\u200d'), new Rune(0x1f692) }),
                                  "👩🏽‍🚒", 3, 7, 7, 4);
            PrintTextElementCount(ustring.Make(new Rune[] { new Rune(0x1f469), new Rune(0x1f3fd), new Rune('\u200d'), new Rune(0x1f692) }),
                                  "\U0001f469\U0001f3fd\u200d\U0001f692", 3, 7, 7, 4);
            PrintTextElementCount(ustring.Make(new Rune('\ud801', '\udccf')),
                                  "\ud801\udccf", 1, 2, 2, 1);
        }
Пример #5
0
        public void TestColumnWidth()
        {
            Assert.AreEqual(1, Rune.ColumnWidth(a));
            Assert.AreEqual("a", a.ToString());
            Assert.AreEqual(1, a.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(a));
            Assert.AreEqual(1, Rune.ColumnWidth(b));
            Assert.AreEqual("b", b.ToString());
            Assert.AreEqual(1, b.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(b));
            var rl = a < b;

            Assert.IsTrue(rl);
            Assert.AreEqual(1, Rune.ColumnWidth(c));
            Assert.AreEqual("{", c.ToString());
            Assert.AreEqual(1, c.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(c));
            Assert.AreEqual(2, Rune.ColumnWidth(d));
            Assert.AreEqual("ᅐ", d.ToString());
            Assert.AreEqual(1, d.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(d));
            Assert.AreEqual(0, Rune.ColumnWidth(e));
            Assert.AreEqual("ᅡ", e.ToString());
            Assert.AreEqual(1, e.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(e));
            Assert.AreEqual(-1, Rune.ColumnWidth(f));
            Assert.AreEqual(1, f.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(f));
            Assert.AreEqual(-1, Rune.ColumnWidth(g));
            Assert.AreEqual(1, g.ToString().Length);
            Assert.AreEqual(1, Rune.RuneLen(g));
            var uh = ustring.Make(h);

            (var runeh, var sizeh) = Rune.DecodeRune(uh);
            Assert.AreEqual(2, Rune.ColumnWidth(runeh));
            Assert.AreEqual("🨁", h);
            Assert.AreEqual(2, runeh.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runeh));
            Assert.AreEqual(sizeh, Rune.RuneLen(runeh));
            for (int i = 0; i < uh.Length - 1; i++)
            {
                Assert.False(Rune.DecodeSurrogatePair(uh[i], uh[i + 1]) > 0);
            }
            Assert.IsTrue(Rune.ValidRune(runeh));
            Assert.True(Rune.Valid(uh.ToByteArray()));
            Assert.True(Rune.FullRune(uh.ToByteArray()));
            Assert.AreEqual(1, Rune.RuneCount(uh));
            (var runelh, var sizelh) = Rune.DecodeLastRune(uh);

            Assert.AreEqual(2, Rune.ColumnWidth(runelh));
            Assert.AreEqual(2, runelh.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runelh));
            Assert.AreEqual(sizelh, Rune.RuneLen(runelh));
            Assert.IsTrue(Rune.ValidRune(runelh));

            var ui = ustring.Make(i);

            (var runei, var sizei) = Rune.DecodeRune(ui);
            Assert.AreEqual(1, Rune.ColumnWidth(runei));
            Assert.AreEqual("󠿡", i);
            Assert.AreEqual(2, runei.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runei));
            Assert.AreEqual(sizei, Rune.RuneLen(runei));
            for (int i = 0; i < ui.Length - 1; i++)
            {
                Assert.False(Rune.DecodeSurrogatePair(ui[i], ui[i + 1]) > 0);
            }
            Assert.IsTrue(Rune.ValidRune(runei));
            Assert.True(Rune.Valid(ui.ToByteArray()));
            Assert.True(Rune.FullRune(ui.ToByteArray()));
            (var runeli, var sizeli) = Rune.DecodeLastRune(ui);
            Assert.AreEqual(1, Rune.ColumnWidth(runeli));
            Assert.AreEqual(2, runeli.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(runeli));
            Assert.AreEqual(sizeli, Rune.RuneLen(runeli));
            Assert.IsTrue(Rune.ValidRune(runeli));

            Assert.AreNotEqual(Rune.ColumnWidth(runeh), Rune.ColumnWidth(runei));
            Assert.AreNotEqual(h, i);
            Assert.AreEqual(runeh.ToString().Length, runei.ToString().Length);
            Assert.AreEqual(Rune.RuneLen(runeh), Rune.RuneLen(runei));
            Assert.AreEqual(Rune.RuneLen(runeh), Rune.RuneLen(runei));
            var uj = ustring.Make(j);

            (var runej, var sizej) = Rune.DecodeRune(uj);
            Assert.AreEqual(0, Rune.ColumnWidth(j));
            Assert.AreEqual(0, Rune.ColumnWidth(uj.RuneAt(0)));
            Assert.AreEqual(j, uj.RuneAt(0));
            Assert.AreEqual("⃐", j.ToString());
            Assert.AreEqual("⃐", uj.ToString());
            Assert.AreEqual(1, j.ToString().Length);
            Assert.AreEqual(1, runej.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(j));
            Assert.AreEqual(sizej, Rune.RuneLen(runej));
            Assert.AreEqual(1, Rune.ColumnWidth(k));
            Assert.AreEqual("■", k.ToString());
            Assert.AreEqual(1, k.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(k));
            Assert.AreEqual(1, Rune.ColumnWidth(l));
            Assert.AreEqual("□", l.ToString());
            Assert.AreEqual(1, l.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(l));
            Assert.AreEqual(1, Rune.ColumnWidth(m));
            Assert.AreEqual("", m.ToString());
            Assert.AreEqual(1, m.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(m));
            var rn = Rune.DecodeRune(ustring.Make(n)).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(rn));
            Assert.AreEqual("🍕", rn.ToString());
            Assert.AreEqual(2, rn.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(rn));
            Assert.AreEqual(1, Rune.ColumnWidth(o));
            Assert.AreEqual("🍕", o.ToString());
            Assert.AreEqual(2, o.ToString().Length);
            Assert.AreEqual(4, Rune.RuneLen(o));
            var rp = Rune.DecodeRune(ustring.Make(p)).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(rp));
            Assert.AreEqual("🍕", p);
            Assert.AreEqual(2, p.Length);
            Assert.AreEqual(4, Rune.RuneLen(rp));
            Assert.AreEqual(1, Rune.ColumnWidth(q));
            Assert.AreEqual("℃", q.ToString());
            Assert.AreEqual(1, q.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(q));
            var rq = Rune.DecodeRune(ustring.Make(q)).rune;

            Assert.AreEqual(1, Rune.ColumnWidth(rq));
            Assert.AreEqual("℃", rq.ToString());
            Assert.AreEqual(1, rq.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(rq));
            Assert.AreEqual(2, Rune.ColumnWidth(r));
            Assert.AreEqual("ᄀ", r.ToString());
            Assert.AreEqual(1, r.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(r));
            Assert.AreEqual(1, Rune.ColumnWidth(s));
            Assert.AreEqual("━", s.ToString());
            Assert.AreEqual(1, s.ToString().Length);
            Assert.AreEqual(3, Rune.RuneLen(s));
            var buff = new byte[4];
            var sb   = Rune.EncodeRune('\u2503', buff);
            var scb  = char.ConvertToUtf32("℃", 0);
            var scr  = '℃'.ToString().Length;
        }