Skip to content
This repository has been archived by the owner on May 5, 2020. It is now read-only.

Commit

Permalink
2.1.3.0
Browse files Browse the repository at this point in the history
  • Loading branch information
Nho Quy Dinh committed Jun 12, 2019
1 parent fbdc6b7 commit 203fd36
Show file tree
Hide file tree
Showing 27 changed files with 443 additions and 69 deletions.
9 changes: 8 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,12 +1,19 @@
# Changelog

## 2.1.3.0
- Fixed a crash causing EarTrumpet disappear on startup
- Fixed various potential leaks
- Added a help dialog to assist when EarTrumpet can't start due to broken fonts

## 2.1.2.0
- Fixed icon handle leak that caused a crash
- Fixed hotkeys not being properly unregistered
- Fixed arrow keys changing the default device volume
- Fixed High Contrast theme colors
- Fixed settings window covering the Taskbar when maximized
- Tray icon should remain in place after updates going forward
- Tray and app icons will now scale correctly
- Tray icon supports scrolling without opening the flyout
- Removed unwanted metadata from telemetry

## 2.1.1.0
Expand All @@ -28,7 +35,7 @@
- Additional bugfixes

## 2.0.8.0
- Changed grouping behavior to key off app install paths vice executable name
- Changed grouping behavior to key off app install path vs. executable name
- Disabled flyout window blur when not visible to ensure it doesn't appear in task switcher
- Fixed an issue where the Enhancements tab was missing in playback devices dialog
- Fixed an issue where the flyout was too tall when the taskbar is configured to auto-hide
Expand Down
2 changes: 1 addition & 1 deletion EarTrumpet.Package/Package.appxmanifest
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<Package xmlns="http://schemas.microsoft.com/appx/manifest/foundation/windows10" xmlns:mp="http://schemas.microsoft.com/appx/2014/phone/manifest" xmlns:uap="http://schemas.microsoft.com/appx/manifest/uap/windows10" xmlns:rescap="http://schemas.microsoft.com/appx/manifest/foundation/windows10/restrictedcapabilities" xmlns:desktop="http://schemas.microsoft.com/appx/manifest/desktop/windows10" IgnorableNamespaces="uap mp rescap desktop">
<Identity Name="40459File-New-Project.EarTrumpet" ProcessorArchitecture="x86" Publisher="CN=6099D0EF-9374-47ED-BDFE-A82136831235" Version="2.1.2.0" />
<Identity Name="40459File-New-Project.EarTrumpet" ProcessorArchitecture="x86" Publisher="CN=6099D0EF-9374-47ED-BDFE-A82136831235" Version="2.1.3.0" />
<Properties>
<DisplayName>EarTrumpet</DisplayName>
<PublisherDisplayName>File-New-Project</PublisherDisplayName>
Expand Down
6 changes: 3 additions & 3 deletions EarTrumpet/App.xaml
Original file line number Diff line number Diff line change
Expand Up @@ -1583,7 +1583,7 @@
<Grid>
<Grid MaxWidth="420"
MaxHeight="500"
Margin="20"
Margin="20,6,20,20"
HorizontalAlignment="Center"
VerticalAlignment="Center">
<Grid.RowDefinitions>
Expand Down Expand Up @@ -1618,7 +1618,7 @@

<TextBlock Grid.Row="2"
Grid.Column="0"
Margin="0,20,0,0"
Margin="0,20,6,0"
HorizontalAlignment="Left"
VerticalAlignment="Center">
<Hyperlink Command="{Binding LearnMore}">
Expand All @@ -1627,7 +1627,7 @@
</TextBlock>
<Button Grid.Row="2"
Grid.Column="1"
Width="160"
MinWidth="160"
Margin="0,20,0,0"
HorizontalAlignment="Right"
VerticalAlignment="Bottom"
Expand Down
41 changes: 37 additions & 4 deletions EarTrumpet/App.xaml.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading;
using System.Windows;
using System.Windows.Input;

Expand Down Expand Up @@ -38,7 +39,17 @@ private void OnAppStartup(object sender, StartupEventArgs e)
if (SingleInstanceAppMutex.TakeExclusivity())
{
Exit += (_, __) => SingleInstanceAppMutex.ReleaseExclusivity();
ContinueStartup();

try
{
ContinueStartup();
}
catch (Exception ex) when (ex.StackTrace.Contains(
"MS.Internal.Text.TextInterface.FontFamily.GetFirstMatchingFont"))
{
ErrorReporter.LogWarning(ex);
OnCriticalFontLoadFailure();
}
}
else
{
Expand Down Expand Up @@ -77,7 +88,7 @@ private void CreateTrayExperience()
{
if (_settings.UseLegacyIcon)
{
icon.Dispose();
icon?.Dispose();
icon = IconHelper.LoadIconForTaskbar(SystemSettings.IsSystemLightTheme ? $"{AssetBaseUri}Application.ico" : $"{AssetBaseUri}Tray.ico");
}

Expand Down Expand Up @@ -136,6 +147,28 @@ private void DisplayFirstRunExperience()
}
}

