diff --git a/Plugins/Wox.Plugin.BrowserBookmark/Wox.Plugin.BrowserBookmark.csproj b/Plugins/Wox.Plugin.BrowserBookmark/Wox.Plugin.BrowserBookmark.csproj index b7d0690ab..413b0aec7 100644 --- a/Plugins/Wox.Plugin.BrowserBookmark/Wox.Plugin.BrowserBookmark.csproj +++ b/Plugins/Wox.Plugin.BrowserBookmark/Wox.Plugin.BrowserBookmark.csproj @@ -37,32 +37,13 @@ false - - ..\..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.dll - - - ..\..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.SqlServer.dll - - - ..\..\packages\System.Data.SQLite.Core.1.0.111.0\lib\net451\System.Data.SQLite.dll - - - ..\..\packages\System.Data.SQLite.EF6.1.0.111.0\lib\net451\System.Data.SQLite.EF6.dll - - - ..\..\packages\System.Data.SQLite.Linq.1.0.111.0\lib\net451\System.Data.SQLite.Linq.dll - - - ..\..\packages\UnidecodeSharp.1.0.0.0\lib\net35\UnidecodeSharp.dll - True - @@ -79,7 +60,6 @@ - PreserveNewest @@ -123,16 +103,19 @@ Designer - + + + 1.0.111 + + + 1.0.111 + + + 1.0.0 + + - - - - This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. - - - +
@@ -18,10 +18,5 @@ - - - - - - + \ No newline at end of file diff --git a/Plugins/Wox.Plugin.BrowserBookmark/packages.config b/Plugins/Wox.Plugin.BrowserBookmark/packages.config deleted file mode 100644 index fc01b224e..000000000 --- a/Plugins/Wox.Plugin.BrowserBookmark/packages.config +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - \ No newline at end of file diff --git a/Plugins/Wox.Plugin.Calculator/Wox.Plugin.Calculator.csproj b/Plugins/Wox.Plugin.Calculator/Wox.Plugin.Calculator.csproj index 4f7590273..c682cd19a 100644 --- a/Plugins/Wox.Plugin.Calculator/Wox.Plugin.Calculator.csproj +++ b/Plugins/Wox.Plugin.Calculator/Wox.Plugin.Calculator.csproj @@ -64,7 +64,6 @@ - PreserveNewest @@ -130,6 +129,17 @@ PreserveNewest + + + 10.3.0 + + + 1.5.0 + + + 4.0.0 + + Designer diff --git a/Plugins/Wox.Plugin.Calculator/packages.config b/Plugins/Wox.Plugin.Calculator/packages.config deleted file mode 100644 index c17f6726f..000000000 --- a/Plugins/Wox.Plugin.Calculator/packages.config +++ /dev/null @@ -1,6 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/Plugins/Wox.Plugin.Color/Wox.Plugin.Color.csproj b/Plugins/Wox.Plugin.Color/Wox.Plugin.Color.csproj index f5b1ff160..ca75ed8f3 100644 --- a/Plugins/Wox.Plugin.Color/Wox.Plugin.Color.csproj +++ b/Plugins/Wox.Plugin.Color/Wox.Plugin.Color.csproj @@ -55,7 +55,6 @@ - PreserveNewest @@ -112,6 +111,14 @@ PreserveNewest + + + 10.3.0 + + + 4.0.0 + + + + +
+ + + + + + https://github.com/Wox-launcher/Wox + + + \ No newline at end of file diff --git a/Wox/App.xaml.cs b/Wox/App.xaml.cs index 0ec1614bf..0fc1e8c95 100644 --- a/Wox/App.xaml.cs +++ b/Wox/App.xaml.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Diagnostics; using System.Threading.Tasks; using System.Timers; @@ -25,6 +25,9 @@ namespace Wox private Settings _settings; private MainViewModel _mainVM; private SettingWindowViewModel _settingsVM; + private readonly Updater _updater = new Updater(Wox.Properties.Settings.Default.GithubRepo); + private readonly Alphabet _alphabet = new Alphabet(); + private StringMatcher _stringMatcher; [STAThread] public static void Main() @@ -50,17 +53,18 @@ namespace Wox ImageLoader.Initialize(); - _settingsVM = new SettingWindowViewModel(); + _settingsVM = new SettingWindowViewModel(_updater); _settings = _settingsVM.Settings; - Alphabet.Initialize(_settings); - - StringMatcher.UserSettingSearchPrecision = _settings.QuerySearchPrecision; + _alphabet.Initialize(_settings); + _stringMatcher = new StringMatcher(_alphabet); + StringMatcher.Instance = _stringMatcher; + _stringMatcher.UserSettingSearchPrecision = _settings.QuerySearchPrecision; PluginManager.LoadPlugins(_settings.PluginSettings); _mainVM = new MainViewModel(_settings); var window = new MainWindow(_settings, _mainVM); - API = new PublicAPIInstance(_settingsVM, _mainVM); + API = new PublicAPIInstance(_settingsVM, _mainVM, _alphabet); PluginManager.InitializePlugins(API); Log.Info($"|App.OnStartup|Dependencies Info:{ErrorReporting.DependenciesInfo()}"); @@ -110,12 +114,12 @@ namespace Wox var timer = new Timer(1000 * 60 * 60 * 5); timer.Elapsed += async (s, e) => { - await Updater.UpdateApp(); + await _updater.UpdateApp(); }; timer.Start(); // check updates on startup - await Updater.UpdateApp(); + await _updater.UpdateApp(); } }); } @@ -144,10 +148,6 @@ namespace Wox private static void RegisterAppDomainExceptions() { AppDomain.CurrentDomain.UnhandledException += ErrorReporting.UnhandledExceptionHandle; - AppDomain.CurrentDomain.FirstChanceException += (_, e) => - { - Log.Exception("|App.RegisterAppDomainExceptions|First Chance Exception:", e.Exception); - }; } public void Dispose() @@ -156,13 +156,7 @@ namespace Wox // but if sessionending is not called, exit won't be called when log off / shutdown if (!_disposed) { - _mainVM.Save(); - _settingsVM.Save(); - - PluginManager.Save(); - ImageLoader.Save(); - Alphabet.Save(); - + API.SaveAppAllSettings(); _disposed = true; } } diff --git a/Wox/Converters/HighlightTextConverter.cs b/Wox/Converters/HighlightTextConverter.cs new file mode 100644 index 000000000..b7d6d0683 --- /dev/null +++ b/Wox/Converters/HighlightTextConverter.cs @@ -0,0 +1,53 @@ +using System; +using System.Collections.Generic; +using System.Globalization; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using System.Windows; +using System.Windows.Data; +using System.Windows.Documents; + +namespace Wox.Converters +{ + public class HighlightTextConverter : IMultiValueConverter + { + public object Convert(object[] value, Type targetType, object parameter, CultureInfo cultureInfo) + { + var text = value[0] as string; + var highlightData = value[1] as List; + + var textBlock = new Span(); + + if (highlightData == null || !highlightData.Any()) + { + // No highlight data, just return the text + return new Run(text); + } + + for (var i = 0; i < text.Length; i++) + { + var currentCharacter = text.Substring(i, 1); + if (this.ShouldHighlight(highlightData, i)) + { + textBlock.Inlines.Add(new Bold(new Run(currentCharacter))); + } + else + { + textBlock.Inlines.Add(new Run(currentCharacter)); + } + } + return textBlock; + } + + public object[] ConvertBack(object value, Type[] targetType, object parameter, CultureInfo culture) + { + return new[] { DependencyProperty.UnsetValue, DependencyProperty.UnsetValue }; + } + + private bool ShouldHighlight(List highlightData, int index) + { + return highlightData.Contains(index); + } + } +} diff --git a/Wox/MainWindow.xaml b/Wox/MainWindow.xaml index 7dfe8cd1e..d50411b83 100644 --- a/Wox/MainWindow.xaml +++ b/Wox/MainWindow.xaml @@ -87,4 +87,4 @@ - \ No newline at end of file + diff --git a/Wox/Properties/Settings.Designer.cs b/Wox/Properties/Settings.Designer.cs index 7a4226349..a61339f5e 100644 --- a/Wox/Properties/Settings.Designer.cs +++ b/Wox/Properties/Settings.Designer.cs @@ -12,7 +12,7 @@ namespace Wox.Properties { [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] - [global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "14.0.0.0")] + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "16.3.0.0")] internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase { private static Settings defaultInstance = ((Settings)(global::System.Configuration.ApplicationSettingsBase.Synchronized(new Settings()))); @@ -22,5 +22,14 @@ namespace Wox.Properties { return defaultInstance; } } + + [global::System.Configuration.ApplicationScopedSettingAttribute()] + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.Configuration.DefaultSettingValueAttribute("https://github.com/Wox-launcher/Wox")] + public string GithubRepo { + get { + return ((string)(this["GithubRepo"])); + } + } } } diff --git a/Wox/Properties/Settings.settings b/Wox/Properties/Settings.settings index a585a6308..1fc52390b 100644 --- a/Wox/Properties/Settings.settings +++ b/Wox/Properties/Settings.settings @@ -1,7 +1,9 @@  - - - - - + + + + + https://github.com/Wox-launcher/Wox + + \ No newline at end of file diff --git a/Wox/PublicAPIInstance.cs b/Wox/PublicAPIInstance.cs index 4bcc82530..314fc13b6 100644 --- a/Wox/PublicAPIInstance.cs +++ b/Wox/PublicAPIInstance.cs @@ -20,16 +20,17 @@ namespace Wox { private readonly SettingWindowViewModel _settingsVM; private readonly MainViewModel _mainVM; + private readonly Alphabet _alphabet; #region Constructor - public PublicAPIInstance(SettingWindowViewModel settingsVM, MainViewModel mainVM) + public PublicAPIInstance(SettingWindowViewModel settingsVM, MainViewModel mainVM, Alphabet alphabet) { _settingsVM = settingsVM; _mainVM = mainVM; + _alphabet = alphabet; GlobalHotkey.Instance.hookedKeyboardCallback += KListener_hookedKeyboardCallback; WebRequest.RegisterPrefix("data", new DataWebRequestFactory()); - } #endregion @@ -70,7 +71,7 @@ namespace Wox _settingsVM.Save(); PluginManager.Save(); ImageLoader.Save(); - Alphabet.Save(); + _alphabet.Save(); } public void ReloadAllPluginData() @@ -90,12 +91,12 @@ namespace Wox _mainVM.MainWindowVisibility = Visibility.Visible; } - public void ShowMsg(string title, string subTitle = "", string iconPath = "") + public void ShowMsg(string title, string subTitle = "", string iconPath = "", bool useMainWindowAsOwner = true) { Application.Current.Dispatcher.Invoke(() => { - var m = new Msg { Owner = Application.Current.MainWindow }; - m.Show(title, subTitle, iconPath); + var msg = useMainWindowAsOwner ? new Msg {Owner = Application.Current.MainWindow} : new Msg(); + msg.Show(title, subTitle, iconPath); }); } diff --git a/Wox/ReportWindow.xaml.cs b/Wox/ReportWindow.xaml.cs index 38509a728..ac7e986fd 100644 --- a/Wox/ReportWindow.xaml.cs +++ b/Wox/ReportWindow.xaml.cs @@ -23,7 +23,7 @@ namespace Wox private void SetException(Exception exception) { - string path = Path.Combine(Constant.DataDirectory, Log.DirectoryName, Constant.Version); + string path = Log.CurrentLogDirectory; var directory = new DirectoryInfo(path); var log = directory.GetFiles().OrderByDescending(f => f.LastWriteTime).First(); diff --git a/Wox/ResultListBox.xaml b/Wox/ResultListBox.xaml index cad02d519..dc3100e0e 100644 --- a/Wox/ResultListBox.xaml +++ b/Wox/ResultListBox.xaml @@ -4,6 +4,7 @@ xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:vm="clr-namespace:Wox.ViewModel" + xmlns:converter="clr-namespace:Wox.Converters" mc:Ignorable="d" d:DesignWidth="100" d:DesignHeight="100" d:DataContext="{d:DesignInstance vm:ResultsViewModel}" MaxHeight="{Binding MaxHeight}" @@ -30,6 +31,9 @@ + + + @@ -44,9 +48,23 @@ + Text="{Binding Result.Title}"> + + + + + + + + Grid.Row="1" x:Name="SubTitle" Text="{Binding Result.SubTitle}"> + + + + + + + diff --git a/Wox/SettingWindow.xaml b/Wox/SettingWindow.xaml index 9a5146c7e..a6f23814f 100644 --- a/Wox/SettingWindow.xaml +++ b/Wox/SettingWindow.xaml @@ -62,7 +62,7 @@ + SelectedItem="{Binding Settings.QuerySearchPrecisionString}" /> diff --git a/Wox/SettingWindow.xaml.cs b/Wox/SettingWindow.xaml.cs index c041d7ddd..67d67351e 100644 --- a/Wox/SettingWindow.xaml.cs +++ b/Wox/SettingWindow.xaml.cs @@ -260,53 +260,16 @@ namespace Wox #region Proxy private void OnTestProxyClick(object sender, RoutedEventArgs e) - { - if (string.IsNullOrEmpty(_settings.Proxy.Server)) - { - MessageBox.Show(InternationalizationManager.Instance.GetTranslation("serverCantBeEmpty")); - return; - } - if (_settings.Proxy.Port <= 0) - { - MessageBox.Show(InternationalizationManager.Instance.GetTranslation("portCantBeEmpty")); - return; - } - - HttpWebRequest request = (HttpWebRequest)WebRequest.Create(Infrastructure.Constant.Repository); - if (string.IsNullOrEmpty(_settings.Proxy.UserName) || string.IsNullOrEmpty(_settings.Proxy.Password)) - { - request.Proxy = new WebProxy(_settings.Proxy.Server, _settings.Proxy.Port); - } - else - { - request.Proxy = new WebProxy(_settings.Proxy.Server, _settings.Proxy.Port) - { - Credentials = new NetworkCredential(_settings.Proxy.UserName, _settings.Proxy.Password) - }; - } - try - { - var response = (HttpWebResponse)request.GetResponse(); - if (response.StatusCode == HttpStatusCode.OK) - { - MessageBox.Show(InternationalizationManager.Instance.GetTranslation("proxyIsCorrect")); - } - else - { - MessageBox.Show(InternationalizationManager.Instance.GetTranslation("proxyConnectFailed")); - } - } - catch - { - MessageBox.Show(InternationalizationManager.Instance.GetTranslation("proxyConnectFailed")); - } + { // TODO: change to command + var msg = _viewModel.TestProxy(); + MessageBox.Show(msg); // TODO: add message box service } #endregion private async void OnCheckUpdates(object sender, RoutedEventArgs e) { - await Updater.UpdateApp(); + _viewModel.UpdateApp(); // TODO: change to command } private void OnRequestNavigate(object sender, RequestNavigateEventArgs e) diff --git a/Wox/Settings.cs b/Wox/Settings.cs new file mode 100644 index 000000000..b45d4a5a1 --- /dev/null +++ b/Wox/Settings.cs @@ -0,0 +1,28 @@ +namespace Wox.Properties { + + + // This class allows you to handle specific events on the settings class: + // The SettingChanging event is raised before a setting's value is changed. + // The PropertyChanged event is raised after a setting's value is changed. + // The SettingsLoaded event is raised after the setting values are loaded. + // The SettingsSaving event is raised before the setting values are saved. + internal sealed partial class Settings { + + public Settings() { + // // To add event handlers for saving and changing settings, uncomment the lines below: + // + // this.SettingChanging += this.SettingChangingEventHandler; + // + // this.SettingsSaving += this.SettingsSavingEventHandler; + // + } + + private void SettingChangingEventHandler(object sender, System.Configuration.SettingChangingEventArgs e) { + // Add code to handle the SettingChangingEvent event here. + } + + private void SettingsSavingEventHandler(object sender, System.ComponentModel.CancelEventArgs e) { + // Add code to handle the SettingsSaving event here. + } + } +} diff --git a/Wox/ViewModel/MainViewModel.cs b/Wox/ViewModel/MainViewModel.cs index a7e17d9a7..bd1314a27 100644 --- a/Wox/ViewModel/MainViewModel.cs +++ b/Wox/ViewModel/MainViewModel.cs @@ -13,7 +13,6 @@ using Wox.Core.Resource; using Wox.Helper; using Wox.Infrastructure; using Wox.Infrastructure.Hotkey; -using Wox.Infrastructure.Image; using Wox.Infrastructure.Storage; using Wox.Infrastructure.UserSettings; using Wox.Plugin; @@ -25,7 +24,7 @@ namespace Wox.ViewModel { #region Private Fields - private bool _queryHasReturn; + private bool _isQueryRunning; private Query _lastQuery; private string _queryTextBeforeLeaveResults; @@ -41,7 +40,7 @@ namespace Wox.ViewModel private CancellationToken _updateToken; private bool _saved; - private Internationalization _translator = InternationalizationManager.Instance; + private readonly Internationalization _translator = InternationalizationManager.Instance; #endregion @@ -312,7 +311,7 @@ namespace Wox.ViewModel { var filtered = results.Where ( - r => StringMatcher.FuzzySearch(query, r.Title).IsSearchPrecisionScoreMet() + r => StringMatcher.FuzzySearch(query, r.Title).IsSearchPrecisionScoreMet() || StringMatcher.FuzzySearch(query, r.SubTitle).IsSearchPrecisionScoreMet() ).ToList(); ContextMenu.AddResults(filtered, id); @@ -371,63 +370,59 @@ namespace Wox.ViewModel if (!string.IsNullOrEmpty(QueryText)) { _updateSource?.Cancel(); - _updateSource = new CancellationTokenSource(); - _updateToken = _updateSource.Token; + var currentUpdateSource = new CancellationTokenSource(); + _updateSource = currentUpdateSource; + var currentCancellationToken = _updateSource.Token; + _updateToken = currentCancellationToken; ProgressBarVisibility = Visibility.Hidden; - _queryHasReturn = false; + _isQueryRunning = true; var query = PluginManager.QueryInit(QueryText.Trim()); if (query != null) { // handle the exclusiveness of plugin using action keyword - string lastKeyword = _lastQuery.ActionKeyword; - string keyword = query.ActionKeyword; - if (string.IsNullOrEmpty(lastKeyword)) - { - if (!string.IsNullOrEmpty(keyword)) - { - Results.RemoveResultsExcept(PluginManager.NonGlobalPlugins[keyword].Metadata); - } - } - else - { - if (string.IsNullOrEmpty(keyword)) - { - Results.RemoveResultsFor(PluginManager.NonGlobalPlugins[lastKeyword].Metadata); - } - else if (lastKeyword != keyword) - { - Results.RemoveResultsExcept(PluginManager.NonGlobalPlugins[keyword].Metadata); - } - } + RemoveOldQueryResults(query); _lastQuery = query; - Task.Delay(200, _updateToken).ContinueWith(_ => - { - if (query.RawQuery == _lastQuery.RawQuery && !_queryHasReturn) + Task.Delay(200, currentCancellationToken).ContinueWith(_ => + { // start the progress bar if query takes more than 200 ms and this is the current running query and it didn't finish yet + if (currentUpdateSource == _updateSource && _isQueryRunning) { ProgressBarVisibility = Visibility.Visible; } - }, _updateToken); + }, currentCancellationToken); var plugins = PluginManager.ValidPluginsForQuery(query); Task.Run(() => { - Parallel.ForEach(plugins, plugin => + // so looping will stop once it was cancelled + var parallelOptions = new ParallelOptions { CancellationToken = currentCancellationToken }; + try { - var config = _settings.PluginSettings.Plugins[plugin.Metadata.ID]; - if (!config.Disabled) + Parallel.ForEach(plugins, parallelOptions, plugin => { - var results = PluginManager.QueryForPlugin(plugin, query); - UpdateResultView(results, plugin.Metadata, query); - } - }); + var config = _settings.PluginSettings.Plugins[plugin.Metadata.ID]; + if (!config.Disabled) + { + var results = PluginManager.QueryForPlugin(plugin, query); + UpdateResultView(results, plugin.Metadata, query); + } + }); + } + catch (OperationCanceledException) + { + // nothing to do here + } + // this should happen once after all queries are done so progress bar should continue // until the end of all querying - _queryHasReturn = true; - ProgressBarVisibility = Visibility.Hidden; - }, _updateToken); + _isQueryRunning = false; + if (currentUpdateSource == _updateSource) + { // update to hidden if this is still the current query + ProgressBarVisibility = Visibility.Hidden; + } + }, currentCancellationToken); } } else @@ -437,6 +432,30 @@ namespace Wox.ViewModel } } + private void RemoveOldQueryResults(Query query) + { + string lastKeyword = _lastQuery.ActionKeyword; + string keyword = query.ActionKeyword; + if (string.IsNullOrEmpty(lastKeyword)) + { + if (!string.IsNullOrEmpty(keyword)) + { + Results.RemoveResultsExcept(PluginManager.NonGlobalPlugins[keyword].Metadata); + } + } + else + { + if (string.IsNullOrEmpty(keyword)) + { + Results.RemoveResultsFor(PluginManager.NonGlobalPlugins[lastKeyword].Metadata); + } + else if (lastKeyword != keyword) + { + Results.RemoveResultsExcept(PluginManager.NonGlobalPlugins[keyword].Metadata); + } + } + } + private Result ContextMenuTopMost(Result result) { @@ -660,4 +679,4 @@ namespace Wox.ViewModel #endregion } -} +} \ No newline at end of file diff --git a/Wox/ViewModel/RelayCommand.cs b/Wox/ViewModel/RelayCommand.cs index 3a52f3000..b1dbc551c 100644 --- a/Wox/ViewModel/RelayCommand.cs +++ b/Wox/ViewModel/RelayCommand.cs @@ -5,7 +5,6 @@ namespace Wox.ViewModel { public class RelayCommand : ICommand { - private Action _action; public RelayCommand(Action action) diff --git a/Wox/ViewModel/ResultsViewModel.cs b/Wox/ViewModel/ResultsViewModel.cs index f8197f78e..76a7ee75b 100644 --- a/Wox/ViewModel/ResultsViewModel.cs +++ b/Wox/ViewModel/ResultsViewModel.cs @@ -3,7 +3,9 @@ using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using System.Windows; +using System.Windows.Controls; using System.Windows.Data; +using System.Windows.Documents; using Wox.Infrastructure.UserSettings; using Wox.Plugin; @@ -154,14 +156,14 @@ namespace Wox.ViewModel private List NewResults(List newRawResults, string resultId) { var results = Results.ToList(); - var newResults = newRawResults.Select(r => new ResultViewModel(r)).ToList(); + var newResults = newRawResults.Select(r => new ResultViewModel(r)).ToList(); var oldResults = results.Where(r => r.Result.PluginID == resultId).ToList(); // Find the same results in A (old results) and B (new newResults) var sameResults = oldResults .Where(t1 => newResults.Any(x => x.Result.Equals(t1.Result))) .ToList(); - + // remove result of relative complement of B in A foreach (var result in oldResults.Except(sameResults)) { @@ -197,8 +199,37 @@ namespace Wox.ViewModel return results; } + #endregion + #region FormattedText Dependency Property + public static readonly DependencyProperty FormattedTextProperty = DependencyProperty.RegisterAttached( + "FormattedText", + typeof(Inline), + typeof(ResultsViewModel), + new PropertyMetadata(null, FormattedTextPropertyChanged)); + public static void SetFormattedText(DependencyObject textBlock, IList value) + { + textBlock.SetValue(FormattedTextProperty, value); + } + + public static Inline GetFormattedText(DependencyObject textBlock) + { + return (Inline)textBlock.GetValue(FormattedTextProperty); + } + + private static void FormattedTextPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) + { + var textBlock = d as TextBlock; + if (textBlock == null) return; + + var inline = (Inline)e.NewValue; + + textBlock.Inlines.Clear(); + if (inline == null) return; + + textBlock.Inlines.Add(inline); + } #endregion public class ResultCollection : ObservableCollection @@ -217,6 +248,10 @@ namespace Wox.ViewModel } } + /// + /// Update the results collection with new results, try to keep identical results + /// + /// public void Update(List newItems) { int newCount = newItems.Count; @@ -228,7 +263,7 @@ namespace Wox.ViewModel ResultViewModel oldResult = this[i]; ResultViewModel newResult = newItems[i]; if (!oldResult.Equals(newResult)) - { + { // result is not the same update it in the current index this[i] = newResult; } else if (oldResult.Result.Score != newResult.Result.Score) @@ -255,4 +290,4 @@ namespace Wox.ViewModel } } } -} +} \ No newline at end of file diff --git a/Wox/ViewModel/SettingWindowViewModel.cs b/Wox/ViewModel/SettingWindowViewModel.cs index 67b8d7af0..923e456b0 100644 --- a/Wox/ViewModel/SettingWindowViewModel.cs +++ b/Wox/ViewModel/SettingWindowViewModel.cs @@ -2,6 +2,7 @@ using System.Collections.Generic; using System.IO; using System.Linq; +using System.Net; using System.Windows; using System.Windows.Controls; using System.Windows.Media; @@ -20,10 +21,12 @@ namespace Wox.ViewModel { public class SettingWindowViewModel : BaseModel { + private readonly Updater _updater; private readonly WoxJsonStorage _storage; - public SettingWindowViewModel() + public SettingWindowViewModel(Updater updater) { + _updater = updater; _storage = new WoxJsonStorage(); Settings = _storage.Load(); Settings.PropertyChanged += (s, e) => @@ -39,6 +42,10 @@ namespace Wox.ViewModel public Settings Settings { get; set; } + public async void UpdateApp() + { + await _updater.UpdateApp(); + } public void Save() { @@ -73,7 +80,7 @@ namespace Wox.ViewModel public List QuerySearchPrecisionStrings { get - { + { var precisionStrings = new List(); var enumList = Enum.GetValues(typeof(StringMatcher.SearchPrecisionScore)).Cast().ToList(); @@ -88,6 +95,50 @@ namespace Wox.ViewModel public List Languages => _translater.LoadAvailableLanguages(); public IEnumerable MaxResultsRange => Enumerable.Range(2, 16); + public string TestProxy() + { + var proxyServer = Settings.Proxy.Server; + var proxyUserName = Settings.Proxy.UserName; + if (string.IsNullOrEmpty(proxyServer)) + { + return InternationalizationManager.Instance.GetTranslation("serverCantBeEmpty"); + } + if (Settings.Proxy.Port <= 0) + { + return InternationalizationManager.Instance.GetTranslation("portCantBeEmpty"); + } + + HttpWebRequest request = (HttpWebRequest)WebRequest.Create(_updater.GitHubRepository); + + if (string.IsNullOrEmpty(proxyUserName) || string.IsNullOrEmpty(Settings.Proxy.Password)) + { + request.Proxy = new WebProxy(proxyServer, Settings.Proxy.Port); + } + else + { + request.Proxy = new WebProxy(proxyServer, Settings.Proxy.Port) + { + Credentials = new NetworkCredential(proxyUserName, Settings.Proxy.Password) + }; + } + try + { + var response = (HttpWebResponse)request.GetResponse(); + if (response.StatusCode == HttpStatusCode.OK) + { + return InternationalizationManager.Instance.GetTranslation("proxyIsCorrect"); + } + else + { + return InternationalizationManager.Instance.GetTranslation("proxyConnectFailed"); + } + } + catch + { + return InternationalizationManager.Instance.GetTranslation("proxyConnectFailed"); + } + } + #endregion #region plugin @@ -220,7 +271,7 @@ namespace Wox.ViewModel }, new Result { - Title = $"Open Source: {Constant.Repository}", + Title = $"Open Source: {_updater.GitHubRepository}", SubTitle = "Please star it!" } }; @@ -330,8 +381,8 @@ namespace Wox.ViewModel #region about - public static string Github => Constant.Repository; - public static string ReleaseNotes => @"https://github.com/Wox-launcher/Wox/releases/latest"; + public string Github => _updater.GitHubRepository; + public string ReleaseNotes => _updater.GitHubRepository + @"/releases/latest"; public static string Version => Constant.Version; public string ActivatedTimes => string.Format(_translater.GetTranslation("about_activate_times"), Settings.ActivateTimes); #endregion diff --git a/Wox/Wox.csproj b/Wox/Wox.csproj index ef7714829..3b942ca65 100644 --- a/Wox/Wox.csproj +++ b/Wox/Wox.csproj @@ -65,72 +65,8 @@ app.manifest - - ..\packages\DeltaCompressionDotNet.1.0.0\lib\net45\DeltaCompressionDotNet.dll - True - - - ..\packages\DeltaCompressionDotNet.1.0.0\lib\net45\DeltaCompressionDotNet.MsDelta.dll - True - - - ..\packages\DeltaCompressionDotNet.1.0.0\lib\net45\DeltaCompressionDotNet.PatchApi.dll - True - - - ..\packages\squirrel.windows.1.4.0\lib\Net45\ICSharpCode.SharpZipLib.dll - True - - - ..\packages\Mono.Cecil.0.9.6.1\lib\net45\Mono.Cecil.dll - True - - - ..\packages\Mono.Cecil.0.9.6.1\lib\net45\Mono.Cecil.Mdb.dll - True - - - ..\packages\Mono.Cecil.0.9.6.1\lib\net45\Mono.Cecil.Pdb.dll - True - - - ..\packages\Mono.Cecil.0.9.6.1\lib\net45\Mono.Cecil.Rocks.dll - True - - - False - ..\packages\Newtonsoft.Json.9.0.1\lib\net45\Newtonsoft.Json.dll - - - ..\packages\NHotkey.1.2.1\lib\net20\NHotkey.dll - True - - - ..\packages\NHotkey.Wpf.1.2.1\lib\net35\NHotkey.Wpf.dll - True - - - ..\packages\NLog.4.2.0\lib\net45\NLog.dll - True - - - ..\packages\squirrel.windows.1.4.0\lib\Net45\NuGet.Squirrel.dll - True - - - ..\packages\PropertyChanged.Fody.1.51.0\lib\dotnet\PropertyChanged.dll - False - - - ..\packages\Splat.1.6.2\lib\Net45\Splat.dll - True - - - False - ..\packages\squirrel.windows.1.5.2\lib\Net45\Squirrel.dll - @@ -149,21 +85,19 @@ - - ..\packages\InputSimulator.1.0.4.0\lib\net20\WindowsInput.dll - True - Properties\SolutionAssemblyInfo.cs + ResultListBox.xaml + @@ -346,9 +280,6 @@ Designer MSBuild:Compile - - Designer - MSBuild:Compile Designer @@ -469,7 +400,44 @@ PreserveNewest - + + + 1.29.2 + runtime; build; native; contentfiles; analyzers; buildtransitive + all + + + 1.0.4 + + + 10.3.0 + + + 9.0.1 + + + 1.2.1 + + + 4.2.0 + + + 3.4.3 + runtime; build; native; contentfiles; analyzers; buildtransitive + all + + + 1.51.0 + runtime; build; native; contentfiles; analyzers; buildtransitive + all + + + 1.5.2 + + + 4.0.0 + + powershell.exe -NoProfile -ExecutionPolicy Bypass -File $(SolutionDir)Scripts\post_build.ps1 $(ConfigurationName) $(SolutionDir) @@ -484,11 +452,4 @@ - - - - This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. - - - \ No newline at end of file diff --git a/Wox/packages.config b/Wox/packages.config deleted file mode 100644 index 1b5478afe..000000000 --- a/Wox/packages.config +++ /dev/null @@ -1,18 +0,0 @@ - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/azure-pipelines.yml b/azure-pipelines.yml new file mode 100644 index 000000000..5307ec006 --- /dev/null +++ b/azure-pipelines.yml @@ -0,0 +1,34 @@ +# .NET Desktop +# Build and run tests for .NET Desktop or Windows classic desktop solutions. +# Add steps that publish symbols, save build artifacts, and more: +# https://docs.microsoft.com/azure/devops/pipelines/apps/windows/dot-net + +trigger: +- master +- dev + +pool: + vmImage: 'vs2017-win2016' #'due to windows SDK dependency for building UWP project' + +variables: + solution: '**/*.sln' + buildPlatform: 'Any CPU' + buildConfiguration: 'Release' + +steps: +- task: NuGetToolInstaller@1 + +- task: NuGetCommand@2 + inputs: + restoreSolution: '$(solution)' + +- task: VSBuild@1 + inputs: + solution: '$(solution)' + platform: '$(buildPlatform)' + configuration: '$(buildConfiguration)' + +- task: VSTest@2 + inputs: + platform: '$(buildPlatform)' + configuration: '$(buildConfiguration)'