Hey guys,
I’m looking for a way to press several buttons in safari, one after another.
The thing is that all of the buttons are named the same.
When I’m setting the “press a button” command, it will only press the first button in that name and then will stop.
Does someone know what can be done?
Cheers,
Daniel
Hey Daniel,
What buttons?
In the app itself or a web page?
If a web page what page?
Which version of OSX?
–
Best Regards,
Chris
1 Like
Hey there Chris,
Thank you for replying.
It’s os x yosemite 10.10.3,
The buttons are on an internal web page.
It’s an internal net at my work. I’m using Safari to work on it.
I’m sure you’ll need more information to help me here, could you please advise me what should I’ll be looking for?
best regards,
Daniel
Hey Daniel,
Okay.
The first thing to do is to recognize there is a big difference between OSX UI-Elements and UI-Elements within a web page in a web browser.
Keyboard Maestro can see OSX UI-Elements, but it cannot directly see UI-Elements within a web page.
This is why KM’s actions only include Safari and Google Chrome — because they are both AppleScriptable.
KM is able to make queries of the apps where that scriptability gives access.
Within a web page KM has to interrogate with AppleScript and a do javascript query.
So. You’ll want to try using a Click Safari Link Action. Within that is a pop-up dialog with the elements KM can see.
Hopefully the same-named buttons in your web page have different internal identifiers (they should), and KM will be able to see and discriminate between them.
If that doesn’t work then you’ll need to right-click on the relevant buttons and look at them with Safari’s web-inspector tool. With that you can determine what kind of web-widget you’re looking at and whether the naming is unique enough to access with JavaScript.
That should give you enough to start, and that’s about as much advice as I can give without seeing the code of the page itself.
-Chris
Hey Chris,
Thank you for the informative comment!
Unfortunately, safari can’t see the specific button through the ‘click
safari link action’.
I inspected it, as you suggested.
Maybe it has something to do with the fact that it’s says that this button
won’t load until the back end is merged?
I’m attaching a bit of the code for your inspection. just to make things
clear, I’m looking for a way to press the “Filter Credited Items” button:
<footer class="ng-scope">
<!-- Will not enable this button until the back end is merged. -->
<!-- <a
ng-if="lsp.user.is_credential_user"
target="_self"
class="btn btn-success btn-sm download-credit-btn"
ng-href="/csv/{{env}}/{{token}}/{{scrapeSetId}}"
>Download Creditings</a> -->
<a target="_self" class="btn btn-warning btn-sm filter-credited-btn
ng-click-active" ng-click="filterCredited(this)"
onclick="this.blur()">Filter Credited Items</a>
<!-- ngIf: hasUncredited --><a ng-if="hasUncredited" class="btn
btn-danger btn-sm ng-scope"
ng-click="openUncredited()" onclick="this.blur()">Open Uncredited</a><!--
end ngIf: hasUncredited -->
<span class="tart-footer-stat">
<span>Total Items</span>
<span class="badge mapEnter ng-binding">1000</span>
</span>
</footer>
Best regards
Dan
Daniel Rozenberg
+972-(0)543020345
Hey Dan,
Try the following script in the Applescript Editor (Script Editor on Yosemite).
Replace ‘appinfo_toolbar-txt_link’ with your class name which appears to be:
“btn btn-warning btn-sm filter-credited-btn
ng-click-active”
I don’t know where the wrap came from on this, so it could be btnng or btn ng, and you’ll have to figure that out.
That’s about the extent of my JavaScript-Savvy, so if it doesn’t work maybe @ComplexPoint can help.
------------------------------------------------------------
doJavaScriptInSafari("document.getElementsByClassName('appinfo_toolbar-txt_link')[0].click()")
------------------------------------------------------------
--» HANDLERS
------------------------------------------------------------
on doJavaScriptInSafari(javascriptStr)
try
tell application "Safari" to do JavaScript javascriptStr in front document
on error e
error "Error in handler doJavaScriptInSafari() of library NLb!" & return & return & e
end try
end doJavaScriptInSafari
------------------------------------------------------------
If the script works you can run it from Keyboard Maestro with an Execute AppleScript Action.
-Chris
Not sure if this helps, but I find that I can, for example, click the search button on this forum page with, in Applescript:
-- APPLESCRIPT
-- Get an object by getElementById (returns one object)
-- Or getElementByClass (could return several, take the first [0])
-- try to click, and return a message
set strJS to "
(function () {
var btn,
strResult = 'clicked';
try {
//btn = document.getElementsByClassName('appinfo_toolbar-txt_link')[0];
btn = document.getElementById('search-button');
btn.click();
} catch (e) {
return e.name + ' ' + e.message;
}
return strResult;
})()
"
tell application "Safari"
set oTab to current tab of front window
tell front document
return (do JavaScript strJS in oTab) as string
end tell
end tell
or in Yosemite JXA Javascript for Applications:
// YOSEMITE Javascript for Applications JXA
// Get an object by getElementById (returns one object)
// Or getElementByClass (could return several, take the first [0])
// try to click, and return a message
var eventResult = function () {
var btn,
strResult = 'clicked';
try {
//btn = document.getElementsByClassName('appinfo_toolbar-txt_link')[0];
btn = document.getElementById('search-button');
btn.click();
} catch (e) {
return e.name + '\n' + e.message;
}
return strResult;
};
function run() {
var appSafari = Application("Safari"),
strJS = "(" + eventResult.toString() + ")()";
return appSafari.doJavaScript(strJS, {
in: appSafari.windows[0].currentTab
});
}
Or, for example, to get an array of similar items by class name, and click the Nth by its [index], we could, again on this page, choose which of the avatar icons to click with
btn = document.getElementsByClassName('avatar')[0];
as in:
-- APPLESCRIPT
-- Get an object by getElementById (returns one object)
-- Or getElementByClass (could return several, take the first [0])
-- try to click, and return a message
set strJS to "
(function () {
var btn,
strResult = 'clicked';
try {
btn = document.getElementsByClassName('avatar')[0];
//btn = document.getElementById('search-button');
btn.click();
} catch (e) {
strResult = e.name + ' ' + e.message;
}
return strResult;
})()
"
tell application "Safari"
set oTab to current tab of front window
tell front document
return (do JavaScript strJS in oTab) as string
end tell
end tell