/// <summary> /// This method will execute a js function for highlighting a item (<div></div>) in the WebBrowser instance located inside the LibraryView using reflection /// </summary> /// <param name="visible">enable or disable the highlight in a specific Library item</param> internal void HighlightLibraryItem(bool visible) { const string jsMethodName = "highlightLibraryItem"; object[] parametersInvokeScript = new object[] { jsMethodName, new object[] { HostPopupInfo.HighlightRectArea.WindowElementNameString, visible } }; ResourceUtilities.ExecuteJSFunction(MainWindow, HostPopupInfo, parametersInvokeScript); }
/// <summary> /// This method will calculate the Popup location based in a item from the Library /// </summary> internal static void CalculateLibraryItemLocation(Step stepInfo, StepUIAutomation uiAutomationData, bool enableFunction, GuideFlow currentFlow) { CurrentExecutingStep = stepInfo; if (uiAutomationData == null) { return; } var jsFunctionName = uiAutomationData.JSFunctionName; object[] jsParameters = new object[] { uiAutomationData.JSParameters[0] }; //Create the array for the paramateres that will be sent to the WebBrowser.InvokeScript Method object[] parametersInvokeScript = new object[] { jsFunctionName, jsParameters }; //Execute the JS function with the provided parameters var returnedObject = ResourceUtilities.ExecuteJSFunction(CurrentExecutingStep.MainWindow, CurrentExecutingStep.HostPopupInfo, parametersInvokeScript); if (returnedObject == null) { return; } //Due that the returned object is a json then we get the values from the json JObject json = JObject.Parse(returnedObject.ToString()); double top = Convert.ToDouble(json["client"]["top"].ToString()); double bottom = Convert.ToDouble(json["client"]["bottom"].ToString()); //We calculate the Vertical location taking the average position "(top + bottom) / 2" and the height of the popup double verticalPosition = (top + bottom) / 2 - CurrentExecutingStep.Height / 2; CurrentExecutingStep.UpdatePopupVerticalPlacement(verticalPosition); }
/// <summary> /// This method will call the collapseExpandPackage javascript method with reflection, so the package expander in LibraryView will be clicked /// </summary> internal static void CollapseExpandPackage(Step stepInfo) { CurrentExecutingStep = stepInfo; var firstUIAutomation = stepInfo.UIAutomation.FirstOrDefault(); if (firstUIAutomation == null || firstUIAutomation.JSParameters.Count == 0) { return; } object[] parametersInvokeScript = new object[] { firstUIAutomation.JSFunctionName, new object[] { firstUIAutomation.JSParameters.FirstOrDefault() } }; ResourceUtilities.ExecuteJSFunction(stepInfo.MainWindow, stepInfo.HostPopupInfo, parametersInvokeScript); }
/// <summary> /// This method will call a js function that will scroll down until the bottom of the page /// </summary> internal static void LibraryScrollToBottom(Step stepInfo, StepUIAutomation uiAutomationData, bool enableFunction, GuideFlow currentFlow) { CurrentExecutingStep = stepInfo; if (uiAutomationData == null) { return; } string jsFunctionName = uiAutomationData.JSFunctionName; //Create the array for the paramateres that will be sent to the WebBrowser.InvokeScript Method object[] parametersInvokeScript = new object[] { jsFunctionName, new object[] { } }; //Execute the JS function with the provided parameters ResourceUtilities.ExecuteJSFunction(CurrentExecutingStep.MainWindow, CurrentExecutingStep.HostPopupInfo, parametersInvokeScript); }
/// <summary> /// This method will execute an UIAutomation action over a specific UIElement /// </summary> /// <param name="uiAutomationData">UIAutomation info read from a json file</param> /// <param name="enableUIAutomation">Enable/Disable the automation action for a specific UIElement</param> private void ExecuteUIAutomationStep(StepUIAutomation uiAutomationData, bool enableUIAutomation, Guide.GuideFlow currentFlow) { var popupBorderName = "SubmenuBorder"; //This section will search the UIElement dynamically in the Dynamo VisualTree in which an automation action will be executed UIElement automationUIElement = Guide.FindChild(MainWindow, uiAutomationData.Name); if (automationUIElement != null) { uiAutomationData.UIElementAutomation = automationUIElement; } switch (uiAutomationData.ControlType) { case StepUIAutomation.UIControlType.MENUITEM: if (uiAutomationData.UIElementAutomation == null) { return; } MenuItem menuEntry = uiAutomationData.UIElementAutomation as MenuItem; if (menuEntry == null) { return; } switch (uiAutomationData.Action) { case StepUIAutomation.UIAction.OPEN: menuEntry.IsSubmenuOpen = enableUIAutomation; menuEntry.StaysOpenOnClick = enableUIAutomation; break; } //Means that the Popup location needs to be updated after the MenuItem is opened if (uiAutomationData.UpdatePlacementTarget) { //We need to find the border inside the MenuItem.Popup so we can get its Width (this template is defined in MenuStyleDictionary.xaml) var menuPopupBorder = menuEntry.Template.FindName(popupBorderName, menuEntry) as Border; if (menuPopupBorder == null) { return; } //We need to do this substraction so the Step Popup wil be located at the end of the MenuItem Popup. stepUIPopup.HorizontalOffset = (menuPopupBorder.ActualWidth - menuEntry.ActualWidth) + HostPopupInfo.HorizontalPopupOffSet; UpdatePopupLocationInvoke(stepUIPopup); } break; //In this case the UI Automation will be done using a Function located in the static class GuidesValidationMethods case StepUIAutomation.UIControlType.FUNCTION: MethodInfo builderMethod = typeof(GuidesValidationMethods).GetMethod(uiAutomationData.Name, BindingFlags.Static | BindingFlags.NonPublic); object[] parametersArray = new object[] { this, uiAutomationData, enableUIAutomation, currentFlow }; builderMethod.Invoke(null, parametersArray); //If UpdatePlacementTarget = true then means that a new Window was opened after executing the funtion then we need to update the Popup.PlacementTarget if (uiAutomationData.UpdatePlacementTarget) { UpdatePlacementTarget(); } break; //In this case the UI Automation will be done over a WPF Button case StepUIAutomation.UIControlType.BUTTON: if (string.IsNullOrEmpty(uiAutomationData.WindowName)) { return; } //This means that the Button is in a PopupWindow (instead of the DynamoView) so we need to find the button and then apply the automation if (uiAutomationData.WindowName.Equals(WindowNamePopup)) { //Finds the Button inside the PopupWindow var buttonFound = Guide.FindChild((stepUIPopup as PopupWindow).mainPopupGrid, uiAutomationData.Name) as Button; if (buttonFound == null) { return; } switch (uiAutomationData.Action) { case StepUIAutomation.UIAction.DISABLE: if (enableUIAutomation) { buttonFound.IsEnabled = false; } else { buttonFound.IsEnabled = true; } break; } } break; case StepUIAutomation.UIControlType.JSFUNCTION: if (string.IsNullOrEmpty(uiAutomationData.JSFunctionName)) { return; } //We need to create a new list for the parameters due that we will be adding the enableUIAutomation boolean value var parametersJSFunction = new List <object>(uiAutomationData.JSParameters); parametersJSFunction.Add(enableUIAutomation); //Create the array for the parameters that will be sent to the JS Function object[] jsParameters = parametersJSFunction.ToArray(); //Create the array for the paramateres that will be sent to the WebBrowser.InvokeScript Method object[] parametersInvokeScript = new object[] { uiAutomationData.JSFunctionName, jsParameters }; //Execute the JS function with the provided parameters ResourceUtilities.ExecuteJSFunction(MainWindow, HostPopupInfo, parametersInvokeScript); break; } }