Most Python developers can parse a CSV, write a decorator and pip install their way out of a problem.

Python experts know what happens when the operating system doesn't want you to do the thing: when a hotkey is reserved, when an audio device goes quiet, when a screen grab is slower than your frame rate, and when ctypes quietly cuts your pointers in half.

I found out which one I was while building ASNIPP: a screenshot tool, screen recorder, live-drawing overlay, colour picker and video editor for Windows. It is one Python file, about 7,600 lines, with no ads, no analytics and no network calls. Everything runs on your machine.

Every test below is a real bug or design decision from that file. The code is trimmed for reading, but the ideas are exactly what ships. Score yourself honestly. 👇

Test 1: Can you take a hotkey that Windows says is reserved?

I wanted Win+Shift+S to open ASNIPP instead of the Snipping Tool. The obvious tool is RegisterHotKey. It fails: that combo belongs to the shell.

The way in is a low-level keyboard hook (WH_KEYBOARD_LL) through ctypes. It sees the keystroke before anyone else, and if your callback returns 1, the key never reaches Windows.

def cb(nCode, wParam, lParam): if nCode == 0 and wParam in (0x100, 0x101, 0x104, 0x105): # key down / up  kb = ctypes.cast(lParam, ctypes.POINTER(_KBDLLHOOKSTRUCT)).contents if kb.vkCode in SNIP_HOOK_KEYS: # only S and R, nothing else  action, self._pending[kb.vkCode] = snip_hook_decision( kb.vkCode, wParam in (0x100, 0x104), bool(kb.flags & 0x10), pressed(0x5B, 0x5C), pressed(0x10), pressed(0x11), pressed(0x12), self._pending.get(kb.vkCode, False)) if action == "trigger": u.keybd_event(0xE8, 0, 0, 0) # inject an unassigned key...  u.keybd_event(0xE8, 0, 2, 0) # ...so releasing Win doesn't open Start  QTimer.singleShot(0, lambda: self.on_trigger("photo")) return 1 # swallowed  if action == "swallow": return 1 return u.CallNextHookEx(None, nCode, wParam, lParam) self._proc = HOOKPROC(cb) # keep a reference or it gets garbage-collected self.hook = u.SetWindowsHookExW(13, self._proc, k.GetModuleHandleW(None), 0) 

Four details separate "it works once" from "it works":

  1. Swallow the key-up too. If you eat the S press but let the release through, apps see a stray key-up. ASNIPP remembers it ate the press and eats exactly one release.
  2. Inject a dummy key (0xE8). Press and release Win alone and Windows opens Start. A harmless unassigned keystroke in between cancels that.
  3. Ignore injected events (flags & 0x10), or your own keybd_event call will trigger you again.
  4. The decision logic is a pure function with no ctypes in it, so it can be tested without a keyboard:
def snip_hook_decision(vk, down, injected, win, shift, ctrl, alt, pending_up): if injected or vk not in SNIP_HOOK_KEYS: return "pass", pending_up if down: if win and shift and not ctrl and not alt: return "trigger", True return "pass", pending_up if pending_up: return "swallow", False return "pass", pending_up 

It only looks at S and R while Win+Shift are held. Nothing is logged or stored, and the source says so at the top of the class, because a keyboard hook should always be honest about what it reads.

Developer: pip install keyboard.
Expert: knows where the hook sits in the input chain, and writes the state machine as a pure function.

Test 2: Why is my recording's audio 40 seconds shorter than the video?

ASNIPP records system audio with WASAPI loopback. The first test recording looked fine, until I played a video with long silent parts: the sound drifted further and further ahead of the picture.

The cause: loopback delivers no data at all while nothing is playing. No callbacks, no zeros, nothing. If you just append whatever arrives, silence disappears from the file and everything after it slides earlier.

The fix is to treat the wall clock as the truth and pad the gaps yourself:

def push(self, data): # called from the audio thread  with self.lock: if self.fill: # only for loopback, not the mic  now = rec.active_time() # seconds of *unpaused* recording  gap = int((now - n / self.rate) * self.rate) - self.frames if gap > self.rate * 0.12: # ignore jitter under 120 ms  self._zeros(gap) # write real silence  self.f.write(pcm.tobytes()) self.frames += n 

