The official source of product insight from the Visual Studio Engineering Team
As mentioned in the previous performance post on Typing and Editing we would follow with a post on the improvements to Visual Studio 2012 from enhancements in the Toolbox. I would like to introduce Duke Kamstra and Chuck England from two teams in Visual Studio to describe to you the work done to improve responsiveness via the Toolbox.
Visual Studio is packed with awesome rapid application development features. Sometimes getting all of these great features comes at a price. Producing Intellisense, red squiggles, smart rename, refactoring, etc. can require quite a bit of work. As features have become more versatile, and solutions have grown in size and complexity, we’ve seen that the additional workload can cause the UI to become slow to respond, repaint, or even hang. In Visual Studio 2012, we wanted to improve this experience. In today’s blog post, we will discuss one of the features, the toolbox, and the performance enhancements we have made.
In previous blog posts on performance we mentioned PerfWaston. The Toolbox is one of the features that generated a lot of hits. Armed with this data we designed several test scenarios. We profiled these scenarios using solutions provided by customers as well as ones we created to simulate large, complex solutions.
We learned several things analyzing the performance traces:
To help explain what we changed to improve toolbox performance, it may help to first describe how the toolbox works. At a high-level, the toolbox works in conjunction with a designer to filter the list of all known visual components to a list that is contextually relevant for the loaded designer. So, for example, if you are working in the Windows Forms designer, you see Windows Forms controls, and when working in the WPF designer, you see WPF controls.
The list is built from two distinct types of visual components. First, there are the items that are registered on the machine. These are items that are supplied with Visual Studio out of the box or installed by the user from a 3rd party vendor. The toolbox builds a cached list of these components and makes that list available to the designer. The designer then filters them as appropriate for its needs.
Second, there are user components that are defined in user projects. These are the custom components like user controls, datasets, etc. that you define. For these components, the designer itself is responsible for searching through the built solution’s output and adding them to the toolbox.
The big distinction between these two types is that the registered components are static and seldom change, whereas user components may change often as you update the code in your solution.
For user components, the basic discovery process consists of iterating through all of the build outputs for the solution to locate potential controls that are available for use in the designers. This is performed through a reflection-like process to find the controls. We learned through our performance traces that this “discovery” of user controls is proportionately expensive to the size and complexity of your solution.
While the general mechanism of updating the list of user components was common across most of the designers in the product, each designer had to be specifically investigated to understand the opportunities to improve performance. While there are many designers in the product (e.g. Workflow, UML modeling, DSL (Domain Specific Languages), WCF, DataSet), most are based on one of three common base implementations (WinForms, WebForms, and WPF/XAML). For each of these base implementations, we saw that the largest performance opportunities existed when a user was performing one of the following operations:
To improve the performance in these scenarios, we followed a few basic principles.
The first principle we followed was to stop doing work we did not have to do. It seems to go without saying, but life is rarely that simple. Just because you have established a simple and viable design at one point in time does not mean it will stay that way. This is where performance tuning is required.
One such case for the toolbox is the choice on when the work is performed. If you have a designer open and you have the Toolbox open, then we presume you want to interact with the Toolbox and the design surface. So, we make sure that all the visual components in the toolbox are up to date and relevant.
But what if you never open a designer? What if you have a designer open, but the toolbox window itself is closed? In these cases, we found that we were still making sure that the toolbox stayed up to date. As a result of our tuning work, we have eliminated this work until we see that you have an open designer and the Toolbox is visible.
Another tuning opportunity was found in designers’ code that ensured the toolbox is always up to date. After a designer searches for new or changed visual components, the toolbox window is updated with the results. In Visual Studio 2010, several designers accomplished this by removing everything and then adding all of the newly discovered items in bulk. In many cases, the items may not have changed much if at all. Our analysis showed this to be very inefficient, requiring considerable work and UI repainting. To improve, we only add or remove visual components from the Toolbox that have changed since the last update.
A second principle we applied was to remove work from the UI thread. When long running work occurs on the UI thread, Visual Studio can’t respond to messages from the operating system to repaint the window or to process user input such as mouse clicks or typing. In contrast work that occurs asynchronously on a background thread does not prevent the UI thread from processing messages. This is how we ensure a responsive UI.
The performance traces identified several cases where work for toolbox was being performed on the UI thread. One example was the work that is performed by designers to discover the custom components in the solution.
After we applied these principles, we compared the before and after of some common scenarios with the toolbox and a designer open. The chart below shows the performance gains that we made based on all of the tuning and targeted performance changes that we made over the course of Visual Studio 2012. (Yes, these are % gains over previous times.)
Note that these numbers are against a set of internal benchmark solutions. Different solutions may see different results. The typical margin of error for these test cases is +/-5%.
Load Solution with Toolbox and Designer Open
Load Solution with Toolbox Open
Open Designer with Toolbox Open
Change Build Configuration with Toolbox Open
Rebuild with Toolbox Open
Incremental build with Toolbox Open
Close Solution with Toolbox Open
Remember the ~30 seconds of unresponsiveness I mentioned when closing a large solution in Visual Studio 2010 SP1? Our tuning reduced this time in our test case down to ~700ms.
But the numbers are only part of the story. To see the impact, you really have to see it for yourself. You can pick up the latest pre-release version of Visual Studio 2012 here. For those of you who have tried the RC, feel free share your impressions on its overall performance in the comments section, on our UserVoice Site, or you can report new issues to us using the Visual Studio 11 Feedback Tool. If you regularly work with a large number of custom components, in Visual Studio 2012 you will find that it is now much more responsive and you can almost immediately get to work.
Chuck England – Program Manager, Visual Studio
Short Bio: Chuck England is a Program Manager who currently works on core architectural and performance related improvements in Visual Studio. He previously worked to help deliver the Project System and MSBuild which shipped in Visual Studio 2010 / .NET 4.0 and now in the upcoming Visual Studio 2012 / .NET 4.5 releases. Chuck has an extensive history in development with a little over 30 years as an architect and developer in various software industries prior to joining Microsoft in 2008.
Duke Kamstra – Senior Program Manager, Visual Studio
Short Bio: Duke has been at Microsoft 8 years, working on various parts of Visual Studio for the last 5 years. His current role is driving performance improvements across the Visual Studio product line.
We hope these and the other improvements we’ve made Visual Studio 2012 RC are providing you additional productivity gains and making your development experience a great one. Please help us continue to improve through your feedback and suggestions! I greatly appreciate you taking the time to read and comment on these posts and as always I appreciate your continued support of Visual Studio.
Director of Engineering
The biggest problem I have with the Toolbox is that was almost useless in most cases (especially when it's empty), but accidentally hovering over it would block the UI for something like ten seconds.
This seems to be fixed in VS 2012.
Great news!! Good job, guys. Now all that's left is adding back support for XP.
So MS is suddenly thinking about performance improvement after 10 year of VS.Net release? What were you guys doing all these past years when user scramming on performance improvements?
You need to show absolute times here, not percent. For example, if one "test" was 80% faster than old, but was only a blink of an eye (say) anyway, who cares? If in another "test" it was -3%, and long, an often used, then that trumps any other "test" by a mile. We aren't dummies, you know. Well, considering Windows 8, I think you do.
BTW, I've opened the toolbox only for SL/WP/XAML. Dreadful experience for sure, so it's a good place to look at, but compared to editing XAML, my God! that is like going to hell and being eaten alive by some brimstone-wallowing beast. How that is allowed to persist I will never understand. I am a dummy, after all.
That is good to know that you have made improvements in this area, as the toolbox of old was such a pig it was too painful to use. That being said, I think a lot of folks have learned to avoid the toolbox altogether because of its performance issues. Let's just hope they get the message and give it another shot.
@Per Snickety - It is difficult to convey how an experience will feel through numbers alone. I'd encourage you to download and try the VS2012 RC release, and let us know what you think.
Regarding your experience editing XAML files, the best way to help us is to share specific feedback with the team. If you have feedback about general performance scenarios using the XAML editor, please vote on this UserVoice item, and share details in the comments:
If you are running into specific issues, the Visual Studio Feedback Tool mentioned in this post has a mechanism that will allow you to quickly collect and submit performance traces. Submitting a trace with the tool is one of the easiest ways to provide actionable feedback to the team about performance delays you are encountering. You can download the tool from here: go.microsoft.com/fwlink
I don't use XAML anymore. When I have to do it, I do it all in code now. Better that way anyway because the designer (which makes the raw XAML) is nothing more than a glorified dialog editor: no way to have overlapping controls (and make sense of them). This and so many things are easier in code.
But when I did use it, and the .xaml more more than trivial in size, it was bad. Very, very bad.
Not sure why you'd focus on this now given the decline in use of WebForms, WinForms and WPF/XAML. As an aside, anyone who builds web pages by dragging and dropping controls from the toolbox deserves to be shot.
Never though it was a worry, but none the less, good job :)
Great to hear! Looking forward to testing these in VS2012!
Will it finally be possible after all this years to reliably use a Control in the forms designer that is defined in the same project?
Thanks for the update. This was an essential fix for those of use that develop on multiple platforms.
Have to ask how the toolbox was ever thought to be production ready in VS2010. Adding more than a few controls makes the Visual Studio performance awful.
Can 64-bit control library be added into the toolbox now?
Yay! A performance improvement instead of a "design" one. Excellent news and focus.
Better late than never, but why we should wait 10 years to have the toolbox rendering out of the Main thread?