private void OnCriticalFontLoadFailure()
{
Trace.WriteLine($"App OnCriticalFontLoadFailure");

new Thread(() =>
{
if (MessageBox.Show(
EarTrumpet.Properties.Resources.CriticalFailureFontLookupHelpText,
EarTrumpet.Properties.Resources.CriticalFailureDialogHeaderText,
MessageBoxButton.OKCancel,
MessageBoxImage.Error,
MessageBoxResult.OK) == MessageBoxResult.OK)
{
Trace.WriteLine($"App OnCriticalFontLoadFailure OK");
ProcessHelper.StartNoThrow("https://eartrumpet.app/jmp/fixfonts");
}
Environment.Exit(0);
}).Start();

Thread.CurrentThread.Suspend();
}

private IEnumerable<ContextMenuItem> GetTrayContextMenuItems()
{
var ret = new List<ContextMenuItem>(PlaybackDevicesViewModel.AllDevices.OrderBy(x => x.DisplayName).Select(dev => new ContextMenuItem
Expand Down Expand Up @@ -211,8 +244,8 @@ private Window CreateSettingsExperience()
{
new EarTrumpetShortcutsPageViewModel(_settings),
new EarTrumpetLegacySettingsPageViewModel(_settings),
new EarTrumpetAboutPageViewModel(() => _errorReporter.DisplayDiagnosticData(AddonManager.GetDiagnosticInfo()))
}.ToList());
new EarTrumpetAboutPageViewModel(() => _errorReporter.DisplayDiagnosticData())
});

var allCategories = new List<SettingsCategoryViewModel>();
allCategories.Add(defaultCategory);
Expand Down
2 changes: 1 addition & 1 deletion EarTrumpet/Assets/DevVersion.txt
Original file line number Diff line number Diff line change
@@ -1 +1 @@
2.1.2.0
2.1.3.0
2 changes: 2 additions & 0 deletions EarTrumpet/DataModel/ProcessWatcherService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,8 @@ private static void EnsureWatcherThreadRunning()
// We don't expect WAIT_FAILED here since we did a test WaitForSingleObject on each handle before ingestion.
case Kernel32.WAIT_FAILED:
Debug.Assert(false);
// Avoid creating an infintite loop if we end up with a bad handle causing WAIT_FAILED.
Thread.Sleep(TimeSpan.FromSeconds(5));
break;
case Kernel32.WAIT_TIMEOUT:
// Go again
Expand Down
4 changes: 2 additions & 2 deletions EarTrumpet/Diagnosis/ErrorReporter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -29,9 +29,9 @@ public ErrorReporter()
}
}

public void DisplayDiagnosticData(string addons)
public void DisplayDiagnosticData()
{
LocalDataExporter.DumpAndShowData(_listener.GetLogText(), addons);
LocalDataExporter.DumpAndShowData(_listener.GetLogText());
}

public static void LogWarning(Exception ex) => s_instance.LogWarningInstance(ex);
Expand Down
4 changes: 2 additions & 2 deletions EarTrumpet/Diagnosis/LocalDataExporter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,15 +13,15 @@ namespace EarTrumpet.Diagnosis
{
public class LocalDataExporter
{
public static void DumpAndShowData(string logText, string addons)
public static void DumpAndShowData(string logText)
{
var ret = new StringBuilder();
ret.AppendLine(DumpDevices(WindowsAudioFactory.Create(AudioDeviceKind.Playback)));
ret.AppendLine(DumpDevices(WindowsAudioFactory.Create(AudioDeviceKind.Recording)));
Populate(ret, SnapshotData.App);
Populate(ret, SnapshotData.Device);
Populate(ret, SnapshotData.AppSettings);
ret.AppendLine($"Addons: {addons}");
Populate(ret, SnapshotData.LocalOnly);
ret.AppendLine();
ret.AppendLine(logText);

Expand Down
16 changes: 16 additions & 0 deletions EarTrumpet/Diagnosis/SnapshotData.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
using EarTrumpet.DataModel;
using EarTrumpet.Extensibility.Hosting;
using EarTrumpet.Extensions;
using EarTrumpet.Interop;
using EarTrumpet.Interop.Helpers;
using System;
using System.Collections.Generic;
using System.Globalization;
Expand Down Expand Up @@ -70,5 +73,18 @@ public static Dictionary<string, Func<object>> AppSettings
};
}
}

