ورود

View Full Version : سوال: مشکل در MediElement



MortezaGity
سه شنبه 27 تیر 1391, 08:54 صبح
سلام. من یه mediaelement روی یک window دارم. از یه window جدید اونو new می کنم و source مربوط به medielement رو تو تابع سازندش میدم. ولی مشکل اینه که من میخام وقتی window حاوی mediaelement بسته شد اون فایلی که source ش هست آزاد بشه تا من بتونم روش بنویسم یا پاکش کنم یا هر چیز دیگه. خیلی راه ها رو امتحان دارم که تو فروم های خارجی نوشته شده بود ولی هیچکدوم جواب نداد. مثلا رویداد Close اون window که mediaelement توش هست رو override کردم و... هیچکدوم جواب نداد. وقتی window مربوط به mediaelement رو میبندم و میخام با فایل شروع کنم کار کردن(مثلا توش بنویسم) خطای مبنی به اینکه این فایل توسط یه پروسه دیگه داره استفاده میشه میده ولی اگر برنامه رو stop کنم و دوباره play کنم میتونم توش بنویسم. لطفا کمک کنید.

Player p = new Player(new Uri("")));
p.ShowDialog();


private void Window_Closed(object sender, EventArgs e)
{
mediaPlayerMain.Close();
}

Amir Oveisi
سه شنبه 27 تیر 1391, 09:28 صبح
چه راه هایی رو برای این کار امتحان کردید؟
اگر این دو راه رو تست نکردید، تست کنید و نتیجه رو اعلام کنید:
۱- با MediaElement.Stop مدیایی رو که play میشه Stop‌کنید و بعد windows‌ رو ببندید.
۲- قبل از بسته شدن window،مقدار Source کنترل MediaElement‌ رو با null‌ مقدار بدید.

MortezaGity
سه شنبه 27 تیر 1391, 12:35 عصر
دوست عزیز خیلی ممنون که توجه می کنید ولی این دو راه رو هم قبلاً امتحان کردم و جواب نگرفتم. تو فروم های انگلیسی هم همین راه ها رو پیشنهاد دادن ولی متاسفانه جواب نمیدن. هیچکدوم.

یاسردرا
سه شنبه 27 تیر 1391, 13:27 عصر
<Window x:Class="WpfApplication6.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="300" Width="300" Loaded="Window_Loaded" Closing="Window_Closing" Closed="Window_Closed">
<Grid>
<MediaElement x:Name="mediaelemnt"/>
</Grid>
</Window>

پنجره بعدی

<Window x:Class="WpfApplication6.Window2"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window2" Height="300" Width="300" Loaded="Window_Loaded">
<Grid></Grid>
</Window>

پنجره اصلی:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace WpfApplication6
{
/// <summary>
/// Interaction logic for Window1.xaml
/// </summary>
public partial class Window1 : Window
{
public Window1()
{
InitializeComponent();
}

private void Window_Loaded(object sender, RoutedEventArgs e)
{
MediaClock c = mediaelemnt.Clock;
MediaTimeline t = new MediaTimeline(new Uri(@"E:\music\01-evanescence-whisper_2002-fxn.mp3"));
c = t.CreateClock();
mediaelemnt.Clock = c;
}

private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
mediaelemnt.Clock = null;
Window2 w2 = new Window2();
w2.ShowDialog();
}

}
}

پنجره دوم

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;

namespace WpfApplication6
{
/// <summary>
/// Interaction logic for Window2.xaml
/// </summary>
public partial class Window2 : Window
{
public Window2()
{
InitializeComponent();
}



private void Window_Loaded(object sender, RoutedEventArgs e)
{
System.IO.File.Copy(@"E:\music\01-evanescence-whisper_2002-fxn.mp3",AppDomain.CurrentDomain.BaseDirectory+"c.mp3");
}
}
}

MortezaGity
سه شنبه 27 تیر 1391, 14:53 عصر
واقعا ممنون از زحمتی که می کشید. لطف میکنید وقت میذارید ولی بازم مشکل من حل نشد. این کد ها رو هم امتحان کردم. بذارید یه کم توضیح بدم. من تو window1 با زدن یه دکمه با متد File.WriteAllBytes یه فایل می سازم و بعد پنجره ی MediaElement رو new میکنم و شروع میکنم به پخش اون فایل. حالا می خوام وقتی این پنجره بسته شد و به پنجره ی اول برگشتم فایل آزاد بشه و من بتونم تغییرش بدم که نمی تونم. مشکل از اینجاست که MediaElement بعد از اینکه پنجرش بسته می شه انگار فایل رو آزاد نمیکنه. مشکل از متد File.WriteAllBytes نیست. چون من اگر پنجره ی MediElement رو new نکنم میتونم بعد از ساخت فایلم با این متد، تغییرش بدم. یعنی اینکه این متد بعد از ساخت فایل، اونو آزاد میکنه ولی پنجره ای که MediaElement توشه بعد از بسته شدنش فایل رو آزاد نمیکنه. اگه راه حلی میدونید کمک کنید.

