public static void ShowTitleCard(
            string title,
            int tryCount,
            DateTime recordingTime)
        {
            if (window == null)
            {
                window = new TitleCardView();
            }

            window.VideoTitle    = title;
            window.TryCount      = tryCount;
            window.RecordingTime = recordingTime;

            window.Show();

            if (!window.Config.IsAlwaysShow)
            {
                WPFHelper.BeginInvoke(async() =>
                {
                    await Task.Delay(TimeSpan.FromSeconds(2.7));
                    window.Close();
                    window = null;
                });
            }
        }
예제 #2
0
        private void AppendLogLine(
            string message,
            Exception ex = null,
            bool err     = false)
        {
            // UIに出力する
            var text = $"[{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.ffff")}] {message}";

            if (ex != null)
            {
                text += Environment.NewLine + ex.ToString();
            }

            this.log.AppendLine(text);
            WPFHelper.BeginInvoke(() => this.RaisePropertyChanged(nameof(this.Log)));

            // NLogに出力する
            var log = $"[DISCORD] {message}";

            if (ex == null && !err)
            {
                this.Logger.Trace(log);
            }
            else
            {
                this.Logger.Error(ex, log);
            }
        }
예제 #3
0
        public static void LoadTTSCache()
        {
            if (Settings.Default.Player != WavePlayerTypes.WASAPIBuffered)
            {
                return;
            }

            var volume = Settings.Default.WaveVolume / 100f;

            WPFHelper.BeginInvoke(() =>
            {
            },
                                  DispatcherPriority.SystemIdle).Task.ContinueWith((_) => Task.Run(() =>
            {
                var count = 0;

                try
                {
                    Logger.Info("Started loading TTS caches.");
                    BufferedWavePlayer.PlayerSet.LoadTTSHistory();
                    count = BufferedWavePlayer.Instance.BufferWaves(volume);
                }
                finally
                {
                    Logger.Info($"Completed loading TTS caches. {count} files has loaded.");
                }
            }));
        }
        public TimelineManagerView()
        {
            this.InitializeComponent();
            this.SetLocale(Settings.Default.UILocale);
            this.LoadConfigViewResources();

            if (!WPFHelper.IsDesignMode)
            {
                if (this.TimelineConfig.Enabled)
                {
                    WPFHelper.BeginInvoke(async() =>
                    {
                        try
                        {
                            await Task.Run(() => TimelineManager.Instance.LoadTimelineModels());
                        }
                        catch (Exception ex)
                        {
                            TimelineModel.ShowRazorDumpFile();

                            ModernMessageBox.ShowDialog(
                                ex.Message,
                                "Timeline Loader",
                                MessageBoxButton.OK,
                                ex.InnerException);
                        }
                    });
                }
            }

            this.StyleListView.SelectionChanged += (x, y) =>
            {
                if (this.TimelineConfig.DesignMode)
                {
                    var selectedStyle = this.StyleListView.SelectedItem as TimelineStyle;

                    TimelineOverlay.HideDesignOverlay(false);
                    TimelineOverlay.ShowDesignOverlay(selectedStyle);

                    TimelineNoticeOverlay.HideDesignOverlay();
                    TimelineNoticeOverlay.ShowDesignOverlay(selectedStyle);
                }
            };

            this.timer.Tick += (x, y) =>
            {
                if (TimelineController.CurrentController != null)
                {
                    // ついでにスタートボタンのラベルを切り替える
                    this.StartButtonLabel = TimelineController.CurrentController.IsRunning ?
                                            StopString :
                                            StartString;
                }
            };

            this.timer.Start();
        }
예제 #5
0
 public MainSimpleViewModel()
 {
     AppLog.AppendedLog += (s, e) =>
     {
         WPFHelper.BeginInvoke(() =>
         {
             this.RaisePropertyChanged(nameof(this.Messages));
         });
     };
 }
 public void RefreshNotices()
 {
     if (!this.Config.IsTimelineLiveUpdate)
     {
         WPFHelper.BeginInvoke(() =>
         {
             this.noticesSource?.View?.Refresh();
         },
                               DispatcherPriority.Background);
     }
 }
예제 #7
0
        public void NotifyProperties()
        {
            var pis = this.GetType().GetProperties();

            WPFHelper.BeginInvoke(() =>
            {
                foreach (var pi in pis)
                {
                    this.RaisePropertyChanged(pi.Name);
                }
            });
        }
예제 #8
0
        private void LogTextChanged(object sender, TextChangedEventArgs e)
        {
            var textBox = sender as TextBox;

            if (textBox != null)
            {
                WPFHelper.BeginInvoke(() =>
                {
                    textBox.CaretIndex = textBox.Text.Length;
                    textBox.ScrollToEnd();
                });
            }
        }
예제 #9
0
        private void BeginAnimation()
        {
            this.IsVisibleSyncIndicator = true;

            (this.View as MPTickerView)?.BeginAnimation();

            WPFHelper.BeginInvoke(async() =>
            {
                await Task.Delay(1200);
                this.IsVisibleSyncIndicator = false;
            },
                                  DispatcherPriority.Normal);
        }
예제 #10
0
        public void SelectedChanged()
        {
            if (this.isInitialize)
            {
                return;
            }

            Task.Run(() =>
            {
                var mustStartIDs = new List <Guid>();
                mustStartIDs.AddRange(this.ActiveSpells.Where(x => x.IsSelected).Select(x => x.ID));
                mustStartIDs.AddRange(this.ActiveTickers.Where(x => x.IsSelected).Select(x => x.ID));

                var mustStopIDs = new List <Guid>();
                mustStopIDs.AddRange(this.InactiveSpells.Where(x => x.IsSelected).Select(x => x.ID));
                mustStopIDs.AddRange(this.InactiveTickers.Where(x => x.IsSelected).Select(x => x.ID));

                if (this.Spell != null)
                {
                    this.Spell.TimersMustRunningForStart  = mustStartIDs.ToArray();
                    this.Spell.TimersMustStoppingForStart = mustStopIDs.ToArray();

                    WPFHelper.BeginInvoke(() => this.RaisePropertyChanged(nameof(this.IsFiltered)));
                }
                else
                {
                    if (this.Ticker != null)
                    {
                        this.Ticker.TimersMustRunningForStart  = mustStartIDs.ToArray();
                        this.Ticker.TimersMustStoppingForStart = mustStopIDs.ToArray();

                        WPFHelper.BeginInvoke(() => this.RaisePropertyChanged(nameof(this.IsFiltered)));
                    }
                }
            });
        }
