123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520 |
- using Microsoft.WindowsAPICodePack.Shell;
- using System;
- using System.Collections.Generic;
- using System.IO;
- using System.Linq;
- using System.Text;
- using System.Threading.Tasks;
- 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.Animation;
- using System.Windows.Media.Imaging;
- using System.Windows.Navigation;
- using System.Windows.Shapes;
- using System.Windows.Threading;
- namespace HistoryDLL
- {
- /// <summary>
- /// PlaneRotateMap.xaml 的互動邏輯
- /// </summary>
- public partial class PlaneRotateMap : UserControl
- {
- //創造 PlaneRotateMap 物件
- private delegate void CreatePlaneRotateMapDelegate();
- private delegate void DynamicChangeLan();
- private DispatcherTimer RotateWaitTime = new DispatcherTimer();
- //該PlaneRotate中有幾個可以顯示的物件
- private int ImageWidth, ImageHeight;
- private List<FrameworkElement> ElementForRotateList = new List<FrameworkElement>();
- private Rectangle RectForTouch = new Rectangle();
- //當前顯示的物件是屬於ElementForRotateList中的第幾個索引
- private int CurrentShowIndex = 0;
- //該輪播塊是屬於該年事件中的第幾個索引
- public int indexOfEvent = -1;
- //亂數產生
- private Random rnd = new Random(Guid.NewGuid().GetHashCode());
- //切換資訊的亂數時間範圍 changeInfoTimeMin <= s < changeInfoTimeMax
- private int changeInfoTimeMin = 8;
- private int changeInfoTimeMax = 32;
- //Other Number
- private double RotateAngle = 10.0; //區塊旋轉時候的角度
- private double TextFontSize = 23; //顯示的資訊如果是文字~則設定文字大小
- private int RotateAnimationTime = 400;
- private Storyboard sbStepOne = new Storyboard();
- private DoubleAnimation dbOffsetOne = new DoubleAnimation();
- private Storyboard sbStepTwo = new Storyboard();
- private DoubleAnimation dbOffsetTwo = new DoubleAnimation();
- private SolidColorBrush RotateContainColor = new SolidColorBrush(ConfigSettingClass.EventCollect.BackgroundColor);
- private SolidColorBrush RotateContainTextColor = new SolidColorBrush(ConfigSettingClass.EventCollect.TextColor);
- //判斷是否資料已經到底的紀錄的 Index
- private int RecordInfoCount = 1;
- //資料暫存
- public MonthClass RotateMonthClass = new MonthClass();
- private string[] imgfilter = { ".jpeg", ".jpg", ".bmp", ".png" };
- private string[] mediafilter = { ".mp4", ".wmv", ".mpeg", "mpg", "avi" };
- //該PlaneRotateMap在LiveContainer 中的哪個區塊
- public int BlockIndex = -1;
- public bool ChangeInfo = false;
- public PlaneRotateMap()
- { InitializeComponent(); }
- public PlaneRotateMap(MonthClass sourcemonthClass, int ImageWidth, int ImageHeight)
- {
- InitializeComponent();
- if (GlobalFunction.isSolutionUsing4K)
- TextFontSize *= 1.5;
- //將暫時設定一下顏色
- uxRotateContain.Background = RotateContainColor;
- //設定翻轉頻率
- SetRotateFreq();
- //設定旋轉動作的相關Timer
- SettingRotateMap();
- RotateWaitTime.Tick += new EventHandler(RotateWaitTime_Tick);
- //資料存到緩衝
- RotateMonthClass = sourcemonthClass;
- //設定寬高
- uxRotateContain.Width = uxRotateMainGrid.Width = this.ImageWidth = ImageWidth;
- uxRotateContain.Height = uxRotateMainGrid.Height = this.ImageHeight = ImageHeight;
- //設定可觸控層
- SetTouchLay(ImageWidth, ImageHeight);
- //翻轉角度設定
- uxMyPlanerator.FieldOfView = RotateAngle;
- }
- private void DynamicChangeLanEvent()
- {
- //第 0 個一定是文字
- Grid gd = ElementForRotateList[0] as Grid;
- TextBlock tb = gd.Children[0] as TextBlock;
- //假如現在是第一種語系
- if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language1")
- {
- tb.Text = RotateMonthClass.titleLan1;
- }
- else if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language2")
- {
- tb.Text = RotateMonthClass.titleLan2;
- }
- else if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language3")
- {
- tb.Text = RotateMonthClass.titleLan3;
- }
- else if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language4")
- {
- tb.Text = RotateMonthClass.titleLan4;
- }
- }
- //動態改變 PlaneRotate 內容物件的語系
- internal void ChangeLanByDynamic()
- {
- this.Dispatcher.BeginInvoke(new DynamicChangeLan(DynamicChangeLanEvent),
- DispatcherPriority.Background);
- }
- private void SetRotateFreq()
- {
- changeInfoTimeMin = 8;
- if (ConfigSettingClass.MainBackCollect.ScreenSetting == 1)
- {
- changeInfoTimeMax = 32;
- }
- else if (ConfigSettingClass.MainBackCollect.ScreenSetting == 2)
- {
- changeInfoTimeMax = 48;
- }
- else if (ConfigSettingClass.MainBackCollect.ScreenSetting == 3)
- {
- changeInfoTimeMax = 64;
- }
- }
- internal void CreatePlaneRotateMap()
- {
- //透過RotateMonthClass取得該PlaneRotateMap 顯示資訊
- GetInformationToShow();
- }
- private void GetInformationToShow()
- {
- System.Windows.Application.Current.Dispatcher.Invoke(new CreatePlaneRotateMapDelegate(AddRotateInfoToList), DispatcherPriority.Background);
- //點擊區
- uxRotateMainGrid.Children.Add(RectForTouch);
- }
- private void SettingRotateMap()
- {
- dbOffsetOne = new DoubleAnimation()
- {
- Duration = TimeSpan.FromMilliseconds(RotateAnimationTime),
- EasingFunction = new PowerEase()
- {
- EasingMode = EasingMode.EaseIn,
- Power = 2
- },
- };
- dbOffsetOne.From = 0;
- dbOffsetOne.To = 90;
- dbOffsetTwo = new DoubleAnimation()
- {
- Duration = TimeSpan.FromMilliseconds(RotateAnimationTime),
- EasingFunction = new PowerEase()
- {
- EasingMode = EasingMode.EaseOut,
- Power = 2
- },
- };
- dbOffsetTwo.From = -90;
- dbOffsetTwo.To = 0;
- Storyboard.SetTarget(dbOffsetOne, (DependencyObject)this.FindName("uxMyPlanerator"));
- Storyboard.SetTargetProperty(dbOffsetOne, new PropertyPath(NLPlaneRotator.PlaneRotator.RotationXProperty));
- sbStepOne.Children.Add(dbOffsetOne);
- sbStepOne.FillBehavior = FillBehavior.HoldEnd;
- sbStepOne.Completed += new EventHandler(sbStepOne_Completed);
- Storyboard.SetTarget(dbOffsetTwo, (DependencyObject)this.FindName("uxMyPlanerator"));
- Storyboard.SetTargetProperty(dbOffsetTwo, new PropertyPath(NLPlaneRotator.PlaneRotator.RotationXProperty));
- sbStepTwo.Children.Add(dbOffsetTwo);
- sbStepTwo.FillBehavior = FillBehavior.HoldEnd;
- }
- /// <summary>
- /// 旋轉
- /// </summary>
- public void RotateTheObject()
- {
- sbStepOne.Begin();
- }
- public void sbStepOne_Completed(object sender, EventArgs e)
- {
- //改變資料
- if (ChangeInfo)
- {
- SendChangeBlockIndex("Prepare", BlockIndex);
- }
- CurrentShowIndex++;
- ChangeElementForShow(ref CurrentShowIndex);
- sbStepTwo.Begin();
- }
- /// <summary>
- /// 判斷該資料是否已經到底了~如果是~則通知 LiveContainer
- /// </summary>
- /// <param name="RecordInfoCount">紀錄已經播放幾筆資料</param>
- private void CheckTheFileEndToSend(ref int RecordInfoCount)
- {
- if (RecordInfoCount >= ElementForRotateList.Count)
- {
- //到底~將該區塊的索引值傳回 LiveContainer
- SendChangeBlockIndex("DataEnd", BlockIndex);
- }
- }
- /// <summary>
- /// 設定可觸控層以方便之後能夠點擊觸發
- /// </summary>
- private void SetTouchLay(int ImageWidth, int ImageHeight)
- {
- RectForTouch.Width = ImageWidth;
- RectForTouch.Height = ImageHeight;
- RectForTouch.Fill = Brushes.Transparent;
- RectForTouch.PreviewTouchDown += new EventHandler<TouchEventArgs>(RectForTouch_PreviewTouchDown);
- }
- void RectForTouch_PreviewTouchDown(object sender, TouchEventArgs e)
- {
- //通知被點擊
- SendInfoToLiveContainer(indexOfEvent, CurrentShowIndex - 1);
- }
- /// <summary>
- /// 該PlaneRotate 顯示資訊
- /// </summary>
- public void startShow()
- {
- //將紀錄設定為第一筆資料 <一開始會先顯示的資料>
- RecordInfoCount = 1;
- //一開始先顯示圖片或者文字(亂數取)
- CurrentShowIndex = rnd.Next(0, ElementForRotateList.Count);
- //透過索引值~改變要顯示的是該月份的第幾個資料~文字或者圖~?
- ChangeElementForShow(ref CurrentShowIndex);
- }
- /// <summary>
- /// 停止該PlaneRotate自轉模式
- /// </summary>
- public void stopShow()
- {
- //清除所有顯示資訊
- uxRotateContain.Children.Clear();
- ElementForRotateList.Clear();
- RotateWaitTime.Stop();
- }
- /// <summary>
- /// 取得下次要翻轉的等待時間 (翻轉開始呼叫函數~)
- /// </summary>
- public void StartCountDownForRatate()
- {
- //亂數取得
- int time = rnd.Next(changeInfoTimeMin, changeInfoTimeMax);
- RotateWaitTime.Interval = TimeSpan.FromSeconds(time);
- RotateWaitTime.Start();
- }
- //如果等待時間到~則開始旋轉並在設定其下次要旋轉的等待時間
- void RotateWaitTime_Tick(object sender, EventArgs e)
- {
- RotateWaitTime.Stop();
- StartCountDownForRatate();
- RotateTheObject();
- #region 判斷是否資料已經到底
- //該遍資料紀錄值加一
- RecordInfoCount++;
- //判斷該資料是否已經到底了~如果是~則通知 LiveContainer
- CheckTheFileEndToSend(ref RecordInfoCount);
- #endregion
- }
- /// <summary>
- /// 停止翻轉功能
- /// </summary>
- public void StopCountDownForRatate()
- {
- RotateWaitTime.Stop();
- }
- /// <summary>
- /// 先將可以顯示的資訊放到 ElementForRotateList 中
- /// </summary>
- private void AddRotateInfoToList()
- {
- ElementForRotateList.Clear();
- #region 先加文字
- Grid gridfortext = new Grid();
- TextBlock textblock = new TextBlock();
- if (ConfigSettingClass.MainBackCollect.DefaultLangIndex < ConfigSettingClass.MainBackCollect.LangFlowDir.Length)
- {
- textblock.FlowDirection = ConfigSettingClass.MainBackCollect.LangFlowDir[ConfigSettingClass.MainBackCollect.DefaultLangIndex];
- }
- try
- {
- //假如現在是第一種語系
- if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language1")
- {
- textblock.Text = RotateMonthClass.titleLan1;
- }
- else if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language2")
- {
- textblock.Text = RotateMonthClass.titleLan2;
- }
- else if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language3")
- {
- textblock.Text = RotateMonthClass.titleLan3;
- }
- else if (System.Windows.Application.Current.Properties["Language"].ToString() == "Language4")
- {
- textblock.Text = RotateMonthClass.titleLan4;
- }
- }
- catch
- {
- }
- gridfortext.VerticalAlignment = System.Windows.VerticalAlignment.Center;
- gridfortext.HorizontalAlignment = System.Windows.HorizontalAlignment.Center;
- gridfortext.Width = ImageWidth;
- gridfortext.Height = ImageHeight;
- textblock.TextWrapping = TextWrapping.Wrap;
- textblock.FontSize = TextFontSize;
- textblock.Foreground = RotateContainTextColor;
- textblock.Margin = new Thickness(10);
- gridfortext.Children.Add(textblock);
- ElementForRotateList.Add(gridfortext);
- #endregion
- #region 加圖片
- //做法 : 先將 imagepath 路徑下的圖片縮圖, 之後放到 image controller 下再放到 ElementForRotateList 中
- if (RotateMonthClass.imagepath != "")
- {
- string[] tempFile;
- if (Directory.Exists(GlobalFunction.EventFileImgPath + RotateMonthClass.imagepath))
- {
- tempFile = Directory.GetFiles(GlobalFunction.EventFileImgPath + RotateMonthClass.imagepath);
- // tempFile 為全部的圖片張數,避免記憶體吃太多~ 每個事件框以亂數載入五張為最多
- int startupIndex = 0;
- int targetIndex = 0;
- bool startGet = true;
- int maxLoadValue = 5;
- if (tempFile.Count() > maxLoadValue)
- {
- startGet = false;
- startupIndex = rnd.Next(0, tempFile.Count() - maxLoadValue);
- }
- foreach (string item in tempFile)
- {
- if (targetIndex != startupIndex && !startGet)
- {
- targetIndex++;
- }
- else
- {
- // 開始取圖
- startGet = true;
- if (maxLoadValue < 0)
- break;
- maxLoadValue--;
- if (imgfilter.Contains(System.IO.Path.GetExtension(item).ToLower()))
- {
- Grid gd = new Grid();
- Image img = new Image();
- FileInfo fileinfo = new FileInfo(item);
- string FilePath = fileinfo.FullName.ToString().Trim();
- RenderOptions.SetBitmapScalingMode(img, BitmapScalingMode.HighQuality);
- img.Source = MediaViewerLib.Utilities.MediaUtilties.LoadBitmapImage(FilePath, ImageWidth);
- img.Stretch = Stretch.UniformToFill;
- img.VerticalAlignment = System.Windows.VerticalAlignment.Center;
- img.HorizontalAlignment = System.Windows.HorizontalAlignment.Center;
- gd.Width = ImageWidth;
- gd.Height = ImageHeight;
- gd.Children.Add(img);
- ElementForRotateList.Add(gd);
- }
- else if (mediafilter.Contains(System.IO.Path.GetExtension(item).ToLower()))
- {
- Grid gd = new Grid();
- Image img = new Image();
- FileInfo fileinfo = new FileInfo(item);
- string FilePath = fileinfo.FullName.ToString().Trim();
- // 影片取縮圖
- RenderOptions.SetBitmapScalingMode(img, BitmapScalingMode.HighQuality);
- ShellFile shellFile = ShellFile.FromFilePath(FilePath);
- BitmapSource shellThumb = shellFile.Thumbnail.ExtraLargeBitmapSource;
- img.Source = shellThumb;
- img.Stretch = Stretch.UniformToFill;
- img.VerticalAlignment = System.Windows.VerticalAlignment.Center;
- img.HorizontalAlignment = System.Windows.HorizontalAlignment.Center;
- gd.Width = ImageWidth;
- gd.Height = ImageHeight;
- gd.Children.Add(img);
- ElementForRotateList.Add(gd);
- }
- }
- }
- }
- }
- #endregion
- #region 加預設logo圖
- //如果以上圖文只有一個有資料~則加上預設的圖
- if (ElementForRotateList.Count <= 1 && ConfigSettingClass.MainBackCollect.ImgLogo != "")
- {
- string DefaultLogoPath = ConfigSettingClass.MainBackCollect.ImgLogo;
- if (File.Exists(GlobalFunction.thumbPath + DefaultLogoPath))
- {
- Grid gd = new Grid();
- Image img = new Image();
- img.Source = MediaViewerLib.Utilities.MediaUtilties.LoadBitmapImage(GlobalFunction.thumbPath + DefaultLogoPath, ImageWidth);
- img.Stretch = Stretch.Uniform;
- img.VerticalAlignment = System.Windows.VerticalAlignment.Center;
- img.HorizontalAlignment = System.Windows.HorizontalAlignment.Center;
- gd.Width = ImageWidth;
- gd.Height = ImageHeight;
- gd.Children.Add(img);
- ElementForRotateList.Add(gd);
- }
- }
- #endregion
- SendChangeBlockIndex("Load Complete", 0);
- }
- /// <summary>
- /// 增加事件~增加從 LiveContainer Callback Event
- /// </summary>
- /// <param name="liveContainer"></param>
- public void ListenFromLiveContainerCode(LiveContainer liveContainer)
- {
- liveContainer.LiveContainerBubbleToPlaneRotateEvent += new LiveContainer.LiveContainerBubbleToPlaneRotateMap(ReceiveFromLiveContainerForFileChange);
- }
- /// <summary>
- /// 將該索引加到uxRotateContain
- /// </summary>
- /// <param name="CurrentShowIndex">指向 ElementForRotateList 中的索引值</param>
- private void ChangeElementForShow(ref int index)
- {
- uxRotateContain.Children.Clear();
- if (index >= ElementForRotateList.Count)
- {
- //超過資料上限~重頭播放
- index = 0;
- }
- if (ElementForRotateList.Count == 0)
- {
- return;
- }
- uxRotateContain.Children.Add(ElementForRotateList[index]);
- }
- /// <summary>
- /// 取得圖片Source
- /// </summary>
- /// <param name="imgpath">指定圖片路徑</param>
- /// <returns></returns>
- private ImageSource GetBitmapImage(string imgpath)
- {
- BitmapImage bitmapImg = new BitmapImage();
- bitmapImg.BeginInit();
- bitmapImg.UriSource = new Uri(imgpath, UriKind.RelativeOrAbsolute);
- //忽略原始圖檔的色盤設定,使用預設值,可縮短載入圖檔的時間
- //如有遇到色彩不正確的問題,或者原圖有特殊的自定義色盤,請不要使用此設定
- bitmapImg.CreateOptions = BitmapCreateOptions.IgnoreColorProfile;
- //使用以下的預先載入設定,在BitmapImage創建完成之後,可立刻釋放其所占用或鎖住的資源,以免咬住檔案
- bitmapImg.CacheOption = BitmapCacheOption.OnLoad;
- //根據欲顯示的區域長或寬,來設定 DecodePixelHeight 或 DecodePixelWidth 的值
- //bitmapImg.DecodePixelHeight = THUMB_HEIGHT;
- //bitmapImg.DecodePixelWidth = THUMB_WIDTH;
- bitmapImg.EndInit();
- bitmapImg.Freeze();
- return bitmapImg;
- }
- }
- }
|