مهدی فرزاد
سه شنبه 27 تیر 1391, 20:31 عصر
سلام
من یک نمونه درست کردم البته بدون متدFile.WriteAllBytes که یک فایل رو در مسیر مشخص اجرا میکرد بعد قبل از پاک کردن ابتدا میدیا رو stop و سورس اون رو null کردم و فایل به راحتی پاک شد!

میتونی نمونه رو بگذاری تا روش بررسی انجام بشه ؟( خیلی از دوستان از جمله من فرصت ساختن سمپل و تست کردن و به جواب رسیدن رو نداریم) اگر نمونه ای طبق توضیحی که دادی ضمیمه کنی من بشخصه تست میکنم و راه کار رو درصورت نتیجه گرفتن اعلام میکنم

MortezaGity
چهارشنبه 28 تیر 1391, 17:59 عصر
سلام دوست عزیز. با تشکر.
تمام کدمو در زیر نوشتم. تمام این راهکارایی که ذکر کردید هم انجام دادم ولی جواب نمیده. انگار مدیاالمنت فایل رو آزاد نمیکنه

byte[] file = File.ReadAllBytes(FilePath.FullName);
File.WriteAllBytes(Path, file);
------------------------------------------------------
Player p = new Player() { VideoPath = new Uri(Path) };
p.ShowDialog();
------------------------------------------------------

مهدی فرزاد
پنج شنبه 29 تیر 1391, 09:15 صبح
سلام
من این کد رو در اونت Closing نوشتم و با روش شما پاک کرد!!
شما مشکل رو در جای دیگه بررسی کنید

لطفا کد پنجره Player رو بگذارید


void MainWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
this.mediaElement.Stop();
this.mediaElement.Source = null;
System.IO.File.Delete( this.VideoPath.AbsolutePath);
}

MortezaGity
پنج شنبه 29 تیر 1391, 21:04 عصر
نه پاک نمیکنه. Exception هم نمیده. من با break point دقیقا فهمیدم که مشکل وقتی پیش میاد که Player رو new میکنم. یعنی اگر فایل ایجاد شده رو ندم به Source مربوط به MediaElement می تونم راحت پاکش کنم. ولی وقتی میدمش به اون و بعد از تمام شدن کار و بسته شدن پنجره می خوام پاکش کنم یا اصلا هر بلای دیگه ای سرش بیارم Exception میده که این فایل توسط یه پروسه دیگه داره استفاده می شه. باور کنید مطمئن هستم.

مهدی فرزاد
جمعه 30 تیر 1391, 11:58 صبح
دوست گرامی من دقیقا سمپل شما رو درست کردم و پاک کرد
شما به چه شکلی سورس میدیا المنت رو مقدار دهی کردید؟؟ لطفا کد پنجره Player رو بگذارید تا بتونیم کمکتون کنیم

MortezaGity
جمعه 30 تیر 1391, 20:58 عصر
با استفاده از پارامتری که توی تابع سازندش می گیره.
public Player(Uri VideoPath) { InitializeComponent(); mediaPlayerMain.Source = VideoPath; }

همچنین خطی که صدا می زنم پنجره رو به این شکله

Player p = new Player(new Uri("C:\\file.avi")); p.ShowDialog();

روی فرم تقریبا دیگه چیزی نیست جز این مدیاالمنت

مهدی فرزاد
شنبه 31 تیر 1391, 08:09 صبح
سلام
دوست عزیز طبق کدهایی که شما نوشتید عمل کردم و فقط در یک مورد موفق به پاک کردن فایل نشد اون هم زمانی بود که فایل در درایو C قرار داشت
فایل رو به درایو دیگه ای بردم و کاملا پاک شد

یک نکته دیگه اینکه خاصیت LoadedBehavior مربوط یه میدیا باید بر روی حالت Manual باشه تا Stop بشه
شما کد های پنجره Player رو دقیقا مطابق زیر بنویسید
من که نتیجه گرفتم

public partial class Player : Window
{
Uri VideoPath;
public Player(Uri VideoPath)
{
InitializeComponent();
this.VideoPath = VideoPath;
mediaElement1.LoadedBehavior = MediaState.Manual;
mediaElement1.Source = VideoPath;
mediaElement1.Play();

this.Closing += new System.ComponentModel.CancelEventHandler(Player_Cl osing);
}

void Player_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
this.mediaElement1.Stop();
this.mediaElement1.Source = null;
System.IO.File.Delete(this.VideoPath.AbsolutePath) ;
}
}

MortezaGity
یک شنبه 01 مرداد 1391, 07:21 صبح
خیلی ممنون بله فراموش کردم بگم فایلمو تو درایو C میسازم. خیلی لطف کردید. از زحمتی که کشیدید ممنون. اگه بخوام از تو درایو C پاک کنم راهی نداره.

مهدی فرزاد
یک شنبه 01 مرداد 1391, 07:43 صبح
باید دسترسی کامل و Admin داشته باشید
به تنظیمات ویندوز بر میگرده