예제 #1
0
		void Populate(object callbacks, object o, RootElement root)
		{
			MemberInfo last_radio_index = null;
			var members = o.GetType().GetMembers(BindingFlags.DeclaredOnly | BindingFlags.Public |
												 BindingFlags.NonPublic | BindingFlags.Instance);

			Section section = null;

			foreach (var mi in members)
			{
				Type mType = GetTypeForMember(mi);

				if (mType == null)
					continue;

				string caption = null;
				object[] attrs = mi.GetCustomAttributes(false);
				bool skip = false;
				foreach (var attr in attrs)
				{
					if (attr is SkipAttribute)
						skip = true;
					if (attr is CaptionAttribute)
						caption = ((CaptionAttribute)attr).Caption;
					else if (attr is SectionAttribute)
					{
						if (section != null)
							root.Add(section);
						var sa = attr as SectionAttribute;
						section = new Section(sa.Caption, sa.Footer);
					}
				}
				if (skip)
					continue;

				if (caption == null)
					caption = MakeCaption(mi.Name);

				if (section == null)
					section = new Section();

				Element element = null;
				
				if (mType == typeof(string)) {
					PasswordAttribute pa = null;
					AlignmentAttribute align = null;
					EntryAttribute ea = null;
					object html = null;
					EventHandler invoke = null;
					bool multi = false;

					foreach (object attr in attrs) {
						if (attr is PasswordAttribute)
							pa = attr as PasswordAttribute;
						else if (attr is EntryAttribute)
							ea = attr as EntryAttribute;
						else if (attr is MultilineAttribute)
							multi = true;
						else if (attr is HtmlAttribute)
							html = attr;
						else if (attr is AlignmentAttribute)
							align = attr as AlignmentAttribute;

						if (attr is OnTapAttribute) {
							string mname = ((OnTapAttribute)attr).Method;

							if (callbacks == null) {
								throw new Exception("Your class contains [OnTap] attributes, but you passed a null object for `context' in the constructor");
							}

							var method = callbacks.GetType().GetMethod(mname);
							if (method == null)
								throw new Exception("Did not find method " + mname);
							invoke = delegate {
								 method.Invoke(method.IsStatic ? null : callbacks, new object[0]);
							 };
						}
					}

					string value = (string)GetValue(mi, o);
					if (pa != null)
						element = new EntryElement(caption, value) { Hint = pa.Placeholder, Password = true };
					else if (ea != null)
						element = new EntryElement(caption, value) { Hint = ea.Placeholder };
					else if (multi)
						element = new MultilineElement(caption, value);
					else if (html != null)
						element = new HtmlElement(caption, value);
					else
					{
						var selement = new StringElement(caption, value);
						element = selement;

						if (align != null)
							selement.Alignment = align.Alignment;
					}

					if (invoke != null)
					{
						//                        ((StringElement)element).Click += invoke;
					}
				}
				else if (mType == typeof(float))
				{
					var floatElement = new FloatElement(null, null, (int)GetValue(mi, o));
					floatElement.Caption = caption;
					element = floatElement;

					foreach (object attr in attrs)
					{
						if (attr is RangeAttribute)
						{
							var ra = attr as RangeAttribute;
							floatElement.MinValue = ra.Low;
							floatElement.MaxValue = ra.High;
							floatElement.ShowCaption = ra.ShowCaption;
						}
					}
				}
				else if (mType == typeof(bool))
				{
					bool checkbox = false;
					foreach (object attr in attrs)
					{
						if (attr is CheckboxAttribute)
							checkbox = true;
					}

					if (checkbox)
						element = new CheckboxElement(caption, (bool)GetValue(mi, o));
					else
						element = new BooleanElement(caption, (bool)GetValue(mi, o));
				}
				else if (mType == typeof(DateTime))
				{
					var dateTime = (DateTime)GetValue(mi, o);
					bool asDate = false, asTime = false;

					foreach (object attr in attrs)
					{
						if (attr is DateAttribute)
							asDate = true;
						else if (attr is TimeAttribute)
							asTime = true;
					}

					if (asDate)
						element = new DateElement(caption, dateTime);
					else if (asTime)
						element = new TimeElement(caption, dateTime);
					else
						element = new DateTimeElement(caption, dateTime);
				}
				else if (mType.IsEnum)
				{
					var csection = new Section();
					ulong evalue = Convert.ToUInt64(GetValue(mi, o), null);
					int idx = 0;
					int selected = 0;

					foreach (var fi in mType.GetFields(BindingFlags.Public | BindingFlags.Static))
					{
						ulong v = Convert.ToUInt64(GetValue(fi, null));

						if (v == evalue)
							selected = idx;

						csection.Add(new RadioElement(MakeCaption(fi.Name)));
						idx++;
					}

					element = new RootElement(caption, new RadioGroup(null, selected)) { csection };
				}
				else if (mType == typeof(ImageView))
				{
					element = new ImageElement(null); // (ImageView)GetValue(mi, o));
				}
				else if (typeof(System.Collections.IEnumerable).IsAssignableFrom(mType))
				{
					var csection = new Section();
					int count = 0;

					if (last_radio_index == null)
						throw new Exception("IEnumerable found, but no previous int found");
					foreach (var e in (IEnumerable)GetValue(mi, o))
					{
						csection.Add(new RadioElement(e.ToString()));
						count++;
					}
					int selected = (int)GetValue(last_radio_index, o);
					if (selected >= count || selected < 0)
						selected = 0;
					element = new RootElement(caption, new MemberRadioGroup(null, selected, last_radio_index)) { csection };
					last_radio_index = null;
				}
				else if (typeof(int) == mType)
				{
					foreach (object attr in attrs)
					{
						if (attr is RadioSelectionAttribute)
						{
							last_radio_index = mi;
							break;
						}
					}
				}
				else
				{
					var nested = GetValue(mi, o);
					if (nested != null)
					{
						var newRoot = new RootElement(caption);
						Populate(callbacks, nested, newRoot);
						element = newRoot;
					}
				}

				if (element == null)
					continue;

				section.Add(element);
				mappings[element] = new MemberAndInstance(mi, o);
			}
			root.Add(section);
		}
