Was macht Slack-GIF-Ersteller?
Ein Toolkit mit Werkzeugen und Wissen zur Erstellung animierter GIFs, optimiert für Slack.
Slack-Anforderungen
Abmessungen:
- Emoji-GIFs: 128×128 (empfohlen)
- Nachrichten-GIFs: 480×480
Parameter:
- FPS: 10–30 (niedriger = kleinere Dateigröße)
- Farben: 48–128 (weniger = kleinere Dateigröße)
- Dauer: Bei Emoji-GIFs unter 3 Sekunden halten
Kern-Workflow
from core.gif_builder import GIFBuilder
from PIL import Image, ImageDraw
# 1. Builder erstellen
builder = GIFBuilder(width=128, height=128, fps=10)
# 2. Frames generieren
for i in range(12):
frame = Image.new('RGB', (128, 128), (240, 248, 255))
draw = ImageDraw.Draw(frame)
# Zeichnen Sie Ihre Animation mit PIL-Primitiven
# (Kreise, Polygone, Linien, etc.)
builder.add_frame(frame)
# 3. Mit Optimierung speichern
builder.save('output.gif', num_colors=48, optimize_for_emoji=True)
Grafiken zeichnen
Arbeiten mit vom Benutzer hochgeladenen Bildern
Wenn ein Benutzer ein Bild hochlädt, überlegen Sie, ob er es:
- Direkt verwenden möchte (z. B. „animieren Sie dies“, „teilen Sie dies in Einzelbilder auf“)
- Als Inspiration nutzen möchte (z. B. „machen Sie etwas Ähnliches“)
Laden und arbeiten Sie mit Bildern mit PIL:
from PIL import Image
uploaded = Image.open('file.png')
# Direkt verwenden oder nur als Referenz für Farben/Stil
Von Grund auf zeichnen
Wenn Sie Grafiken von Grund auf zeichnen, verwenden Sie PIL-ImageDraw-Primitive:
from PIL import ImageDraw
draw = ImageDraw.Draw(frame)
# Kreise/Ovale
draw.ellipse([x1, y1, x2, y2], fill=(r, g, b), outline=(r, g, b), width=3)
# Sterne, Dreiecke, beliebige Polygone
points = [(x1, y1), (x2, y2), (x3, y3), ...]
draw.polygon(points, fill=(r, g, b), outline=(r, g, b), width=3)
# Linien
draw.line([(x1, y1), (x2, y2)], fill=(r, g, b), width=5)
# Rechtecke
draw.rectangle([x1, y1, x2, y2], fill=(r, g, b), outline=(r, g, b), width=3)
Nicht verwenden: Emoji-Schriftarten (plattformabhängig unzuverlässig) oder davon ausgehen, dass in diesem Skill vorgefertigte Grafiken vorhanden sind.
Grafiken ansprechend gestalten
Grafiken sollten poliert und kreativ wirken, nicht primitiv. So geht's:
Verwenden Sie dickere Linien – Setzen Sie bei Konturen und Linien immer width=2 oder höher. Dünne Linien (width=1) wirken abgehackt und amateurhaft.
Tiefe hinzufügen:
- Verwenden Sie Farbverläufe für Hintergründe (
create_gradient_background) - Überlagern Sie mehrere Formen für mehr Komplexität (z. B. ein Stern mit einem kleineren Stern darin)
Formen interessanter machen:
- Zeichnen Sie nicht nur einen einfachen Kreis – fügen Sie Highlights, Ringe oder Muster hinzu
- Sterne können Glühen erhalten (größere, halbtransparente Versionen dahinter zeichnen)
- Kombinieren Sie mehrere Formen (Sterne + Glitzer, Kreise + Ringe)
Achten Sie auf Farben:
- Verwenden Sie lebendige, komplementäre Farben
- Setzen Sie Kontraste (dunkle Konturen auf hellen Formen, helle Konturen auf dunklen Formen)
- Berücksichtigen Sie die Gesamtkomposition
Für komplexe Formen (Herzen, Schneeflocken, etc.):
- Verwenden Sie Kombinationen aus Polygonen und Ellipsen
- Berechnen Sie Punkte sorgfältig für Symmetrie
- Fügen Sie Details hinzu (ein Herz kann eine Highlight-Kurve haben, Schneeflocken haben verzweigte Strukturen)
Seien Sie kreativ und detailreich! Ein gutes Slack-GIF sollte poliert wirken, nicht wie Platzhaltergrafiken.
Verfügbare Hilfsprogramme
GIFBuilder (core.gif_builder)
Setzt Frames zusammen und optimiert für Slack:
builder = GIFBuilder(width=128, height=128, fps=10)
builder.add_frame(frame) # PIL Image hinzufügen
builder.add_frames(frames) # Liste von Frames hinzufügen
builder.save('out.gif', num_colors=48, optimize_for_emoji=True, remove_duplicates=True)
Validatoren (core.validators)
Prüfen, ob ein GIF den Slack-Anforderungen entspricht:
from core.validators import validate_gif, is_slack_ready
# Detaillierte Validierung
passes, info = validate_gif('my.gif', is_emoji=True, verbose=True)
# Kurzcheck
if is_slack_ready('my.gif'):
print("Bereit!")
Easing-Funktionen (core.easing)
Sanfte Bewegungen statt linearer:
from core.easing import interpolate
# Fortschritt von 0.0 bis 1.0
t = i / (num_frames - 1)
# Easing anwenden
y = interpolate(start=0, end=400, t=t, easing='ease_out')
# Verfügbar: linear, ease_in, ease_out, ease_in_out,
# bounce_out, elastic_out, back_out
Frame-Helfer (core.frame_composer)
Praktische Funktionen für häufige Anforderungen:
from core.frame_composer import (
create_blank_frame, # Einfarbiger Hintergrund
create_gradient_background, # Vertikaler Farbverlauf
draw_circle, # Helfer für Kreise
draw_text, # Einfache Textwiedergabe
draw_star # Fünfzackiger Stern
)
Animationskonzepte
Schütteln/Vibrieren
Verschieben Sie die Objektposition mit einer Schwingung:
- Verwenden Sie
math.sin()odermath.cos()mit dem Frame-Index - Fügen Sie kleine zufällige Abweichungen für einen natürlichen Eindruck hinzu
- Wenden Sie es auf x- und/oder y-Position an
Puls/Herzschlag
Skalieren Sie die Objektgröße rhythmisch:
- Verwenden Sie
math.sin(t * frequency * 2 * math.pi)für einen sanften Puls - Für Herzschlag: zwei schnelle Pulse, dann Pause (Sinuswelle anpassen)
- Skalieren Sie zwischen 0,8 und 1,2 der Basisgröße
Springen
Objekt fällt und springt:
- Verwenden Sie
interpolate()miteasing='bounce_out'für die Landung - Verwenden Sie
easing='ease_in'für den Fall (Beschleunigung) - Wenden Sie Schwerkraft an, indem Sie die y-Geschwindigkeit pro Frame erhöhen
Drehen/Rotieren
Objekt um den Mittelpunkt drehen:
- PIL:
image.rotate(angle, resample=Image.BICUBIC) - Für Wackeln: Sinuswelle für den Winkel verwenden anstatt linear
Ein-/Ausblenden
Allmähliches Erscheinen oder Verschwinden:
- Erstellen Sie ein RGBA-Bild, passen Sie den Alpha-Kanal an
- Oder verwenden Sie
Image.blend(image1, image2, alpha) - Einblenden: Alpha von 0 auf 1
- Ausblenden: Alpha von 1 auf 0
Einfliegen
Objekt von außerhalb des Bildes in die Position bewegen:
- Startposition: außerhalb der Rahmenbegrenzung
- Endposition: Zielort
- Verwenden Sie
interpolate()miteasing='ease_out'für einen sanften Stopp - Für Überschwingen:
easing='back_out'verwenden
Zoomen
Skalieren und Positionieren für Zoomeffekt:
- Hineinzoomen: Skalierung von 0,1 auf 2,0, Bildmitte zuschneiden
- Herauszoomen: Skalierung von 2,0 auf 1,0
- Kann für Dramatik Bewegungsunschärfe hinzufügen (PIL-Filter)
Explosion/Partikelausbruch
Partikel erzeugen, die nach außen strahlen:
- Generieren Sie Partikel mit zufälligen Winkeln und Geschwindigkeiten
- Aktualisieren Sie jedes Partikel:
x += vx,y += vy - Fügen Sie Schwerkraft hinzu:
vy += gravity_constant - Blenden Sie Partikel im Laufe der Zeit aus (Alpha reduzieren)
Optimierungsstrategien
Nur wenn Sie gebeten werden, die Dateigröße zu verkleinern, implementieren Sie einige der folgenden Methoden:
- Weniger Frames – Niedrigere FPS (10 statt 20) oder kürzere Dauer
- Weniger Farben –
num_colors=48statt 128 - Kleinere Abmessungen – 128×128 statt 480×480
- Duplikate entfernen –
remove_duplicates=Truein save() - Emoji-Modus –
optimize_for_emoji=Trueoptimiert automatisch
# Maximale Optimierung für Emoji
builder.save(
'emoji.gif',
num_colors=48,
optimize_for_emoji=True,
remove_duplicates=True
)
Philosophie
Dieser Skill bietet:
- Wissen: Slacks Anforderungen und Animationskonzepte
- Werkzeuge: GIFBuilder, Validatoren, Easing-Funktionen
- Flexibilität: Erstellen Sie die Animationslogik mit PIL-Primitiven
Er bietet NICHT:
- Starre Animationsvorlagen oder vorgefertigte Funktionen
- Emoji-Schriftarten-Darstellung (plattformabhängig unzuverlässig)
- Eine Bibliothek vorgefertigter Grafiken, die in den Skill integriert ist
Hinweis zu Benutzer-Uploads: Dieser Skill enthält keine vorgefertigten Grafiken, aber wenn ein Benutzer ein Bild hochlädt, verwenden Sie PIL, um es zu laden und damit zu arbeiten – interpretieren Sie basierend auf seiner Anfrage, ob er es direkt verwenden oder nur als Inspiration nutzen möchte.
Seien Sie kreativ! Kombinieren Sie Konzepte (Springen + Drehen, Pulsieren + Einfliegen, etc.) und nutzen Sie die vollen Fähigkeiten von PIL.
Abhängigkeiten
pip install pillow imageio numpy