Почему событие рисования моего пользовательского элемента управления не заполняет мой прямоугольник только на одном элементе управления? - PullRequest
0 голосов
/ 23 июня 2018

Я не могу понять, что я делаю неправильно. Для одного из двух элементов управления, которые я создаю (первый), это работает. Но для второго это не так? Я пробовал много вещей, чтобы исправить это, но я не подошел к решению каких-либо идей?

Что происходит

Код, где они созданы:

    public MessageLogView()
    {
        MessageBubble bubble = new MessageBubble("Hey there Steve I love you", DateTime.Today, Color.FromArgb(255,255,255), new Padding(10, 10, 10, 10));

        bubble.Location = new Point(5, 5);

        this.Controls.Add(bubble);

        MessageBubble bubble2 = new MessageBubble("K, good for you", DateTime.Today, Color.FromArgb(220, 248, 198), new Padding(10, 10, 10, 10));

        bubble2.Location = new Point(5, 5 + bubble.BubbleHeight + 5);

        this.Controls.Add(bubble2);

    }

Пользовательский контроль:

 public partial class MessageBubble : UserControl
{
    private string Text;
    private DateTime Date;
    private Color BubbleColor = Color.FromArgb(220, 248, 198);
    private Size stringSize, datestringSize;
    public Font textFont { get; set; } = new Font("Arial", 12, FontStyle.Regular);
    public Font dateFont { get; set; } = new Font("Arial", 9, FontStyle.Bold);
    public Color textColor { get; set; } = Color.Black;
    public Color dateColor { get; set; } = Color.FromArgb(180, 208, 158);
    public int cornerRadius { get; set; } = 5;

    public int BubbleHeight { get
        {
            return this.Padding.Top + this.Padding.Bottom + stringSize.Height + 5 + datestringSize.Height;
        }
    }
    public int BubbleWidth
    {
        get
        {
            return this.Padding.Left + this.Padding.Right + stringSize.Width;
        }
    }

    public MessageBubble(string text, DateTime date, Color color, Padding padding)
    {
        InitializeComponent();
        Text = text;
        this.BubbleColor = color;
        Date = date;
        stringSize = this.CreateGraphics().MeasureString(Text, this.textFont).ToSize();
        datestringSize = this.CreateGraphics().MeasureString(Date.ToString("hh:mm tt"), this.dateFont).ToSize();
        this.Padding = padding;
        this.Width = this.BubbleWidth;
        this.Height = this.BubbleHeight;
    }

    protected override void OnPaint(PaintEventArgs e)
    {
        e.Graphics.FillRectangle(new SolidBrush(this.BubbleColor), Bounds);
        e.Graphics.DrawString(this.Text, this.textFont, new SolidBrush(this.textColor), new Point(this.Padding.Left,this.Padding.Top));
        e.Graphics.DrawString(this.Date.ToString("hh:mm tt"), this.dateFont, new SolidBrush(this.dateColor), new Point(this.Width - datestringSize.Width - Padding.Right, this.Padding.Top + stringSize.Height + 5));
        Console.WriteLine($"Drawn: {this.Text} - {this.Bounds.X}, {this.Bounds.Y} - {this.BubbleWidth}, {this.BubbleHeight}/{this.Bounds.Width}, {this.Bounds.Height} - {this.BubbleColor.ToString() }");
    }
}

Ответы [ 2 ]

0 голосов
/ 23 июня 2018

Странное поведение из-за использования Bounds вместо ClientRectangle. Они разные:

  • Bounds: размер и расположение элемента управления относительно родительского элемента управления .
  • ClientRectangle: прямоугольник, представляющий клиентскую область элемента управления.

Используйте ClientRectangle при заполнении прямоугольника.

Когда вы помещаете элемент управления с размером (100, 100) в точку (10,10) на родительском элементе, прямоугольник клиента будет (0, 0, 100, 100), а Bounds будет (10, 10, 100, 100).

Примечание: Вам необходимо утилизировать объекты GDI +, в противном случае вы скоро столкнетесь с утечкой GDI . Создайте и используйте их в использовании:

using (var brush = new SolidBrush(this.BubbleColor))
    e.Graphics.FillRectangle(brush, ClientRectangle);
0 голосов
/ 23 июня 2018

Вы можете установить Usercontrol BackColor на BubbleColor в конструкторе.

BubbleColor = color;

Теперь это выглядит так, как ожидалось:

enter image description here

Но фактическая ошибка происходит из свойства Bounds. Это прямоугольник, в котором содержится элемент управления, и его местоположение - это расположение элементов управления , поэтому, в зависимости от чисел, вы рисуете в основном за пределами пузыря.

Вместо этого вы можете использовать:

Rectangle rect = new Rectangle(Point.Empty, Bounds.Size);

Но наиболее естественным решением является использование правильного свойства , которое равно ClientRectangle ..

И, как говорится в перекрестном сообщении Резы: Обязательно распоряжайтесь ресурсами GDI +, а именно Кистями.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...