예제 #2
0
		//
		// Creates one of the various StringElement classes, based on the
		// properties set.   It tries to load the most memory efficient one
		// StringElement, if not, it fallsback to MultilineStringElement or
		// StyledStringElement
		//
		static Element LoadString (JsonObject json, object data)
		{
			string value = null;
			string caption = value;
			string background = null;
			NSAction ontap = null;
			NSAction onaccessorytap = null;
			int? lines = null;
			UITableViewCellAccessory? accessory = null;
			UILineBreakMode? linebreakmode = null;
			UITextAlignment? alignment = null;
			UIColor textcolor = null, detailcolor = null;
			UIFont font = null;
			UIFont detailfont = null;
			UITableViewCellStyle style = UITableViewCellStyle.Value1;

			foreach (var kv in json){
				string kvalue = (string) kv.Value;
				switch (kv.Key){
				case "caption":
					caption = kvalue;
					break;
				case "value":
					value = kvalue;
					break;
				case "background":	
					background = kvalue;
					break;
				case "style":
					style = ToCellStyle (kvalue);
					break;
				case "ontap": case "onaccessorytap":
					string sontap = kvalue;
					int p = sontap.LastIndexOf ('.');
					if (p == -1)
						break;
					NSAction d = delegate {
						string cname = sontap.Substring (0, p);
						string mname = sontap.Substring (p+1);
						foreach (var a in AppDomain.CurrentDomain.GetAssemblies ()){
							Type type = a.GetType (cname);
						
							if (type != null){
								var mi = type.GetMethod (mname, BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic);
								if (mi != null)
									mi.Invoke (null, new object [] { data });
								break;
							}
						}
					};
					if (kv.Key == "ontap")
						ontap = d;
					else
						onaccessorytap = d;
					break;
				case "lines":
					int res;
					if (int.TryParse (kvalue, out res))
						lines = res;
					break;
				case "accessory":
					accessory = ToAccessory (kvalue);
					break;
				case "textcolor":
					textcolor = ParseColor (kvalue);
					break;
				case "linebreak":
					linebreakmode = ToLinebreakMode (kvalue);
					break;
				case "font":
					font = ToFont (kvalue);
					break;
				case "subtitle":
					value = kvalue;
					style = UITableViewCellStyle.Subtitle;
					break;
				case "detailfont":
					detailfont = ToFont (kvalue);
					break;
				case "alignment":
					alignment = ToAlignment (kvalue);
					break;
				case "detailcolor":
					detailcolor = ParseColor (kvalue);
					break;
				case "type":
					break;
				default:
					Console.WriteLine ("Unknown attribute: '{0}'", kv.Key);
					break;
				}
			}
			if (caption == null)
				caption = "";
			if (font != null || style != UITableViewCellStyle.Value1 || detailfont != null || linebreakmode.HasValue || textcolor != null || accessory.HasValue || onaccessorytap != null || background != null || detailcolor != null){
				StyledStringElement styled;
				
				if (lines.HasValue){
					styled = new StyledMultilineElement (caption, value, style);
					styled.Lines = lines.Value;
				} else {
					styled = new StyledStringElement (caption, value, style);
				}
				if (ontap != null)
					styled.Tapped += ontap;
				if (onaccessorytap != null)
					styled.AccessoryTapped += onaccessorytap;
				if (font != null)
					styled.Font = font;
				if (detailfont != null)
					styled.SubtitleFont = detailfont;
				if (detailcolor != null)
					styled.DetailColor = detailcolor;
				if (textcolor != null)
					styled.TextColor = textcolor;
				if (accessory.HasValue)
					styled.Accessory = accessory.Value;
				if (linebreakmode.HasValue)
					styled.LineBreakMode = linebreakmode.Value;
				if (background != null){
					if (background.Length > 1 && background [0] == '#')
						styled.BackgroundColor = ParseColor (background);
					else
						styled.BackgroundUri = new Uri (background);
				}
				if (alignment.HasValue)
					styled.Alignment = alignment.Value;
				return styled;
			} else {
				StringElement se;
				if (lines == 0)
					se = new MultilineElement (caption, value);
				else
					se = new StringElement (caption, value);
				if (alignment.HasValue)
					se.Alignment = alignment.Value;
				if (ontap != null)
					se.Tapped += ontap;
				return se;
			}
		}