public static Dictionary<string, Func<object>> LocalOnly
{
get
{
return new Dictionary<string, Func<object>>
{
{ "systemDpi", () => User32.GetDpiForSystem() },
{ "taskbarDpi", () => WindowsTaskbar.Dpi },
{ "addons", () => AddonManager.GetDiagnosticInfo() },
};
}
}
}
}
2 changes: 1 addition & 1 deletion EarTrumpet/EarTrumpet.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@
<Reference Include="System.Xml" />
<Reference Include="Windows, Version=255.255.255.255, Culture=neutral, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion>
<HintPath>..\..\Program Files (x86)\Windows Kits\10\UnionMetadata\Windows.winmd</HintPath>
<HintPath>..\..\..\..\Program Files (x86)\Windows Kits\10\UnionMetadata\Windows.winmd</HintPath>
</Reference>
<Reference Include="WindowsBase" />
<Reference Include="PresentationCore" />
Expand Down
6 changes: 3 additions & 3 deletions EarTrumpet/Extensibility/Hosting/AddonManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,14 @@ public static void Load()
}
}

Host.AppLifecycleItems.ToList().ForEachNoThrow(x => x.OnApplicationLifecycleEvent(ApplicationLifecycleEvent.Startup));
Host.AppLifecycleItems.ToList().ForEachNoThrow(x => x.OnApplicationLifecycleEvent(ApplicationLifecycleEvent.Startup2));
Host.AppLifecycleItems.ForEachNoThrow(x => x.OnApplicationLifecycleEvent(ApplicationLifecycleEvent.Startup));
Host.AppLifecycleItems.ForEachNoThrow(x => x.OnApplicationLifecycleEvent(ApplicationLifecycleEvent.Startup2));
}

public static void Shutdown()
{
Trace.WriteLine($"AddonManager Shutdown");
Host.AppLifecycleItems.ToList().ForEachNoThrow(x => x.OnApplicationLifecycleEvent(ApplicationLifecycleEvent.Shutdown));
Host.AppLifecycleItems.ForEachNoThrow(x => x.OnApplicationLifecycleEvent(ApplicationLifecycleEvent.Shutdown));
}

public static AddonInfo FindAddonInfoForObject(object addonObject)
Expand Down
2 changes: 1 addition & 1 deletion EarTrumpet/Extensions/IEnumerableExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ public static HashSet<T> ToSet<T>(this IEnumerable<T> collection)
return ret;
}

