protected override FlowLayoutPanel GenerateControl(string nesting, PropertyInfo pi, object config, ConfigEditorMetadata metadata)
            {
                if (pi.PropertyType != typeof(int))
                {
                    throw new Exception();
                }
                var baseline   = (int)pi.GetValue(config);
                var nestedName = $"{nesting}/{pi.Name}";

                metadata.BaselineValues[nestedName] = baseline;
                var tag = new ConfigPropEditorUITag(metadata, this);

                return(new FlowLayoutPanel {
                    AutoSize = true,
                    Controls =
                    {
                        new Label {
                            Anchor = AnchorStyles.None, AutoSize = true, Text = GetPropertyNameDesc(pi)
                        },
                        new NumericUpDown
                        {
                            Maximum = int.MaxValue,
                            Minimum = int.MinValue,
                            Size = new Size(72, 20),
                            Value = baseline
                        }.Also(it =>
                        {
                            if (pi.GetCustomAttributes(typeof(RangeAttribute), false).FirstOrDefault() is RangeAttribute range)
                            {
                                it.Maximum = (int)range.Maximum;
                                it.Minimum = (int)range.Minimum;
                            }
                            it.ValueChanged += ControlEventHandler;
                        })
                    },
            protected override CheckBox GenerateControl(string nesting, PropertyInfo pi, object config, ConfigEditorMetadata metadata)
            {
                if (pi.PropertyType != typeof(bool))
                {
                    throw new Exception();
                }
                var baseline   = (bool)pi.GetValue(config);
                var nestedName = $"{nesting}/{pi.Name}";

                metadata.BaselineValues[nestedName] = baseline;
                var tag = new ConfigPropEditorUITag(metadata, this);

                return(new CheckBox
                {
                    AutoSize = true,
                    Checked = baseline,
                    ForeColor = GetUnchangedComparisonColor(nestedName, in baseline, tag),
                    Name = nestedName,
                    Tag = tag,
                    Text = GetPropertyNameDesc(pi)
                }.Also(it => it.CheckedChanged += ControlEventHandler));
 /// <inheritdoc cref="ConfigPropEditorUIGen.MatchesBaseline"/>
 protected override bool MatchesBaseline(TListed c, ConfigEditorMetadata metadata)
 => metadata.BaselineValues[c.Name] is TValue v
 /// <inheritdoc cref="ConfigPropEditorUIGen.MatchesBaseline"/>
 protected override bool MatchesBaseline(TListed c, ConfigEditorMetadata metadata)
 => metadata.BaselineValues[c.Name] is TValue v?TValueEquality(GetTValue(c), v) : throw new Exception();
 bool IConfigPropEditorUIGen.MatchesBaseline(Control c, ConfigEditorMetadata metadata) => MatchesBaseline((TListed)c, metadata);
 /// <remarks>
 /// Default implementation didn't play nice with <see langword="null"/>, so multiple behaviours are available for custom generators:
 /// inherit from <see cref="ConfigPropEditorUIGenRefT"/> or <see cref="ConfigPropEditorUIGenValT"/> instead.
 /// </remarks>
 protected abstract bool MatchesBaseline(TListed c, ConfigEditorMetadata metadata);
 Control IConfigPropEditorUIGen.GenerateControl(string nesting, PropertyInfo pi, object config, ConfigEditorMetadata metadata) => GenerateControl(nesting, pi, config, metadata);
 /// <inheritdoc cref="IConfigPropEditorUIGen.GenerateControl"/>
 protected abstract TListed GenerateControl(string nesting, PropertyInfo pi, object config, ConfigEditorMetadata metadata);
 public ConfigPropEditorUITag(ConfigEditorMetadata metadata, IConfigPropEditorUIGen generator)
 {
     Metadata  = metadata;
     Generator = generator;
 }