Как вы можете остановить прокрутку панели Winforms? - PullRequest
21 голосов
/ 07 января 2009

Если вы поместите DataGridView высотой 400 пикселей на панель высотой 300 пикселей, чтобы на панели была полоса прокрутки, затем прокрутите вниз, чтобы отобразить нижнюю половину сетки, затем щелкните элемент управления. за пределами панели, затем щелкните линию в сетке, панель прокручивается вверх и выбирается неправильная строка в сетке.

Это не просто DataGridView; это происходит с любым элементом управления, который выше панели, например Infragistics UltraWinGrid, Rich Text Box. Я поднял это как ошибку в Infragistics, но они говорят, что это проблема Microsoft.

Я пытался использовать все соответствующие события для элементов управления, но прокрутка панели происходит до того, как сработают события.

Есть предложения?

Ответы [ 4 ]

44 голосов
/ 27 мая 2009

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

Способ остановить это поведение - переопределить обработчик события ScrollToControl, например:

class PanelNoScrollOnFocus : Panel
{
    protected override System.Drawing.Point ScrollToControl(Control activeControl)
    {
        return DisplayRectangle.Location;
    }
}

Замените панель управления этой панелью управления. Готово.

2 голосов
/ 07 января 2009

Я предполагаю, что вы устанавливаете для свойства AutoScroll панели значение true. При этом переключение приложений сбрасывает позицию прокрутки в ноль, а панель сбрасывает свою позицию.

Если вы отключите автопрокрутку и добавите собственную полосу прокрутки, вы можете установить максимум и минимум полосы прокрутки в соответствии с требованиями для панели, а затем установить значения прокрутки панели в событии прокрутки полосы прокрутки. Это не сбрасывается при переключении окон.

Что-то вроде:

private void vScrollBar1_Scroll(object sender, ScrollEventArgs e)
{
    panel1.VerticalScroll.Value = vScrollBar1.Value;
}

Это было новым для меня, и мне пришлось воссоздать его. Возможно, мне придется добавить статью на мой сайт об этом: -)

1 голос
/ 09 декабря 2009

Спасибо skypecakes, это прекрасно работает :) Вот отредактированная версия вашего элемента управления, которая также отслеживает, где полосы прокрутки, где:

class AutoScrollPanel : Panel
{
    public AutoScrollPanel()
    {
        Enter += PanelNoScrollOnFocus_Enter;
        Leave += PanelNoScrollOnFocus_Leave;
    }

    private System.Drawing.Point scrollLocation;

    void PanelNoScrollOnFocus_Enter(object sender, System.EventArgs e)
    {
        // Set the scroll location back when the control regains focus.
        HorizontalScroll.Value = scrollLocation.X;
        VerticalScroll.Value = scrollLocation.Y;
    }

    void PanelNoScrollOnFocus_Leave(object sender, System.EventArgs e)
    {
        // Remember the scroll location when the control loses focus.
        scrollLocation.X = HorizontalScroll.Value;
        scrollLocation.Y = VerticalScroll.Value;
    }

    protected override System.Drawing.Point ScrollToControl(Control activeControl)
    {
        // When there's only 1 control in the panel and the user clicks
        //  on it, .NET tries to scroll to the control. This invariably
        //  forces the panel to scroll up. This little hack prevents that.
        return DisplayRectangle.Location;
    }
}

Это работает, только если в Panel есть только один элемент управления (хотя я не тестировал его с более чем одним элементом управления).

0 голосов
/ 07 января 2009

Я понимаю вашу боль, это заставило меня не раз.

Если ваш DataGridView - единственное на панели, просто установите Dock на Fill и позвольте DGV самостоятельно управлять прокруткой. Я не думаю, что это сделает прыжок больше. В противном случае, я думаю, вы могли бы просто изменить его размер, чтобы он был меньше, чем панель, и позволить ему выполнять прокрутку самостоятельно.

...