主にプログラミングに関して。Python, .NET Framework(C#), JavaScript, その他いくらか。
記事にあるサンプルやコードは要検証。使用に際しては責任を負いかねます

スポンサーサイト

                
tags:
上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

WPF: マルチディスプレイ環境でメディア再生が止まってしまう

                
Visual like MediaElement stops on multi display environment

http://social.msdn.microsoft.com/Forums/en-AU/wpf/thread/75d72afa-2fff-44fd-9f0a-87753002daa1
WPFのMediaElementを使ってウィンドウで動画を再生しながら、そのウィンドウをプライマリディスプレイからサブディスプレイにドラッグしたら再生が止まった。どうやらレンダリングモードの問題で、マイクロソフトはこれを解決していないらしい。
てっとりばやい解決法として、マルチディスプレイ環境では、アプリケーション立ち上げ時にレンダリングをソフトウェアオンリーにしてしまう方法が載っていた。もうちょっといい解決法を考える。プライマリディスプレイで表示している間はフリーズしなかったのだから、プライマリディスプレイで表示しているあいだはハードウェアによる描画支援がされていてもいい。
ウィンドウがプライマリディスプレイとサブディスプレイを移動するときに、レンダリング方法を切り換えるようにする。テストしてみたところフリーズも回避できた。クラス化して再利用できるようにしておいた。System.Windows.FormsとSystem.DrawingのDLLへの参照追加が必須となる。これらの参照を追加してモジュールとしてインポートしたら、ウィンドウ初期化時に引数としてWindowオブジェクトと動画再生するMediaElementを渡して実行するだけ。
PreventMEFreeze(self, self.mediaEl)

Window1.py
import wpf, clr

import System
##from System.Windows import Window

clr.AddReference("System.Drawing")
clr.AddReference("System.Windows.Forms")
import System.Drawing
import System.Windows.Forms

class PreventMEFreeze():
def __init__(self, main, mediaEl, debug=False):
if (System.Windows.Forms.Screen.AllScreens.Length > 1):
if not isinstance(main, System.Windows.Window):
raise TypeError
if not isinstance(mediaEl, System.Windows.Controls.MediaElement):
raise TypeError
self.debug = debug
main.Show()
self.renderMode = System.Windows.PresentationSource.FromVisual(mediaEl).CompositionTarget
self.primary = True
main.LocationChanged += self.LocationChange

def LocationChange(self, target, e):
p = System.Drawing.Point(int(target.Left) + 50, int(target.Top) + 50)
screenFromPoint = System.Windows.Forms.Screen.FromPoint(p)
if self.primary != screenFromPoint.Primary:
if self.renderMode.RenderMode == System.Windows.Interop.RenderMode.Default:
self.renderMode.RenderMode = System.Windows.Interop.RenderMode.SoftwareOnly
else:
self.renderMode.RenderMode = System.Windows.Interop.RenderMode.Default
self.primary = screenFromPoint.Primary
if self.debug:
print int(target.Left), int(target.Top)
print "On Primary Display;", screenFromPoint.Primary
print "Render Mode;", self.renderMode.RenderMode, "\n"


class Window1 (System.Windows.Window):
def __init__(self):
wpf.LoadComponent(self, 'Window1.xaml')
self.mediaEl = self.FindName('mediaEl')
self.prevent = PreventMEFreeze(self, self.mediaEl, True)



Window1.xaml
<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="preventMEFreeze"
Height="300"
Width="300">
<Grid>
<MediaElement Name="mediaEl" Source="C:\Users\hoge\Videos\hoge.mp4"
LoadedBehavior="Play" UnloadedBehavior="Stop"></MediaElement>
</Grid>
</Window>


Application.py
import wpf

from System.Windows import Application
from Window1 import Window1

window = Window1()
app = Application()
app.Run(window)



            

コメントの投稿

非公開コメント

プロフィール

hMatoba

Author:hMatoba
Github

最新記事
リンク
作ったものなど
月別アーカイブ
カテゴリ
タグリスト

検索フォーム
Amazon
上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。