private void EnsureBindings(object itemObject) { if (itemDataBindings == null && !itemIsViewModel.HasValue) { itemIsViewModel = itemObject is ViewModelBase; if (!itemIsViewModel.Value) { itemDataBindings = new List <ItemDataBinding>(); Type itemType = itemObject.GetType(); foreach (var pi in itemType.GetProperties(BindingFlags.Public | BindingFlags.Instance)) { var resourceId = AndroidHelpers.FindResourceId(IdName(pi.Name)); if (resourceId.HasValue) { itemDataBindings.Add(new ItemDataBinding(pi, resourceId.Value)); } } foreach (var fi in itemType.GetFields(BindingFlags.Public | BindingFlags.Instance)) { var resourceId = AndroidHelpers.FindResourceId(IdName(fi.Name)); if (resourceId.HasValue) { itemDataBindings.Add(new ItemDataBinding(fi, resourceId.Value)); } } } } }
protected override void OnResume() { base.OnResume(); AndroidHelpers.SetCurrentActivity(this); EnsureHandlersAreAdded(); }
protected override void OnPause() { EnsureHandlersAreRemoved(); AndroidHelpers.ClearActivityReference(this); base.OnPause(); }
protected override void OnCreate(Bundle savedInstanceState) { base.OnCreate(savedInstanceState); AndroidHelpers.SetCurrentActivity(this); }
private DataBinding AddBinding(string propertyName, BindingMode mode = BindingMode.OneWay, string listPropertyName = null, View view = null, AdapterView commandParameterSelectedItemAdapterView = null) { string idName = (view != null) ? view.Id.ToString() : IdName(propertyName); int? resourceId = AndroidHelpers.FindResourceId(idName); if (view == null && resourceId.HasValue) { view = rootView.FindViewById(resourceId.Value); } if (view == null) { return(null); } bool itemIsValue = false; string itemTemplateName = null, itemValueId = null; int? commandParameterListId = null; if (view.Tag != null) { // Get optional parameters from tag: // {Binding propertyName, Mode=OneWay|TwoWay|Command} // {List ItemsSource=listPropertyName, ItemIsValue=false|true, ItemTemplate=listItemTemplateName, ItemValueId=listItemValueId} // {CommandParameter ListId=<view Id>} // Defaults: // propertyName is known by convention from view Id = <rootview prefix><propertyName>; the default for the rootview prefix is the rootview class name + "_". // Mode = OneWay // Additional defaults for views derived from AdapterView (i.e. lists): // ItemsSource = propertyName + "List" // ItemIsValue = false // ItemTemplate = ItemsSource + "Item" // ItemValueId : if ItemIsValue = true then the default for ItemValueId = ItemTemplate string tag = view.Tag.ToString(); if (tag != null && tag.Contains("{")) { var match = Regex.Match(tag, @"({Binding\s+((?<assignment>[^,{}]+),?)+\s*})?(\s*{List\s+((?<assignment>[^,{}]+),?)+\s*})?(\s*{CommandParameter\s+((?<assignment>[^,{}]+),?)+\s*})?"); if (match.Success) { var gc = match.Groups["assignment"]; if (gc != null) { var cc = gc.Captures; if (cc != null) { for (int i = 0; i < cc.Count; i++) { string[] assignmentElements = cc[i].Value.Split('='); if (assignmentElements.Length == 1) { string value = assignmentElements[0].Trim(); if (value != "") { propertyName = value; } } else if (assignmentElements.Length == 2) { string name = assignmentElements[0].Trim(); string value = assignmentElements[1].Trim(); switch (name) { case "Mode": Enum.TryParse <BindingMode>(value, true, out mode); break; case "ItemsSource": listPropertyName = value; break; case "ItemIsValue": Boolean.TryParse(value, out itemIsValue); break; case "ItemTemplate": itemTemplateName = value; break; case "ItemValueId": itemValueId = value; break; case "ListId": commandParameterListId = AndroidHelpers.FindResourceId(value); if (commandParameterSelectedItemAdapterView == null && commandParameterListId.HasValue) { commandParameterSelectedItemAdapterView = rootView.FindViewById <AdapterView>(commandParameterListId.Value); } break; default: throw new ArgumentException("Unknown tag binding parameter: " + name); } } } } } } } } var binding = new DataBinding { View = view, ResourceId = resourceId, Mode = mode, ViewModelPropertyInfo = viewModel.GetType().GetProperty(propertyName), CommandParameterListId = commandParameterListId, CommandParameterListView = commandParameterSelectedItemAdapterView }; if (binding.View is AdapterView) { if (listPropertyName == null) { listPropertyName = propertyName + "List"; } var pi = viewModel.GetType().GetProperty(listPropertyName); if (pi == null && binding.ViewModelPropertyInfo.PropertyType.GetInterface("IList") != null) { listPropertyName = propertyName; pi = binding.ViewModelPropertyInfo; binding.ViewModelPropertyInfo = null; } binding.ViewModelListPropertyInfo = pi; pi = binding.View.GetType().GetProperty("Adapter", BindingFlags.Public | BindingFlags.Instance); if (pi != null) { var adapter = pi.GetValue(binding.View); if (adapter == null) { if (itemTemplateName == null) { itemTemplateName = listPropertyName + "Item"; } if (itemIsValue && itemValueId == null) { itemValueId = itemTemplateName; } int?itemTemplateResourceId = AndroidHelpers.FindResourceId(itemTemplateName, AndroidHelpers.ResourceCategory.Layout); int?itemValueResourceId = AndroidHelpers.FindResourceId(itemValueId); if (itemTemplateResourceId.HasValue) { adapter = new DataBindableListAdapter <object>(layoutInflater, itemTemplateResourceId.Value, itemTemplateName + "_", itemValueResourceId, rootViewExtensionPoints); pi.SetValue(binding.View, adapter); } } binding.ListAdapter = adapter as IDataBindableListAdapter; } } switch (binding.Mode) { case BindingMode.TwoWay: AddTwoWayHandler(binding); break; case BindingMode.Command: AddCommandHandler(binding); break; } dataBindings.Add(idName, binding); return(binding); }
private DataBinding AddBinding(BindingParameters bp) { object view = bp.View; View androidView = view as View; string propertyName = bp.ViewModelPropertyName; if (string.IsNullOrEmpty(propertyName)) { throw new ArgumentNullException("ViewModelPropertyName"); } string idName = IdName(propertyName); int? resourceId; if (androidView != null) { string viewIdName = AndroidHelpers.FindResourceName(androidView.Id); if (viewIdName != idName) { throw new ArgumentException(string.Format("View Id '{0}' does not match expected value '{1}'; adjust either the view Id or the ViewModelPropertyName binding parameter.", viewIdName, idName)); } resourceId = androidView.Id; } else { resourceId = AndroidHelpers.FindResourceId(idName); } if (view == null && resourceId.HasValue) { view = androidView = rootView.FindViewById(resourceId.Value); } if (view == null) { return(null); } if (androidView != null && androidView.Tag != null) { bp = ParseBindingParameters(androidView.Tag.ToString(), bp); } string viewMemberName = bp.ViewMemberName; if ((bp.Mode == BindingMode.OneWay || bp.Mode == BindingMode.TwoWay) && bp.UpdateView == null && viewMemberName == null) { ViewDefaultPropertyOrFieldName.TryGetValue(view.GetType().FullName, out viewMemberName); } var viewModelPropertyInfo = (string.IsNullOrEmpty(propertyName) || propertyName == ".") ? null : viewModel.GetType().GetProperty(propertyName); AdapterView commandParameterSelectedItemAdapterView = bp.CommandParameterSelectedItemAdapterView; if (commandParameterSelectedItemAdapterView == null && bp.ListId.HasValue) { commandParameterSelectedItemAdapterView = rootView.FindViewById <AdapterView>(bp.ListId.Value); } var binding = new DataBinding { ViewProperty = new PropertyReference(view, viewMemberName, viewModelPropertyInfo != null ? viewModelPropertyInfo.PropertyType : null), ResourceId = resourceId, UpdateViewAction = bp.UpdateView, UpdateViewModelAction = bp.UpdateViewModel, Mode = bp.Mode, ViewModelPropertyInfo = viewModelPropertyInfo, CommandParameterListId = bp.ListId, CommandParameterListView = commandParameterSelectedItemAdapterView }; string listPropertyName = bp.ListPropertyName; if (listPropertyName == null) { listPropertyName = propertyName + "List"; } var pi = viewModel.GetType().GetProperty(listPropertyName); if (pi == null && binding.ViewModelPropertyInfo.PropertyType.GetInterface("IList") != null) { listPropertyName = propertyName; pi = binding.ViewModelPropertyInfo; binding.ViewModelPropertyInfo = null; } binding.ViewModelListPropertyInfo = pi; if (view is AdapterView) { pi = view.GetType().GetProperty("Adapter", BindingFlags.Public | BindingFlags.Instance); if (pi != null) { var adapter = pi.GetValue(view); if (adapter == null) { string itemTemplateName = bp.ListItemTemplateName ?? listPropertyName + "Item"; string itemValueId = (bp.ListItemIsValue && bp.ListItemValueId == null) ? itemTemplateName : bp.ListItemValueId; int? itemTemplateResourceId = AndroidHelpers.FindResourceId(itemTemplateName, AndroidHelpers.ResourceCategory.Layout); int? itemValueResourceId = AndroidHelpers.FindResourceId(itemValueId); if (itemTemplateResourceId.HasValue) { adapter = new DataBindableListAdapter <object>(layoutInflater, itemTemplateResourceId.Value, itemTemplateName + "_", itemValueResourceId, rootViewExtensionPoints); pi.SetValue(view, adapter); } } binding.ListAdapter = adapter as IDataBindableListAdapter; } } switch (binding.Mode) { case BindingMode.TwoWay: AddTwoWayHandler(binding); break; case BindingMode.Command: AddCommandHandler(binding); break; } dataBindings.Add(idName, binding); return(binding); }
public static BindingParameters ParseBindingParameters(string tag, BindingParameters bp = null) { if (tag != null && tag.Contains("{")) { var match = Regex.Match(tag, @"({Binding\s+((?<assignment>[^,{}]+),?)+\s*})?(\s*{List\s+((?<assignment>[^,{}]+),?)+\s*})?(\s*{CommandParameter\s+((?<assignment>[^,{}]+),?)+\s*})?"); if (match.Success) { var gc = match.Groups["assignment"]; if (gc != null) { var cc = gc.Captures; if (cc != null) { if (bp == null) { bp = new BindingParameters(); } for (int i = 0; i < cc.Count; i++) { string[] assignmentElements = cc[i].Value.Split('='); if (assignmentElements.Length == 1) { string value = assignmentElements[0].Trim(); if (value != "") { bp.ViewModelPropertyName = value; } } else if (assignmentElements.Length == 2) { string name = assignmentElements[0].Trim(); string value = assignmentElements[1].Trim(); if (name.StartsWith(".")) { bp.ViewMemberName = name.Substring(1); if (value != "") { bp.ViewModelPropertyName = value; } } else { switch (name) { case "Mode": Enum.TryParse <BindingMode>(value, true, out bp.Mode); break; case "ItemsSource": bp.ListPropertyName = value; break; case "ItemIsValue": Boolean.TryParse(value, out bp.ListItemIsValue); break; case "ItemTemplate": bp.ListItemTemplateName = value; break; case "ItemValueId": bp.ListItemValueId = value; break; case "ListId": bp.ListId = AndroidHelpers.FindResourceId(value); break; default: throw new ArgumentException("Unknown tag binding parameter: " + name); } } } } } } } } return(bp); }