active_time() is perf_counter() minus the start time minus every second spent paused. So pausing the recording pauses the audio clock too.

Bonus trap: sounddevice has no WASAPI loopback. System audio needs PyAudioWPatch, with a "Stereo Mix" device as the fallback. ASNIPP tries both and tells the user which one is missing instead of silently recording nothing.

Developer: appends the bytes it receives.
Expert: asks "what does this API do when there is nothing to say?"

Test 3: What happens when grab() can't keep up with 30 FPS?

The recorder is a loop of mss.grab() → cv2.VideoWriter.write(). On a busy 4K screen a grab can take longer than 33 ms. If you write one frame per grab, a 10-second recording is stored as 6 seconds of video, and it plays back too fast.

The loop doesn't count frames. It counts time, and writes as many frames as the clock says are owed:

active += dt # unpaused seconds so far img = sct.grab(self.monitor) fr = np.ascontiguousarray(np.asarray(img)[:, :, :3]) # BGRA -> BGR  target = int(active * fps) + 1 # frames that SHOULD exist by now n = max(1, min(target - written, fps)) # catch up, but never more than 1 s at once for _ in range(n): out.write(fr) written += n wait = written / fps - (active + (time.perf_counter() - last)) if wait > 0: time.sleep(min(wait, 0.05)) # too fast? sleep. Too slow? duplicate. 

A slow machine gets a few repeated frames. A fast machine gets a sleep. Either way the video is exactly as long as the real recording, which is what keeps the audio from Test 2 in sync.

Two small things make it production-grade: the min(..., fps) cap stops a long stall from dumping thousands of frames, and the audio clock starts from an on_ready callback fired right before the first frame, so both streams share the same zero.

Developer: time.sleep(1/30) in a loop.
Expert: knows sleep is a request, not a guarantee, and schedules against a clock.

Test 4: Why did my mic get quieter when I turned on system audio?

After recording, ASNIPP mixes the system track and the mic track into the MP4 with ffmpeg. Turn on both and the voice sounded half as loud.

amix divides each input by the number of inputs by default. Two tracks, so each is halved. The fix is normalize=0, but not every ffmpeg build knows that option, so the mixer tries variants in order and moves on when one fails:

