Не удается получить NotifyIcon для загрузки ресурса с высоким DPI для масштабирования DPI>= 150%
Мое приложение поддерживает DPI, вот полный манифест:
<?xml version="1.0" encoding="utf-8"?>
<asmv1:assembly xmlns:asmv1="urn:schemas-microsoft-com:asm.v1"
manifestVersion="1.0">
<assemblyIdentity name="SlackUI"
type="win32"
version="1.0.0.0" />
<asmv3:application xmlns:asmv3="urn:schemas-microsoft-com:asm.v3">
<asmv3:windowsSettings xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">
<dpiAware>true</dpiAware>
</asmv3:windowsSettings>
</asmv3:application>
</asmv1:assembly>
И я устанавливаю свой NotifyIcon
Свойство icon вроде этого:
notifyIcon.Icon = new Icon(Program.Settings.Data.WhiteNotificationIcon ?
Properties.Resources.NotifyWhite : Properties.Resources.NotifyColor, SystemInformation.SmallIconSize)
Однако это не работает для масштабирования DPI, равного или превышающего 150% в моей системе Windows 8.1. Когда он установлен на 100% SystemInformation.SmallIconSize
сообщает размер 16x16 (правильный), когда он составляет 125%, он сообщает размер 20x20 (правильный), при этом выше, например, 150%, он должен сообщать размер 24x24, но вместо этого сообщает 16x16 и загружает неправильное разрешение из моего файла значков.
Читая следующую статью ( http://blog.quppa.net/2011/01/07/small-icon-size-dpi-in-windows/), я узнаю, что...
И WPF, и WinForms обернуты вокруг функции Win32 GetSystemMetrics, принимая аргументы SM_CXSMICON (малая ширина значка) и SM_CYSMICON (малая высота значка).
Это означает, что, вероятно, нет необходимости звонить GetSystemMetrics
себя, верно?
Любая идея о том, как я могу решить это?
PS: я говорю о приложении с открытым исходным кодом, которое я разрабатываю, поэтому, если вы хотите поближе взглянуть на полный исходный код, вы можете сделать это здесь.
1 ответ
Сильный намек на то, что ваш манифест на самом деле не выполняет свою работу
Это не. Из вашего файла github SlackUI/SlackUI.csproj:
<ItemGroup>
<None Include="app.manifest">
<SubType>Designer</SubType>
</None>
</ItemGroup>
Как это должно выглядеть:
<PropertyGroup>
<ApplicationManifest>app.manifest</ApplicationManifest>
</PropertyGroup>
Обратите внимание на весьма специфический <ApplicationManifest>
элемент, необходимый, чтобы MSBuild знал, что это должен быть манифест для исполняемого файла. Я проверил вашу версию, вставив ее в файл.csproj, собрав, а затем, используя File + Open + File, выберите файл.exe из каталога bin/Debug. Открыл узел RT_MANIFEST и дважды щелкнул ресурс #1. Компилятор автоматически генерирует компилятор по умолчанию, а не модифицированный из файла app.manifest.
Вот почему это не работает. У меня нет фантастической теории, как это произошло, может быть, вы добавили это вручную. Чтобы исправить это, щелкните правой кнопкой мыши app.manifest в окне обозревателя решений и удалите его. Теперь используйте "Проект"> "Добавить новый элемент"> "Основные"> "Файл манифеста приложения". Вставьте изменения снова.