• Caliburn笔记Action的创建(wpf框架)


        若一个对象被设置成为DataContext,该对象的方法称之为Action,caliburn通过附加属性来绑定这些Action,首先则需要获取绑定对象的方法.如下示例对象,则有4个方法.
    [Rescue("GeneralRescue")]
    public class Calculator
    {
        //Note: This rescue catches exceptions thrown by this method.
        //[Rescue("ActionSpecificRescue")]
        //Note: Preview indicates something that will happen before execution of the action.
        //Note: If AffectsTriggers = false, then this filter will not effect the state of the UI in real time.
       // [Preview("CanDivide")]
        //Note: The return value is bound to the UI if present.
        public int Divide(int left, int right)
        {
            return left / right;
        }
    
        //Note: See Preview filter.
        public bool CanDivide(int left, int right)
        {
            return right != 0;
        }
    
        //Note: See class level rescue filter.
        public void GeneralRescue(Exception ex)
        {
            MessageBox.Show(ex.Message);
        }
    
        //Note: See rescue filter on Divide method.
        public void ActionSpecificRescue(Exception ex)
        {
            MessageBox.Show("Divide Action: " + ex.Message);
        }
    }


    Action只包含公开方法,并不包含属性与事件等,所以需要对象成员进行过滤.如下逻辑

    protected virtual IEnumerable<IGrouping<string, MethodInfo>> SelectMethods(Type targetType)
    {
        return
            from method in targetType.GetMethods(BindingFlags.Public | BindingFlags.Instance | BindingFlags.Static)
            where method.DeclaringType != typeof(object)
                  && !method.ContainsGenericParameters
                  && !method.Name.StartsWith("get_")
                  && !method.Name.StartsWith("set_")
                  && !method.Name.StartsWith("remove_")
                  && !method.Name.StartsWith("add_")
                  && method.GetParameters().All(x => !x.IsOut)
            group method by method.Name
            into groups
                select groups;
    }

    方法与Action的转换


    完成方法过滤后,为了添加功能,还要对方法进行转换.

    首先根据方法,创建一个IMethod.然后创建Action.

    当然Action还有其他功能,这里分为同步与异步.

    protected virtual IAction CreateAction(IActionHost host, MethodInfo methodInfo)
    {
        var method = _methodFactory.CreateFrom(methodInfo);
        var asyncAtt = method.GetMetadata<AsyncActionAttribute>();
    
        var filters = host.GetFilterManager(method);
    
        TryAddCanExecute(filters, method);
    
        if(asyncAtt == null)
            return new SynchronousAction(method, _messageBinder, filters);
        return new AsynchronousAction(method, _messageBinder, filters, asyncAtt.BlockInteraction);
    }


    创建好以后再将其保存,创建过程由实现IActionFactory接口的ActionFactory完成.

    image

    public IEnumerable<IAction> CreateFor(IActionHost host)
    {
        var actions = new List<IAction>();
        var methodGroups = SelectMethods(host.TargetType);
    
        foreach(var methodGroup in methodGroups)
        {
            var methodList = methodGroup.ToList();
    
            if(methodList.Count == 1)
                actions.Add(CreateAction(host, methodList[0]));
            else
            {
                var overloadedAction = new OverloadedAction(methodGroup.Key);
    
                foreach(var methodInfo in methodList)
                {
                    overloadedAction.AddOverload(CreateAction(host, methodInfo));
                }
    
                actions.Add(overloadedAction);
            }
        }
    
        return actions;
    }
  • 相关阅读:
    [資料]VS2008技巧
    [資料]MarshalAs的用法
    MS SQL Server 2000安装不成功的原因
    Zend產品線
    [轉]Flex 开发必备10武器
    [轉]C#中的XML注释
    [轉]onpropertychange事件
    [轉]fckeditor添加自定义按钮
    [資源]Web設計資源以及线框工具
    [轉]JS中showModalDialog 详细使用
  • 原文地址:https://www.cnblogs.com/Clingingboy/p/1631936.html
Copyright © 2020-2023  润新知