예제 #11
0
        public void InitPluginCore(
            TabPage pluginScreenSpace,
            Label pluginStatusText)
        {
            // タイトルをセットする
            pluginScreenSpace.Text = "SPESPE";

            WPFHelper.Start();
            WPFHelper.BeginInvoke(async() =>
            {
                // FFXIV_MemoryReaderを先にロードさせる
                await FFXIVReader.Instance.WaitForReaderToStartedAsync();

                this.PluginStatusLabel = pluginStatusText;

                AppLog.LoadConfiguration(AppLog.HojoringConfig);
                this.AppLogger.Trace(Assembly.GetExecutingAssembly().GetName().ToString() + " start.");

                try
                {
                    Logger.Init();
                    Logger.Write("[SPESPE] Start InitPlugin");

                    // .NET FrameworkとOSのバージョンを確認する
                    if (!UpdateChecker.IsAvailableDotNet() ||
                        !UpdateChecker.IsAvailableWindows())
                    {
                        return;
                    }

                    // メイン設定ファイルを読み込む
                    Settings.Default.Load();
                    Settings.Default.ApplyRenderMode();

                    // 最小化する?
                    if (Settings.Default.IsMinimizeOnStart)
                    {
                        ActGlobals.oFormActMain.WindowState = FormWindowState.Minimized;
                        Application.DoEvents();
                    }

                    // HojoringのSplashを表示する
                    UpdateChecker.ShowSplash();

                    // 自身の場所を格納しておく
                    var plugin = ActGlobals.oFormActMain.PluginGetSelfData(this.PluginRoot);
                    if (plugin != null)
                    {
                        this.Location = plugin.pluginFile.DirectoryName;
                    }

                    // 設定ファイルを読み込む
                    SpellPanelTable.Instance.Load();
                    SpellTable.Instance.Load();
                    TickerTable.Instance.Load();
                    TagTable.Instance.Load();

                    await Task.Run(() =>
                    {
                        SpellPanelTable.Instance.Backup();
                        SpellTable.Instance.Backup();
                        TickerTable.Instance.Backup();
                        TagTable.Instance.Backup();
                    });

                    TTSDictionary.Instance.Load();

                    // 設定Panelを追加する
                    var baseView = new BaseView(pluginScreenSpace.Font);
                    pluginScreenSpace.Controls.Add(new ElementHost()
                    {
                        Child = baseView,
                        Dock  = DockStyle.Fill,
                        Font  = pluginScreenSpace.Font,
                    });

                    // 本体を開始する
                    PluginMainWorker.Instance.Begin();
                    TimelineController.Init();

                    // 付加情報オーバーレイを表示する
                    LPSView.ShowLPS();
                    POSView.ShowPOS();

                    this.SetSwitchVisibleButton();
                    this.PluginStatusLabel.Text = "Plugin Started";

                    Logger.Write("[SPESPE] End InitPlugin");

                    // アップデートを確認する
                    await Task.Run(() => this.Update());
                }
                catch (Exception ex)
                {
                    Logger.Write("InitPlugin error.", ex);

                    if (this.PluginStatusLabel != null)
                    {
                        this.PluginStatusLabel.Text = "Plugin Initialize Error";
                    }

                    ModernMessageBox.ShowDialog(
                        "Plugin init error !",
                        "ACT.SpecialSpellTimer",
                        System.Windows.MessageBoxButton.OK,
                        ex);
                }
            });
        }
예제 #12
0
        public static void LoadTTSCache(
            bool isNow = false)
        {
            if (Settings.Default.Player != WavePlayerTypes.WASAPIBuffered)
            {
                return;
            }

            var volume = Settings.Default.WaveVolume / 100f;

            WPFHelper.BeginInvoke(() =>
                                  { },
                                  DispatcherPriority.ContextIdle).Task.ContinueWith((_) =>
            {
                if (!isNow)
                {
                    Thread.Sleep(TimeSpan.FromSeconds(60));
                }
                else
                {
                    Thread.Sleep(TimeSpan.FromMilliseconds(100));
                }

                var dirs = new[]
                {
                    Path.Combine(
                        Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData),
                        @"anoyetta\ACT\tts cache"),
                    DirectoryHelper.FindSubDirectory(@"resources\wav"),
                };

                var files = new List <string>();

                foreach (var dir in dirs)
                {
                    if (!Directory.Exists(dir))
                    {
                        continue;
                    }

                    files.AddRange(Directory.GetFiles(dir, "*.wav"));
                    files.AddRange(Directory.GetFiles(dir, "*.mp3"));
                }

                if (files.Count > 0)
                {
                    try
                    {
                        Logger.Info("Load TTS caches.");

                        BufferedWavePlayer.Instance.BufferWaves(
                            files,
                            volume);
                    }
                    finally
                    {
                        Logger.Info("Load TTS caches, done.");
                    }
                }
            });
        }
