void SetValueActual(BindableProperty property, BindablePropertyContext context, object value, bool currentlyApplying, SetValueFlags attributes, bool silent = false)
        {
            object original              = context.Value;
            bool   raiseOnEqual          = (attributes & SetValueFlags.RaiseOnEqual) != 0;
            bool   clearDynamicResources = (attributes & SetValueFlags.ClearDynamicResource) != 0;
            bool   clearOneWayBindings   = (attributes & SetValueFlags.ClearOneWayBindings) != 0;
            bool   clearTwoWayBindings   = (attributes & SetValueFlags.ClearTwoWayBindings) != 0;

            bool same = Equals(value, original);

            if (!silent && (!same || raiseOnEqual))
            {
                if (property.PropertyChanging != null)
                {
                    property.PropertyChanging(this, original, value);
                }

                OnPropertyChanging(property.PropertyName);
            }

            if (!same || raiseOnEqual)
            {
                context.Value = value;
            }

            context.Attributes &= ~BindableContextAttributes.IsDefaultValue;

            if ((context.Attributes & BindableContextAttributes.IsDynamicResource) != 0 && clearDynamicResources)
            {
                RemoveDynamicResource(property);
            }

            BindingBase binding = context.Binding;

            if (binding != null)
            {
                if (clearOneWayBindings && binding.GetRealizedMode(property) == BindingMode.OneWay || clearTwoWayBindings && binding.GetRealizedMode(property) == BindingMode.TwoWay)
                {
                    RemoveBinding(property, context);
                    binding = null;
                }
            }

            if (!silent && (!same || raiseOnEqual))
            {
                if (binding != null && !currentlyApplying)
                {
                    _applying = true;
                    binding.Apply(true);
                    _applying = false;
                }

                OnPropertyChanged(property.PropertyName);

                if (property.PropertyChanged != null)
                {
                    property.PropertyChanged(this, original, value);
                }
            }
        }
        void ClearValue(BindableProperty property, bool checkaccess)
        {
            if (property == null)
            {
                throw new ArgumentNullException("property");
            }

            if (checkaccess && property.IsReadOnly)
            {
                throw new InvalidOperationException(string.Format("The BindableProperty \"{0}\" is readonly.", property.PropertyName));
            }

            BindablePropertyContext bpcontext = GetContext(property);

            if (bpcontext == null)
            {
                return;
            }

            object original = bpcontext.Value;

            object newValue = property.GetDefaultValue(this);

            bool same = Equals(original, newValue);

            if (!same)
            {
                if (property.PropertyChanging != null)
                {
                    property.PropertyChanging(this, original, newValue);
                }

                OnPropertyChanging(property.PropertyName);
            }

            bpcontext.Attributes &= ~BindableContextAttributes.IsManuallySet;
            bpcontext.Value       = newValue;
            bpcontext.Attributes |= BindableContextAttributes.IsDefaultValue;

            if (!same)
            {
                OnPropertyChanged(property.PropertyName);
                if (property.PropertyChanged != null)
                {
                    property.PropertyChanged(this, original, newValue);
                }
            }
        }