4

How to know which process or App is responsible for creating/managing a particular window in macOS?

In my case I got really cryptic error message, in non modal free floating window.
Using message found that it is from Sparkle framework, but I don't know which process or App cause it.

1
  • 3
    You could summarize your finding as an answer and accept it linking to the source rather than delete the question.
    – Allan
    Mar 7, 2018 at 19:21

1 Answer 1

5

This script will print information(owning PID) about visible windows.
And information for the window that changed position within a 5 second interval.
Credit goes to superuser answer

#!/usr/bin/env python
    
import Quartz
import time
from Foundation import NSSet, NSMutableSet
def transformWindowData(data):
    list1 = []
    for v in data:
        if not v.valueForKey_('kCGWindowIsOnscreen'):
            continue
        

        row = ( \
            str(v.valueForKey_('kCGWindowOwnerPID') or '?').rjust(7) + \
            ' ' + str(v.valueForKey_('kCGWindowNumber') or '?').rjust(5) + \
            ' {' + ('' if v.valueForKey_('kCGWindowBounds') is None else \
                ( \
                    str(int(v.valueForKey_('kCGWindowBounds').valueForKey_('X')))     + ',' + \
                    str(int(v.valueForKey_('kCGWindowBounds').valueForKey_('Y')))     + ',' + \
                    str(int(v.valueForKey_('kCGWindowBounds').valueForKey_('Width'))) + ',' + \
                    str(int(v.valueForKey_('kCGWindowBounds').valueForKey_('Height'))) \
                ) \
                ).ljust(21) + \
            '}' + \
            '\t[' + ((v.valueForKey_('kCGWindowOwnerName') or '') + ']') + \
            ('' if v.valueForKey_('kCGWindowName') is None else (' ' + v.valueForKey_('kCGWindowName') or '')) \
        ).encode('utf8')
        list1.append(row)

    return list1;

def printBeautifully(dataSet):
    print 'PID'.rjust(7) + ' ' + 'WinID'.rjust(5) + '  ' + 'x,y,w,h'.ljust(21) + ' ' + '\t[Title] SubTitle'
    print '-'.rjust(7,'-') + ' ' + '-'.rjust(5,'-') + '  ' + '-'.ljust(21,'-') + ' ' + '\t-------------------------------------------'

    # print textList1
    for v in dataSet:
        print v;

#grab initial set
wl = Quartz.CGWindowListCopyWindowInfo( Quartz.kCGWindowListOptionAll, Quartz.kCGNullWindowID)
wl = sorted(wl, key=lambda k: k.valueForKey_('kCGWindowOwnerPID'))

#convert into readable format
textList1 = transformWindowData(wl);

#print everything we have on the screen
print 'all windows:'
printBeautifully(textList1)

print 'Move target window'
time.sleep(5)

#grab window data the second time
wl2 = Quartz.CGWindowListCopyWindowInfo(Quartz.kCGWindowListOptionAll, Quartz.kCGNullWindowID)
textList2 = transformWindowData(wl2)

#check the difference
w = NSMutableSet.setWithArray_(textList1)
w.minusSet_(NSSet.setWithArray_(textList2))

#print the difference
printBeautifully(w)

Output:

all windows:
    PID WinID  x,y,w,h                  [Title] SubTitle
------- -----  ---------------------    -------------------------------------------
    204     2 {0,0,1280,800         }   [Window Server] Desktop
    479    36 {0,0,1280,800         }   [Dock] Desktop Picture - DefaultDesktop.jpg
    731  2893 {640,0,640,800        }   [Finder] /Users/wolf/Downloads
    731   260 {-608,-1440,2560,1440 }   [Finder]
    731   259 {0,0,1280,800         }   [Finder]
   1301   321 {0,366,1280,411       }   [Audio Hijack] Application Audio
Move target window
    PID WinID  x,y,w,h                  [Title] SubTitle
------- -----  ---------------------    -------------------------------------------
   1301   321 {0,366,1280,411       }   [Audio Hijack] Application Audio
2
  • 1
    To get it work I've used macports: sudo port install python27 sudo port select --set python python27 sudo port install py27-pip sudo port select --set pip pip27 pip install pyobjc-framework-Quartz. Once these are set up the script worked as expected.
    – sbnc.eu
    Feb 13 at 17:55
  • I'd recommend checking out the other answers on the linked SU post — there are some simpler solutions for most use cases. In particular the Automator and Accessibility Inspector answers are more user friendly. (probably worth bringing them over here as an answer, in fact, but I don't have time at the moment)
    – Tuesday
    May 14 at 18:41

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .