Zonza : dictée vocale locale macOS (MLX-Whisper + cercle pulsant)
Reconstruction propre de l'ancien projet Dictée. Bundle id neuf (cloud.mrtechlab.zonza), chemin de build unique vers /Applications (plus jamais de builds /tmp enregistrés dans LaunchServices). Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,64 @@
|
||||
"""Génère assets/icon.png (1024×1024) : un micro stylisé sur un carré violet dégradé.
|
||||
|
||||
Reproductible et sans dépendance externe (Pillow seulement). Lancer : python assets/make_icon.py
|
||||
"""
|
||||
import os
|
||||
|
||||
from PIL import Image, ImageDraw
|
||||
|
||||
SIZE = 1024
|
||||
BG_TOP = (130, 80, 235) # violet
|
||||
BG_BOT = (85, 50, 180) # violet plus foncé (dégradé vertical)
|
||||
MIC = (255, 255, 255)
|
||||
|
||||
|
||||
def _rounded_gradient(size, radius):
|
||||
"""Carré arrondi avec dégradé vertical."""
|
||||
base = Image.new("RGBA", (size, size), (0, 0, 0, 0))
|
||||
grad = Image.new("RGBA", (size, size))
|
||||
for y in range(size):
|
||||
t = y / (size - 1)
|
||||
r = int(BG_TOP[0] * (1 - t) + BG_BOT[0] * t)
|
||||
g = int(BG_TOP[1] * (1 - t) + BG_BOT[1] * t)
|
||||
b = int(BG_TOP[2] * (1 - t) + BG_BOT[2] * t)
|
||||
for x in range(size):
|
||||
grad.putpixel((x, y), (r, g, b, 255))
|
||||
mask = Image.new("L", (size, size), 0)
|
||||
ImageDraw.Draw(mask).rounded_rectangle([0, 0, size, size], radius=radius, fill=255)
|
||||
base.paste(grad, (0, 0), mask)
|
||||
return base
|
||||
|
||||
|
||||
def make_icon(path):
|
||||
img = _rounded_gradient(SIZE, radius=int(SIZE * 0.22))
|
||||
d = ImageDraw.Draw(img)
|
||||
cx = SIZE / 2
|
||||
# corps du micro (capsule arrondie)
|
||||
mic_w, mic_h = SIZE * 0.26, SIZE * 0.40
|
||||
top = SIZE * 0.20
|
||||
d.rounded_rectangle(
|
||||
[cx - mic_w / 2, top, cx + mic_w / 2, top + mic_h],
|
||||
radius=mic_w / 2, fill=MIC,
|
||||
)
|
||||
# arceau (support en U sous le micro)
|
||||
arc_r = SIZE * 0.20
|
||||
arc_cy = top + mic_h * 0.55
|
||||
d.arc(
|
||||
[cx - arc_r, arc_cy - arc_r, cx + arc_r, arc_cy + arc_r],
|
||||
start=20, end=160, fill=MIC, width=int(SIZE * 0.035),
|
||||
)
|
||||
# pied du micro
|
||||
foot_top = arc_cy + arc_r
|
||||
d.line([cx, foot_top, cx, foot_top + SIZE * 0.10], fill=MIC, width=int(SIZE * 0.035))
|
||||
d.line(
|
||||
[cx - SIZE * 0.10, foot_top + SIZE * 0.10, cx + SIZE * 0.10, foot_top + SIZE * 0.10],
|
||||
fill=MIC, width=int(SIZE * 0.035),
|
||||
)
|
||||
os.makedirs(os.path.dirname(path), exist_ok=True)
|
||||
img.save(path)
|
||||
print(f"icône écrite : {path}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
here = os.path.dirname(os.path.abspath(__file__))
|
||||
make_icon(os.path.join(here, "icon.png"))
|
||||
Reference in New Issue
Block a user