Link to home
Start Free TrialLog in
Avatar of Richard Payne
Richard PayneFlag for Bulgaria

asked on

C#, XML to datagridvew for data load, edits and then save back (serialize and deserialize)

Based on earlier discussion, the datagridview would be better solution than listbox since it display member and associated data.

I have setup the datagridview and bind it which works fine.

The question is
(1) Would I benefit using Dataset to manage the data, if so why?, I do not need to sort or copy but need to make data member name visable as in datagridview.
(2) Once the data is modified within datagridview, I then click a button to save it (serialize), what code needed to do that?
(3)  A demo code would be very useful.
Avatar of it_saige
it_saige
Flag of United States of America image

A dataset is probably overkill for your needs right now.  In reality, datasets are more beneficial when dealing with multiple tables and relationships between them.  With your current data model, I wouldn't make it more complex than needed.  Perhaps something like:

Form1.cs -
using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Reflection;
using System.Windows.Forms;
using System.Xml.Serialization;

namespace EE_Q28741920
{
	public partial class Form1 : Form
	{
		List<ConfigurationX> configurations;

		public Form1()
		{
			InitializeComponent();

			if (File.Exists("Configurations.xml"))
			{
				configurations = DeserializeFromFile<List<ConfigurationX>>("Configurations.xml");
			}
			else
			{
				if (configurations == null)
				{
					configurations = new List<ConfigurationX>();
					for (int i = 0; i < 10; i++)
						configurations.Add(new ConfigurationX() { CompanyID = (uint)i, CompanyString = string.Format("ZMDI{0}", i) });
				}
				SerializeToFile<List<ConfigurationX>>("Configurations.xml");
			}
		}

		private void OnLoad(object sender, EventArgs e)
		{
			bindingSource1.DataSource = configurations;
			dataGridView1.DataSource = bindingSource1;
		}

		T DeserializeFromFile<T>(string fileName) where T : class
		{
			if (typeof(T).IsSerializable)
			{
				using (var stream = new FileStream(fileName, FileMode.Open, FileAccess.Read))
				{
					XmlSerializer serializer = new XmlSerializer(typeof(T));
					return (T)serializer.Deserialize(stream);
				}
			}
			return default(T);
		}

		void SerializeToFile<T>(string fileName) where T : class
		{
			if (typeof(T).IsSerializable)
			{
				if (File.Exists("Configurations.xml"))
					File.Delete("Configurations.xml");

				using (var stream = new FileStream(fileName, FileMode.CreateNew, FileAccess.ReadWrite))
				{
					XmlSerializer serializer = new XmlSerializer(typeof(T));
					serializer.Serialize(stream, configurations);
				}
			}
		}

		private void OnClosing(object sender, FormClosingEventArgs e)
		{
			SerializeToFile<List<ConfigurationX>>("Configurations.xml");
		}
	}

	[Serializable]
	public class ConfigurationX
	{
		public uint CompanyID { get; set; }
		public string CompanyString { get; set; }
		public uint Test1 { get; set; }
		public uint Test2 { get; set; }
		public uint Test3 { get; set; }

		public ConfigurationX()
		{
			// Leave blank, do not install default data here.
		}

		public static ConfigurationX Default()
		{
			return new ConfigurationX() { CompanyID = 10, CompanyString = "ZMDI", Test1 = 9678, Test2 = 34453, Test3 = 12981 };
		}
	}

	class SortableBindingList<T> : BindingList<T>
	{
		private bool IsSorted;
		private ListSortDirection SortDirection;
		private PropertyDescriptor SortProperty;

		protected override void ApplySortCore(PropertyDescriptor property, ListSortDirection direction)
		{
			var items = Items as List<T>;
			if (items == null)
				IsSorted = false;
			else
			{
				var comparer = new PropertyCompare<T>(property.Name, direction);
				items.Sort(comparer);
				IsSorted = true;
				SortDirection = direction;
				SortProperty = property;
			}
			base.ApplySortCore(property, direction);
		}

		protected override bool IsSortedCore { get { return IsSorted; } }
		protected override void RemoveSortCore() { IsSorted = false; }
		protected override ListSortDirection SortDirectionCore { get { return SortDirection; } }
		protected override PropertyDescriptor SortPropertyCore { get { return SortProperty; } }
		protected override bool SupportsSortingCore { get { return true; } }

		public SortableBindingList() { ;}
		public SortableBindingList(ICollection<T> source) : base(source as List<T>) { ;}
	}

	class PropertyCompare<T> : IComparer<T>
	{
		private PropertyInfo PropertyInfo;
		private ListSortDirection SortDirection;

		protected internal PropertyCompare(string property, ListSortDirection direction)
		{
			PropertyInfo = typeof(T).GetProperty(property);
			SortDirection = direction;
		}

