2

ダブルバッファリングを有効にするという明確な目的で TabControl を派生させましたが、何も期待どおりに機能していません。TabControl コードは次のとおりです。

class DoubleBufferedTabControl : TabControl
{
    public DoubleBufferedTabControl() : base()
    {
        this.DoubleBuffered = true;
        this.SetStyle
            (
                ControlStyles.UserPaint |
                ControlStyles.AllPaintingInWmPaint |
                ControlStyles.ResizeRedraw |
                ControlStyles.OptimizedDoubleBuffer |
                ControlStyles.SupportsTransparentBackColor,
                false
            );
    }
}

この Tabcontrol は、描画モードが「OwnerDrawnFixed」に設定されているため、色を変更できます。カスタム描画方法は次のとおりです。

    private void Navigation_PageContent_DrawItem(object sender, DrawItemEventArgs e)
    {
        //Structure.
        Graphics g = e.Graphics;
        TabControl t = (TabControl)sender;
        TabPage CurrentPage = t.TabPages[e.Index];

        //Get the current tab
        Rectangle CurrentTabRect = t.GetTabRect(e.Index);

        //Get the last tab.
        Rectangle LastTab = t.GetTabRect(t.TabPages.Count - 1);

        //Main background rectangle.
        Rectangle BackgroundRect = new Rectangle(LastTab.Width, t.Bounds.Y - 4, t.Width - (LastTab.Width), t.Height);

        //Tab background rectangle.
        Rectangle TabBackgroundRect = new Rectangle(0, LastTab.Y + LastTab.Height, LastTab.Width, t.Bounds.Height - (LastTab.Y + LastTab.Height));

        //Set anitialiasing for the text.
        e.Graphics.TextRenderingHint = System.Drawing.Text.TextRenderingHint.ClearTypeGridFit;

        //String format for the text.
        StringFormat StringFormat = new StringFormat();
        StringFormat.Alignment = StringAlignment.Center;
        StringFormat.LineAlignment = StringAlignment.Center;

        //Fill the background.
        g.FillRectangle(Brushes.LightGray, BackgroundRect);
        g.FillRectangle(Brushes.Bisque, TabBackgroundRect);

        //Draw the selected tab.
        if(e.State == DrawItemState.Selected)
        {
            g.FillRectangle(Brushes.White, e.Bounds);
            Rectangle SelectedTabOutline = new Rectangle(e.Bounds.X + 2, e.Bounds.Y + 2, e.Bounds.Width, e.Bounds.Height - 4);
            g.DrawRectangle(new Pen(Brushes.LightGray, 4f), SelectedTabOutline);
            g.DrawString(CurrentPage.Text, new Font("Arial", 12f, FontStyle.Bold, GraphicsUnit.Point), new SolidBrush(Color.FromArgb(70, 70, 70)), CurrentTabRect, StringFormat);
        }
        else
        {
            g.FillRectangle(new SolidBrush(Color.FromArgb(230, 230, 230)), e.Bounds);
            g.DrawString(CurrentPage.Text, new Font("Arial", 12f, FontStyle.Regular, GraphicsUnit.Point), Brushes.Gray, CurrentTabRect, StringFormat);
        }

    }

ただし、このコントロールはダブル バッファリングされておらず、サイズ変更時にちらつきが発生するため、まったく役に立ちません。

何か案は?

4

6 に答える 6

2

まず第一に、TabControlコードを取り除くことができます。バッファリングをオンにしてからすぐにオフにするので、実際には何の役にも立ちません。

問題の一部は、の一部だけをペイントしようとしていることですTabControl

約 90% の解決策 (まだちらつきが発生する可能性があります) を与える最も簡単な解決策は、これをフォーム クラスに追加することです。

protected override CreateParams CreateParams
{
    get
    {
        CreateParams cp = base.CreateParams;
        cp.ExStyle |= 0x02000000;
        return cp;
    }
}

ちらつきが発生しないことを確実にしたい場合は、自分で全体を描画し、TabControl背景の描画要求を無視するようにする必要があります。

編集:これはXP以降でのみ機能することに注意してください。

于 2008-11-10T19:53:32.433 に答える
2

ドキュメントを読むと、「このメンバーはこのコントロールにとって意味がありません」と書かれています。ダブル バッファリングを使用してコントロールを描画する場合は、自分で実装する必要があります。コントロールをオーナーで描画する場合、とにかく自分でダブルバッファリングを実装する必要があるという事実に加えて。

于 2008-10-23T00:03:39.263 に答える
1

過去にコントロールのダブル バッファリングに問題がありましたが、ちらつきを止める唯一の方法は、継承された OnPaintBackground メソッドが呼び出されていないことを確認することでした。(以下のコードを参照してください)また、ペイント呼び出し中に背景全体がペイントされるようにする必要があります。

protected override void OnPaintBackground( PaintEventArgs pevent )
{
    //do not call base - I don't want the background re-painted!
}
于 2008-11-19T17:48:02.643 に答える
0

わかりませんが、タブコントロールを含むコントロールをダブルバッファリングしてみてください。

于 2008-10-21T22:00:30.903 に答える
0

ダブルバッファリングを無効にしているため、機能しないと思います!

ControlStyles.OptimizedDoubleBufferthis.DoubleBuffered = trueを true に設定するだけです。プログラムの次の行でそのフラグを無効にしているので、実際には何もしていません。ControlStyles.OptimizedDoubleBuffer (およびおそらく ControlStyles.AllPaintingInWmPaint) を削除すると、うまくいくはずです。

于 2008-11-10T13:43:56.267 に答える
0

私はかなり見回し、あなたのコードと私が考えることができるものをすべて試しましたが、ちらつきを取り除く方法がわかりません. 残念ながら、私のテストでは、通常の (所有者が描画していない) タブ コントロールでさえ、サイズ変更中にちらつきます。

価値のあることとして、「ドラッグ中にウィンドウの内容を表示する」をオフにすると修正されますが、それは役に立たないかもしれません.

于 2008-10-22T03:49:09.187 に答える