예제 #3
0
        void Populate(object callbacks, object o, RootElement root)
        {
            MemberInfo last_radio_index = null;
            var        members          = o.GetType().GetMembers(BindingFlags.DeclaredOnly | BindingFlags.Public |
                                                                 BindingFlags.NonPublic | BindingFlags.Instance);

            Section section = null;

            foreach (var mi in members)
            {
                Type mType = GetTypeForMember(mi);

                if (mType == null)
                {
                    continue;
                }

                string    caption = null;
                object [] attrs   = mi.GetCustomAttributes(false);
                bool      skip    = false;
                foreach (var attr in attrs)
                {
                    if (attr is SkipAttribute || attr is System.Runtime.CompilerServices.CompilerGeneratedAttribute)
                    {
                        skip = true;
                    }
                    else if (attr is CaptionAttribute)
                    {
                        caption = ((CaptionAttribute)attr).Caption;
                    }
                    else if (attr is SectionAttribute)
                    {
                        if (section != null)
                        {
                            root.Add(section);
                        }
                        var sa = attr as SectionAttribute;
                        section = new Section(sa.Caption, sa.Footer);
                    }
                }
                if (skip)
                {
                    continue;
                }

                if (caption == null)
                {
                    caption = MakeCaption(mi.Name);
                }

                if (section == null)
                {
                    section = new Section();
                }

                Element element = null;
                if (mType == typeof(string))
                {
                    PasswordAttribute  pa     = null;
                    AlignmentAttribute align  = null;
                    EntryAttribute     ea     = null;
                    object             html   = null;
                    Action             invoke = null;
                    bool multi = false;

                    foreach (object attr in attrs)
                    {
                        if (attr is PasswordAttribute)
                        {
                            pa = attr as PasswordAttribute;
                        }
                        else if (attr is EntryAttribute)
                        {
                            ea = attr as EntryAttribute;
                        }
                        else if (attr is MultilineAttribute)
                        {
                            multi = true;
                        }
                        else if (attr is HtmlAttribute)
                        {
                            html = attr;
                        }
                        else if (attr is AlignmentAttribute)
                        {
                            align = attr as AlignmentAttribute;
                        }

                        if (attr is OnTapAttribute)
                        {
                            string mname = ((OnTapAttribute)attr).Method;

                            if (callbacks == null)
                            {
                                throw new Exception("Your class contains [OnTap] attributes, but you passed a null object for `context' in the constructor");
                            }

                            var method = callbacks.GetType().GetMethod(mname);
                            if (method == null)
                            {
                                throw new Exception("Did not find method " + mname);
                            }
                            invoke = delegate {
                                method.Invoke(method.IsStatic ? null : callbacks, new object [0]);
                            };
                        }
                    }

                    string value = (string)GetValue(mi, o);
                    if (pa != null)
                    {
                        element = new EntryElement(caption, pa.Placeholder, value, true);
                    }
                    else if (ea != null)
                    {
                        element = new EntryElement(caption, ea.Placeholder, value)
                        {
                            KeyboardType = ea.KeyboardType, AutocapitalizationType = ea.AutocapitalizationType, AutocorrectionType = ea.AutocorrectionType, ClearButtonMode = ea.ClearButtonMode
                        }
                    }
                    ;
                    else if (multi)
                    {
                        element = new MultilineElement(caption, value);
                    }
                    else if (html != null)
                    {
                        element = new HtmlElement(caption, value);
                    }
                    else
                    {
                        var selement = new StringElement(caption, value);
                        element = selement;

                        if (align != null)
                        {
                            selement.Alignment = align.Alignment;
                        }
                    }

                    if (invoke != null)
                    {
                        ((StringElement)element).Tapped += invoke;
                    }
                }
                else if (mType == typeof(float))
                {
                    var floatElement = new FloatElement(null, null, (float)GetValue(mi, o));
                    floatElement.Caption = caption;
                    element = floatElement;

                    foreach (object attr in attrs)
                    {
                        if (attr is RangeAttribute)
                        {
                            var ra = attr as RangeAttribute;
                            floatElement.MinValue    = (float)ra.Low;
                            floatElement.MaxValue    = (float)ra.High;
                            floatElement.ShowCaption = ra.ShowCaption;
                        }
                    }
                }
                else if (mType == typeof(bool))
                {
                    bool checkbox = false;
                    foreach (object attr in attrs)
                    {
                        if (attr is CheckboxAttribute)
                        {
                            checkbox = true;
                        }
                    }

                    if (checkbox)
                    {
                        element = new CheckboxElement(caption, (bool)GetValue(mi, o));
                    }
                    else
                    {
                        element = new BooleanElement(caption, (bool)GetValue(mi, o));
                    }
                }
                else if (mType == typeof(DateTime))
                {
                    var  dateTime = (DateTime)GetValue(mi, o);
                    bool asDate = false, asTime = false;

                    foreach (object attr in attrs)
                    {
                        if (attr is DateAttribute)
                        {
                            asDate = true;
                        }
                        else if (attr is TimeAttribute)
                        {
                            asTime = true;
                        }
                    }

//					if (asDate)
//						element = new DateElement (caption, dateTime);
//					else if (asTime)
//						element = new TimeElement (caption, dateTime);
//					else
//						 element = new DateTimeElement (caption, dateTime);
                }
                else if (mType.IsEnum)
                {
                    var   csection = new Section();
                    ulong evalue   = Convert.ToUInt64(GetValue(mi, o), null);
                    int   idx      = 0;
                    int   selected = 0;

                    foreach (var fi in mType.GetFields(BindingFlags.Public | BindingFlags.Static))
                    {
                        ulong v = Convert.ToUInt64(GetValue(fi, null));

                        if (v == evalue)
                        {
                            selected = idx;
                        }

                        CaptionAttribute ca = Attribute.GetCustomAttribute(fi, typeof(CaptionAttribute)) as CaptionAttribute;
                        csection.Add(new RadioElement(ca != null ? ca.Caption : MakeCaption(fi.Name)));
                        idx++;
                    }

                    element = new RootElement(caption, new RadioGroup(null, selected))
                    {
                        csection
                    };
                }
                else if (mType == typeof(UIImage))
                {
                    element = new ImageElement((UIImage)GetValue(mi, o));
                }
                else if (typeof(System.Collections.IEnumerable).IsAssignableFrom(mType))
                {
                    var csection = new Section();
                    int count    = 0;

                    if (last_radio_index == null)
                    {
                        throw new Exception("IEnumerable found, but no previous int found");
                    }
                    foreach (var e in (IEnumerable)GetValue(mi, o))
                    {
                        csection.Add(new RadioElement(e.ToString()));
                        count++;
                    }
                    int selected = (int)GetValue(last_radio_index, o);
                    if (selected >= count || selected < 0)
                    {
                        selected = 0;
                    }
                    element = new RootElement(caption, new MemberRadioGroup(null, selected, last_radio_index))
                    {
                        csection
                    };
                    last_radio_index = null;
                }
                else if (typeof(int) == mType)
                {
                    foreach (object attr in attrs)
                    {
                        if (attr is RadioSelectionAttribute)
                        {
                            last_radio_index = mi;
                            break;
                        }
                    }
                }
                else
                {
                    var nested = GetValue(mi, o);
                    if (nested != null)
                    {
                        var newRoot = new RootElement(caption);
                        Populate(callbacks, nested, newRoot);
                        element = newRoot;
                    }
                }

                if (element == null)
                {
                    continue;
                }
                section.Add(element);
                mappings [element] = new MemberAndInstance(mi, o);
            }
            root.Add(section);
        }
