Как заставить RightToLeftLayout работать для элементов управления внутри групповых ящиков и панелей? - PullRequest
5 голосов
/ 29 сентября 2008

По MSDN

form.RightToLeftLayout = True;
form.RightToLeft = ifWeWantRTL() ? RightToLeft.True : RightToLeft.False;

достаточно для зеркального отображения содержимого формы для языков RTL.

Но размещение элементов управления отражается только для элементов управления непосредственно в форме,
те, что находятся внутри GroupBox или Panel , не отражаются , если только я не поместил их в TableLayoutPanel или в FlowLayoutPanel.

Это большая ручная работа по размещению TableLayoutPanel внутри каждого GroupBox, и особенно для перестановки элементов управления (один элемент управления на ячейку таблицы, отступы, поля и т. д.)

Есть ли более простой способ заставить зеркалирование работать для всех элементов управления?

Или, по крайней мере, как я могу обойти шаг переупорядочения, поскольку это довольно сложная задача с нашим количеством форм?


Редактировать : свойство RightToLeft для каждого элемента управления в форме по умолчанию наследуется,
поэтому панели и групповые ящики всегда имеют необходимую настройку RightToLeft.
Тем не менее, я попытался переназначить его для них как программно, так и от дизайнера, это не помогло.

Ответы [ 4 ]

8 голосов
/ 29 сентября 2008

Видно, что у вас на руках довольно неприятная проблема. Поиграл с ним некоторое время и придумал следующее:

Используя небольшую рекурсию, вы можете запустить все элементы управления и выполнить RTL-преобразование для тех элементов управления, которые захвачены в панелях и групповых окнах.

Это быстрый небольшой макет кода, который я собрал вместе. Я бы посоветовал вам поместить это в BaseForm (он надеется, что он у вас есть) и вызвать загрузку базовой формы.

private void SetRTL (bool setRTL)
{
    ApplyRTL(setRTL, this);
}

private void ApplyRTL(bool yes, Control startControl)
{
    if ((startControl is Panel ) || (startControl is GroupBox))
    {
        foreach (Control control in startControl.Controls)
        {
            control.Location = CalculateRTL(control.Location, startControl.Size, control.Size);
        }
    }

    foreach (Control control in startControl.Controls)
        ApplyRTL(yes, control);
}

private Point CalculateRTL (Point currentPoint, Size parentSize, Size currentSize)
{
    return new Point(parentSize.Width - currentSize.Width - currentPoint.X, currentPoint.Y);
}
3 голосов
/ 26 мая 2011

Я не помню, где я впервые увидел этот совет по переопределению CreateParams, но вот вы здесь;) Самый быстрый и простой способ - наследовать от Panel, GroupBox или Usercontrol и переопределить свойство CreateParams

    protected override CreateParams CreateParams
    {
        get
        {
            return Control_RTF(base.CreateParams, base.RightToLeft);
        }
    }

    private CreateParams Control_RTF(CreateParams CP, RightToLeft rightToLeft)
    {
        if (rightToLeft == System.Windows.Forms.RightToLeft.Yes)
            CP.ExStyle = ((CP.ExStyle | 0x400000) | 0x100000);
        return CP;
    }
1 голос
/ 29 сентября 2008

Согласно статье Visual Studio 2005: разработка приложений для Windows Forms на арабском языке У меня осталось только две альтернативы

  • продолжить добавление TableLayoutPanels здесь и там
  • Переместите дочерние элементы управления на RTL, измените себя

Очень жаль, что так должно быть.

0 голосов
/ 03 мая 2013

Если у вас есть класс, производный от Control, который содержит дочерние элементы управления (например, ContainerControl), вы можете добавить следующий код, чтобы заставить все дочерние элементы управления отображаться, когда для родительской формы RightToLeftLayout установлено значение true и когда ваш RightToLeft элемента управления установлен на RightToLeft.Yes.

protected override CreateParams CreateParams
{
    get
    {
        CreateParams createParams = base.CreateParams;
        Form parent = this.FindForm();
        bool parentRightToLeftLayout = parent != null ? parent.RightToLeftLayout : false;
        if ((this.RightToLeft == RightToLeft.Yes) && parentRightToLeftLayout)
        {
            createParams.ExStyle |= 0x500000; // WS_EX_LAYOUTRTL | WS_EX_NOINHERITLAYOUT
            createParams.ExStyle &= ~0x7000; // WS_EX_RIGHT | WS_EX_RTLREADING | WS_EX_LEFTSCROLLBAR
        }
        return createParams;
    }
}

protected override void OnRightToLeftChanged(EventArgs e)
{
    base.OnRightToLeftChanged(e);
    RecreateHandle();
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...