I'm creating a simple WYSIWYG editor for HTML in C#, and I want to implement a simple group of controls to view and manipulate the various properties of HTML form elements. I envision the properties panel to look like the one in Visual Studio:
Such that when the user clicks on an HTML element they've added they can change the text, class, id, etc. of the element. The problem is, I can't find how to make a panel that looks like this using C#. Obviously I know how to implement the dropdown list and the buttons, but the main body that actually contains the properties is like a slick version of a tree-view that I don't even know where to begin coding.
I'm not looking for someone to code this whole thing for me, but it would be great if somebody could point me to a form control that looks like the tree-view. I have tried googling around for answers but haven't had any luck. I have also tried looking at the open source project Sharp Develop which uses a similar control, but I've had considerable trouble wading through the hundreds of files of code to find the specific part of the GUI I'm focused on.
Any help on this would be greatly appreciated. Sorry if I was a tad bit vauge above, I guess what I'm really looking for is a nice form control or set of controls in C# to mimick the main body of the properties window. I've tried to be as thorough as possible, but if you have any questions leave a comment and I'll try to improve my question.
The body of that panel contains a PropertyGrid control, which you can use yourself. It's not in the Toolbox by default but you can add it.
Being horrible at the design end, I tried creating the above code and it looked horrible. I still did not figure out how to create the tabbed look and move between screens.
Any leads or help with this would appreciated... I am not looking for the entire work, but just how do I create that white space when a tab is selected with the options in them.
Any other information required, I would be happy to reply.
Thank you
PS: The problem is solved...thank you
Why don't you use Tab Control of Windows Forms? Do you need to create it yourself?
http://msdn.microsoft.com/en-us/library/4akwf92a.aspx
I have an idea for a personal project. And I know one way of accomplishing it in Windows Forms (which I no longer wish to use). Basically I could (in WinForms) just draw everything onto the screen (Form) and then when I need to switch views/states of the application, just redraw the new stuff in the old stuff's place.
But how can we have different states in WPF? Is there a "right" or "proper" way of doing this? Is something like this covered somewhere in the docs?
I'd like to do my own searching, but I have no idea what exactly to look for, and current attempts at finding the right information, so far have yielded no helpful (or even relevant) results.
Any help at all will be greatly appreciated. I am new to WPF, but have been making a lot of progress this past week!
Thank you!
P.S.:
I just thouhght of something. If the solution was to draw what is needed for one screen, and when it is time to display the next screen, just dispose of/hide everything and create/display the new stuff, then how would we get around this? Because we can't/shouldn't change XAML markup at runtime, can/should we? :/
Not sure how you drawn your views/states in WinForms (direct painting on a Graphics object?).
The closest to what you're describing is the VisualStateManager. You can use it to statically define several visual states inside a single XAML and transit between them (using a smooth animation if you want).
If what you've done was show different Forms with Show/ShowDialog(), then the equivalent would be to use different Windows and Show/Hide them.
If you just cleared/added Controls to your form, then you can do just the same in WPF. Most Controls in WPF have a Content or Children property instead of Control.Controls in Forms.
I don't know if I understand what you really want. But here are my thoughts:
You can use several Windows and Show/Hide them accordingly
You can use the Frame/Page functionality in WP (MSDN)
if you really need to you could load your XAML and remove the topmost content in your Window and replace it with the loaded content
You could use the VisualStateGroup functionality to change the appearance of your current window
I think you will be happy with the second solution
I have a WPF application, and it's slow.
It is NOT the rendering. Firstly, the rendering is quite simple, and secondly, I looked at it with WPF Performance Toolkit - nothing.
It is NOT in my own code. Firstly, the unit tests work fast, and secondly, if I replace all DataTemplates with blank ones, everything works fast.
So far, it looks like the slow part is template instantiation. That is, when you start the application, and open some complicated screen, it takes a lot of time. And by "a lot" I mean "a lot". Sometimes can be as much as 3-5 seconds - for example, when there's a datagrid with 100 rows. But when you go to another tab, and then go back to that same screen, it opens fast (as long as its viewmodel stays put).
This is very annoying not just because it's slow, but because I can't do anything about it. If I had some control over the slowness, I could, maybe, display some "opening, please wait" message or something...
Besides, when I look at some other WPF applications (most notably, ILSpy), they seem to work reasonably fast, despite the large amounts of data. This makes me believe that I'm probably doing something wrong. But I have no idea where to start.
Any ideas? Any classic mistakes? Any tips?
My exerience comes from working on the WPF mind mapping application NovaMind
A couple of months ago we completely rewrote our intermediate layer to solve the performance issues we had experienced. In a nutshell, creating our user controls seemed to be way to slow. Unfortunately I couldn't find a great way to profile the performance as neither the WPF Performance Suite nor commercial applications such as ANTS Profiler give you any detailed information on this part of the WPF process. (I asked this question back then)
We resorted to manually test our application by trial and error and removed parts of our user controls to see what exactly is the culprit.
In the end we solved the performance issues by completely rewriting our controls. We also cut down on the complexity of our visual tree dramatically. Before the rewrite, one of our most used user controls, when inspected with Snoop, consisted out of 61 different things, now there are only 3. Wherever possible we only added things to the visual tree on demand. (As you know in XAML even when you set things to Collapsed, they need to be created first).
Finally we were forced to write our own rich text rendering control as the built in RichtextBox is ridiculously slow and the visual tree of the RichtextBox is quite complex.
I don't know if this will apply to your situation but I would recommend that you investigate your user controls and see if they are complex. Maybe you have things that you could trim.
Low hanging fruits would be parts that are only rarely visible or can be created in a lazy manner. You could create these parts from code behind when necessary rather than having them in XAML. This should help you a lot.
Otherwise virtualization is your friend, if possible. In our case we couldn't do that unfortunately.
This sounds similar to a problem i was having. I posted the fix here: WPF UI Automation issue . Just posting for the benefit of searchers, as it took ages to resolve.
Following comment on link only answer, here is the crux of that post:
I did the following:
Downloaded Hotfix - - http://archive.msdn.microsoft.com/KB978520 (may not be required)
Downloaded Hotfix - - http://archive.msdn.microsoft.com/KB2484841 (definitely required even if you have Windows 7 / .NET 4)
Improved the code further (the validation was causing an excess of objects) - Why does WPF Style to show validation errors in ToolTip work for a TextBox but fails for a ComboBox?
It may be that only Number 3 was required, but it worked. Just posting here so people dont lose the days I lost in memory profilers etc.
User Control in your data template, is not completely bad idea but if you crave for performance then you should consider switching to lighter control. For example, having a UserControl just hosting a TextBox is very bad idea, as UserControl is made up of ContentControl, ContentControl hosts ContentPresenter and ContentPresenter will host TextBox so if you notice your Visual Tree, it has three new layer of UI Elements. Reducing Visual Tree will certainly improve the performance.
Most likely, I would suggest creating Custom Controls that may be a completely a new control having few dependency properties that can relate to data you want to present and you can have its own custom template in generic.xaml. Second, you can just simply derive a control from existing controls and redefine its default template in generic.xaml.
This approach will certainly work better as you will be reducing your Visual Tree, thus reducing Visual State Manager's job.
Changing theme or template will be slower then changing the element that hosts content. And let the element have the default template in its own generic resource dictionary.
Try moving all the resources up as
far as they'll go, preferably into
app.xaml
Check if you could use StaticResource
instead of dynamic ones, static ones
are alot faster
If possible, try using depedency
properties in your VMs, especially if
you have alot of them at once or if
they have alot of properties. That will keep wpf from having to do a bunch of reflection.
You mention you are using a DataGrid with, say, 100 rows. A likely culprit of your perf problems is that whatever datagrid you are using isn't doing virtualization, and so your visual tree is gigantic.
Normally, long startup time in WPF screens points to a large visual tree.
I'm not sure if you're using a datatemplate per row, or some 3rd party grid that binds columns, or what - but lets say you have 8 columns with controls. Depending on your grid/validation/etc, this could be a visual tree of 20-60 items per row. If you have a combobox, then each item in the dropdown may be created per row as well.
To fix this just takes watching the details, and taking measures as you go:
Use a virtualizing control as much as possible. This means using a virtualizingstackpanel inside list controls, and making sure your 3rd party controls do as well (many stock WPF controls do now by default)
Do not overuse UserControls, composite controls, etc. Adding depth adds time, and putting in extra visual tree depth in a datatemplate or other repeated area adds up fast.
If all else fails, show a simple screen and add controls through code to improve perceived performance
I am interested in creating my very own control from scratch. (Yes, I know...) - here's what I was thinking, I'll only choose one of the following, but depending on the complexity, I think I am going to go with a TextBox or ComboBox:
TextBox
ComboBox
FormTyper
I made the third name up. FormTyper is simply a "way" of being able to click absolutely anywhere on the Form and just start typing, and the letters/numbers etc will appear as if you were typing in a textbox. This would be my ideal new project, I would love to do this, but I haven't seen it done before, and I'm not sure how to start.
Does anyone have any advice, suggestions, or really good, in-depth (but simple :P) tutorials/articles/code I can read up on/play around with?
Any help at all will be greatly appreciated.
Thanks :)
Jase
You picked the wrong kind of control to get started with. Making your own text editor from scratch is unreasonably hard. Seemingly simple things like displaying a caret requires pinvoking obscure api functions. Calculating where to show it inside of a string is very hard.
Pick an easier one to get started with. A calendar for example. Essential skills you'll learn is how to write your own OnPaint() method to give a control a visual appearance, how to do mouse hit testing and how to pick the right kind of events and properties to make the control useful in a program.