예제 #4
0
		public static RootElement TestElements()
		{
			RootElement re1 = new RootElement("re1");
			Debug.WriteLine(re1.ToString());
			Section s1 = new Section();
			Debug.WriteLine(s1.ToString());
			//Section s2 = new Section(new Android.Views.View(a1));
			//Debug.WriteLine(s2.ToString());
			Section s3 = new Section("s3");
			Debug.WriteLine(s3.ToString());
			//Section s4 = new Section
			//					(
			//					  new Android.Views.View(a1)
			//					, new Android.Views.View(a1)
			//					);
			//Debug.WriteLine(s4.ToString());
			Section s5 = new Section("caption", "footer");
			Debug.WriteLine(s5.ToString());

			StringElement se1 = new StringElement("se1");
			Debug.WriteLine(se1.ToString());
			StringElement se2 = new StringElement("se2", delegate() { });
			Debug.WriteLine(se2.ToString());
			//StringElement se3 = new StringElement("se3", 4);
			StringElement se4 = new StringElement("se4", "v4");
			Debug.WriteLine(se4.ToString());
			//StringElement se5 = new StringElement("se5", "v5", delegate() { });
			
			// removed - protected (all with LayoutID)
			// StringElement se6 = new StringElement("se6", "v6", 4);
			// Debug.WriteLine(se6.ToString());

			// not cross platform! 
			// TODO: make it!?!?!?
			// AchievementElement
			
			BooleanElement be1 = new BooleanElement("be1", true);
			Debug.WriteLine(be1.ToString());
			BooleanElement be2 = new BooleanElement("be2", false, "key");
			Debug.WriteLine(be2.ToString());
			
			// Abstract
			// BoolElement be3 = new BoolElement("be3", true);

			CheckboxElement cb1 = new CheckboxElement("cb1");
			Debug.WriteLine(cb1.ToString());
			CheckboxElement cb2 = new CheckboxElement("cb2", true);
			Debug.WriteLine(cb2.ToString());
			CheckboxElement cb3 = new CheckboxElement("cb3", false, "group1");
			Debug.WriteLine(cb3.ToString());
			CheckboxElement cb4 = new CheckboxElement("cb4", false, "subcaption", "group2");
			Debug.WriteLine(cb4.ToString());

			DateElement de1 = new DateElement("dt1", DateTime.Now);
			Debug.WriteLine(de1.ToString());

			// TODO: see issues 
			// https://github.com/kevinmcmahon/MonoDroid.Dialog/issues?page=1&state=open
			EntryElement ee1 = new EntryElement("ee1", "ee1");
			Debug.WriteLine(ee1.ToString());
			EntryElement ee2 = new EntryElement("ee2", "ee2 placeholder", "ee2 value");
			Debug.WriteLine(ee2.ToString());
			EntryElement ee3 = new EntryElement("ee3", "ee3 placeholder", "ee3 value", true);
			Debug.WriteLine(ee3.ToString());

			FloatElement fe1 = new FloatElement("fe1");
			Debug.WriteLine(fe1.ToString());
			FloatElement fe2 = new FloatElement(-0.1f, 0.1f, 3.2f);
			Debug.WriteLine(fe2.ToString());
			FloatElement fe3 = new FloatElement
									(
									  null
									, null // no ctors new Android.Graphics.Bitmap()
									, 1.0f
									);
			Debug.WriteLine(fe3.ToString());

			HtmlElement he1 = new HtmlElement("he1", "http://holisiticware.net");
			Debug.WriteLine(he1.ToString());

			
			// TODO: image as filename - cross-platform
			ImageElement ie1 = new ImageElement(null);
			Debug.WriteLine(ie1.ToString());

			// TODO: not in Kevin's MA.D
			// ImageStringElement

			MultilineElement me1 = new MultilineElement("me1");
			Debug.WriteLine(me1.ToString());
			MultilineElement me2 = new MultilineElement("me2", delegate() { });
			Debug.WriteLine(me2.ToString());
			MultilineElement me3 = new MultilineElement("me3", "me3 value");
			Debug.WriteLine(me3.ToString());

			RadioElement rde1 = new RadioElement("rde1");
			Debug.WriteLine(rde1.ToString());
			RadioElement rde2 = new RadioElement("rde1", "group3");
			Debug.WriteLine(rde2.ToString());

			// TODO: not in Kevin's MA.D
			// StyledMultilineElement

			TimeElement te1 = new TimeElement("TimeElement", DateTime.Now);
			Debug.WriteLine(te1.ToString());



			re1.Add(s1);
			//re1.Add(s2);
			re1.Add(s3);
			//re1.Add(s4);
			re1.Add(s5);

			return re1;
		}
