Applescript "can't get miniaturized of window" - applescript

I'm a beginner working on a script that counts windows in locations on screen. So far it works fairly well, although one flaw is it counts windows that are minimized.
Here is the working code currently:
tell application "System Events"
set winCount1 to 0
set winCount2 to 0
set winCount3 to 0
set winCount4 to 0
set theProcesses to application processes
repeat with theProcess from 1 to count theProcesses
if visible of process theProcess is true then
tell process theProcess
repeat with x from 1 to (count windows)
if ((description of window x is not "dialog") then
set Pos to position of window x
if item 1 of Pos is less than -960 then
set winCount1 to winCount1 + 1
else if item 1 of Pos is less than 0 then
set winCount2 to winCount2 + 1
else if item 1 of Pos is less than 960 then
set winCount3 to winCount3 + 1
else
set winCount4 to winCount4 + 1
end if
end if
end repeat
end tell
end if
end repeat
set countList to {winCount1, winCount2, winCount3, winCount4}
return countList
end tell
Now to try to solve this issue, I tried adding a new condition:
if ((description of window x) is not "dialog") and window x is not miniaturized then
But this returns the error stated in the title. So I tried:
set props to get properties of window x
if props contains miniaturized then
This returns the same error.
I also tried:
set props to get properties of class of window x
if props contains miniaturized then
Same error.
It can't be that difficult to avoid windows without the miniaturized property before testing for it, but I'm not having luck finding a solution. Any ideas?

Get the value of attribute "AXMinimized" of the window, like this:
set winCount1 to 0
set winCount2 to 0
set winCount3 to 0
set winCount4 to 0
tell application "System Events"
repeat with theProcess in (application processes whose visible is true)
tell theProcess
repeat with thisWin in windows
if (description of thisWin is not "dialog") and not (value of attribute "AXMinimized" of thisWin) then
set Pos to position of thisWin
if item 1 of Pos is less than -960 then
set winCount1 to winCount1 + 1
else if item 1 of Pos is less than 0 then
set winCount2 to winCount2 + 1
else if item 1 of Pos is less than 960 then
set winCount3 to winCount3 + 1
else
set winCount4 to winCount4 + 1
end if
end if
end repeat
end tell
end repeat
end tell
return {winCount1, winCount2, winCount3, winCount4}

Related

Run AppleScript handlers parallel

I would like to run this AppleScript handler in parallel two times (so I want two calls of tillSideBySideWindows("right") to run asynchronously and not after each other), is there a way to do it?
on tillSideBySideWindows(direction)
tell application "System Events"
set allVisibleProcessNames to name of processes whose visible is true
repeat with processName in allVisibleProcessNames
set windowsOfCurrentApp to every window of application process processName
repeat with currentWindow in windowsOfCurrentApp
set currentWindowsSize to size of currentWindow
set currentWindowsWidth to item 1 of currentWindowsSize
set currentWindowsPosition to position of currentWindow
set currentWindowsLeftPos to item 1 of currentWindowsPosition
if currentWindowsLeftPos = 0 then
if direction = "right" then
set currentWindowsWidth to currentWindowsWidth + 30
else
set currentWindowsWidth to currentWindowsWidth - 30
end if
set currentWindowsHeight to item 2 of currentWindowsSize
set winName to name of currentWindow
set size of window winName of application process processName to {currentWindowsWidth, currentWindowsHeight}
end if
if (currentWindowsLeftPos + currentWindowsWidth) = 1680 then
set currentWindowsHeight to item 2 of currentWindowsSize
if direction = "right" then
set currentWindowsLeftPos to currentWindowsLeftPos + 30
set currentWindowsWidth to currentWindowsWidth - 30
else
set currentWindowsLeftPos to currentWindowsLeftPos - 30
set currentWindowsWidth to currentWindowsWidth + 30
end if
set winName to name of currentWindow
set position of window winName of application process processName to {currentWindowsLeftPos, 0}
set size of window winName of application process processName to {currentWindowsWidth, currentWindowsHeight}
get currentWindowsWidth
end if
end repeat
end repeat
end tell
end tillSideBySideWindows
tillSideBySideWindows("right")

Applescript to extract YouTube Livestream Video ID

I want to develop an Applescript to extract youtube live stream video ID using the Channel ID.
Currently, I'm doing it manually as Youtube changes live stream video ID time to time.
For an example, I'm practising following;
Open https://www.youtube.com/embed/live_stream?channel=UCu7cGbQEMgGk8TD0ZYucM5g
Right-click on the player and select "Copy video URL"
This URL is used to an Applescript I wrote to automate Livestreamer. (This script is given below.)
As Youtube changes this URL time to time, following script has to be changed the time to time. My intention is to automate the whole process.
-- Shraddha TV and Radio Recorder --
-- Developed by Anoma --
set pathToShraddha to ((path to downloads folder as text) & "Shraddha:")
set outputExtension to ""
set ls to ""
set sourceURL to ""
set con to ""
set windowInfo to ""
set theTime to ""
set endTime to ""
display dialog "Shraddha TV or Radio" buttons {"TV", "Radio", "Cancel"} default button 1
if result = {button returned:"TV"} then
set outputExtension to ".ts"
set sourceURL to "https://www.youtube.com/watch?v=1yv7JjMP4Dw"
set ls to "livestreamer"
set con to "480p -o"
else if result = {button returned:"Radio"} then
set outputExtension to ".mp3"
set sourceURL to "http://92.222.236.128:8006"
set ls to "ffmpeg -i"
set con to "-c copy"
else
return
end if
set fn to (setFileName(outputExtension))
display dialog "Record now or later?" buttons {"Now", "Later", "Cancel"} default button 1
if result = {button returned:"Now"} then
set endTime to text returned of (display dialog "Please set the time to end recording. (Leave 'hhmm' if you want to record continuously.) " with title "Timer" default answer "hhmm" buttons {"Cancel", "Set"} default button 2)
set windowInfo to recordMedia(ls, sourceURL, con, (POSIX path of pathToShraddha as string), fn)
finishTime(endTime, windowInfo)
else if result = {button returned:"Later"} then
-- get time to be set---
set theTime to text returned of (display dialog "Please set the time to start recording." with title "Timer" default answer "hhmm" buttons {"Cancel", "Set"} default button 2)
if ((theTime as string) is equal to "hhmm") then
display dialog "Time is not set correctly"
return
end if
set endTime to text returned of (display dialog "Please set the time to end recording. (Leave 'hhmm' if you want to record continuously.) " with title "Timer" default answer "hhmm" buttons {"Cancel", "Set"} default button 2)
display dialog (getTimeInHoursAndMinutes())
display dialog theTime
set i to 0
repeat while (getTimeInHoursAndMinutes()) is less than theTime
if (i = 0) then
set i to (i + 1)
recordMedia("", "", "", "", "")
end if
delay 60
end repeat
finishTime(endTime, (recordMedia(ls, sourceURL, con, (POSIX path of pathToShraddha as string), fn)))
else
return
end if
-- This method generates the file name
on setFileName(outputExt)
set fileName to do shell script "date +'%Y-%m-%d_%H-%M-%S'"
set outputExt to the outputExt as string
set fileName to ("STV_" & fileName as string) & outputExt
return fileName as string
end setFileName
-- This method gives the current time in "hhmm" format (24hr)
on getTimeInHoursAndMinutes()
set timeStr to time string of (current date)
set hrStr to (characters 1 thru -10 of timeStr as string)
if ((count hrStr) is less than 2) then
set timeStr to ((0 & timeStr) as string)
end if
set ampm to (characters -2 thru -1 of timeStr as string)
if ((ampm as string) is equal to "PM") then
if ((hrStr as integer) is less than 12) then
set hrStr to (((hrStr as integer) + 12) as string)
end if
else
if ((hrStr as integer) = 12) then
set hrStr to (0 as string)
end if
if ((count hrStr) is less than 2) then
set hrStr to ((0 & hrStr) as string)
end if
end if
set mStr to (characters 4 thru 5 of timeStr as string)
set timeStr to (hrStr) & (mStr)
return timeStr as string
end getTimeInHoursAndMinutes
-- This method Record the stream --
on recordMedia(ls, sourceURL, con, pathToShraddhaString, fn)
tell application "Terminal"
set windowInfo to do script "caffeinate -i " & ls & space & sourceURL & space & con & space & pathToShraddhaString & fn
activate of windowInfo
end tell
return windowInfo
end recordMedia
-- This method end recording --
on finishTime(endTime, windowInfo)
if ((endTime as string) is equal to "hhmm") then
else
repeat while (getTimeInHoursAndMinutes()) is less than endTime
delay 60
end repeat
tell application "Terminal"
-- reopen
activate of windowInfo
--tell application "System Events" to keystroke "q"
tell application "System Events" to keystroke "c" using {control down}
end tell
end if
end finishTime
Could you please help me in developing the script to automate the extraction of the Livestream URL every time I run the script?
Thank you.
This is the answer given by Capitainos # Superuser.
It works really fine.
Property LivestreamURL : {}
-- set youtube_channel to choose URL -- just remove comment tag to choose this option
set youtube_channel to "https://www.youtube.com/embed/live_stream?channel=UCu7cGbQEMgGk8TD0ZYucM5g"
tell application "Safari"
launch -- background OR use 'activate' if preferred
open location youtube_channel
end tell
-- wait for Safari to load the webpage
if load_webpage(20) is false then return
tell application "Safari" to set end of LivestreamURL to do JavaScript "document.links[0].href" in document 1
set this_ID to item 1 of LivestreamURL
set channel_ID to (characters 51 thru -1 of youtube_channel) as string
set video_ID to (characters 33 thru -1 of this_ID) as string
-- return LivestreamURL -- or;
return return & "Channel ID : " & channel_ID & linefeed & "Video ID : " & video_ID & linefeed & linefeed
-- This is the Handler 'load_webpage'
on load_webpage(timeout_variable)
delay 2
repeat with i from 1 to the timeout_variable
tell application "Safari"
if (do JavaScript "document.readyState" in document 1) is "complete" then
return true
else if i is the timeout_variable then
return false
else
delay 1
end if
end tell
end repeat
return false
end load_webpage

Applescript Infinite Repeat Keystrokes hangs up applications

So for an infinite monkey theorem test i need applescript to input random numbers (0-6) into TextEdit.
I have a working code which doesn't slow down the cpu or anything, but i can't terminate it after running it once without terminating TextEdit.
So my question is:
How can i improve this code so it allows me to terminate it without any concerns.
delay 2
repeat
delay 0.2
tell application "System Events"
if (item 1 of (get name of processes whose frontmost is true)) is "TextEdit" then
set r to (random number from 0 to 1)
if (r = 0) then
keystroke "0"
else if (r = 1) then
keystroke "1"
end if
end if
end tell
end repeat
It will take a long time to create a large sample with a .2 delay and keystrokes.
Try something like this:
set csvOutputPath to (POSIX path of (path to desktop as text)) & "test.txt"
set fileRef to (open for access csvOutputPath)
close access csvOutputPath
set numberList to {}
set counter to 0
repeat
set end of numberList to (random number from 0 to 1)
set counter to counter + 1
if (counter mod 10000) = 0 then
write (numberList as text) to csvOutputPath starting at eof
set numberList to {}
end if
end repeat

Applescript: Passing track metadata from text file to broadcast streaming app

I know virtually nothing about AppleScript and could do with some help.
While running, my broadcast playout system (MegaSeg) writes details of the track currently playing to a textfile called "NowPlaying" which contains solely the following contents, each on its own line and without square brackets:
Title: [title]
Artist: [artist]
Album: [album]
Time: [time in some format or other]
I want to pass this to my broadcast streamer LadioCast, which can be addressed via AppleScript, so that it sends info on what is playing to the streaming server.
MegaSeg doesn't support Applescript calls like 'tell application "MegaSeg"... set trackName to name of current track' so I can't do it that way. I have no idea about how to do this.
If we imagine that I was able to grab that info, this is what I would do with it:
set lastName to ""
set lastArtist to ""
set lastAlbum to ""
repeat
** insert missing file reading section here
** in the following, "title", "artist" and "album" are from the text file **
set trackName to title
set trackArtist to artist
set trackAlbum to album
** end of missing section
if trackName is not lastName and trackArtist is not lastArtist and trackAlbum is not lastAlbum then
set lastName to trackName
set lastArtist to trackArtist
set lastAlbum to trackAlbum
tell application "LadioCast"
set metadata song to trackName & " – " & trackArtist & " – " & trackAlbum
end tell
end if
delay 15
end repeat
Thanks in advance.
--Richard E
===
I tried the suggestions from #DigiMonk and they were very helpful, but not all of them worked. First, the file is in a specific location and not on the desktop; second, I could not get 'trim_line' to work at all - I got "script does not understand trim_line message". However the text in the file seems to be already trimmed.
The script below nearly works; when run from the Applescript Editor it does seem to get the Title, Artist and Album into the variables. However when I try running it from LadioCast I get an EOF -39 error. More importantly, as soon as I run this, MegaSeg stops updating the file, forever. I am presumably locking the file to read from it and stopping MegaSeg writing to it. How do I avoid this?
set lastName to ""
set lastArtist to ""
set lastAlbum to ""
set lastTime to ""
set trackName to ""
set trackArtist to ""
set trackAlbum to ""
set sourcePath to ""
repeat
set sourcePath to open for access file "Library:MegaSeg User Data:Logs:Logs for MegaSeg System (4):NowPlaying"
set thisText to read sourcePath as text
close access file "Library:MegaSeg User Data:Logs:Logs for MegaSeg System (4):NowPlaying"
set the paragraphList to every paragraph of thisText
repeat with i from 1 to number of items in paragraphList
set thisItem to item i of paragraphList
if thisItem starts with "Title:" then
set x to the offset of "Title:" in thisItem
set trackName to (text (x + 6) thru -1 of thisItem)
else if thisItem starts with "Artist:" then
set x to the offset of "Artist:" in thisItem
set trackArtist to (text (x + 7) thru -1 of thisItem)
else if thisItem starts with "Album:" then
set x to the offset of "Album:" in thisItem
set trackAlbum to (text (x + 6) thru -1 of thisItem)
end if
end repeat
if trackName is not lastName and trackArtist is not lastArtist and trackAlbum is not lastAlbum then
set lastName to trackName
set lastArtist to trackArtist
set lastAlbum to trackAlbum
tell application "LadioCast"
set metadata song to trackName & " – " & trackArtist & " – " & trackAlbum
end tell
end if
delay 15
end repeat
May be this helps: (feed sourcePath with the path to your NowPlaying.txt file)
set sourcePath to (path to desktop) & "NowPlaying.txt" as text
set thisText to my readFile(sourcePath)
set the paragraphList to every paragraph of thisText
set lastName to ""
set lastArtist to ""
set lastAlbum to ""
set lastTime to ""
repeat with i from 1 to number of items in paragraphList
set thisItem to item i of paragraphList
--log thisItem
if thisItem starts with "Title:" then
set x to the offset of "Title:" in thisItem
set y to (text (x + 6) thru -1 of thisItem)
set lastName to my trim_line(y, " ", 2)
else if thisItem starts with "Artist:" then
set x to the offset of "Artist:" in thisItem
set y to (text (x + 7) thru -1 of thisItem)
set lastArtist to my trim_line(y, " ", 2)
else if thisItem starts with "Album:" then
set x to the offset of "Album:" in thisItem
set y to (text (x + 6) thru -1 of thisItem)
set lastAlbum to my trim_line(y, " ", 2)
else if thisItem starts with "Time:" then
set x to the offset of "Time:" in thisItem
set y to (text (x + 5) thru -1 of thisItem)
set lastTime to my trim_line(y, " ", 2)
end if
end repeat
log "lastName = '" & lastName & "'"
log "lastArtist = '" & lastArtist & "'"
log "lastAlbum = '" & lastAlbum & "'"
on readFile(thisFile)
set thisFile to thisFile as text
if thisFile is "" then return ""
try
set fi to open for access file the thisFile
set myData to read fi as text
close access file the thisFile
return myData
on error
try
close access file the thisFile
return ""
end try
end try
end readFile
on trim_line(this_text, trim_chars, trim_indicator)
-- 0 = beginning, 1 = end, 2 = both
set x to the length of the trim_chars
-- TRIM BEGINNING
if the trim_indicator is in {0, 2} then
repeat while this_text begins with the trim_chars
try
set this_text to characters (x + 1) thru -1 of this_text as string
on error
-- the text contains nothing but the trim characters
return ""
end try
end repeat
end if
-- TRIM ENDING
if the trim_indicator is in {1, 2} then
repeat while this_text ends with the trim_chars
try
set this_text to characters 1 thru -(x + 1) of this_text as string
on error
-- the text contains nothing but the trim characters
return ""
end try
end repeat
end if
return this_text
end trim_line

Repeat function if variable is changed?

Having trouble figuring out this loop - I want the below function to repeat ONLY if myText changes (i.e. the album the individual is listening to changes) - I have been able to make it loop a certain number of times or repeat in the event the track changes, but I want it to repeat in the event the album changes.
tell application "iTunes"
repeat if myText changes
if player state is playing then
set albumName to (get album of current track)
set myText to text 1 thru 10 of albumName
end if
end repeat
end tell
open location "http://bandsite.com/shows/" & myText
When the code works without the repeat command it looks like this:
tell application "iTunes"
if player state is playing then
set albumName to (get album of current track)
set myText to text 1 thru 10 of albumName
end if
end tell
open location "http://bandsite.com/shows/" & myText
I need the whole function to repeat in the event myText changes
Save this as a stay open application:
property myList : {}
on run
set albumA to my playCheck()
if albumA ≠ false then
set end of myList to albumA
else
quit -- Quit on the next idle.
return 1 -- Please send the next idle as soon as possible.
end if
end run
on idle
set albumA to my playCheck()
if albumA ≠ false then
set end of myList to albumA
if (item -1 of myList) ≠ (item -2 of myList) then
open location "http://bandsite.com/shows/" & (text 1 thru 10 of albumA)
end if
end if
return 3
end idle
on playCheck()
tell application "iTunes"
if player state is playing then return (get album of current track)
return false
end tell
end playCheck
temptext = mytext
do
if temptext != myText
tell application "iTunes"
if player state is playing then
set albumName to (get album of current track)
set myText to text 1 thru 10 of albumName
end if
end tell
temptext = myText
end if
while temptext==text
Try this
Hope this is what you want...

Resources