cycle4passion icon

IE COM DOM Set Manipulations - Made Easy

cycle4passion | PRO | 04/23/17 06:00:47 AM UTC | 0 ⭐ | 10399 👁️ | Never ⏰ | []
Autohotkey |

11.57 KB

|

None

|

0 👍

/

0 👎

COMDOM(pwb, pGetby, pElemtext, pAction = "", pShowerrors = true, exitonfail := true) ;6/6/17 ----------------------------------------
/* Function allow easy set manipulation of IE COM DOM elements with error checking with suppressible error dialogs.
it is not all inclusive for DOM manipulation and concentrates mostly on Set functions for form elements
In particular, it keeps me from re-learning more complex manipulations of things like selects/options
Auto blurs (removes focus) after setting values allowing native form errorchecking, etc.
Auto enables disabled controls, bypassing native JS blocking
returns element object if error free which can be further manipulated (style, etc), or false if error
 
EXAMPLES:
 
COMDOM(wb, "id", "login", "srhamy")
COMDOM(wb, "name[1]", "login", "srhamy")
COMDOM(wb, "text[a], "Download", "click") ; assumes 1st match
COMDOM(wb, "id", "Optionals", "check[2,3]")
 
ARGUMENTS
    pWb             : IE web browser COM object
    pGetby      : method to conduct search for <elemtext>
                            - id                        : default, same a getElementByID()
                            - name              : same as getElementsByName(), default to [0] or can specify array element like name[1]
                            - class                 : same as getElementsByClass(), defaults to [0] or can specify array element like class[2]
                            - tagname           : same as getElementsByTagName(), defaults to [0] or specify array element like tagname[3]
                            - query             : same as querySelectorAll(), defaults to [0] or can specify array element like query[4]
                            - form                  : same as form[x], defaults to [0] or can specify array element form[5]
                            - text[tagname]     : find HTML element by value/placeholder or HTML Text node by innerText, tagname 
                                                          defaults to * or better/faster to filter by element tag type examples: a,div,input, button
    pElemtext   : identifier used for finding desired element
    pAction         : action to perform on found element (exist,click,focus,select,submit,check/uncheck,placeholder) ; set is default
                            - customtext                : set element value to <customtext>
                            - click                         : click element
                            - focus                         : set focus to element
                            - check/select                  : checks/selects option(s) for checkboxes, dropdowns, selects, and mult-selects
                            - uncheck/unselect              : unchecks/unselect option(s) in checkboxes, dropdowns, selects, and mult-selects
                            - submit                        : submits form
                            - exist                         : determine if control exists, aborts remainder of commands if not
                            - placeholder                   : set placeholder text of element
                            - enable                        : enable control (note this is done automatically before issing other commands)
                            - disable                       : disable control
                            - hide                          : hide element
                            - show/unhide                   : show element
    showerrors: 
                            - TRUE                          : popup errors
                            - FALSE                         : silent errors
                            
    Examples
 
    Instead of wb.document.getElementByID("login") := "me"
    IECOMDOM(wb, "id", "login", "me") ; finds element by id "login" and with fills with "me"
    Instead of wb.document.getElementsByClassName("password")[2].Focus()
    IECOMDOM(wb, "class", "password[2]", "focus) ; finds elements by classname of "password" and focuses on 1st one (zero based index) 
    Instead of a long set of commands...
    IECOMDOM(wb, "id", "location", "check[index1,index2]") ; finds input with id "location" and checks 2nd and 3rd option (zero based index)
    IECOMDOM(wb, "text['a']", "Download", "click") ; click link with HTML showing "Download" 
    COMDOM(wb, "tag","*[17]","hide") - hides 17th element on page
*/
{
  try
  { 
    if (Not IsObject(pWb))
        throw Exception("pWb Object not defined.", -1)
    if (Not InStr(pWb.FullName, "iexplore.exe"))
        throw Exception("pWb Object in not IE Object.", -1) 
    if (Not pGetby)
        throw Exception("pGetby argument cannot be blank.", -1) 
    if (Not pElemtext)
        throw Exception("pElemText argument cannot be blank.", -1) 
    if (Not pAction)
        throw Exception("Action argument cannot be blank.", -1) 
 
    arrelemtext := StrSplit(pElemtext,"|",A_Space) , arrgetby :=StrSplit(pGetby,"|",A_Space), arraction :=StrSplit(pAction,"|",A_Space)
 
    if (arrelemtext.Length != arrgetby.Length and arrgetby.Length != 1)
      throw Exception("Unmatched array lengths for pGetby ( " . arrgetby.Length . ") and pElemtext (" . arrelemtext.Length . ") arguments `r`n`r`n pGetBy= """ . pGetBy . """`r`n`r`npElemtext=""" . pElemtext . """", -1)
    if (arrelemtext.Length != arraction.Length)
      throw Exception( "Unmatched array lengths for pElemtext  (" . arrElemtext.Length . ") and pAction (" . arrAction.Length . ") arguments`r`n`r`npElemtext= """ . pElemtext . """`r`n`r`npAction=""" . pAction . """ arguments", -1)
    
    Loop,  % arraction.MaxIndex()
    { ; SPLITS ====================================================================================
    ; Split GetBy[]
      StringLower, getby, % (arrgetby.MaxIndex() = 1) ? trim(arrgetby[1]) : trim(arrgetby[A_Index]) ; if 1 getby apply to all, and lowerase normalize/trim leading/trailing ws
 
      if selpos := RegExMatch(getby, "\[([a-zA-Z0-9 '" . """" . "]*)\]",elemsearchtype)
      {
        StringReplace,elemsearchtype, elemsearchtype1, "", , All ; remove double quotes
        StringReplace, elemsearchtype, elemsearchtype, ', , All ; remove single quotes
        getby  := SubStr(getby,1,selpos-1)                                        ; simplify getby w/o [??]
      }
      ; Split ElemText[]
      elemtext := trim(arrelemtext[A_Index])
      if selpos := RegExMatch(elemtext, "\[([0-9 '" . """" . "]*)\]",elemindex) ; optional enclosing ' or " s
      {
        StringReplace,elemindex, elemindex1, "", , All ; remove double quotes
        StringReplace, elemindex, elemindex, ', , All   ; remove single quotes
        elemtext  := SubStr(elemtext,1,selpos-1)           ; simplify elemtext w/o [??]
      }
      else
        elemindex = 0
 
    ; Split Action[]
      action := trim(arraction[A_Index])
      if selpos := RegExMatch(action, "\[([a-zA-Z0-9, '" . """" . "]*)\]",sels)
      {
        arrsels := StrSplit(sels1,",", "'" . """") ; strips enclosing single and double quotes
        action  := SubStr(action,1,selpos-1) ; simply action w/o [??]
      }
 
    if RegExMatch(action,"i)(click|focus|select|submit|check|uncheck|enable|disable|hide|unhide|show|exist|placeholder|value)")  ; normalize to lower case & avoiding others (ie sent text)
      StringLower, action, action
      if (action = "exist")
        ComObjError(false)
     else
      ComObjError(pShowerrors)
     ; TARGET ========================================================
     if (getby = "name") ; same as getElementsByName, COMDOM(wb, "tag[0]","username","focus")
        target := pWb.document.getElementsByName(elemtext)[elemindex]
      else if (InStr(getby, "class")) ; same as getElementsByClassName, COMDOM(wb, "class","edit-new","focus")
        target := pWb.document.getElementsByClassName(elemtext)[elemindex]
      else if (InStr(getby, "tag") or getby = "index") ; same as GetElementsByTagName
        target := pWb.document.GetElementsByTagName(elemtext)[elemindex] 
      else if (InStr(getby,"query")) ; same as get elements by querySelectorAll
        target := pWb.document.querySelectorAll(elemtext)[elemindex]
      else if (InStr(getby,"form"))
        target := pWb.document.forms[elemindex]
      else if (getby = "text") ; get element by HTML text, COMDOM(wb,"text['a'],"Download","click")
      {
        if elemsearchtype =
          elemsearchtype := "*"
        nodes := pWb.document.GetElementsByTagName(elemsearchtype)
        debugbytext := true
        if debugbytext
          out("Matches (type=" . elemsearchtype . ") = " . nodes.Length)
        Loop % nodes.Length
        {
          StringLower, nodetype, % nodes[A_Index-1].tagname
          if (nodetype = "input") {
            if (nodes[A_Index-1].value = trim(elemtext)) or (nodes[A_Index-1].placeholder = trim(elemtext) ) {
            if debugbytext
              out("(" . A_Index  - 1 . ") " . Quote(nodes[A_Index-1].Value) . " (type=" . nodetype . ") ?= " . Quote(elemtext))
            target := nodes[A_Index-1]
            break
            }
          } else { ; examples buttons span p div
            if debugbytext
              out("(" . A_Index  - 1 . ") " . Quote(nodes[A_Index-1].InnerText) . " (type=" . nodetype . ") ?= " . Quote(elemtext))
            if (nodes[A_Index-1].InnerText = trim(elemtext)) {
            target := nodes[A_Index-1]
            break
            }
          }
        }
      }
      else ; assume getby ID
        target := pWb.document.getElementByID(elemtext)
      
      if not target and action != "exist"
        throw Exception("Sent Item #" . A_Index . " - Target elem not found`r`n`r`nelemtext= """ . elemtext . """`r`nusing getby=""" . getby . """", -1) 
    ;if target.tagname???? = "option" ; automatically backstep from option to select (user sent wrong one)
        ;target := target.parentNode
    if target.disabled := true
        target.disabled := false  ; Force through disabled controls
      ; ACTION =======================================================
      if (action = "exist")
        if target
          continue
        else
          return "" ; ? false
    else if (action = "value")
        return target.value
    else if (action="click")
      {
        target.Click()
        IEWaitReady(pWb)
      }
        else if (action = "focus")
          target.Focus()
        else if (action = "enable" or action = "disable")
            target.enable := (action="enable") ? true : false
        else if (action = "hide" or action = "unhide" or action = "show")
            target.style.visibility := (action="hide") ? "hidden" : "visible"
        else if (action = "placeholder" and arrsels[1])
          target.placeholder := arrsels[1]
        else if (action = "select" and (target.type = "input" or or target.type = "email" or target.type = "password" or target.type = "textarea"))
          target.Select()
        else if (action = "submit")
        {
          target.Submit()
          IEWaitReady(pWb)
        }
        else if (action = "check" or action = "uncheck" or elemtext ="select" or elemtext ="unselect")
        { ; for select, multi-select, dropdowns and checkboxes
          if (target.type = "checkbox")
            target.checked := (action="check") ? true : false
          else if (InStr(target.type,select) or target.type = "dropdown")
          { ; handles single or multiple select + dropdowns
            Loop % arrsels.MaxIndex()
            {
              seloptvalue := arrsels[A_Index]
              Loop %  target.Length
              {
                if (seloptvalue = "all" or target.options[A_Index-1].text = Trim(seloptvalue) or target.options[A_Index-1].value = Trim(seloptvalue) or A_Index - 1 = trim(seloptvalue))
                target[A_Index-1].selected := (action="check" or action = "select") ? true : false
              }
            }
          }
        }
        else
          target.Value := action
        if (action != "focus" and action != "exist") { ; force lose focus to trigger JS error checking/enabling etc.
            ComObjError(false)
            target.Blur()
            ComObjError(pShowerrors)
        }
      } ; Close Loop
  } catch e ; ERRORS ==============================================================================
    {
        target := ""
        errmsg := (e.What = ":= ") ? "Error in " . e.what . " Function - Line " . e.line  : "Error - Line " . e.line . ", " . e.message . "`n", e.message . "`n" . e.extra
        LogErrors(true,false,pShowerrors,"COMDOM",errmsg)
        if (exitonfail)
            Exit
    }
return target
} ; End COMDOM ==================================================================================

Comments

  •  icon
    01/01/70 12:00:00 AM UTC
    Plain Text |

    0 B

    |

    👍

    /

    👎

    
        
  •  icon
    01/01/70 12:00:00 AM UTC
    Plain Text |

    0 B

    |

    👍

    /

    👎