none
WPF MainWindowを移動するときに、this.Left以外の方法 RRS feed

  • 質問

  • 現在、WPFのMainWindowを移動するときに

                    this.Left = x;
                    this.Top = y;

    のように書き動作させると、一度、横方向に動いて、次は縦方向に動きます。

    軽いWindowだと目立たないのですが、重い処理させているので、かなりカクカク移動してしまいます。

    座標の設定を一度で済ますような、例えば「.Location」のような方法はないでしょうか?

    よろしくお願いします。

    XP C# 2010 Express WPF

    • 移動 佐伯玲 2013年3月14日 8:23 Visual C#からWPFへ
    2013年3月13日 7:36

回答

  • class ChangeEventPreventableFrameworkPropertyMetadata : FrameworkPropertyMetadata
    {
    	public ChangeEventPreventableFrameworkPropertyMetadata(PropertyChangedCallback callback)
    		: base(callback)
    	{
    		this.m_callback = callback;
    	}
    	public PropertyChangedCallback BaseCallback { get; set; }
    	private PropertyChangedCallback m_callback;
    	protected override void Merge(PropertyMetadata baseMetadata, DependencyProperty dp)
    	{
    		base.Merge(baseMetadata, dp);
    		var baseCallback = baseMetadata.PropertyChangedCallback;
    		this.BaseCallback = baseCallback;
    		this.PropertyChangedCallback = this.m_callback;
    	}
    }
    class Win : Window
    {
    	static Win()
    	{
    		Window.LeftProperty.OverrideMetadata(typeof(Win), new ChangeEventPreventableFrameworkPropertyMetadata(OnLeftChanged));
    	}
    	static void OnLeftChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    	{
    		var win = d as Win;
    		if (win != null)
    		{
    			if (!win.m_suspending)
    			{
    				var meta = (ChangeEventPreventableFrameworkPropertyMetadata)LeftProperty.GetMetadata(win);
    				meta.BaseCallback(d, e);
    			}
    		}
    	}
    	public void SetPosition(double left, double top)
    	{
    		this.m_suspending = true;
    		this.Left = left;
    		this.m_suspending = false;
    		this.Top = top;
    	}
    	private bool m_suspending;
    }

    こんなので、SPY++で確認する限りWM_MOVEが1回しか飛ばないようになりましたが。

    2013年3月14日 13:29

すべての返信

  • うまくいくかどうかわかりませんが、以下を試してみて下さい。

    using (var d = Dispatcher.DisableProcessing())
    {
        this.Left = x;
        this.Top = y;
    }

    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2013年3月14日 7:24
    モデレータ
  • こんにちは、まさ20120528 さん
    フォーラムオペレータの佐伯 玲 です。

    こちら「Windows Presentation Foundation (WPF)」フォーラムのほうがより適切なカテゴリかと思われますので移動させていただきますね。

    宜しくお願い致します。
    __________________________
    日本マイクロソフト株式会社 フォーラム オペレータ 佐伯 玲

    2013年3月14日 8:22
  • 移動ありがとうございます。

    次からは、こちらに投稿したいと思います。

    2013年3月14日 12:20
  • 提案していただいたコードに、さっそく差し替えてみたのですが残念ながら改善されませんでした・・。
    2013年3月14日 12:24
  • class ChangeEventPreventableFrameworkPropertyMetadata : FrameworkPropertyMetadata
    {
    	public ChangeEventPreventableFrameworkPropertyMetadata(PropertyChangedCallback callback)
    		: base(callback)
    	{
    		this.m_callback = callback;
    	}
    	public PropertyChangedCallback BaseCallback { get; set; }
    	private PropertyChangedCallback m_callback;
    	protected override void Merge(PropertyMetadata baseMetadata, DependencyProperty dp)
    	{
    		base.Merge(baseMetadata, dp);
    		var baseCallback = baseMetadata.PropertyChangedCallback;
    		this.BaseCallback = baseCallback;
    		this.PropertyChangedCallback = this.m_callback;
    	}
    }
    class Win : Window
    {
    	static Win()
    	{
    		Window.LeftProperty.OverrideMetadata(typeof(Win), new ChangeEventPreventableFrameworkPropertyMetadata(OnLeftChanged));
    	}
    	static void OnLeftChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    	{
    		var win = d as Win;
    		if (win != null)
    		{
    			if (!win.m_suspending)
    			{
    				var meta = (ChangeEventPreventableFrameworkPropertyMetadata)LeftProperty.GetMetadata(win);
    				meta.BaseCallback(d, e);
    			}
    		}
    	}
    	public void SetPosition(double left, double top)
    	{
    		this.m_suspending = true;
    		this.Left = left;
    		this.m_suspending = false;
    		this.Top = top;
    	}
    	private bool m_suspending;
    }

    こんなので、SPY++で確認する限りWM_MOVEが1回しか飛ばないようになりましたが。

    2013年3月14日 13:29
  • 教えていただいたコードで試したところ 思うように動作するようになりました。

    とても助かりました。

    まだ、理解できてない部分が多いので、これからも勉強してみようと思います。

    ありがとうございました。

    2013年3月16日 2:34