179 lines
		
	
	
		
			6.5 KiB
		
	
	
	
		
			C#
		
	
	
	
	
	
			
		
		
	
	
			179 lines
		
	
	
		
			6.5 KiB
		
	
	
	
		
			C#
		
	
	
	
	
	
using System;
 | 
						|
using System.Collections.Generic;
 | 
						|
using System.Text;
 | 
						|
using System.Drawing.Design;
 | 
						|
using System.ComponentModel;
 | 
						|
using System.Windows.Forms.Design;
 | 
						|
using System.Windows.Forms;
 | 
						|
using System.Threading;
 | 
						|
using System.Collections;
 | 
						|
 | 
						|
namespace DevComponents.DotNetBar.Design
 | 
						|
{
 | 
						|
    public class DataMembersSelector : UITypeEditor
 | 
						|
    {
 | 
						|
        #region Constructor
 | 
						|
        private CheckedListBoxSelector _ListSelector;
 | 
						|
        private BindingContext _BindingContext;
 | 
						|
        /// <summary>
 | 
						|
        /// Initializes a new instance of the DataMembersSelector class.
 | 
						|
        /// </summary>
 | 
						|
        public DataMembersSelector()
 | 
						|
        {
 | 
						|
            _ListSelector = new CheckedListBoxSelector();
 | 
						|
            _BindingContext = new BindingContext();
 | 
						|
        }
 | 
						|
        
 | 
						|
        #endregion
 | 
						|
 | 
						|
        #region Implementation
 | 
						|
        public override object EditValue(ITypeDescriptorContext context, IServiceProvider provider, object value)
 | 
						|
        {
 | 
						|
            if (context != null
 | 
						|
                && context.Instance != null
 | 
						|
                && provider != null)
 | 
						|
            {
 | 
						|
                IWindowsFormsEditorService edSvc = (IWindowsFormsEditorService)provider.GetService(typeof(IWindowsFormsEditorService));
 | 
						|
                if (edSvc != null)
 | 
						|
                {
 | 
						|
                    PropertyDescriptor descriptor = TypeDescriptor.GetProperties(context.Instance)["DataSource"];
 | 
						|
                    if (descriptor == null)
 | 
						|
                    {
 | 
						|
                        return value;
 | 
						|
                    }
 | 
						|
                    object dataSource = descriptor.GetValue(context.Instance);
 | 
						|
                    LoadDataMembers(_ListSelector, dataSource, value);
 | 
						|
 | 
						|
                    edSvc.DropDownControl(_ListSelector);
 | 
						|
 | 
						|
                    string returnValue = "";
 | 
						|
                    foreach (string item in _ListSelector.ListBox.CheckedItems)
 | 
						|
                    {
 | 
						|
                        if (returnValue.Length > 0) returnValue += ",";
 | 
						|
                        returnValue += item;
 | 
						|
                    }
 | 
						|
                    return returnValue;
 | 
						|
                }
 | 
						|
            }
 | 
						|
            return value;
 | 
						|
        }
 | 
						|
 | 
						|
        private bool IsSelected(string str,ref string[] selected)
 | 
						|
        {
 | 
						|
            string strl = str.ToLower();
 | 
						|
            for (int i = 0; i < selected.Length; i++)
 | 
						|
            {
 | 
						|
                string item = selected[i];
 | 
						|
                if (item.Trim().ToLower() == strl)
 | 
						|
                {
 | 
						|
                    selected[i] = str;
 | 
						|
                    return true;
 | 
						|
                }
 | 
						|
            }
 | 
						|
            return false;
 | 
						|
        }
 | 
						|
        private void LoadDataMembers(CheckedListBoxSelector listSelector, object dataSource, object value)
 | 
						|
        {
 | 
						|
            listSelector.ListBox.Items.Clear();
 | 
						|
            string v = value as string;
 | 
						|
            if (v == null) v = "";
 | 
						|
            string[] selected = v.Split(',');
 | 
						|
            string dataMember = string.Empty;
 | 
						|
 | 
						|
            if (dataSource is Type)
 | 
						|
            {
 | 
						|
                try
 | 
						|
                {
 | 
						|
                    BindingSource source = new BindingSource();
 | 
						|
                    source.DataSource = dataSource;
 | 
						|
                    dataSource = source.List;
 | 
						|
                }
 | 
						|
                catch (Exception exception)
 | 
						|
                {
 | 
						|
                    if (IsCriticalException(exception))
 | 
						|
                    {
 | 
						|
                        throw;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                catch
 | 
						|
                {
 | 
						|
                }
 | 
						|
            }
 | 
						|
            if (this.IsBindableDataSource(dataSource))
 | 
						|
            {
 | 
						|
                PropertyDescriptorCollection properties = GetItemProperties(dataSource, string.Empty);
 | 
						|
                if (properties == null)
 | 
						|
                    return;
 | 
						|
                for (int i = 0; i < properties.Count; i++)
 | 
						|
                {
 | 
						|
                    PropertyDescriptor property = properties[i];
 | 
						|
                    if (this.IsBindableDataMember(property))
 | 
						|
                    {
 | 
						|
                        string str = string.IsNullOrEmpty(dataMember) ? property.Name : (dataMember + "." + property.Name);
 | 
						|
                        _ListSelector.ListBox.Items.Add(str, IsSelected(str,ref selected));
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                if (selected.Length > 1)
 | 
						|
                {
 | 
						|
                    for (int i = 0; i < selected.Length; i++)
 | 
						|
                    {
 | 
						|
                        string s1 = selected[i];
 | 
						|
                        int i1 = _ListSelector.ListBox.Items.IndexOf(s1);
 | 
						|
                        _ListSelector.ListBox.Items.RemoveAt(i1);
 | 
						|
                        _ListSelector.ListBox.Items.Insert(i, s1);
 | 
						|
                        _ListSelector.ListBox.SetItemChecked(i, true);
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        private bool IsBindableDataMember(PropertyDescriptor property)
 | 
						|
        {
 | 
						|
            if (!typeof(byte[]).IsAssignableFrom(property.PropertyType))
 | 
						|
            {
 | 
						|
                ListBindableAttribute attribute = (ListBindableAttribute)property.Attributes[typeof(ListBindableAttribute)];
 | 
						|
                if ((attribute != null) && !attribute.ListBindable)
 | 
						|
                {
 | 
						|
                    return false;
 | 
						|
                }
 | 
						|
            }
 | 
						|
            return true;
 | 
						|
        }
 | 
						|
        private PropertyDescriptorCollection GetItemProperties(object dataSource, string dataMember)
 | 
						|
        {
 | 
						|
            CurrencyManager manager = (CurrencyManager)_BindingContext[dataSource, dataMember];
 | 
						|
            if (manager != null)
 | 
						|
            {
 | 
						|
                return manager.GetItemProperties();
 | 
						|
            }
 | 
						|
            return null;
 | 
						|
        }
 | 
						|
        private bool IsBindableDataSource(object dataSource)
 | 
						|
        {
 | 
						|
            if ((!(dataSource is IListSource) && !(dataSource is IList)) && !(dataSource is Array))
 | 
						|
            {
 | 
						|
                return false;
 | 
						|
            }
 | 
						|
            ListBindableAttribute attribute = (ListBindableAttribute)TypeDescriptor.GetAttributes(dataSource)[typeof(ListBindableAttribute)];
 | 
						|
            if ((attribute != null) && !attribute.ListBindable)
 | 
						|
            {
 | 
						|
                return false;
 | 
						|
            }
 | 
						|
            return true;
 | 
						|
        }
 | 
						|
        private static bool IsCriticalException(Exception ex)
 | 
						|
        {
 | 
						|
            return (((((ex is NullReferenceException) || (ex is StackOverflowException)) || ((ex is OutOfMemoryException) ||
 | 
						|
                (ex is ThreadAbortException))) || ((ex is ExecutionEngineException) ||
 | 
						|
                (ex is IndexOutOfRangeException))) || (ex is AccessViolationException));
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        public override UITypeEditorEditStyle GetEditStyle(ITypeDescriptorContext context)
 | 
						|
        {
 | 
						|
            return UITypeEditorEditStyle.DropDown;
 | 
						|
        }
 | 
						|
        #endregion
 | 
						|
    }
 | 
						|
}
 |