public static void ForEachNoThrow<T>(this List<T> list, Action<T> action)
public static void ForEachNoThrow<T>(this IEnumerable<T> list, Action<T> action)
{
foreach (var item in list)
{
Expand Down
28 changes: 1 addition & 27 deletions EarTrumpet/Extensions/IconExtensions.cs
Original file line number Diff line number Diff line change
@@ -1,36 +1,10 @@
using EarTrumpet.Interop;
using System;
using System.Drawing;
using System.Drawing;
using System.Reflection;
using System.Windows;
using System.Windows.Interop;
using System.Windows.Media;
using System.Windows.Media.Imaging;

namespace EarTrumpet.Extensions
{
public static class IconExtensions
{
public static ImageSource ToImageSource(this Icon icon)
{
var bitmap = icon.ToBitmap();
var hBitmap = bitmap.GetHbitmap();
ImageSource bitmapSource;
try
{
bitmapSource = Imaging.CreateBitmapSourceFromHBitmap(
hBitmap,
IntPtr.Zero,
Int32Rect.Empty,
BitmapSizeOptions.FromEmptyOptions());
}
finally
{
Gdi32.DeleteObject(hBitmap);
}
return bitmapSource;
}

public static Icon AsDisposableIcon(this Icon icon)
{
// System.Drawing.Icon does not expose a method to declare
Expand Down
20 changes: 11 additions & 9 deletions EarTrumpet/Interop/Helpers/IconHelper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -33,16 +33,18 @@ public static Icon LoadIconForTaskbar(string path)

public static Icon LoadIconResource(string path, int iconOrdinal, int cx, int cy)
{
var hModule = Kernel32.LoadLibraryEx(path, IntPtr.Zero, Kernel32.LoadLibraryFlags.LOAD_LIBRARY_AS_DATAFILE | Kernel32.LoadLibraryFlags.LOAD_LIBRARY_AS_IMAGE_RESOURCE);
var groupResInfo = Kernel32.FindResourceW(hModule, new IntPtr(iconOrdinal), Kernel32.RT_GROUP_ICON);
var groupResData = Kernel32.LockResource(Kernel32.LoadResource(hModule, groupResInfo));
var iconId = User32.LookupIconIdFromDirectoryEx(groupResData, true, cx, cy, User32.LoadImageFlags.LR_DEFAULTCOLOR);
using (var hModule = Kernel32.LoadLibraryEx(path, IntPtr.Zero, Kernel32.LoadLibraryFlags.LOAD_LIBRARY_AS_DATAFILE | Kernel32.LoadLibraryFlags.LOAD_LIBRARY_AS_IMAGE_RESOURCE))
{
var groupResInfo = Kernel32.FindResourceW(hModule, new IntPtr(iconOrdinal), Kernel32.RT_GROUP_ICON);
var groupResData = Kernel32.LockResource(Kernel32.LoadResource(hModule, groupResInfo));
var iconId = User32.LookupIconIdFromDirectoryEx(groupResData, true, cx, cy, User32.LoadImageFlags.LR_DEFAULTCOLOR);

var iconResInfo = Kernel32.FindResourceW(hModule, new IntPtr(iconId), Kernel32.RT_ICON);
var iconResData = Kernel32.LockResource(Kernel32.LoadResource(hModule, iconResInfo));
var iconResSize = Kernel32.SizeofResource(hModule, iconResInfo);
var iconHandle = User32.CreateIconFromResourceEx(iconResData, iconResSize, true, User32.IconCursorVersion.Default, cx, cy, User32.LoadImageFlags.LR_DEFAULTCOLOR);
return Icon.FromHandle(iconHandle).AsDisposableIcon();
var iconResInfo = Kernel32.FindResourceW(hModule, new IntPtr(iconId), Kernel32.RT_ICON);
var iconResData = Kernel32.LockResource(Kernel32.LoadResource(hModule, iconResInfo));
var iconResSize = Kernel32.SizeofResource(hModule, iconResInfo);
var iconHandle = User32.CreateIconFromResourceEx(iconResData, iconResSize, true, User32.IconCursorVersion.Default, cx, cy, User32.LoadImageFlags.LR_DEFAULTCOLOR);
return Icon.FromHandle(iconHandle).AsDisposableIcon();
}
}

public static Icon ColorIcon(Icon originalIcon, double fillPercent, System.Windows.Media.Color newColor)
Expand Down
2 changes: 1 addition & 1 deletion EarTrumpet/Interop/SndVolSSO.cs
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ public static bool SystemIconsAreAvailable()
}
catch (Exception ex)
{
Trace.WriteLine($"SndVolSSO VerifySystemIconsAreAvailable Failed: {ex}");
Trace.WriteLine($"SndVolSSO SystemIconsAreAvailable Failed: {ex}");
return false;
}
}
Expand Down
3 changes: 3 additions & 0 deletions EarTrumpet/Interop/User32.cs
Original file line number Diff line number Diff line change
Expand Up @@ -280,6 +280,9 @@ public static extern int SetWindowLong(
[DllImport("user32.dll", PreserveSig = true)]
public static extern uint GetDpiForWindow(IntPtr hWnd);

[DllImport("user32.dll", PreserveSig = true)]
public static extern uint GetDpiForSystem();

public enum SystemMetrics : int
{
// ...
Expand Down
4 changes: 2 additions & 2 deletions EarTrumpet/Properties/AssemblyInfo.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
[assembly: AssemblyCopyright("")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
[assembly: AssemblyVersion("2.1.2.0")]
[assembly: AssemblyFileVersion("2.1.2.0")]
[assembly: AssemblyVersion("2.1.3.0")]
[assembly: AssemblyFileVersion("2.1.3.0")]
[assembly: ComVisible(false)]
[assembly: ThemeInfo(ResourceDictionaryLocation.None, ResourceDictionaryLocation.SourceAssembly)]
20 changes: 20 additions & 0 deletions EarTrumpet/Properties/Resources.Designer.cs

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

8 changes: 8 additions & 0 deletions EarTrumpet/Properties/Resources.resx
Original file line number Diff line number Diff line change
Expand Up @@ -279,4 +279,12 @@
<data name="WelcomeDialogHeaderText" xml:space="preserve">
<value>Welcome to EarTrumpet</value>
</data>
<data name="CriticalFailureDialogHeaderText" xml:space="preserve">
<value>EarTrumpet couldn't start</value>
</data>
<data name="CriticalFailureFontLookupHelpText" xml:space="preserve">
<value>A broken font on your system is preventing EarTrumpet from starting.

Open [https://eartrumpet.app/jmp/fixfonts] now?</value>
</data>
</root>
Loading

0 comments on commit 203fd36

Please sign in to comment.