		public int Compare(T x, T y)
		{
			return (SortDirection.Equals(ListSortDirection.Ascending)) ?
				Comparer.Default.Compare(PropertyInfo.GetValue(x, null), PropertyInfo.GetValue(y, null)) :
				Comparer.Default.Compare(PropertyInfo.GetValue(y, null), PropertyInfo.GetValue(x, null));
		}
	}
}

Open in new window

Form1.Designer.cs -
namespace EE_Q28741920
{
	partial class Form1
	{
		/// <summary>
		/// Required designer variable.
		/// </summary>
		private System.ComponentModel.IContainer components = null;

		/// <summary>
		/// Clean up any resources being used.
		/// </summary>
		/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
		protected override void Dispose(bool disposing)
		{
			if (disposing && (components != null))
			{
				components.Dispose();
			}
			base.Dispose(disposing);
		}

		#region Windows Form Designer generated code

		/// <summary>
		/// Required method for Designer support - do not modify
		/// the contents of this method with the code editor.
		/// </summary>
		private void InitializeComponent()
		{
			this.components = new System.ComponentModel.Container();
			this.dataGridView1 = new System.Windows.Forms.DataGridView();
			this.bindingSource1 = new System.Windows.Forms.BindingSource(this.components);
			((System.ComponentModel.ISupportInitialize)(this.dataGridView1)).BeginInit();
			((System.ComponentModel.ISupportInitialize)(this.bindingSource1)).BeginInit();
			this.SuspendLayout();
			// 
			// dataGridView1
			// 
			this.dataGridView1.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
			this.dataGridView1.Dock = System.Windows.Forms.DockStyle.Fill;
			this.dataGridView1.Location = new System.Drawing.Point(0, 0);
			this.dataGridView1.Name = "dataGridView1";
			this.dataGridView1.RowHeadersVisible = false;
			this.dataGridView1.Size = new System.Drawing.Size(530, 295);
			this.dataGridView1.TabIndex = 0;
			// 
			// Form1
			// 
			this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
			this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
			this.ClientSize = new System.Drawing.Size(530, 295);
			this.Controls.Add(this.dataGridView1);
			this.Name = "Form1";
			this.Text = "Form1";
			this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.OnClosing);
			this.Load += new System.EventHandler(this.OnLoad);
			((System.ComponentModel.ISupportInitialize)(this.dataGridView1)).EndInit();
			((System.ComponentModel.ISupportInitialize)(this.bindingSource1)).EndInit();
			this.ResumeLayout(false);

		}

		#endregion

		private System.Windows.Forms.DataGridView dataGridView1;
		private System.Windows.Forms.BindingSource bindingSource1;
	}
}

Open in new window

Which produces the following output -User generated imageUser generated imageAfter we close the form the changes are automatically saved to the Xml file:
<?xml version="1.0"?>
<ArrayOfConfigurationX xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <ConfigurationX>
    <CompanyID>0</CompanyID>
    <CompanyString>ZMDI0</CompanyString>
    <Test1>12</Test1>
    <Test2>0</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>1</CompanyID>
    <CompanyString>ZMDI1</CompanyString>
    <Test1>0</Test1>
    <Test2>12</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>2</CompanyID>
    <CompanyString>ZMDI2</CompanyString>
    <Test1>0</Test1>
    <Test2>0</Test2>
    <Test3>12</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>3</CompanyID>
    <CompanyString>ZMDI3</CompanyString>
    <Test1>12</Test1>
    <Test2>0</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>4</CompanyID>
    <CompanyString>ZMDI4</CompanyString>
    <Test1>0</Test1>
    <Test2>12</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>5</CompanyID>
    <CompanyString>ZMDI5</CompanyString>
    <Test1>0</Test1>
    <Test2>0</Test2>
    <Test3>12</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>6</CompanyID>
    <CompanyString>ZMDI6</CompanyString>
    <Test1>12</Test1>
    <Test2>0</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>7</CompanyID>
    <CompanyString>ZMDI7</CompanyString>
    <Test1>0</Test1>
    <Test2>12</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>8</CompanyID>
    <CompanyString>ZMDI8</CompanyString>
    <Test1>0</Test1>
    <Test2>0</Test2>
    <Test3>12</Test3>
  </ConfigurationX>
  <ConfigurationX>
    <CompanyID>9</CompanyID>
    <CompanyString>ZMDI9</CompanyString>
    <Test1>12</Test1>
    <Test2>0</Test2>
    <Test3>0</Test3>
  </ConfigurationX>
</ArrayOfConfigurationX>

Open in new window

-saige-
ASKER CERTIFIED SOLUTION
Avatar of it_saige
it_saige
Flag of United States of America image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of Richard Payne

ASKER

Well done....I take it from there with much thank!