CodedUI“ FindMatchingControls()”的工作时间为10%,但通常会返回大约一半的控件

时间:2018-10-03 13:07:45

标签: coded-ui-tests

问题::我正在使用FindMatchingControls()在WPF表中创建行集合。我编写了一个循环,将每一行中的ComboBox设置为给定值。整个过程有时有效,但并非总是如此,FindMatchingControls()实际上找到大约一半的行。我该如何配置超时或更改设置,以使其每次都能找到所有50个控件,或者找到前10个,然后找到接下来的10个,等等?

背景:我正在测试WPF窗口,上面有一个表格,表格中的每一行都有一个下拉列表。一共有50行,将来还会有更多行,因此我无法记录每个行的设置,我记录的测试对于每个新版本都会过时(每个月左右)。

因此,我记录了1个ComboBox的设置,然后使用FindMatchingControls()创建了一个Collection。我遍历Collection,将该集合中的每个ComboBox设置为所需的选择。前23行显示在我当前的屏幕分辨率上。唯一的问题是FindMatchingControls()有时返回23,有时26,有时34,有时返回所有50行!我的问题是,如何修复下面的代码,使其始终返回全部50行(将来可能还会返回更多行)。

从代码中您可以看到我两次找到了Parent控件,因此下面是伪代码。

伪代码

1)查找父容器(表) 2)定义一行(它是父表的子表) 3)使用FindMatchingControls获取行集合 4)遍历Collection,在每一行中找到ComboBox并将其选择设置为传递给方法的值。

代码:

    public void PlaceAnOrderScreen_SelectItems_List(String item /*Value to set all 50 ComboBoxes to*/)
    {
        WpfControl rowOfOrderItems = new WpfControl(this.UIOptimalOrderSystemClientShWindow.UIItemCustom22.UIListViewAutoID37Table);
        rowOfOrderItems.SearchProperties[WpfControl.PropertyNames.ControlType] = "DataItem";
        rowOfOrderItems.SearchProperties[WpfControl.PropertyNames.ClassName] = "Uia.ListViewItem";
        rowOfOrderItems.WindowTitles.Add("Order Management System");

        rowOfOrderItems.Find();
        rowOfOrderItems.DrawHighlight();  //Visible diagnostic

        //should get a collection of 50 controls ...
        //... but this is dodgy, it sometimes finds 23, 26, 34 or ocassionaly all 50 controls.
        //There are 23 visible controls and the rest, you have to scroll down to see.
        UITestControlCollection itemRows = rowOfOrderItems.FindMatchingControls();

        int c = 0;
        int i = 1;
        string label = String.Empty;

        foreach (var auditSelectionBox in itemRows)
        {
            //After the top 15 drop down selections have been made, strat scrolling down.
            //This is because setting the Value for a list box that is off the screen
            //causes it to complain the control is blocked...
            if (c >= 15)
            {
                if (i >= 3) //The scroll wheel moves 3 rows at a time, so only scroll once for every 3 rows...
                {
                    Mouse.MoveScrollWheel(-1);
                    i = 0;
                }                    
            }
            i++;
            c++;

            WpfCell auditDDL1 = new WpfCell(auditSelectionBox);
            auditDDL1.SearchProperties[WpfCell.PropertyNames.ColumnHeader] = "Total";
            auditDDL1.WindowTitles.Add("OrderSystem 5");

            //Works but takes 5 - 16 seconds per drop down list
            auditDDL1.Value = item;
        }
    }    

2 个答案:

答案 0 :(得分:2)

您可以使用一种采用父方法(在您的情况下为表)并以递归方式返回其所有子方法的方法,而不是尝试根据另一行查找匹配的控件。它一直向下挖掘,直到找到所有可用的子代。您的表有多少行无关紧要,它将尝试获取所有行。它可用于任何UITestControl。

public ParentControl GetChildControls(UITestControl parentControl)
{
    ParentControl parent = new ParentControl();

    if (parentControl != null)
    {
        List<ParentControl> children = new List<ParentControl>();

        foreach (UITestControl childControl in parentControl.GetChildren())
        {
            children.Add(GetChildControls(childControl));
        }

        parent.Children = new KeyValuePair<UITestControl, List<ParentControl>>(parentControl, children);
    }

    return parent;
}

父类

public class ParentControl
{
    public KeyValuePair<UITestControl, List<ParentControl>> Children { get; set; }
    public string Value
    {
        get
        {
            return Children.Key.Name;
        }
    }
}

我刚刚添加了Value属性,以便于访问UITestControl的名称。

答案 1 :(得分:0)

PixelPlex(以上)提供了最佳答案。我需要添加到PixelPlex的代码中的只是一个If语句,以在找到ComboBox时将其设置为一个值。因此,就我而言,foreach如下...

            foreach (UITestControl childControl in parentControl.GetChildren())
            {
                children.Add(GetChildControls(childControl));

                //Added below If statement to set ComboBox selected item to "Carrots"...
                if (childControl.ClassName == "Uia.ComboBox")
                {
                    WpfComboBox cb = (WpfComboBox)childControl; 
                    cb.SelectedItem = "Carrots";
                }
            }

这将从我的ComboBox中选择胡萝卜...不满足我的If语句的所有内容都不相关,因此我对此不做任何事情。