예제 #13
0
        protected override async void GetCombatant()
        {
            if ((DateTime.Now - this.combatantsTimestamp).TotalMilliseconds
                < Settings.Instance.MobList.RefreshRateMin)
            {
                return;
            }

            this.combatantsTimestamp = DateTime.Now;

            #region Test Mode

            // テストモード?
            if (Settings.Instance.MobList.TestMode)
            {
                var dummyPlayer = new Combatant()
                {
                    ID   = 1,
                    PosX = 0,
                    PosY = 0,
                    PosZ = 0,
                };

                var dummyTargets = new List <MobInfo>();

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:シルバーの吉田直樹",
                    Rank      = "EX",
                    Combatant = new Combatant()
                    {
                        ID     = 1,
                        Name   = "TEST:シルバーの吉田直樹",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 0,
                        PosY   = 10,
                        PosZ   = 10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:イクシオン",
                    Rank      = "EX",
                    Combatant = new Combatant()
                    {
                        ID     = 2,
                        Name   = "TEST:イクシオン",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 100,
                        PosY   = 100,
                        PosZ   = -10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:イクシオン",
                    Rank      = "EX",
                    Combatant = new Combatant()
                    {
                        ID     = 21,
                        Name   = "TEST:イクシオン",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 100,
                        PosY   = 100,
                        PosZ   = -10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:ソルト・アンド・ライト",
                    Rank      = "S",
                    Combatant = new Combatant()
                    {
                        ID     = 3,
                        Name   = "TEST:ソルト・アンド・ライト",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 10,
                        PosY   = 0,
                        PosZ   = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:オルクス",
                    Rank      = "A",
                    Combatant = new Combatant()
                    {
                        ID     = 4,
                        Name   = "TEST:オルクス",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 100,
                        PosY   = -100,
                        PosZ   = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:宵闇のヤミニ",
                    Rank      = "B",
                    Combatant = new Combatant()
                    {
                        ID     = 5,
                        Name   = "TEST:宵闇のヤミニ",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 0,
                        PosY   = -100,
                        PosZ   = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:どこかのヒメちゃん",
                    Rank      = string.Empty,
                    Combatant = new Combatant()
                    {
                        ID     = 6,
                        Name   = "TEST:どこかのヒメちゃん",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = -100,
                        PosY   = -100,
                        PosZ   = 0,
                    },
                });

                lock (this.TargetInfoLock)
                {
                    this.TargetInfo    = dummyTargets.First().Combatant;
                    this.targetMobList = dummyTargets;
                }

                return;
            }

            #endregion Test Mode

            var combatants = FFXIVPlugin.Instance.GetCombatantList();

            // 画面ダンプ用のCombatantsを更新する
            CombatantsViewModel.RefreshCombatants(combatants);

            var targets = default(IEnumerable <MobInfo>);

            await Task.Run(() =>
            {
                targets =
                    from x in combatants
                    where
                    ((x.MaxHP <= 0) || (x.MaxHP > 0 && x.CurrentHP > 0)) &&
                    Settings.Instance.MobList.TargetMobList.ContainsKey(x.Name)
                    select new MobInfo()
                {
                    Name        = x.Name,
                    Combatant   = x,
                    Rank        = Settings.Instance.MobList.TargetMobList[x.Name].Rank,
                    MaxDistance = Settings.Instance.MobList.TargetMobList[x.Name].MaxDistance,
                    TTSEnabled  = Settings.Instance.MobList.TargetMobList[x.Name].TTSEnabled,
                };

                // 距離で絞り込む
                targets = targets.Where(x => x.Distance <= x.MaxDistance);
            });

            lock (this.TargetInfoLock)
            {
                this.targetMobList = targets.ToList();
                this.TargetInfo    = this.targetMobList.FirstOrDefault()?.Combatant;

                if (this.TargetInfo == null)
                {
                    var model = this.Model as MobListModel;
                    if (model != null &&
                        model.MobList.Any())
                    {
                        WPFHelper.BeginInvoke(model.ClearMobList);
                    }
                }
            }
        }
예제 #14
0
        public Task <FFXIVReaderStartingResult> WaitForReaderToStartedAsync(
            TabPage baseTabPage) => Task.Run(() =>
        {
            var result = new FFXIVReaderStartingResult();

            lock (this)
            {
                // 旧の単独DLL版が存在したら念のため削除する
                var dll = Path.Combine(
                    Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location),
                    "FFXIV_MemoryReader.dll");
                if (File.Exists(dll))
                {
                    var message = new StringBuilder();

                    try
                    {
                        File.Delete(dll);

                        message.Clear();
                        message.AppendLine($@"""FFXIV_MemoryReader.dll"" was deleted.");
                        message.AppendLine($@"Please, restart ACT.");
                        WPFHelper.BeginInvoke(() => ModernMessageBox.ShowDialog(
                                                  message.ToString(),
                                                  "Warning",
                                                  MessageBoxButton.OK));
                    }
                    catch (Exception)
                    {
                    }

                    if (File.Exists(dll))
                    {
                        message.Clear();
                        message.AppendLine($@"""FFXIV_MemoryReader.dll"" is exists yet.");
                        message.AppendLine($@"You should delete ""FFXIV_MemoryReader.dll"".");
                        message.AppendLine();
                        message.AppendLine("Path:");
                        message.AppendLine(dll);

                        WPFHelper.BeginInvoke(() => ModernMessageBox.ShowDialog(
                                                  message.ToString(),
                                                  "Warning",
                                                  MessageBoxButton.OK));
                    }
                }

                if (this.MemoryPlugin != null)
                {
                    result.Status = FFXIVReaderStartingStatus.AlreadyStarted;
                    return(result);
                }

                var succeeded = false;

                WPFHelper.Invoke(() =>
                {
                    var parentTabControl = baseTabPage.Parent as TabControl;
                    if (parentTabControl == null)
                    {
                        return;
                    }

                    var memoryReaderTabPage = new TabPage();
                    var dummyLabel          = new Label();
                    parentTabControl.TabPages.Add(memoryReaderTabPage);

                    this.tab     = parentTabControl;
                    this.tabPage = memoryReaderTabPage;

                    try
                    {
                        this.MemoryPlugin = new MemoryPlugin();
                        this.MemoryPlugin.InitPlugin(memoryReaderTabPage, dummyLabel);

                        succeeded = dummyLabel.Text.ContainsIgnoreCase("Started");

                        if (succeeded)
                        {
                            result.Status = FFXIVReaderStartingStatus.Started;
                        }
                        else
                        {
                            result.Status  = FFXIVReaderStartingStatus.Error;
                            result.Message = "Error occurred initializing FFXIV_MemoryReader.";
                            this.MemoryPlugin?.DeInitPlugin();
                            this.MemoryPlugin = null;
                        }
                    }
                    catch (Exception ex)
                    {
                        result.Status    = FFXIVReaderStartingStatus.Error;
                        result.Message   = "Fatal error occurred initializing FFXIV_MemoryReader.";
                        result.Exception = ex;

                        ModernMessageBox.ShowDialog(
                            result.Message,
                            "Fatal Error",
                            MessageBoxButton.OK,
                            ex);
                    }
                },
                                 DispatcherPriority.Normal);

                this.IsAvailable = succeeded;
            }

            return(result);
        });
예제 #15
0
        private void RefreshCombatants()
        {
            var player = default(Combatant);
            var party  = default(IReadOnlyList <Combatant>);

            lock (SimulationLocker)
            {
                if (this.InSimulation &&
                    this.SimulationPlayer != null &&
                    this.SimulationParty.Any())
                {
                    player = this.SimulationPlayer;
                    party  = this.SimulationParty;
                }
                else
                {
                    player = FFXIVPlugin.Instance?.GetPlayer();
                    party  = FFXIVPlugin.Instance?.GetPartyList();
                }
            }

            if (player != null)
            {
                this.player = player;
            }

            if (party != null)
            {
                var newList = new List <Combatant>(party);

                if (newList.Count < 1 &&
                    !string.IsNullOrEmpty(this.player?.Name))
                {
                    newList.Add(this.player);
                }

                // パーティリストを入れ替える
                this.partyList.Clear();
                this.partyList.AddRange(newList);

                // 読み仮名リストをメンテナンスする
                var newPhonetics =
                    from x in newList
                    select new PCPhonetic()
                {
                    ID     = x.ID,
                    NameFI = x.NameFI,
                    NameIF = x.NameIF,
                    NameII = x.NameII,
                    Name   = x.Name,
                    JobID  = x.JobID,
                };

                WPFHelper.BeginInvoke(() =>
                {
                    var phonetics = TTSDictionary.Instance.Phonetics;

                    var toAdd = newPhonetics.Where(x => !phonetics.Any(y => y.Name == x.Name));
                    phonetics.AddRange(toAdd);

                    var toRemove = phonetics.Where(x => !newPhonetics.Any(y => y.Name == x.Name)).ToArray();
                    foreach (var item in toRemove)
                    {
                        phonetics.Remove(item);
                    }
                });
            }
        }
예제 #16
0
        public void StartPlugin(
            TabPage pluginScreenSpace,
            Label pluginStatusText)
        {
            this.isLoaded = false;

            // タイトルをセットする
            pluginScreenSpace.Text = "ULTRA SCOUTER";

            EnvironmentMigrater.Migrate();
            MasterFilePublisher.Publish();
            WPFHelper.Start();
            WPFHelper.BeginInvoke(async() =>
            {
                AppLog.LoadConfiguration(AppLog.HojoringConfig);
                this.Logger?.Trace(Assembly.GetExecutingAssembly().GetName().ToString() + " start.");

                try
                {
                    this.PluginTabPage     = pluginScreenSpace;
                    this.PluginStatusLabel = pluginStatusText;

                    if (!EnvironmentHelper.IsValidPluginLoadOrder())
                    {
                        if (pluginStatusText != null)
                        {
                            pluginStatusText.Text = "Plugin Initialize Error";
                        }

                        return;
                    }

                    EnvironmentHelper.GarbageLogs();
                    EnvironmentHelper.StartActivator(() =>
                    {
                        BaseView.Instance.SetActivationStatus(false);
                        this.EndPlugin();
                    });

                    this.Logger.Trace("[ULTRA SCOUTER] Start InitPlugin");

                    // .NET FrameworkとOSのバージョンを確認する
                    if (!UpdateChecker.IsAvailableDotNet() ||
                        !UpdateChecker.IsAvailableWindows())
                    {
                        NotSupportedView.AddAndShow(pluginScreenSpace);
                        return;
                    }

                    // FFXIV.Framework.config を読み込ませる
                    lock (FFXIV.Framework.Config.ConfigBlocker)
                    {
                        _ = FFXIV.Framework.Config.Instance;
                    }

                    // HojoringのSplashを表示する
                    UpdateChecker.ShowSplash();

                    // 外部リソースをダウンロードする
                    await ResourcesDownloader.Instance.DownloadAsync();

                    // 設定ファイルを読み込む
                    Settings.Instance.Load();
                    Settings.Instance.MPTicker.UpdateUnlockMPSync();

                    // 設定ファイルをバックアップする
                    await EnvironmentHelper.BackupFilesAsync(
                        Settings.Instance.FileName);

                    // 各種ファイルを読み込む
                    await Task.Run(() =>
                    {
                        TTSDictionary.Instance.Load();
                        Settings.Instance.MobList.LoadTargetMobList();
                    });

                    EnvironmentHelper.WaitInitActDone();

                    // FFXIVプラグインへのアクセスを開始する
                    await Task.Run(() =>
                    {
                        XIVPluginHelper.Instance.Start(
                            Settings.Instance.PollingRate,
                            Settings.Instance.FFXIVLocale);
                    });

                    // ターゲット情報ワーカを開始する
                    MainWorker.Instance.Start();

                    // タブページを登録する
                    this.SetupPluginTabPages(pluginScreenSpace);

                    // テキストコマンドの購読を追加する
                    this.SubscribeTextCommands();

                    if (this.PluginStatusLabel != null)
                    {
                        this.PluginStatusLabel.Text = "Plugin started.";
                    }

                    this.Logger.Trace("[ULTRA SCOUTER] End InitPlugin");

                    // 共通ビューを追加する
                    CommonViewHelper.Instance.AddCommonView(
                        pluginScreenSpace.Parent as TabControl);

                    this.isLoaded = true;

                    // FFLogsの統計データベースをロードする
                    StatisticsDatabase.Instance.Logger = Logger;
                    await StatisticsDatabase.Instance.LoadAsync();

                    // アップデートを確認する
                    await Task.Run(() => this.Update());
                }
                catch (Exception ex)
                {
                    this.Logger.Fatal(ex, "InitPlugin error.");
                    this.ShowMessage("InitPlugin error.", ex);
                }
            });
        }
예제 #17
0
        public void StartPlugin(
            TabPage pluginScreenSpace,
            Label pluginStatusText)
        {
            // タイトルをセットする
            pluginScreenSpace.Text = "ULTRA SCOUTER";

            WPFHelper.Start();
            WPFHelper.BeginInvoke(async() =>
            {
                // FFXIV_MemoryReaderを先にロードさせる
                await FFXIVReader.Instance.WaitForReaderToStartedAsync();

                AppLog.LoadConfiguration(AppLog.HojoringConfig);
                this.Logger.Trace(Assembly.GetExecutingAssembly().GetName().ToString() + " start.");

                try
                {
                    this.Logger.Trace("[ULTRA SCOUTER] Start InitPlugin");

                    this.PluginTabPage     = pluginScreenSpace;
                    this.PluginStatusLabel = pluginStatusText;

                    // .NET FrameworkとOSのバージョンを確認する
                    if (!UpdateChecker.IsAvailableDotNet() ||
                        !UpdateChecker.IsAvailableWindows())
                    {
                        NotSupportedView.AddAndShow(pluginScreenSpace);
                        return;
                    }

                    // 設定ファイルを読み込む
                    Settings.Instance.Load();

                    // HojoringのSplashを表示する
                    WPFHelper.Start();
                    UpdateChecker.ShowSplash();

                    // 各種ファイルを読み込む
                    await Task.Run(() =>
                    {
                        TTSDictionary.Instance.Load();
                        Settings.Instance.MobList.LoadTargetMobList();
                    });

                    // FFXIVプラグインへのアクセスを開始する
                    await Task.Run(() => FFXIVPlugin.Instance.Start(
                                       Settings.Instance.PollingRate,
                                       Settings.Instance.FFXIVLocale));

                    // ターゲット情報ワーカを開始する
                    MainWorker.Instance.Start();

                    // タブページを登録する
                    this.SetupPluginTabPages(pluginScreenSpace);

                    this.PluginStatusLabel.Text = "Plugin started.";
                    this.Logger.Trace("[ULTRA SCOUTER] End InitPlugin");

                    // アップデートを確認する
                    await Task.Run(() => this.Update());
                }
                catch (Exception ex)
                {
                    this.Logger.Fatal(ex, "InitPlugin error.");
                    this.ShowMessage("InitPlugin error.", ex);
                }
            });
        }
예제 #18
0
        public TriggerTesterView()
        {
            this.InitializeComponent();
            this.SetLocale(Settings.Default.UILocale);
            this.LoadConfigViewResources();

            // ウィンドウのスタート位置を決める
            this.WindowStartupLocation = WindowStartupLocation.CenterScreen;

            this.MouseLeftButtonDown += (x, y) => this.DragMove();

            this.Loaded += async(x, y) =>
            {
                await WPFHelper.InvokeAsync(() =>
                {
                    this.MessageLabel.Content    = "Loading, Please wait...";
                    this.MessageLabel.Visibility = Visibility.Visible;
                },
                                            DispatcherPriority.Normal);

                // シミュレーションモードをONにする
                PluginMainWorker.Instance.InSimulation = true;
                TableCompiler.Instance.InSimulation    = true;

                await Task.Delay(TimeSpan.FromSeconds(0.5));

                await WPFHelper.BeginInvoke(() =>
                {
                    this.MessageLabel.Content    = string.Empty;
                    this.MessageLabel.Visibility = Visibility.Collapsed;
                },
                                            DispatcherPriority.ApplicationIdle);
            };

            this.CloseButton.Click += (x, y) =>
            {
                this.testTimer.Stop();
                this.Close();
            };

            this.Closed += (x, y) =>
            {
                PluginMainWorker.Instance.InSimulation = false;
                TableCompiler.Instance.InSimulation    = false;
                this.ClearTestCondition();
            };

            this.testTimer.Tick += this.TestTimer_Tick;

            this.RunButton.Click += async(x, y) =>
            {
                // インスタンススペルを消去する
                SpellTable.Instance.RemoveInstanceSpellsAll();

                await Task.Run(() =>
                {
                    lock (this)
                    {
                        this.testTimer.Stop();
                        this.isPause = false;

                        foreach (var log in this.Logs)
                        {
                            log.IsDone = false;
                        }

                        this.prevTestTimestamp = DateTime.Now;
                        this.TestTime          = TimeSpan.Zero;
                        this.testTimer.Start();
                    }
                });
            };

            this.PauseButton.Click += (x, y) =>
            {
                this.isPause             = !this.isPause;
                this.PauseButton.Content =
                    this.isPause ? "Resume" : "Pause";
            };

            this.StopButton.Click += async(x, y) =>
            {
                await Task.Run(() =>
                {
                    lock (this)
                    {
                        this.testTimer.Stop();

                        foreach (var log in this.Logs)
                        {
                            log.IsDone = false;
                        }

                        this.prevTestTimestamp = DateTime.MinValue;
                    }

                    PluginMainWorker.Instance.InSimulation = false;
                    ChatLogWorker.Instance?.Write(true);
                });

                // インスタンススペルを消去する
                SpellTable.Instance.RemoveInstanceSpellsAll();
            };

            this.OpenButton.Click += (x, y) =>
            {
                var result = this.openFileDialog.ShowDialog(ActGlobals.oFormActMain);
                if (result != System.Windows.Forms.DialogResult.OK)
                {
                    return;
                }

                this.LogFile = this.openFileDialog.FileName;
                this.LoadLog();
            };

            this.ApplyButton.Click += async(x, y) =>
            {
                await WPFHelper.InvokeAsync(() =>
                {
                    this.MessageLabel.Content    = "Loading, Please wait...";
                    this.MessageLabel.Visibility = Visibility.Visible;
                },
                                            DispatcherPriority.Normal);

                await Task.Run(() =>
                {
                    // インスタンススペルを消去する
                    SpellTable.Instance.RemoveInstanceSpellsAll();

                    // テスト条件を適用する
                    this.ApplyTestCondition();
                });

                ModernMessageBox.ShowDialog(
                    "Test Condition was applied.",
                    "Trigger Simulator");

                await Task.Delay(TimeSpan.FromSeconds(0.5));

                await WPFHelper.BeginInvoke(() =>
                {
                    this.MessageLabel.Content    = string.Empty;
                    this.MessageLabel.Visibility = Visibility.Collapsed;
                },
                                            DispatcherPriority.ApplicationIdle);
            };

            this.ClearButton.Click += async(x, y) =>
            {
                await WPFHelper.InvokeAsync(() =>
                {
                    this.MessageLabel.Content    = "Loading, Please wait...";
                    this.MessageLabel.Visibility = Visibility.Visible;
                },
                                            DispatcherPriority.Normal);

                await Task.Run(() =>
                {
                    // インスタンススペルを消去する
                    SpellTable.Instance.RemoveInstanceSpellsAll();

                    // テスト条件を解除する
                    this.ClearTestCondition();
                });

                ModernMessageBox.ShowDialog(
                    "Test Condition was cleard.",
                    "Trigger Simulator");

                await Task.Delay(TimeSpan.FromSeconds(0.5));

                await WPFHelper.BeginInvoke(() =>
                {
                    this.MessageLabel.Content    = string.Empty;
                    this.MessageLabel.Visibility = Visibility.Collapsed;
                },
                                            DispatcherPriority.ApplicationIdle);
            };

            // AddLogLine
            this.AddLogLineButton.Click += async(x, y) => await this.AddLogLineAsync();

            this.AddLogLineTextBox.KeyDown += async(x, y) =>
            {
                if (y.Key == Key.Enter)
                {
                    if (!string.IsNullOrEmpty(this.AddLogLineTextBox.Text))
                    {
                        this.LogLine = this.AddLogLineTextBox.Text;
                    }

                    await this.AddLogLineAsync();
                }
            };
        }
예제 #19
0
        protected override async void GetCombatant()
        {
            if ((DateTime.Now - this.combatantsTimestamp).TotalMilliseconds
                < Settings.Instance.MobList.RefreshRateMin)
            {
                return;
            }

            this.combatantsTimestamp = DateTime.Now;

            #region Test Mode

            // テストモード?
            if (Settings.Instance.MobList.TestMode)
            {
                var dummyPlayer = new Combatant()
                {
                    ID   = 1,
                    PosX = 0,
                    PosY = 0,
                    PosZ = 0,
                };

                var dummyTargets = new List <MobInfo>();

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:シルバーの吉田直樹",
                    Rank      = "EX",
                    Combatant = new Combatant()
                    {
                        ID     = 1,
                        Name   = "TEST:シルバーの吉田直樹",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 0,
                        PosY   = 10,
                        PosZ   = 10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:イクシオン",
                    Rank      = "EX",
                    Combatant = new Combatant()
                    {
                        ID     = 2,
                        Name   = "TEST:イクシオン",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 100,
                        PosY   = 100,
                        PosZ   = -10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:イクシオン",
                    Rank      = "EX",
                    Combatant = new Combatant()
                    {
                        ID     = 21,
                        Name   = "TEST:イクシオン",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 100,
                        PosY   = 100,
                        PosZ   = -10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:ソルト・アンド・ライト",
                    Rank      = "S",
                    Combatant = new Combatant()
                    {
                        ID     = 3,
                        Name   = "TEST:ソルト・アンド・ライト",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 10,
                        PosY   = 0,
                        PosZ   = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:オルクス",
                    Rank      = "A",
                    Combatant = new Combatant()
                    {
                        ID     = 4,
                        Name   = "TEST:オルクス",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 100,
                        PosY   = -100,
                        PosZ   = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:宵闇のヤミニ",
                    Rank      = "B",
                    Combatant = new Combatant()
                    {
                        ID     = 5,
                        Name   = "TEST:宵闇のヤミニ",
                        type   = ObjectType.Monster,
                        MaxHP  = 1,
                        Player = dummyPlayer,
                        PosX   = 0,
                        PosY   = -100,
                        PosZ   = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = Combatant.NameToInitial("Himeko Flower", ConfigBridge.Instance.PCNameStyle),
                    Rank      = "DEAD",
                    Combatant = new Combatant()
                    {
                        ID     = 7,
                        Name   = Combatant.NameToInitial("Himeko Flower", ConfigBridge.Instance.PCNameStyle),
                        type   = ObjectType.PC,
                        Job    = (byte)JobIDs.BLM,
                        MaxHP  = 43462,
                        Player = dummyPlayer,
                        PosX   = -100,
                        PosY   = -100,
                        PosZ   = 0,
                    },
                });

                lock (this.TargetInfoLock)
                {
                    this.TargetInfo    = dummyTargets.First().Combatant;
                    this.targetMobList = dummyTargets;
                }

                return;
            }

            #endregion Test Mode

            var combatants = FFXIVPlugin.Instance.GetCombatantList();

            // 画面ダンプ用のCombatantsを更新する
            CombatantsViewModel.RefreshCombatants(combatants);

            var targets = default(IEnumerable <MobInfo>);

            await Task.Run(() =>
            {
                targets =
                    from x in combatants
                    where
                    ((x.MaxHP <= 0) || (x.MaxHP > 0 && x.CurrentHP > 0)) &&
                    Settings.Instance.MobList.TargetMobList.ContainsKey(x.Name)
                    select new MobInfo()
                {
                    Name        = x.Name,
                    Combatant   = x,
                    Rank        = Settings.Instance.MobList.TargetMobList[x.Name].Rank,
                    MaxDistance = Settings.Instance.MobList.TargetMobList[x.Name].MaxDistance,
                    TTSEnabled  = Settings.Instance.MobList.TargetMobList[x.Name].TTSEnabled,
                };

                // 戦闘不能者を検出する?
                if (Settings.Instance.MobList.IsEnabledDetectDeadmen)
                {
                    var deadmenInfo = Settings.Instance.MobList.GetDetectDeadmenInfo;
                    var party       = FFXIVPlugin.Instance.GetPartyList();
                    var deadmen     =
                        from x in party
                        where
                        !x.IsPlayer &&
                        x.MaxHP > 0 && x.CurrentHP <= 0
                        select new MobInfo()
                    {
                        Name        = x.NameForDisplay,
                        Combatant   = x,
                        Rank        = deadmenInfo.Rank,
                        MaxDistance = deadmenInfo.MaxDistance,
                        TTSEnabled  = deadmenInfo.TTSEnabled,
                    };

                    targets = targets.Concat(deadmen);
                }

                // 距離で絞り込む
                targets = targets.Where(x => x.Distance <= x.MaxDistance);
            });

            lock (this.TargetInfoLock)
            {
                this.targetMobList = targets.ToList();
                this.TargetInfo    = this.targetMobList.FirstOrDefault()?.Combatant;

                if (this.TargetInfo == null)
                {
                    var model = this.Model as MobListModel;
                    if (model != null &&
                        model.MobList.Any())
                    {
                        WPFHelper.BeginInvoke(model.ClearMobList);
                    }
                }
            }
        }
예제 #20
0
        protected override void GetCombatant()
        {
            lock (this.TargetInfoLock)
            {
                var now = DateTime.Now;
                if ((now - this.combatantsTimestamp).TotalMilliseconds
                    < Settings.Instance.MobList.RefreshRateMin)
                {
                    return;
                }

                this.combatantsTimestamp = now;
            }

            #region Test Mode

            // テストモード?
            if (Settings.Instance.MobList.TestMode)
            {
                var dummyTargets = new List <MobInfo>();

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:シルバーの吉田直樹",
                    Rank      = "EX",
                    Combatant = new CombatantEx()
                    {
                        ID    = 1,
                        Name  = "TEST:シルバーの吉田直樹",
                        Type  = (byte)Actor.Type.Monster,
                        MaxHP = 1,
                        PosX  = 0,
                        PosY  = 10,
                        PosZ  = 10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:イクシオン",
                    Rank      = "EX",
                    Combatant = new CombatantEx()
                    {
                        ID    = 2,
                        Name  = "TEST:イクシオン",
                        Type  = (byte)Actor.Type.Monster,
                        MaxHP = 1,
                        PosX  = 100,
                        PosY  = 100,
                        PosZ  = -10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:イクシオン",
                    Rank      = "EX",
                    Combatant = new CombatantEx()
                    {
                        ID    = 21,
                        Name  = "TEST:イクシオン",
                        Type  = (byte)Actor.Type.Monster,
                        MaxHP = 1,
                        PosX  = 100,
                        PosY  = 100,
                        PosZ  = -10,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:ソルト・アンド・ライト",
                    Rank      = "S",
                    Combatant = new CombatantEx()
                    {
                        ID    = 3,
                        Name  = "TEST:ソルト・アンド・ライト",
                        Type  = (byte)Actor.Type.Monster,
                        MaxHP = 1,
                        PosX  = 10,
                        PosY  = 0,
                        PosZ  = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:オルクス",
                    Rank      = "A",
                    Combatant = new CombatantEx()
                    {
                        ID    = 4,
                        Name  = "TEST:オルクス",
                        Type  = (byte)Actor.Type.Monster,
                        MaxHP = 1,
                        PosX  = 100,
                        PosY  = -100,
                        PosZ  = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = "TEST:宵闇のヤミニ",
                    Rank      = "B",
                    Combatant = new CombatantEx()
                    {
                        ID    = 5,
                        Name  = "TEST:宵闇のヤミニ",
                        Type  = (byte)Actor.Type.Monster,
                        MaxHP = 1,
                        PosX  = 0,
                        PosY  = -100,
                        PosZ  = 0,
                    },
                });

                dummyTargets.Add(new MobInfo()
                {
                    Name      = CombatantEx.NameToInitial("TEST:Hime Hana", ConfigBridge.Instance.PCNameStyle),
                    Rank      = "DEAD",
                    Combatant = new CombatantEx()
                    {
                        ID    = 7,
                        Name  = CombatantEx.NameToInitial("TEST:Hime Hana", ConfigBridge.Instance.PCNameStyle),
                        Type  = (byte)Actor.Type.Monster,
                        Job   = (byte)JobIDs.BLM,
                        MaxHP = 43462,
                        PosX  = -100,
                        PosY  = -100,
                        PosZ  = 0,
                    },
                });

                lock (this.TargetInfoLock)
                {
                    this.TargetInfo    = dummyTargets.First().Combatant;
                    this.targetMobList = dummyTargets;
                }

                return;
            }

            #endregion Test Mode

            if ((CombatantsManager.Instance.CombatantsMainCount + CombatantsManager.Instance.CombatantsOtherCount) <= 0)
            {
                return;
            }

            var targets    = default(IEnumerable <MobInfo>);
            var combatants = CombatantsManager.Instance.GetCombatants();

            // モブを検出する
            IEnumerable <MobInfo> GetTargetMobs()
            {
                foreach (var x in combatants)
                {
                    if (string.IsNullOrEmpty(x?.Name))
                    {
                        continue;
                    }

                    if (x.ActorType == Actor.Type.PC ||
                        x.ActorType == Actor.Type.Monster)
                    {
                        if (x.MaxHP <= 0 ||
                            (x.MaxHP > 0 && x.CurrentHP <= 0))
                        {
                            continue;
                        }
                    }

                    var targetInfo = Settings.Instance.MobList.GetTargetMobInfo(x.Name);
                    if (string.IsNullOrEmpty(targetInfo.Name))
                    {
                        continue;
                    }

                    yield return(new MobInfo()
                    {
                        Name = x.Name,
                        Combatant = x,
                        Rank = targetInfo.Rank,
                        MaxDistance = targetInfo.MaxDistance,
                        TTSEnabled = targetInfo.TTSEnabled,
                    });
                }
            }

            targets = GetTargetMobs();

            // 戦闘不能者を検出する?
            var deadmenInfo = Settings.Instance.MobList.GetDetectDeadmenInfo;
            if (!string.IsNullOrEmpty(deadmenInfo.Name))
            {
                var party   = CombatantsManager.Instance.GetPartyList();
                var deadmen =
                    from x in party
                    where
                    x != null &&
                    !x.IsPlayer &&
                    x.ActorType == Actor.Type.PC &&
                    x.MaxHP > 0 && x.CurrentHP <= 0
                    select new MobInfo()
                {
                    Name        = x.NameForDisplay,
                    Combatant   = x,
                    Rank        = deadmenInfo.Rank,
                    MaxDistance = deadmenInfo.MaxDistance,
                    TTSEnabled  = deadmenInfo.TTSEnabled,
                };

                targets = targets.Concat(deadmen);
            }

            // クエリを実行する
            targets = targets.ToArray();

            lock (this.TargetInfoLock)
            {
                this.targetMobList = targets
                                     .Where(x => x.Distance <= x.MaxDistance)
                                     .ToList();

                this.TargetInfo = this.targetMobList.FirstOrDefault()?.Combatant;

                if (this.TargetInfo == null)
                {
                    var model = this.Model as MobListModel;
                    if (model != null &&
                        model.MobList.Any())
                    {
                        WPFHelper.BeginInvoke(model.ClearMobList);
                    }
                }
            }

            if (combatants != null)
            {
                CombatantsViewModel.RefreshCombatants(combatants.ToArray());
            }
        }
예제 #21
0
        public void InitPluginCore(
            TabPage pluginScreenSpace,
            Label pluginStatusText)
        {
            // タイトルをセットする
            pluginScreenSpace.Text = "SPESPE";

            EnvironmentMigrater.Migrate();
            MasterFilePublisher.Publish();
            WPFHelper.Start();
            WPFHelper.BeginInvoke(async() =>
            {
                AppLog.LoadConfiguration(AppLog.HojoringConfig);
                this.AppLogger?.Trace(Assembly.GetExecutingAssembly().GetName().ToString() + " start.");

                try
                {
                    this.PluginStatusLabel = pluginStatusText;

                    if (!EnvironmentHelper.IsValidPluginLoadOrder())
                    {
                        pluginStatusText.Text = "Plugin Initialize Error";
                        return;
                    }

                    EnvironmentHelper.GarbageLogs();
                    EnvironmentHelper.StartActivator(() =>
                    {
                        BaseView.Instance.SetActivationStatus(false);
                        this.DeInitPluginCore();
                    });

                    Logger.Init();
                    Logger.Write("[SPESPE] Start InitPlugin");

                    // .NET FrameworkとOSのバージョンを確認する
                    if (!UpdateChecker.IsAvailableDotNet() ||
                        !UpdateChecker.IsAvailableWindows())
                    {
                        NotSupportedView.AddAndShow(pluginScreenSpace);
                        return;
                    }

                    // メイン設定ファイルを読み込む
                    Settings.Default.Load();
                    Settings.Default.ApplyRenderMode();
                    Settings.Default.StartAutoSave();

                    // 最小化する?
                    if (Settings.Default.IsMinimizeOnStart)
                    {
                        ActGlobals.oFormActMain.WindowState = FormWindowState.Minimized;
                    }

                    // HojoringのSplashを表示する
                    UpdateChecker.ShowSplash();

                    // 自身の場所を格納しておく
                    var plugin = ActGlobals.oFormActMain.PluginGetSelfData(this.PluginRoot);
                    if (plugin != null)
                    {
                        this.Location = plugin.pluginFile.DirectoryName;
                    }

                    // 設定ファイルを読み込む
                    SpellPanelTable.Instance.Load();
                    SpellTable.Instance.Load();
                    TickerTable.Instance.Load();
                    TagTable.Instance.Load();

                    // 設定ファイルをバックアップする
                    await EnvironmentHelper.BackupFilesAsync(
                        Settings.Default.FileName,
                        SpellPanelTable.Instance.DefaultFile,
                        SpellTable.Instance.DefaultFile,
                        TickerTable.Instance.DefaultFile,
                        TagTable.Instance.DefaultFile,
                        FFXIV.Framework.Config.FileName);

                    TTSDictionary.Instance.Load();

                    // 設定Panelを追加する
                    var baseView = new BaseView(pluginScreenSpace.Font);
                    pluginScreenSpace.Controls.Add(new ElementHost()
                    {
                        Child = baseView,
                        Dock  = DockStyle.Fill,
                        Font  = pluginScreenSpace.Font,
                    });

                    EnvironmentHelper.WaitInitActDone();

                    // 本体を開始する
                    PluginMainWorker.Instance.Begin();
                    TimelineController.Init();

                    // 付加情報オーバーレイを表示する
                    LPSView.ShowLPS();
                    POSView.ShowPOS();

                    this.SetSwitchVisibleButton();
                    this.PluginStatusLabel.Text = "Plugin Started";

                    Logger.Write("[SPESPE] End InitPlugin");

                    // 共通ビューを追加する
                    CommonViewHelper.Instance.AddCommonView(
                        pluginScreenSpace.Parent as TabControl);

                    this.isLoaded = true;

                    // アップデートを確認する
                    await Task.Run(() => this.Update());
                }
                catch (Exception ex)
                {
                    Logger.Write("InitPlugin error.", ex);

                    if (this.PluginStatusLabel != null)
                    {
                        this.PluginStatusLabel.Text = "Plugin Initialize Error";
                    }

                    ModernMessageBox.ShowDialog(
                        "Plugin init error !",
                        "ACT.SpecialSpellTimer",
                        System.Windows.MessageBoxButton.OK,
                        ex);
                }
            });
        }
예제 #22
0
        private void NotifyTrigger(
            TimelineTriggerModel tri)
        {
            if (string.IsNullOrEmpty(tri.Name) &&
                string.IsNullOrEmpty(tri.Text) &&
                string.IsNullOrEmpty(tri.Notice))
            {
                return;
            }

            var now = DateTime.Now;
            var log =
                $"{TLSymbol} Notice from TL. " +
                $"name={tri.Name}, text={tri.TextReplaced}, notice={tri.NoticeReplaced}";

            var notice = tri.NoticeReplaced ?? string.Empty;

            notice = TimelineExpressionsModel.ReplaceText(notice);

            if (string.Equals(notice, "auto", StringComparison.OrdinalIgnoreCase))
            {
                notice = !string.IsNullOrEmpty(tri.Text) ?
                         tri.Text :
                         tri.Name;

                if (!string.IsNullOrEmpty(notice))
                {
                    notice += "。";
                }
            }

            var isSync =
                (TimelineRazorModel.Instance?.SyncTTS ?? false) ||
                tri.NoticeSync.Value;

            RaiseLog(log);
            NotifySoundAsync(notice, tri.NoticeDevice.GetValueOrDefault(), isSync, tri.NoticeVolume, tri.NoticeOffset);

            var vnotices = tri.VisualNoticeStatements
                           .Where(x => x.Enabled.GetValueOrDefault());

            var inotices = tri.ImageNoticeStatements
                           .Where(x => x.Enabled.GetValueOrDefault());

            if (!vnotices.Any() &&
                !inotices.Any())
            {
                return;
            }

            var placeholders = TimelineManager.Instance.GetPlaceholders();

            foreach (var v in vnotices)
            {
                // ヒットしたログのシーケンスを格納する
                // ソート用
                v.LogSeq = tri.LogSeq;

                switch (v.Text)
                {
                case TimelineVisualNoticeModel.ParentTextPlaceholder:
                    v.TextToDisplay = tri.TextReplaced;
                    break;

                case TimelineVisualNoticeModel.ParentNoticePlaceholder:
                    v.TextToDisplay = tri.NoticeReplaced;
                    break;

                default:
                    v.TextToDisplay = tri.SyncMatch != null && tri.SyncMatch.Success ?
                                      tri.SyncMatch.Result(v.Text) :
                                      v.Text;
                    break;
                }

                if (string.IsNullOrEmpty(v.TextToDisplay))
                {
                    continue;
                }

                v.TextToDisplay = TimelineExpressionsModel.ReplaceText(v.TextToDisplay);

                // PC名をルールに従って置換する
                v.TextToDisplay = XIVPluginHelper.Instance.ReplacePartyMemberName(
                    v.TextToDisplay,
                    Settings.Default.PCNameInitialOnDisplayStyle);

                WPFHelper.BeginInvoke(async() =>
                {
                    if (v.Delay > 0)
                    {
                        await Task.Delay(TimeSpan.FromSeconds(v.Delay ?? 0));
                    }

                    TimelineNoticeOverlay.NoticeView?.AddNotice(v);
                    v.SetSyncToHide(placeholders);
                    v.AddSyncToHide();
                });
            }

            foreach (var i in inotices)
            {
                WPFHelper.BeginInvoke(async() =>
                {
                    if (i.Delay > 0)
                    {
                        await Task.Delay(TimeSpan.FromSeconds(i.Delay ?? 0));
                    }

                    i.StartNotice();
                    i.SetSyncToHide(placeholders);
                    i.AddSyncToHide();
                });
            }
        }
예제 #23
0
        private void NotifyActivity(
            TimelineActivityModel act)
        {
            if (string.IsNullOrEmpty(act.Name) &&
                string.IsNullOrEmpty(act.Text) &&
                string.IsNullOrEmpty(act.Notice))
            {
                act.IsNotified = true;
                return;
            }

            var now    = DateTime.Now;
            var offset = this.CurrentTime - act.Time;
            var log    =
                $"{TLSymbol} Notice from TL. " +
                $"name={act.Name}, text={act.TextReplaced}, notice={act.NoticeReplaced}, offset={offset.TotalSeconds:N1}";

            var notice = act.NoticeReplaced ?? string.Empty;

            notice = TimelineExpressionsModel.ReplaceText(notice);

            if (string.Equals(notice, "auto", StringComparison.OrdinalIgnoreCase))
            {
                notice = !string.IsNullOrEmpty(act.TextReplaced) ?
                         act.TextReplaced :
                         act.Name;

                if (offset.TotalSeconds <= -1.0)
                {
                    var offsetText = (offset.TotalSeconds * -1).ToString("N0");
                    notice += $" まで、あと{offsetText}秒";
                }

                if (!string.IsNullOrEmpty(notice))
                {
                    notice += "。";
                }
            }

            var isSync =
                (TimelineRazorModel.Instance?.SyncTTS ?? false) ||
                act.NoticeSync.Value;

            RaiseLog(log);
            NotifySoundAsync(notice, act.NoticeDevice.GetValueOrDefault(), isSync, act.NoticeVolume);

            var vnotices = act.VisualNoticeStatements
                           .Where(x => x.Enabled.GetValueOrDefault())
                           .Select(x => x.Clone());

            var inotices = act.ImageNoticeStatements
                           .Where(x => x.Enabled.GetValueOrDefault());

            if (!vnotices.Any() &&
                !inotices.Any())
            {
                return;
            }

            var placeholders = TimelineManager.Instance.GetPlaceholders();

            foreach (var v in vnotices)
            {
                // ソート用にログ番号を格納する
                // 優先順位は最後尾とする
                v.LogSeq    = long.MaxValue;
                v.Timestamp = DateTime.Now;

                switch (v.Text)
                {
                case TimelineVisualNoticeModel.ParentTextPlaceholder:
                    v.TextToDisplay = act.TextReplaced;
                    break;

                case TimelineVisualNoticeModel.ParentNoticePlaceholder:
                    v.TextToDisplay = act.NoticeReplaced;
                    break;

                default:
                    v.TextToDisplay = act.SyncMatch != null && act.SyncMatch.Success ?
                                      act.SyncMatch.Result(v.Text) :
                                      v.Text;
                    break;
                }

                if (string.IsNullOrEmpty(v.TextToDisplay))
                {
                    continue;
                }

                v.TextToDisplay = TimelineExpressionsModel.ReplaceText(v.TextToDisplay);

                // PC名をルールに従って置換する
                v.TextToDisplay = XIVPluginHelper.Instance.ReplacePartyMemberName(
                    v.TextToDisplay,
                    Settings.Default.PCNameInitialOnDisplayStyle);

                WPFHelper.BeginInvoke(async() =>
                {
                    if (v.Delay > 0)
                    {
                        await Task.Delay(TimeSpan.FromSeconds(v.Delay ?? 0));
                    }

                    TimelineNoticeOverlay.NoticeView?.AddNotice(v);
                    v.SetSyncToHide(placeholders);
                    v.AddSyncToHide();
                });
            }

            foreach (var i in inotices)
            {
                WPFHelper.BeginInvoke(async() =>
                {
                    if (i.Delay > 0)
                    {
                        await Task.Delay(TimeSpan.FromSeconds(i.Delay ?? 0));
                    }

                    i.StartNotice();
                    i.SetSyncToHide(placeholders);
                    i.AddSyncToHide();
                });
            }
        }