I have a UltraGrid on my form. When it is first popluted, code sets the values of the DisplayLayout. I then save the displaylayout in a file as the original. I will then check to see if there is a second file with the users saved displaylayout and load that. This will set the display layout to the same settings the last time the user closed this form. A user can then resize columns, reorder and sort etc.
If the user right clicks on the grid a context menu will reset the display layout using the original saved displaylayout and also save this layout as the user defined layout. When the user closes the form the orignal layout file is deleted and the user defined layout file is saved.
Here's my problem. We are about to release a new version of our software and there are some new columns added to collection that is bound to the grid. The first time the user opens this form in the new release it will again save the original display layout (New fields are hidden) and then load the existing displaylayout file. However the new columns that were added in the collection are also shown because they are not part of the display layout and they are visible by default. In our case we don't want these fields to be visible. The user will have to right click and reset the layout in order hide these fields as we intended. (These new fields have sensitive information)
I tried a few different approches. I looped through the columns and set hidden = true. Then set the display layout. No luck. I then hid all the columns again and tried the displaylayout.CopyFrom method. No luck.
Here are some questions.
1. What would be the best approach to handle this.2. If we had removed a column from the collection would this blow up.3. I saved and loaded the DiplayLayout without specifiying PropertyCategories.(What is the default) What should I have done there.
Thanks in advance.
Dan
Hi Dan,
digitaldan3 said:1. What would be the best approach to handle this.
I'm assuming here that these new columns are columns that the users should never see.
What I would do is load the user's layout into an UltraGridLayout variable instead of directly into the grid. Then you can hide the columns within the Layout before applying it to the grid.
Or, you could just load the layout into the grid and THEN hide the columns.
Still another option would be to handle the InitializeLayout event of the grid and hide the columns there.
digitaldan3 said:2. If we had removed a column from the collection would this blow up.
No, it certainly shouldn't blow up.
digitaldan3 said:3. I saved and loaded the DiplayLayout without specifiying PropertyCategories.(What is the default) What should I have done there.
The default is to save everything.
Hi Mike,I hope you are doing fine, ...has been a while (which in this case is a goood thing *LG*).
I just stumbled into the same problem. I have an UltraGrid that displays quite a bunch of columns.We gave our users the oportunity to save tha layout of their grids using DisplayLayout.Save(stream) into a database. No problem at all, everything works smooth and well.
The layout is saved in the Closing event of the surrounding form and loaded in the Shown event.
From time to time the underlying datasource changes, which means that new columns are added.
When the layout is loaded and reapplied the new columns do not show up (as well as unbound columns that I added for testing).
In this case the user does not even know he/she is missing some columns.I thought about deleting their layout data from the database everytime an update is applied to the application, but this would destroy the users preferences on column width etc for all columns everytime. Indeed they are not happy with this approach ;)
Is there a way to overcome this problem?Any ideas are kindly appreciated.
best regards and have a great weekendAndy
Hi Andy,
There's no great way to do this. You might try playing around with the NewColumnLoadStyle property on the grid. Any new columns in the data source of the grid when you load the layout may get hidden, but they are still there in the grid. NewColumnLoadStyle controls how newly-added columns are handled so I think that might also handle what happens when the data source contains columns that do not exist in the layout. I could be wrong.
Another option to consider is loading the layout into an UltraGridLayout variable instead of directly into the grid. You could then bind the grid and compare the columns that exist in the loaded Layout to the columns in the grid. If there are columns in the grid that do not exist in the layout, you could store a list of those columns. Then load the layout into the grid (using grid.DisplayLayout.CopyFrom) and then you can loop through the new columns and make sure they are visible (by setting Hidden to false).
Hi Mike,
just to let you know, the approach using NewColumnLoadStyle" worked like a charm.Thanks again for your help!
I am having the same problem, however the fix has not worked for me. It works when I select the first layout but soon as I select another layout (As there is an option to select from several layouts saved) the new columns appear, is it because these columns are no longer "new columns" so now they already exist?
If I try the other option of hiding the columns not in the layout then this does get around the problem. I got it working with the following code;
Dim layout As UltraGridLayout = Nothing Dim xmlLayout as string 'Load in any grid formating or totals and update the layout name in use (byref) xmlLayout = _SQLMain.LoadProgrammeLayout(_CurrentProgrammeLayout) If xmlLayout <> "" Then ' Create a MemoryStream Dim MStream As MemoryStream = New MemoryStream
Dim WStream As New StreamWriter(MStream)
'Write the xml configuration to the stream WStream.Write(xmlLayout) WStream.Flush()
'Move back to the beginning of the stream MStream.Position = 0
ugrProgrammeView.DisplayLayout.LoadFromXml(MStream, PropertyCategories.AppearanceCollection Or PropertyCategories.Bands Or PropertyCategories.ColScrollRegions Or PropertyCategories.General Or PropertyCategories.Groups Or PropertyCategories.RowScrollRegions Or PropertyCategories.SortedColumns Or PropertyCategories.Summaries Or PropertyCategories.UnboundColumns Or PropertyCategories.ValueLists) 'Load the stream for the second layout file to compare against later. WStream.Write(xmlLayout) WStream.Flush() MStream.Position = 0 layout = New UltraGridLayout layout.LoadFromXml(MStream, PropertyCategories.AppearanceCollection Or PropertyCategories.Bands Or PropertyCategories.ColScrollRegions Or PropertyCategories.General Or PropertyCategories.Groups Or PropertyCategories.RowScrollRegions Or PropertyCategories.SortedColumns Or PropertyCategories.Summaries Or PropertyCategories.UnboundColumns Or PropertyCategories.ValueLists)
_ProgrammeLayoutLoaded = True End If
'Load the datasource ugrProgrammeView.DataSource = _SQLMain.LoadProgrammeView(gCurrentGroupScenarioId) 'Loop through and compare layouts to hide new columns, as the NewColumnLoadStyle property does not do this. If IsNothing(layout) = False Then For Each col In ugrProgrammeView.DisplayLayout.Bands(0).Columns If layout.Bands(0).Columns.Exists(col.Key) = False Then col.Hidden = True End If Next End If
Hi,
Yes, I think you are probably right. Those columns are no longer "new" and do they don't get hidden.
If you need such fine control over what happens when you load the layout, then perhaps what you could do is load the layout into a variable and modify it before loading it into the grid.
You can declare a variable of type UltraGridLayout and load the layout into it. Then you can examine the layout, bands, and columns and set properties on them, hiding whichever columns you choose. Then you use the grid.DisplayLayout.CopyFrom method to copy the layout variable into your grid.
Aye my example essentially does that, I just don't use the "CopyFrom". I simply hide the columns on the main grid that are not in the layout variable using the exists() command.