iOS 16 中引入了全新的天文墙纸,可以将地球照片设置为桌面背景,并且能够根据地理位置和时间进行实时地渲染。那么有办法在 macOS 上用上类似的壁纸么?答案是肯定的,我们可以使用 Himawari 8 气象卫星的地球照片作为壁纸。
在网上搜索相关的关键词,我们可以找到很多 Windows 上的实现。而在 macOS 上,更换壁纸的方式有所不同。比较简单的方式是创建一个 Swift 脚本:1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 #!/ usr/bin/ env swift import Cocoado { if let screen = NSScreen .main { let url = URL (fileURLWithPath: CommandLine .arguments[1 ]) try NSWorkspace .shared.setDesktopImageURL(url, for: screen, options: [:]) } } catch { print (error) }
将其保存为 chwall.swift
,然后将其设置为可执行文件:
然后,我们使用一个 Python 脚本来下载 Himawari 8 的地球照片,并调用 chwall.swift
将图片设置为壁纸:1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 from PIL import Imageimport osimport datetimeimport requestsimport subprocessfrom itertools import productimport tracebackimport tempfileIMAGE_SIZE = 688 IMAGE_ROW = 2 IMAGE_COLUMN = 2 images_dir = os.path.join(os.path.dirname(__file__), 'images' ) if not os.path.exists(images_dir): os.makedirs(images_dir) def compose_img (): latest_times = requests.get('https://rammb-slider.cira.colostate.edu/data/json/himawari/full_disk/geocolor/latest_times.json' ) time = str (latest_times.json()['timestamps_int' ][0 ]) dirpath = f'{time[:4 ]} /{time[4 :6 ]} /{time[6 :8 ]} ' full_image = Image.new( 'RGB' , (IMAGE_SIZE * IMAGE_COLUMN, IMAGE_SIZE * IMAGE_ROW)) for i, j in product([0 , 1 ], [0 , 1 ]): imgname = f'00{i} _00{j} .png' url = 'https://rammb-slider.cira.colostate.edu/data/imagery/' + \ dirpath + '/himawari---full_disk/geocolor/' + time + '/01/' + imgname print (f'图片 {url} 正在下载…' ) response = requests.get(url, stream=True ) image_path = os.path.join(images_dir, imgname) img = Image.open (response.raw) width, height = img.size assert width == height == IMAGE_SIZE img.save(image_path) print (f'图片 {imgname} 下载成功!' ) full_image.paste(img, (j * IMAGE_SIZE, i * IMAGE_SIZE)) full_image.save(os.path.join(images_dir, 'full.png' )) height = int (IMAGE_SIZE * IMAGE_ROW / 0.618 ) width = int (height / 9 * 16 ) image = Image.new('RGB' , (width, height)) image.paste( full_image, (int (width / 2 - IMAGE_SIZE * IMAGE_ROW / 2 ), int (height * 0.382 / 2 ))) image_path = tempfile.NamedTemporaryFile(suffix='.png' ).name image.save(image_path) print (f'图片 {image_path} 保存成功!' ) return image_path try : subprocess.run(['./chwall.swift' , compose_img()]) print ('壁纸设置成功!' ) except Exception as e: print ('壁纸设置失败!' ) traceback.print_exc()
最后,使用 Launchd 来定时运行这个脚本,即可实现自动更换壁纸。
需要注意,macOS 会缓存使用过的壁纸,相关的目录包括
~/Library/Application Support/Dock/desktoppicture.db
/private/var/folders/**/**/com.apple.desktoppicture
这些缓存不会自动清除,经常更换壁纸的话缓存占用的空间会增加。
参考文章:How can I programmatically change the background in Mac OS X? OS X: com.apple.desktoppicture folder grows when changing the wallpaper
有关 GitHub 仓库:SpaceEye