All*_*ech 8 intellisense visual-studio-extensions visual-studio-2012
我正在创建自己的IntelliSense Presenter,因为Visual Studio2012支持更改主题,所以我希望在更改主题时可以自动更改演示者的背景颜色.有没有办法跟踪主题更改事件,或获取Visual Studio的当前颜色主题?
Mat*_*tze 13
是的,这是可能的.我必须用我的一个扩展解决一个类似的问题...当前的主题存储在Windows注册表中; 所以我实现了以下实用程序类.
public enum VsTheme
{
Unknown = 0,
Light,
Dark,
Blue
}
public class ThemeUtil
{
private static readonly IDictionary<string, VsTheme> Themes = new Dictionary<string, VsTheme>()
{
{ "de3dbbcd-f642-433c-8353-8f1df4370aba", VsTheme.Light },
{ "1ded0138-47ce-435e-84ef-9ec1f439b749", VsTheme.Dark },
{ "a4d6a176-b948-4b29-8c66-53c97a1ed7d0", VsTheme.Blue }
};
public static VsTheme GetCurrentTheme()
{
string themeId = GetThemeId();
if (string.IsNullOrWhiteSpace(themeId) == false)
{
VsTheme theme;
if (Themes.TryGetValue(themeId, out theme))
{
return theme;
}
}
return VsTheme.Unknown;
}
public static string GetThemeId()
{
const string CategoryName = "General";
const string ThemePropertyName = "CurrentTheme";
string keyName = string.Format(@"Software\Microsoft\VisualStudio\11.0\{0}", CategoryName);
using (RegistryKey key = Registry.CurrentUser.OpenSubKey(keyName))
{
if (key != null)
{
return (string)key.GetValue(ThemePropertyName, string.Empty);
}
}
return null;
}
}
Run Code Online (Sandbox Code Playgroud)
好的; 这只是帮助确定当前的设置...听主题改变通知有点棘手.加载包后,必须通过DTE获取IVsShell实例; 一旦有了这个对象,就可以使用AdviceBroadcastMessages方法来订阅事件通知.您必须提供一个类型实现IVsBroadcastMessageEvents接口的对象...
我不想发布整个实现,但以下几行可能会说明关键场景......
class VsBroadcastMessageEvents : IVsBroadcastMessageEvent
{
int IVsBroadcastMessageEvent.OnBroadcastMessage(uint msg, IntPtr wParam, IntPtr lParam)
{
const uint WM_SYSCOLORCHANGE = 0x15;
if (msg == WM_SYSCOLORCHANGE)
{
// obtain current theme from the Registry and update any UI...
}
}
}
Run Code Online (Sandbox Code Playgroud)
考虑在该类型上实现IDisposable,以便在卸载包时能够取消订阅事件源.
这就是我订阅事件通知的方式......
class ShellService
{
private readonly IVsShell shell;
private bool advised;
public ShellService(IVsShell shellInstance)
{
this.shell = shellInstance;
}
public void AdviseBroadcastMessages(IVsBroadcastMessageEvents broadcastMessageEvents, out uint cookie)
{
cookie = 0;
try
{
int r = this.shell.AdviseBroadcastMessages(broadcastMessageEvents, out cookie);
this.advised = (r == VSConstants.S_OK);
}
catch (COMException) { }
catch (InvalidComObjectException) { }
}
public void UnadviseBroadcastMessages(uint cookie)
{
...
}
}
Run Code Online (Sandbox Code Playgroud)
保留cookie参数的值; 你需要它才能成功取消订阅.
希望有所帮助( - :
Jon*_*n Z 11
只是想放一个更新以防其他人出现.. @Matze和@Frank完全正确..但是在VS 2015中他们添加了一种简单的方法来检测主题变化.因此,您需要包含PlatformUI,您才能获得超级简单的事件
using Microsoft.VisualStudio.PlatformUI;
....
//Then you get an event
VSColorTheme.ThemeChanged += VSColorTheme_ThemeChanged;
Run Code Online (Sandbox Code Playgroud)
你应该确保你的控制是一次性的,这样你就可以取消订阅活动......
奖金!
它还可以让您轻松访问颜色..即使用户已将其更改为默认值..所以您可以在设置颜色时执行此类操作
var defaultBackground = VSColorTheme.GetThemedColor(EnvironmentColors.ToolWindowBackgroundColorKey);
var defaultForeground = VSColorTheme.GetThemedColor(EnvironmentColors.ToolWindowTextColorKey);
Run Code Online (Sandbox Code Playgroud)
对于VS 2015,这已经发生了变化,解决方案@Matze仍然可以运行,但您需要更新GetThemeId()函数来检查版本,如果它是14.0(VS2015),请查看注册表中的其他位置.存储值的方式也发生了变化,它仍然是一个字符串,但现在包含由'*'分隔的其他值.主题guid是列表中的最后一个值.
if (version == "14.0")
{
string keyName = string.Format(@"Software\Microsoft\VisualStudio\{0}\ApplicationPrivateSettings\Microsoft\VisualStudio", version);
using (RegistryKey key = Registry.CurrentUser.OpenSubKey(keyName))
{
if (key != null)
{
var keyText = (string)key.GetValue("ColorTheme", string.Empty);
if (!string.IsNullOrEmpty(keyText))
{
var keyTextValues = keyText.Split('*');
if (keyTextValues.Length > 2)
{
return keyTextValues[2];
}
}
}
}
return null;
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1699 次 |
| 最近记录: |