variants = [ chains + [f"[a0][a1]amix=inputs=2:duration=longest:normalize=0,apad,atrim=0:{d}[m]"], chains + [f"[a0][a1]amix=inputs=2:duration=longest,volume=2,apad,atrim=0:{d}[m]"], # older builds ] for fc in variants: ok, err = run_ffmpeg(args + ["-filter_complex", ";".join(fc), ...]) if ok: break 

Look at the tail too: apad,atrim=0:{d}. If the audio is a hair shorter than the video, ffmpeg's -shortest would cut the video. Padding the audio and then trimming to the exact video length means a short track can never shorten the video.

And if ffmpeg is missing entirely? ASNIPP mixes the tracks in pure NumPy and saves a .wav next to the video, with a note saying what to install. It degrades, it doesn't crash.

Developer: ffmpeg -i a -i b out.mp4.
Expert: reads what each filter assumes, and keeps a plan B.

Test 5: Why does GetWindowLongPtrW return garbage in Python?

Live drawing mode puts a transparent overlay over your whole screen. Sometimes you want to click through it to the app underneath. That is the WS_EX_TRANSPARENT window style, set through ctypes:

u = ctypes.windll.user32 get_l, set_l = u.GetWindowLongPtrW, u.SetWindowLongPtrW get_l.restype = ctypes.c_ssize_t # <- the whole point get_l.argtypes = [ctypes.c_void_p, ctypes.c_int] set_l.restype = ctypes.c_ssize_t set_l.argtypes = [ctypes.c_void_p, ctypes.c_int, ctypes.c_ssize_t] hwnd = int(widget.winId()) st = get_l(hwnd, -20) # GWL_EXSTYLE st = (st | 0x20 | 0x80000) if on else (st & ~0x20) # TRANSPARENT | LAYERED set_l(hwnd, -20, st) 

ctypes assumes every foreign function returns a 32-bit int and takes 32-bit arguments. On 64-bit Windows, handles and pointer-sized values are 64 bits, so without restype and argtypes you get truncated values, sign errors and crashes that only appear on some machines. Declare every signature, every time.

The function also falls back to Qt's own WA_TransparentForMouseEvents if the Win32 route fails, and a 32-bit Python gets GetWindowLongW instead. Same idea as Test 4: the ideal path first, and an honest fallback after.

Developer: copies the snippet from Stack Overflow.
Expert: writes down the C signature before calling the C function.

Test 6: Does "delete" actually mean delete?

ASNIPP's library has a delete button. os.remove() is permanent, and nobody forgives a tool that permanently deletes their screenshot after one misclick. So deleting sends the file to the Recycle Bin, using SHFileOperationW and no third-party package:

class SHFILEOPSTRUCTW(ctypes.Structure): _pack_ = 1 if ctypes.sizeof(ctypes.c_void_p) == 4 else 8 # 32 vs 64-bit layout  _fields_ = [("hwnd", wt.HWND), ("wFunc", wt.UINT), ("pFrom", wt.LPCWSTR), ("pTo", wt.LPCWSTR), ("fFlags", ctypes.c_ushort), ("fAnyOperationsAborted", wt.BOOL), ("hNameMappings", ctypes.c_void_p), ("lpszProgressTitle", wt.LPCWSTR)] op = SHFILEOPSTRUCTW() op.wFunc = 3 # FO_DELETE op.pFrom = os.path.abspath(path) + "\0" # must end in TWO nulls (Python adds one) op.fFlags = 0x40 | 0x10 | 0x4 | 0x400 # ALLOWUNDO | NOCONFIRM | SILENT | NOERRORUI res = ctypes.windll.shell32.SHFileOperationW(ctypes.byref(op)) return res == 0 and not op.fAnyOperationsAborted and not os.path.exists(path) 

The last line matters most. The function returns True only if the file is really gone. Not "the call returned 0". Not "no exception". The API said yes and the filesystem agrees.

If it can't reach the Recycle Bin (some network drives), the UI can say so rather than claim a delete that didn't happen.

Developer: trusts the return code.
Expert: verifies the world changed.

Test 7: Is your eyedropper accurate to the pixel on a scaled display?

ASNIPP has a colour picker with a magnifier and a pixel ruler. The first version was off by one pixel on my laptop, and by several on my friend's 150% display.

Two decisions fixed it:

1. Freeze the screen first. The picker doesn't read live pixels. It hides ASNIPP's own island, waits 160 ms for the compositor, grabs the screen once, and works on that frozen image. Menus, tooltips and hover states stay exactly as they were when you pressed the key.

def _grab_prepare(self, mode): self.island.hide() QTimer.singleShot(160, lambda: self._grab(mode)) # let the window really disappear  def _grab(self, mode): pix = screen.grabWindow(0) pix.setDevicePixelRatio(1.0) # work in true device pixels 

2. Never assume widget size equals image size. Convert with a ratio, clamp, and put the point back at the centre of its pixel:

def _sx(self): return self.img.width() / max(self.width(), 1) def _to_img(self, pt): # widget -> image pixel  return QPoint(min(max(int(pt.x() * self._sx()), 0), self.img.width() - 1), min(max(int(pt.y() * self._sy()), 0), self.img.height() - 1)) def _to_view(self, ip): # image pixel -> widget  return QPointF((ip.x() + 0.5) / self._sx(), (ip.y() + 0.5) / self._sy()) 

That + 0.5 is the trick. A pixel is a square, not a point. Draw the crosshair on its corner and everything looks half a pixel off. The ruler also snaps to 45° steps with one line of atan2:

ang = round(math.atan2(dy, dx) / (math.pi / 4)) * (math.pi / 4) 

Developer: int(event.x()) and hope.
Expert: knows a pixel has a centre, and that screens have scale factors.

Test 8: Can your app leave the PC exactly how it found it?

To own PrintScreen, ASNIPP has to turn off a Windows setting (PrintScreenKeyForSnippingEnabled) in the registry. That is the user's setting, not mine. So the takeover is a reversible transaction:

cur = read_prtscn_setting() if cur != 0: if self.settings.get("prev_prtscn") == -1: # remember it ONCE  self.settings.set("prev_prtscn", cur) write_prtscn_setting(0) ... # turning ASNIPP's takeover off again: prev = self.settings.get("prev_prtscn") if prev in (0, 1): write_prtscn_setting(prev) # put it back 

Around that sit a handful of unglamorous habits that make software feel trustworthy:

  • Settings are written atomically. Write settings.json.tmp, then os.replace() over the real file. A crash mid-write can't leave half a file.
  • Settings are type-checked on load. A value is only accepted if isinstance(raw[k], type(default)). A hand-edited "autostart": "yes" can't break startup.
  • Apply first, explain second. On first run the takeover is applied before the dialog appears, so closing the box can't undo it.
  • Never show a dialog during a silent login start (--background).
  • One instance only. A named mutex, and GetLastError() == 183 (ERROR_ALREADY_EXISTS) means "someone is already holding the hotkeys, so exit quietly".
  • "Start with Windows" is opt-in, and the command it writes handles Nuitka builds, PyInstaller builds and plain pythonw.exe.

Developer: ships features.
Expert: ships an undo button for every side effect.

Bonus: OCR with zero pip packages

ASNIPP can copy text out of any screenshot. No Tesseract, no model download. Windows already ships an OCR engine (Windows.Media.Ocr), and Python can drive it through PowerShell:

with open(ps1, "w", encoding="utf-8-sig") as f: # BOM so PowerShell reads Unicode correctly  f.write(script) subprocess.run(["powershell", "-NoProfile", "-ExecutionPolicy", "Bypass", "-File", ps1], capture_output=True, timeout=120, creationflags=0x08000000) # no console flash 

The utf-8-sig is the whole lesson: without the BOM, Windows PowerShell 5 reads the script as the legacy code page and non-English text turns to mush. And 0x08000000 (CREATE_NO_WINDOW) stops a black console from flashing on screen every time you press the button.

Also from the file: ffmpeg's atempo only accepts 0.5x to 2x, so a 4x speed-up has to be chained (atempo=2.0,atempo=2.0). A tiny while loop in atempo_chain() does it.

Try the code yourself

All of this lives in ASNIPP, built by Akhouri Systems: a pure-Python Windows app with a "Dynamic Island" style capture bar. It has no ads, no analytics and no network calls. It does exactly what's on the tin, and the hook in Test 1 only ever looks at the keys it needs.

What you get Details
📸 Photo capture Win+Shift+S, Ctrl+Shift+S or PrintScreen. Region, window or full screen, copied to clipboard and saved
🎥 Screen recorder Win+Shift+R, with system audio + mic, pause and a recording border that never appears in the video
✏️ Live drawing Ctrl+Alt+D. Pen, shapes, laser pointer and auto-fade, over any app, and it can be recorded
🎯 Colour picker + ruler Ctrl+Alt+P. Magnifier, HEX/RGB copy, pixel distances and angles
🎞️ Video editor Trim, split, join, speed, reverse, rotate, looks, GIF export
🔤 OCR + pins Copy text from any screenshot, pin an image on top of every window

👉 Download ASNIPP v1 (zip)

If you're learning how Python behaves outside a notebook, run it, press Win+Shift+S, and then ask yourself what is happening between your keypress and the screen. That is the fastest way I know to level up.

Try ASNIPP_v1:https://github.com/Akhouri-Systems/ASNIPP/releases/download/v1.0.0/ASNIPP_v1.zip
not just try it, break it too.
I want feedbacks because feedbacks would make ASNIPP_v2 better.

Your score

  • 0-2 tests known: You're a Python developer. Great start. Now write something that has to talk to the OS.
  • 3-5: Solid. You've shipped something real.
  • 6-8: You're a Python expert. Come argue with me in the comments.

Which test did you fail first? Mine was Test 2: a recording that looked perfect until the first long silence, then slowly drifted out of sync. I lost two evenings to it. Tell me yours below 👇