A couple of days ago I brought up the code definition window. I mentioned what purpose it was trying to serve, how some of the developers were thinking about changing it and how I thought it could be improved. In response to that, a poster mentioned that Eclipse had a behavior that they really liked, specifically that when you held down ctrl and hovered over an identifier it would show a fragment of code showing the definition.
I can see an immediate benefit of that system over our current one in that it allows you to get similar information to the Code Definition View (CDV) without having to move your cursor from where you were working. Thus you can easily hover over a ton of variables in the block of code where you’re working and refresh your understanding of them. I decided to spike that kind of feature to see if it could be done. In order to do this I just tried to leverage our existing architecture as much as possible in order to make the amount of coding effort extremely small and so that I could get some quick results to run by you and the rest of the team as to how good a feature this was.
In order to do that I started with the fact that we already support the concept of giving you information about an identifier when you hover over it through the form of a tooltip. Normally this is pretty basic information. For a field/method we’ll show the name of the type it’s defined in and it’s signature. For a local variable we’ll show it’s type and name. For a type we’ll show if it’s a class/interface/enum/delegate. And for all of the above we’ll also show the doc comment along with it.
I couldn’t think of really relevant information to show when hovering over the name of a class (although maybe seeing the base and interface list would be useful). I also couldn’t’ think of anything useful for a property/method declaration since we already show their entire signature (although it might be useful to know if a property has a getter/setter or not). So that left me with fields, enums, and local variables. For all of those it seemed useful to show not only the type and name of the field when you hovered over it, but also and code that might have initialized it.
I.e. normally when you hover over an enum value you see something pretty basic. Given the following enum:
When you select (or hover over) the use of Yellow you would see
but now you see
This initializer expression can be arbitrarily complex, and it works just fine even with multiple variable declarations. All in all, i think it could be pretty useful like in the following case:
There are of course many ways we could improve on this. For one, i think it would be far more useful to show you the definition in context. So rather than just see the declaration and initialization, you see a few statements above and below that one. There’s a good chance that that auxiliary information will help you understand that member better. That could be a bit confusing, so it would probably be necessary to bold out the actual definition line in the tooltip so you could identify it in the ~5+’ish lines we’d be showing you (this is also something I’d like to spike). IMO, the ideal thing to do would be to pop up a tooltip which contained a perfectly rendered snippet of your code with the appropriate definition highlighted somehow (maybe by slightly adjusting the background color behind it).
The current implementation has some issues with it that would need to be addressed. Firstly, it rather blasé about how much memory it uses. For every item that you have it stores this additional initialization information so that it can be displayed as necessary. As you can imagine, the amount of these items one might have in their solution could be enormous and we need to be conscious of how much memory we use and not go overboard. If the amount of memory this consumed was a problem (on say 250 project solutions) then I’d probably move to a delayed computation mode where the initialization expression was determined when it was needed for the tooltip. But, this implementation was by far the simplest that could work and so I did it that way 🙂 If we were to move to a model where we displayed the context around the definition I’m fairly certain this would have to change as every definition we learned about would suddenly be storing a large amount of duplicated data along with it.
Also, the new display has the potential to be quite confusing in debugger related scenarios. Imagine the following code:
Now, when you’re debugging you hover and you see that text and you go “what?! How is the value 0?? Waitaminute, the watch window shows it as 5. wtfomgnojuo!!!” Other systems, like the class designer and the object browser might then call into this code to get things to display to heir user and this information might not be relevant, and might be completely nonsensical to them. Each of these issues is pretty easily solvable, but the worry is that there might be more out there that we could be unaware of.
The issue of consistency also comes into play. If we added this, it’s not clear that VB/C++/J# would as well. They might not consider it a useful feature “too much clutter”, or they might not be able to do it efficiently and don’t want it affecting their user experience.
Anyways, I’d love to hear your thoughts on this. If you like just the spiked version and would consider that a significant benefit; if you like it but really think it needs more; if you like it but think we’re going down a completely wrong path and we should be doing something else; or if you just plain don’t like it.