2

エクスプレッション ブレンド、Twirl、または Adob​​e Lightroom の一部として出荷されるような黒いカスタム ウィンドウ (境界線とコントロールを含む) を作成できるようにしたいと考えています。

オーナー描画ウィンドウを作成するにはどうすればよいですか?

4

3 に答える 3

6

カスタムChromeツールで希望のルックアンドフィールが得られない場合、この種のことはC#で簡単に実行できます。基本的に、フチなしフォーム(FormBorderStyle = None)を作成してから、必要な場所(タイトルバーのラベル、閉じるおよび最小化するためのコマンドボタンなど)にコントロールを配置したり、描画したりして、すべてのコントロールと境界線を自分で作成します。 Graphicsオブジェクトを使用してフォームの表面に直接。

また、フォームを「偽の」タイトルバーでドラッグできるようにするコードを実装する必要があります(これを行う方法のサンプルについては、この回答を参照してください)。また、独自のサイズ変更メカニズムを実装する必要がある場合もあります(フォームのサイズを変更する必要がある場合)。

最後に、カスタムフォームコードは少し扱いに​​くいかもしれませんが、単一のフォームに実装してから、アプリケーション内の他のすべてのフォームにこのフォームを継承させることができます。これにより、全体をカスタムスキンするための非常に便利な手法になります。応用。

于 2008-11-20T17:09:12.007 に答える
3

私の仕事は、アクティブなウィンドウをアプリの他の非アクティブなウィンドウよりも目立たせて明るくすることでした。アプリには、開いているウィンドウが多数あり、一部はモーダル、一部はモードレス、および MDI の親ウィンドウです。

not-a-border (クライアント領域内のフレーム) のようなものを使用できます。以下は、基本クラスの一部であるコード スニペットです (フォームで直接使用できます)。

    #region Кастомизированное поведение - рамки, активность и т.д.
    private bool isCurrentlyActive = false;
    private bool childControlsAreHandled = false;
    private Pen activeWindowFramePen, inactiveWindowFramePen;
    private Point[] framePoints;

    private void AddControlPaintHandler(Control ctrl)
    {
        ctrl.Paint += DrawWindowFrame;
        if (ctrl.Controls != null)
        {
            foreach (Control childControl in ctrl.Controls)
            {
                AddControlPaintHandler(childControl);
            }
        }
    }

    protected override void OnActivated(EventArgs e)
    {
        base.OnActivated(e);
        if ((this.childControlsAreHandled == false)
            && (WindowFrameType != Forms.WindowFrameType.NoFrame)
            && (this.MdiParent == null))
        {
            RecalculateWindowFramePoints();
            AddControlPaintHandler(this);
            this.childControlsAreHandled = true;
        }

        this.isCurrentlyActive = true;
        if (InactiveWindowOpacity < 1)
        {
            base.Opacity = 1;
        }
        base.Invalidate(true);
    }

    protected override void OnDeactivate(EventArgs e)
    {
        base.OnDeactivate(e);
        this.isCurrentlyActive = false;
        if (InactiveWindowOpacity < 1)
        {
            base.Opacity = InactiveWindowOpacity;
        }
        base.Invalidate(true);
    }

    protected override void OnResizeEnd(EventArgs e)
    {
        base.OnResizeEnd(e);
        this.framePoints = null;
        RecalculateWindowFramePoints();
        this.Invalidate(true);
    }

    private Pen ActivePen
    {
        get
        {
            if (this.isCurrentlyActive)
            {
                if (this.activeWindowFramePen == null)
                {
                    this.activeWindowFramePen = new Pen(Color.FromArgb((int)(WindowFrameOpacity*255), WindowFrameActiveColor), WindowFrameSize * 2);
                }
                return this.activeWindowFramePen;
            }
            else
            {
                if (this.inactiveWindowFramePen == null)
                {
                    this.inactiveWindowFramePen = new Pen(Color.FromArgb((int)(WindowFrameOpacity*255), WindowFrameInactiveColor), WindowFrameSize * 2);
                }
                return this.inactiveWindowFramePen;
            }
        }
    }

    private Point[] RecalculateWindowFramePoints()
    {
        if ((WindowFrameType == Forms.WindowFrameType.AllSides)
            && (this.framePoints != null)
            && (this.framePoints.Length != 5))
        {
            this.framePoints = null;
        }
        if ((WindowFrameType == Forms.WindowFrameType.LeftLine)
            && (this.framePoints != null)
            && (this.framePoints.Length != 2))
        {
            this.framePoints = null;
        }
        if (this.framePoints == null)
        {
            switch (WindowFrameType)
            {
                case Forms.WindowFrameType.AllSides:
                    this.framePoints = new Point[5]
                    {
                        new Point(this.ClientRectangle.X, this.ClientRectangle.Y),
                        new Point(this.ClientRectangle.X + this.ClientRectangle.Width, this.ClientRectangle.Y),
                        new Point(this.ClientRectangle.X + this.ClientRectangle.Width, this.ClientRectangle.Y + this.ClientRectangle.Height),
                        new Point(this.ClientRectangle.X, this.ClientRectangle.Y + this.ClientRectangle.Height),
                        new Point(this.ClientRectangle.X, this.ClientRectangle.Y)
                    };
                    break;
                case Forms.WindowFrameType.LeftLine:
                    this.framePoints = new Point[2]
                    {
                        new Point(this.ClientRectangle.X, this.ClientRectangle.Y),
                        new Point(this.ClientRectangle.X, this.ClientRectangle.Y + this.ClientRectangle.Height)
                    };
                    break;
            }
        }
        return this.framePoints;
    }

    private void DrawWindowFrame(object sender, PaintEventArgs e)
    {
        if (WindowFrameType == Forms.WindowFrameType.NoFrame)
        {
            return;
        }
        if ((this.framePoints == null) || (this.framePoints.Length == 0))
        {
            return;
        }
        Control ctrl = (Control)(sender);
        // пересчитаем точки в координатах контрола.
        List<Point> pts = new List<Point>();
        foreach (var p in this.framePoints)
        {
            pts.Add(ctrl.PointToClient(this.PointToScreen(p)));
        }
        e.Graphics.DrawLines(ActivePen, pts.ToArray());
    }

    public static int WindowFrameSize = 2;
    public static WindowFrameType WindowFrameType = Forms.WindowFrameType.NoFrame;
    public static Color WindowFrameActiveColor = Color.YellowGreen;
    public static Color WindowFrameInactiveColor = SystemColors.ControlDark;
    public static double InactiveWindowOpacity = 1.0;
    public static double WindowFrameOpacity = 0.3;
    #endregion

クラスの静的フィールドはアプリケーション設定フォーム (クラス) から初期化されるため、アプリ内のすべてのフォームは同じ動作をします。

それが誰かに役立つことを願っています。

于 2012-09-20T11:44:34.143 に答える
0

WinForms アプリのカスタム タイトルバー/クロム

于 2008-11-20T16:34:54.227 に答える