예제 #5
0
        //
        // Creates one of the various StringElement classes, based on the
        // properties set.   It tries to load the most memory efficient one
        // StringElement, if not, it fallsback to MultilineStringElement or
        // StyledStringElement
        //
        static Element LoadString(JsonObject json, object data)
        {
            string value          = null;
            string caption        = value;
            string background     = null;
            Action ontap          = null;
            Action onaccessorytap = null;
            int?   lines          = null;
            UITableViewCellAccessory?accessory = null;
            UILineBreakMode?         linebreakmode = null;
            UITextAlignment?         alignment = null;
            UIColor textcolor = null, detailcolor = null;
            UIFont  font       = null;
            UIFont  detailfont = null;
            UITableViewCellStyle style = UITableViewCellStyle.Value1;

            foreach (var kv in json)
            {
                string kvalue = (string)kv.Value;
                switch (kv.Key)
                {
                case "caption":
                    caption = kvalue;
                    break;

                case "value":
                    value = kvalue;
                    break;

                case "background":
                    background = kvalue;
                    break;

                case "style":
                    style = ToCellStyle(kvalue);
                    break;

                case "ontap":
                case "onaccessorytap":
                    string sontap = kvalue;
                    int    p      = sontap.LastIndexOf('.');
                    if (p == -1)
                    {
                        break;
                    }
                    Action d = delegate {
                        string cname = sontap.Substring(0, p);
                        string mname = sontap.Substring(p + 1);
                        foreach (var a in AppDomain.CurrentDomain.GetAssemblies())
                        {
                            Type type = a.GetType(cname);

                            if (type != null)
                            {
                                var mi = type.GetMethod(mname, BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic);
                                if (mi != null)
                                {
                                    mi.Invoke(null, new object [] { data });
                                }
                                break;
                            }
                        }
                    };
                    if (kv.Key == "ontap")
                    {
                        ontap = d;
                    }
                    else
                    {
                        onaccessorytap = d;
                    }
                    break;

                case "lines":
                    int res;
                    if (int.TryParse(kvalue, out res))
                    {
                        lines = res;
                    }
                    break;

                case "accessory":
                    accessory = ToAccessory(kvalue);
                    break;

                case "textcolor":
                    textcolor = ParseColor(kvalue);
                    break;

                case "linebreak":
                    linebreakmode = ToLinebreakMode(kvalue);
                    break;

                case "font":
                    font = ToFont(kvalue);
                    break;

                case "subtitle":
                    value = kvalue;
                    style = UITableViewCellStyle.Subtitle;
                    break;

                case "detailfont":
                    detailfont = ToFont(kvalue);
                    break;

                case "alignment":
                    alignment = ToAlignment(kvalue);
                    break;

                case "detailcolor":
                    detailcolor = ParseColor(kvalue);
                    break;

                case "type":
                    break;

                default:
                    Console.WriteLine("Unknown attribute: '{0}'", kv.Key);
                    break;
                }
            }
            if (caption == null)
            {
                caption = "";
            }
            if (font != null || style != UITableViewCellStyle.Value1 || detailfont != null || linebreakmode.HasValue || textcolor != null || accessory.HasValue || onaccessorytap != null || background != null || detailcolor != null)
            {
                StyledStringElement styled;

                if (lines.HasValue)
                {
                    styled       = new StyledMultilineElement(caption, value, style);
                    styled.Lines = lines.Value;
                }
                else
                {
                    styled = new StyledStringElement(caption, value, style);
                }
                if (ontap != null)
                {
                    styled.Tapped += ontap;
                }
                if (onaccessorytap != null)
                {
                    styled.AccessoryTapped += onaccessorytap;
                }
                if (font != null)
                {
                    styled.Font = font;
                }
                if (detailfont != null)
                {
                    styled.SubtitleFont = detailfont;
                }
                if (detailcolor != null)
                {
                    styled.DetailColor = detailcolor;
                }
                if (textcolor != null)
                {
                    styled.TextColor = textcolor;
                }
                if (accessory.HasValue)
                {
                    styled.Accessory = accessory.Value;
                }
                if (linebreakmode.HasValue)
                {
                    styled.LineBreakMode = linebreakmode.Value;
                }
                if (background != null)
                {
                    if (background.Length > 1 && background [0] == '#')
                    {
                        styled.BackgroundColor = ParseColor(background);
                    }
                    else
                    {
                        styled.BackgroundUri = new Uri(background);
                    }
                }
                if (alignment.HasValue)
                {
                    styled.Alignment = alignment.Value;
                }
                return(styled);
            }
            else
            {
                StringElement se;
                if (lines == 0)
                {
                    se = new MultilineElement(caption, value);
                }
                else
                {
                    se = new StringElement(caption, value);
                }
                if (alignment.HasValue)
                {
                    se.Alignment = alignment.Value;
                }
                if (ontap != null)
                {
                    se.Tapped += ontap;
                }
                return(se);
            }
        }