@caddis/cli 0.4.9 → 0.4.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bundles/antigravity-plugin/agents/code-reviewer.md +2 -2
- package/bundles/antigravity-plugin/plugin.json +1 -1
- package/bundles/antigravity-plugin/scripts/enforcement_inventory.py +1 -1
- package/bundles/antigravity-plugin/scripts/oss_review.py +10 -2
- package/bundles/antigravity-plugin/skills/_registry.md +0 -1
- package/bundles/antigravity-plugin/skills/brainstorming/SKILL.md +2 -2
- package/bundles/antigravity-plugin/skills/cross-review/SKILL.md +5 -2
- package/bundles/antigravity-plugin/skills/explainer-doc/SKILL.md +1 -1
- package/bundles/antigravity-plugin/skills/ship-pr/SKILL.md +1 -1
- package/bundles/antigravity-plugin/skills/spawn-session/SKILL.md +2 -2
- package/bundles/antigravity-plugin-extras/plugin.json +1 -1
- package/bundles/antigravity-plugin-extras/skills/_registry.md +1 -19
- package/bundles/codex/.codex/skills/docs/explainer-doc/SKILL.md +1 -1
- package/bundles/codex/.codex/skills/workflow/brainstorming/SKILL.md +2 -2
- package/bundles/manifest.json +3 -3
- package/package.json +1 -1
- package/bundles/antigravity-plugin-extras/skills/competitive-ads-extractor/SKILL.md +0 -294
- package/bundles/antigravity-plugin-extras/skills/content-research-writer/SKILL.md +0 -539
- package/bundles/antigravity-plugin-extras/skills/domain-name-brainstormer/SKILL.md +0 -213
- package/bundles/antigravity-plugin-extras/skills/humanizer/SKILL.md +0 -194
- package/bundles/antigravity-plugin-extras/skills/image-enhancer/SKILL.md +0 -100
- package/bundles/antigravity-plugin-extras/skills/invoice-organizer/SKILL.md +0 -447
- package/bundles/antigravity-plugin-extras/skills/job-application/SKILL.md +0 -188
- package/bundles/antigravity-plugin-extras/skills/lead-research-assistant/SKILL.md +0 -200
- package/bundles/antigravity-plugin-extras/skills/meeting-insights-analyzer/SKILL.md +0 -328
- package/bundles/antigravity-plugin-extras/skills/notebooklm/AUTHENTICATION.md +0 -154
- package/bundles/antigravity-plugin-extras/skills/notebooklm/SKILL.md +0 -270
- package/bundles/antigravity-plugin-extras/skills/notebooklm/references/api_reference.md +0 -309
- package/bundles/antigravity-plugin-extras/skills/notebooklm/references/troubleshooting.md +0 -376
- package/bundles/antigravity-plugin-extras/skills/notebooklm/references/usage_patterns.md +0 -338
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/__init__.py +0 -81
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/ask_question.py +0 -256
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/auth_manager.py +0 -358
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/browser_session.py +0 -255
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/browser_utils.py +0 -107
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/cleanup_manager.py +0 -302
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/config.py +0 -44
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/notebook_manager.py +0 -410
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/run.py +0 -102
- package/bundles/antigravity-plugin-extras/skills/notebooklm/scripts/setup_environment.py +0 -204
- package/bundles/antigravity-plugin-extras/skills/onboard-project/SKILL.md +0 -192
- package/bundles/antigravity-plugin-extras/skills/pipeline-state/SKILL.md +0 -208
- package/bundles/antigravity-plugin-extras/skills/raffle-winner-picker/SKILL.md +0 -159
- package/bundles/antigravity-plugin-extras/skills/relay/SKILL.md +0 -246
- package/bundles/antigravity-plugin-extras/skills/requesting-code-review/SKILL.md +0 -105
- package/bundles/antigravity-plugin-extras/skills/requesting-code-review/code-reviewer.md +0 -146
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/LICENSE.txt +0 -202
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/SKILL.md +0 -646
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/color_palettes.py +0 -302
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/easing.py +0 -230
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/frame_composer.py +0 -469
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/gif_builder.py +0 -246
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/typography.py +0 -357
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/validators.py +0 -264
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/core/visual_effects.py +0 -494
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/requirements.txt +0 -4
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/bounce.py +0 -106
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/explode.py +0 -331
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/fade.py +0 -329
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/flip.py +0 -291
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/kaleidoscope.py +0 -211
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/morph.py +0 -329
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/move.py +0 -293
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/pulse.py +0 -268
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/shake.py +0 -127
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/slide.py +0 -291
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/spin.py +0 -269
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/wiggle.py +0 -300
- package/bundles/antigravity-plugin-extras/skills/slack-gif-creator/templates/zoom.py +0 -312
- package/bundles/antigravity-plugin-extras/skills/state-tracking/SKILL.md +0 -131
- package/bundles/antigravity-plugin-extras/skills/video-downloader/SKILL.md +0 -107
- package/bundles/antigravity-plugin-extras/skills/youtube-transcript/SKILL.md +0 -416
- package/bundles/codex/.codex/skills/workflow/golden-plan/SKILL.md +0 -586
- /package/bundles/{antigravity-plugin → antigravity-plugin-extras}/skills/golden-plan/SKILL.md +0 -0
|
@@ -1,312 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env python3
|
|
2
|
-
"""
|
|
3
|
-
Zoom Animation - Scale objects dramatically for emphasis.
|
|
4
|
-
|
|
5
|
-
Creates zoom in, zoom out, and dramatic scaling effects.
|
|
6
|
-
"""
|
|
7
|
-
|
|
8
|
-
import sys
|
|
9
|
-
from pathlib import Path
|
|
10
|
-
import math
|
|
11
|
-
|
|
12
|
-
sys.path.append(str(Path(__file__).parent.parent))
|
|
13
|
-
|
|
14
|
-
from PIL import Image, ImageFilter
|
|
15
|
-
from core.gif_builder import GIFBuilder
|
|
16
|
-
from core.frame_composer import create_blank_frame, draw_emoji_enhanced
|
|
17
|
-
from core.easing import interpolate
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
def create_zoom_animation(
|
|
21
|
-
object_type: str = 'emoji',
|
|
22
|
-
object_data: dict | None = None,
|
|
23
|
-
num_frames: int = 30,
|
|
24
|
-
zoom_type: str = 'in', # 'in', 'out', 'in_out', 'punch'
|
|
25
|
-
scale_range: tuple[float, float] = (0.1, 2.0),
|
|
26
|
-
easing: str = 'ease_out',
|
|
27
|
-
add_motion_blur: bool = False,
|
|
28
|
-
center_pos: tuple[int, int] = (240, 240),
|
|
29
|
-
frame_width: int = 480,
|
|
30
|
-
frame_height: int = 480,
|
|
31
|
-
bg_color: tuple[int, int, int] = (255, 255, 255)
|
|
32
|
-
) -> list[Image.Image]:
|
|
33
|
-
"""
|
|
34
|
-
Create zoom animation.
|
|
35
|
-
|
|
36
|
-
Args:
|
|
37
|
-
object_type: 'emoji', 'text', 'image'
|
|
38
|
-
object_data: Object configuration
|
|
39
|
-
num_frames: Number of frames
|
|
40
|
-
zoom_type: Type of zoom effect
|
|
41
|
-
scale_range: (start_scale, end_scale) tuple
|
|
42
|
-
easing: Easing function
|
|
43
|
-
add_motion_blur: Add blur for speed effect
|
|
44
|
-
center_pos: Center position
|
|
45
|
-
frame_width: Frame width
|
|
46
|
-
frame_height: Frame height
|
|
47
|
-
bg_color: Background color
|
|
48
|
-
|
|
49
|
-
Returns:
|
|
50
|
-
List of frames
|
|
51
|
-
"""
|
|
52
|
-
frames = []
|
|
53
|
-
|
|
54
|
-
# Default object data
|
|
55
|
-
if object_data is None:
|
|
56
|
-
if object_type == 'emoji':
|
|
57
|
-
object_data = {'emoji': '🔍', 'size': 100}
|
|
58
|
-
|
|
59
|
-
base_size = object_data.get('size', 100) if object_type == 'emoji' else object_data.get('font_size', 60)
|
|
60
|
-
start_scale, end_scale = scale_range
|
|
61
|
-
|
|
62
|
-
for i in range(num_frames):
|
|
63
|
-
t = i / (num_frames - 1) if num_frames > 1 else 0
|
|
64
|
-
|
|
65
|
-
# Calculate scale based on zoom type
|
|
66
|
-
if zoom_type == 'in':
|
|
67
|
-
scale = interpolate(start_scale, end_scale, t, easing)
|
|
68
|
-
elif zoom_type == 'out':
|
|
69
|
-
scale = interpolate(end_scale, start_scale, t, easing)
|
|
70
|
-
elif zoom_type == 'in_out':
|
|
71
|
-
if t < 0.5:
|
|
72
|
-
scale = interpolate(start_scale, end_scale, t * 2, easing)
|
|
73
|
-
else:
|
|
74
|
-
scale = interpolate(end_scale, start_scale, (t - 0.5) * 2, easing)
|
|
75
|
-
elif zoom_type == 'punch':
|
|
76
|
-
# Quick zoom in with overshoot then settle
|
|
77
|
-
if t < 0.3:
|
|
78
|
-
scale = interpolate(start_scale, end_scale * 1.2, t / 0.3, 'ease_out')
|
|
79
|
-
else:
|
|
80
|
-
scale = interpolate(end_scale * 1.2, end_scale, (t - 0.3) / 0.7, 'elastic_out')
|
|
81
|
-
else:
|
|
82
|
-
scale = interpolate(start_scale, end_scale, t, easing)
|
|
83
|
-
|
|
84
|
-
# Create frame
|
|
85
|
-
frame = create_blank_frame(frame_width, frame_height, bg_color)
|
|
86
|
-
|
|
87
|
-
if object_type == 'emoji':
|
|
88
|
-
current_size = int(base_size * scale)
|
|
89
|
-
|
|
90
|
-
# Clamp size to reasonable bounds
|
|
91
|
-
current_size = max(12, min(current_size, frame_width * 2))
|
|
92
|
-
|
|
93
|
-
# Create emoji on transparent background
|
|
94
|
-
canvas_size = max(frame_width, frame_height, current_size) * 2
|
|
95
|
-
emoji_canvas = Image.new('RGBA', (canvas_size, canvas_size), (0, 0, 0, 0))
|
|
96
|
-
|
|
97
|
-
draw_emoji_enhanced(
|
|
98
|
-
emoji_canvas,
|
|
99
|
-
emoji=object_data['emoji'],
|
|
100
|
-
position=(canvas_size // 2 - current_size // 2, canvas_size // 2 - current_size // 2),
|
|
101
|
-
size=current_size,
|
|
102
|
-
shadow=False
|
|
103
|
-
)
|
|
104
|
-
|
|
105
|
-
# Optional motion blur for fast zooms
|
|
106
|
-
if add_motion_blur and abs(scale - 1.0) > 0.5:
|
|
107
|
-
blur_amount = min(5, int(abs(scale - 1.0) * 3))
|
|
108
|
-
emoji_canvas = emoji_canvas.filter(ImageFilter.GaussianBlur(blur_amount))
|
|
109
|
-
|
|
110
|
-
# Crop to frame size centered
|
|
111
|
-
left = (canvas_size - frame_width) // 2
|
|
112
|
-
top = (canvas_size - frame_height) // 2
|
|
113
|
-
emoji_cropped = emoji_canvas.crop((left, top, left + frame_width, top + frame_height))
|
|
114
|
-
|
|
115
|
-
# Composite
|
|
116
|
-
frame_rgba = frame.convert('RGBA')
|
|
117
|
-
frame = Image.alpha_composite(frame_rgba, emoji_cropped)
|
|
118
|
-
frame = frame.convert('RGB')
|
|
119
|
-
|
|
120
|
-
elif object_type == 'text':
|
|
121
|
-
from core.typography import draw_text_with_outline
|
|
122
|
-
|
|
123
|
-
current_size = int(base_size * scale)
|
|
124
|
-
current_size = max(10, min(current_size, 500))
|
|
125
|
-
|
|
126
|
-
# Create oversized canvas for large text
|
|
127
|
-
canvas_size = max(frame_width, frame_height, current_size * 10)
|
|
128
|
-
text_canvas = Image.new('RGB', (canvas_size, canvas_size), bg_color)
|
|
129
|
-
|
|
130
|
-
draw_text_with_outline(
|
|
131
|
-
text_canvas,
|
|
132
|
-
text=object_data.get('text', 'ZOOM'),
|
|
133
|
-
position=(canvas_size // 2, canvas_size // 2),
|
|
134
|
-
font_size=current_size,
|
|
135
|
-
text_color=object_data.get('text_color', (0, 0, 0)),
|
|
136
|
-
outline_color=object_data.get('outline_color', (255, 255, 255)),
|
|
137
|
-
outline_width=max(2, int(current_size * 0.05)),
|
|
138
|
-
centered=True
|
|
139
|
-
)
|
|
140
|
-
|
|
141
|
-
# Crop to frame
|
|
142
|
-
left = (canvas_size - frame_width) // 2
|
|
143
|
-
top = (canvas_size - frame_height) // 2
|
|
144
|
-
frame = text_canvas.crop((left, top, left + frame_width, top + frame_height))
|
|
145
|
-
|
|
146
|
-
frames.append(frame)
|
|
147
|
-
|
|
148
|
-
return frames
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
def create_explosion_zoom(
|
|
152
|
-
emoji: str = '💥',
|
|
153
|
-
num_frames: int = 20,
|
|
154
|
-
frame_width: int = 480,
|
|
155
|
-
frame_height: int = 480,
|
|
156
|
-
bg_color: tuple[int, int, int] = (255, 255, 255)
|
|
157
|
-
) -> list[Image.Image]:
|
|
158
|
-
"""
|
|
159
|
-
Create dramatic explosion zoom effect.
|
|
160
|
-
|
|
161
|
-
Args:
|
|
162
|
-
emoji: Emoji to explode
|
|
163
|
-
num_frames: Number of frames
|
|
164
|
-
frame_width: Frame width
|
|
165
|
-
frame_height: Frame height
|
|
166
|
-
bg_color: Background color
|
|
167
|
-
|
|
168
|
-
Returns:
|
|
169
|
-
List of frames
|
|
170
|
-
"""
|
|
171
|
-
frames = []
|
|
172
|
-
|
|
173
|
-
for i in range(num_frames):
|
|
174
|
-
t = i / (num_frames - 1) if num_frames > 1 else 0
|
|
175
|
-
|
|
176
|
-
# Exponential zoom
|
|
177
|
-
scale = 0.1 * math.exp(t * 5)
|
|
178
|
-
|
|
179
|
-
# Add rotation for drama
|
|
180
|
-
angle = t * 360 * 2
|
|
181
|
-
|
|
182
|
-
frame = create_blank_frame(frame_width, frame_height, bg_color)
|
|
183
|
-
|
|
184
|
-
current_size = int(100 * scale)
|
|
185
|
-
current_size = max(12, min(current_size, frame_width * 3))
|
|
186
|
-
|
|
187
|
-
# Create emoji
|
|
188
|
-
canvas_size = max(frame_width, frame_height, current_size) * 2
|
|
189
|
-
emoji_canvas = Image.new('RGBA', (canvas_size, canvas_size), (0, 0, 0, 0))
|
|
190
|
-
|
|
191
|
-
draw_emoji_enhanced(
|
|
192
|
-
emoji_canvas,
|
|
193
|
-
emoji=emoji,
|
|
194
|
-
position=(canvas_size // 2 - current_size // 2, canvas_size // 2 - current_size // 2),
|
|
195
|
-
size=current_size,
|
|
196
|
-
shadow=False
|
|
197
|
-
)
|
|
198
|
-
|
|
199
|
-
# Rotate
|
|
200
|
-
emoji_canvas = emoji_canvas.rotate(angle, center=(canvas_size // 2, canvas_size // 2), resample=Image.BICUBIC)
|
|
201
|
-
|
|
202
|
-
# Add motion blur for later frames
|
|
203
|
-
if t > 0.5:
|
|
204
|
-
blur_amount = int((t - 0.5) * 10)
|
|
205
|
-
emoji_canvas = emoji_canvas.filter(ImageFilter.GaussianBlur(blur_amount))
|
|
206
|
-
|
|
207
|
-
# Crop and composite
|
|
208
|
-
left = (canvas_size - frame_width) // 2
|
|
209
|
-
top = (canvas_size - frame_height) // 2
|
|
210
|
-
emoji_cropped = emoji_canvas.crop((left, top, left + frame_width, top + frame_height))
|
|
211
|
-
|
|
212
|
-
frame_rgba = frame.convert('RGBA')
|
|
213
|
-
frame = Image.alpha_composite(frame_rgba, emoji_cropped)
|
|
214
|
-
frame = frame.convert('RGB')
|
|
215
|
-
|
|
216
|
-
frames.append(frame)
|
|
217
|
-
|
|
218
|
-
return frames
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
def create_mind_blown_zoom(
|
|
222
|
-
emoji: str = '🤯',
|
|
223
|
-
num_frames: int = 30,
|
|
224
|
-
frame_width: int = 480,
|
|
225
|
-
frame_height: int = 480,
|
|
226
|
-
bg_color: tuple[int, int, int] = (255, 255, 255)
|
|
227
|
-
) -> list[Image.Image]:
|
|
228
|
-
"""
|
|
229
|
-
Create "mind blown" dramatic zoom with shake.
|
|
230
|
-
|
|
231
|
-
Args:
|
|
232
|
-
emoji: Emoji to use
|
|
233
|
-
num_frames: Number of frames
|
|
234
|
-
frame_width: Frame width
|
|
235
|
-
frame_height: Frame height
|
|
236
|
-
bg_color: Background color
|
|
237
|
-
|
|
238
|
-
Returns:
|
|
239
|
-
List of frames
|
|
240
|
-
"""
|
|
241
|
-
frames = []
|
|
242
|
-
|
|
243
|
-
for i in range(num_frames):
|
|
244
|
-
t = i / (num_frames - 1) if num_frames > 1 else 0
|
|
245
|
-
|
|
246
|
-
# Zoom in then shake
|
|
247
|
-
if t < 0.5:
|
|
248
|
-
scale = interpolate(0.3, 1.2, t * 2, 'ease_out')
|
|
249
|
-
shake_x = 0
|
|
250
|
-
shake_y = 0
|
|
251
|
-
else:
|
|
252
|
-
scale = 1.2
|
|
253
|
-
# Shake intensifies
|
|
254
|
-
shake_intensity = (t - 0.5) * 40
|
|
255
|
-
shake_x = int(math.sin(t * 50) * shake_intensity)
|
|
256
|
-
shake_y = int(math.cos(t * 45) * shake_intensity)
|
|
257
|
-
|
|
258
|
-
frame = create_blank_frame(frame_width, frame_height, bg_color)
|
|
259
|
-
|
|
260
|
-
current_size = int(100 * scale)
|
|
261
|
-
center_x = frame_width // 2 + shake_x
|
|
262
|
-
center_y = frame_height // 2 + shake_y
|
|
263
|
-
|
|
264
|
-
emoji_canvas = Image.new('RGBA', (frame_width, frame_height), (0, 0, 0, 0))
|
|
265
|
-
draw_emoji_enhanced(
|
|
266
|
-
emoji_canvas,
|
|
267
|
-
emoji=emoji,
|
|
268
|
-
position=(center_x - current_size // 2, center_y - current_size // 2),
|
|
269
|
-
size=current_size,
|
|
270
|
-
shadow=False
|
|
271
|
-
)
|
|
272
|
-
|
|
273
|
-
frame_rgba = frame.convert('RGBA')
|
|
274
|
-
frame = Image.alpha_composite(frame_rgba, emoji_canvas)
|
|
275
|
-
frame = frame.convert('RGB')
|
|
276
|
-
|
|
277
|
-
frames.append(frame)
|
|
278
|
-
|
|
279
|
-
return frames
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
# Example usage
|
|
283
|
-
if __name__ == '__main__':
|
|
284
|
-
print("Creating zoom animations...")
|
|
285
|
-
|
|
286
|
-
builder = GIFBuilder(width=480, height=480, fps=20)
|
|
287
|
-
|
|
288
|
-
# Example 1: Zoom in
|
|
289
|
-
frames = create_zoom_animation(
|
|
290
|
-
object_type='emoji',
|
|
291
|
-
object_data={'emoji': '🔍', 'size': 100},
|
|
292
|
-
num_frames=30,
|
|
293
|
-
zoom_type='in',
|
|
294
|
-
scale_range=(0.1, 1.5),
|
|
295
|
-
easing='ease_out'
|
|
296
|
-
)
|
|
297
|
-
builder.add_frames(frames)
|
|
298
|
-
builder.save('zoom_in.gif', num_colors=128)
|
|
299
|
-
|
|
300
|
-
# Example 2: Explosion zoom
|
|
301
|
-
builder.clear()
|
|
302
|
-
frames = create_explosion_zoom(emoji='💥', num_frames=20)
|
|
303
|
-
builder.add_frames(frames)
|
|
304
|
-
builder.save('zoom_explosion.gif', num_colors=128)
|
|
305
|
-
|
|
306
|
-
# Example 3: Mind blown
|
|
307
|
-
builder.clear()
|
|
308
|
-
frames = create_mind_blown_zoom(emoji='🤯', num_frames=30)
|
|
309
|
-
builder.add_frames(frames)
|
|
310
|
-
builder.save('zoom_mind_blown.gif', num_colors=128)
|
|
311
|
-
|
|
312
|
-
print("Created zoom animations!")
|
|
@@ -1,131 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: state-tracking
|
|
3
|
-
context: fork
|
|
4
|
-
description: "USE THIS SKILL when an agent needs to maintain a living record of task progress across multiple sessions or hand-offs. Covers append-only audit logs, CURRENT_STATE head-of-line pattern, relay hand-off protocol, and recovery from mid-session interruptions. Works in both generic and junai-pipeline modes."
|
|
5
|
-
---
|
|
6
|
-
|
|
7
|
-
# State Tracking Skill
|
|
8
|
-
|
|
9
|
-
## When to Use
|
|
10
|
-
|
|
11
|
-
Load this skill when you are:
|
|
12
|
-
|
|
13
|
-
- Running a multi-session implementation where work spans more than one chat context
|
|
14
|
-
- Handing off to another agent mid-plan and need to capture exactly where you stopped
|
|
15
|
-
- Working on a long task where context compaction may occur
|
|
16
|
-
- Recovering from an interrupted session and need to reconstruct current state
|
|
17
|
-
|
|
18
|
-
---
|
|
19
|
-
|
|
20
|
-
## The Two-Document Pattern
|
|
21
|
-
|
|
22
|
-
State tracking uses two distinct documents with different write semantics:
|
|
23
|
-
|
|
24
|
-
| Document | Write mode | Purpose |
|
|
25
|
-
|----------|-----------|---------|
|
|
26
|
-
| **Plan Tracker** (`.caddis/plans/tracker/<slug>-tracker.md`) | Overwrite each row | Per-phase completion record, linked to commits |
|
|
27
|
-
| **CURRENT_STATE** (`.github/agent-docs/CURRENT_STATE.md`) | Overwrite head section | Single-view of right now: what phase, what's done, what's blocked |
|
|
28
|
-
| **Session Log** (inline in CURRENT_STATE, append-only) | Append only | Chronological audit trail — never rewrite past entries |
|
|
29
|
-
|
|
30
|
-
Never mix them: the tracker is the long-term ledger; CURRENT_STATE is the working note.
|
|
31
|
-
|
|
32
|
-
---
|
|
33
|
-
|
|
34
|
-
## CURRENT_STATE.md — Head-of-Line Pattern
|
|
35
|
-
|
|
36
|
-
The CURRENT_STATE document has two sections:
|
|
37
|
-
|
|
38
|
-
### Section 1: Current Status (overwrite on every update)
|
|
39
|
-
|
|
40
|
-
Replace this section wholesale each time:
|
|
41
|
-
|
|
42
|
-
```markdown
|
|
43
|
-
## Current Status
|
|
44
|
-
|
|
45
|
-
**Plan:** `.caddis/plans/<feature-slug>.md`
|
|
46
|
-
**Tracker:** `.caddis/plans/tracker/<feature-slug>-tracker.md`
|
|
47
|
-
**Last updated:** YYYY-MM-DDTHH:MM:SSZ
|
|
48
|
-
**Active agent:** @[Agent] (model: [Model])
|
|
49
|
-
**Current phase:** Phase N — [Name]
|
|
50
|
-
**Phase status:** [Not started | In progress | Blocked | Complete]
|
|
51
|
-
|
|
52
|
-
### What is done
|
|
53
|
-
- Phase 1 ([Name]): complete — commit `abc1234`
|
|
54
|
-
- Phase 2 ([Name]): complete — commit `def5678`
|
|
55
|
-
|
|
56
|
-
### What is in progress
|
|
57
|
-
- Phase 3 ([Name]): step 2 of 5 — [short note on current step]
|
|
58
|
-
|
|
59
|
-
### What is blocked
|
|
60
|
-
- [blocker description, or "nothing"]
|
|
61
|
-
|
|
62
|
-
### Next action
|
|
63
|
-
[One sentence: exactly what the next agent session should start with]
|
|
64
|
-
```
|
|
65
|
-
|
|
66
|
-
### Section 2: Session Log (append-only)
|
|
67
|
-
|
|
68
|
-
Append one entry per session, never edit past entries:
|
|
69
|
-
|
|
70
|
-
```markdown
|
|
71
|
-
## Session Log
|
|
72
|
-
|
|
73
|
-
### [YYYY-MM-DDTHH:MM:SSZ] — @[Agent] (model: [Model])
|
|
74
|
-
**Phase covered:** Phase N [partial | complete]
|
|
75
|
-
**Commits:** `abc1234` (phase(3): [Name] complete)
|
|
76
|
-
**Stopped at:** [exact description of stopping point]
|
|
77
|
-
**Handoff note:** [any context the next agent needs]
|
|
78
|
-
---
|
|
79
|
-
```
|
|
80
|
-
|
|
81
|
-
---
|
|
82
|
-
|
|
83
|
-
## Relay Hand-off Protocol
|
|
84
|
-
|
|
85
|
-
When you are about to end a session mid-plan:
|
|
86
|
-
|
|
87
|
-
1. **Complete the current atomic unit** — do not stop at a half-edited file. Reach the next clean commit point.
|
|
88
|
-
2. **Update CURRENT_STATE.md:**
|
|
89
|
-
- Rewrite the "Current Status" section with the exact stopping point.
|
|
90
|
-
- Append a new entry to the Session Log.
|
|
91
|
-
3. **Update the plan tracker** — mark your current phase's row with `In Progress` if incomplete, or `Complete` if you just finished it.
|
|
92
|
-
4. **Commit both files** with the current phase commit or as a separate `chore(state): update CURRENT_STATE` commit.
|
|
93
|
-
5. **State the hand-off note** in the session log and in your final reply — the next agent must be able to read CURRENT_STATE.md and know exactly where to start.
|
|
94
|
-
|
|
95
|
-
---
|
|
96
|
-
|
|
97
|
-
## Recovery Protocol
|
|
98
|
-
|
|
99
|
-
When starting a session on a plan that has a CURRENT_STATE.md:
|
|
100
|
-
|
|
101
|
-
1. Read `.github/agent-docs/CURRENT_STATE.md` — Current Status section first.
|
|
102
|
-
2. Read the last entry in the Session Log to understand what the previous session did.
|
|
103
|
-
3. Read the plan tracker row for the current phase.
|
|
104
|
-
4. Confirm the stated commit exists: `git show <commit> --stat`.
|
|
105
|
-
5. Start from **"Next action"** in the Current Status section.
|
|
106
|
-
6. Do NOT re-run phases that are marked Complete in the tracker unless the user explicitly asks you to.
|
|
107
|
-
|
|
108
|
-
---
|
|
109
|
-
|
|
110
|
-
## Template: CURRENT_STATE.md
|
|
111
|
-
|
|
112
|
-
The canonical template is at `.github/agent-docs/CURRENT_STATE.md`. Copy it for new plans or use it as the single shared state file (overwriting the Current Status section each session).
|
|
113
|
-
|
|
114
|
-
---
|
|
115
|
-
|
|
116
|
-
## Integration with Golden-Plan
|
|
117
|
-
|
|
118
|
-
When running a golden-plan:
|
|
119
|
-
- The plan tracker (`.caddis/plans/tracker/<slug>-tracker.md`) is the commitment ledger.
|
|
120
|
-
- CURRENT_STATE.md is the working scratch-pad for the current session.
|
|
121
|
-
- After completing a phase, update BOTH the tracker row AND the CURRENT_STATE current-status section.
|
|
122
|
-
- When all tracker rows are `Complete`, follow the Plan Completion Protocol in golden-plan: move the plan to `plans/done/`, set `status: done`.
|
|
123
|
-
|
|
124
|
-
---
|
|
125
|
-
|
|
126
|
-
## Standing Rules
|
|
127
|
-
|
|
128
|
-
1. **Never rewrite past Session Log entries** — the log is append-only. Corrections go in the next entry.
|
|
129
|
-
2. **One CURRENT_STATE per active plan** — if running two plans in parallel, use two separate state files named `CURRENT_STATE-<slug>.md`.
|
|
130
|
-
3. **CURRENT_STATE is not the tracker** — do not put commit hashes or gate results in CURRENT_STATE; they belong in the tracker. CURRENT_STATE is for human-readable context.
|
|
131
|
-
4. **Commit state files** — CURRENT_STATE updates must be committed, not left as unstaged changes.
|
|
@@ -1,107 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: video-downloader
|
|
3
|
-
context: fork
|
|
4
|
-
description: Downloads videos from YouTube and other platforms for offline viewing, editing, or archival. Handles various formats and quality options.
|
|
5
|
-
---
|
|
6
|
-
|
|
7
|
-
# Video Downloader
|
|
8
|
-
|
|
9
|
-
This skill downloads videos from YouTube and other platforms directly to your computer.
|
|
10
|
-
|
|
11
|
-
## When to Use This Skill
|
|
12
|
-
|
|
13
|
-
- Downloading YouTube videos for offline viewing
|
|
14
|
-
- Saving educational content for reference
|
|
15
|
-
- Archiving important videos
|
|
16
|
-
- Getting video files for editing or repurposing
|
|
17
|
-
- Downloading your own content from platforms
|
|
18
|
-
- Saving conference talks or webinars
|
|
19
|
-
|
|
20
|
-
## What This Skill Does
|
|
21
|
-
|
|
22
|
-
1. **Downloads Videos**: Fetches videos from YouTube and other platforms
|
|
23
|
-
2. **Quality Selection**: Lets you choose resolution (480p, 720p, 1080p, 4K)
|
|
24
|
-
3. **Format Options**: Downloads in various formats (MP4, WebM, audio-only)
|
|
25
|
-
4. **Batch Downloads**: Can download multiple videos or playlists
|
|
26
|
-
5. **Metadata Preservation**: Saves title, description, and thumbnail
|
|
27
|
-
|
|
28
|
-
## How to Use
|
|
29
|
-
|
|
30
|
-
### Basic Download
|
|
31
|
-
|
|
32
|
-
```
|
|
33
|
-
Download this YouTube video: https://youtube.com/watch?v=...
|
|
34
|
-
```
|
|
35
|
-
|
|
36
|
-
```
|
|
37
|
-
Download this video in 1080p quality
|
|
38
|
-
```
|
|
39
|
-
|
|
40
|
-
### Audio Only
|
|
41
|
-
|
|
42
|
-
```
|
|
43
|
-
Download the audio from this YouTube video as MP3
|
|
44
|
-
```
|
|
45
|
-
|
|
46
|
-
### Playlist Download
|
|
47
|
-
|
|
48
|
-
```
|
|
49
|
-
Download all videos from this YouTube playlist: [URL]
|
|
50
|
-
```
|
|
51
|
-
|
|
52
|
-
### Batch Download
|
|
53
|
-
|
|
54
|
-
```
|
|
55
|
-
Download these 5 YouTube videos:
|
|
56
|
-
1. [URL]
|
|
57
|
-
2. [URL]
|
|
58
|
-
...
|
|
59
|
-
```
|
|
60
|
-
|
|
61
|
-
## Example
|
|
62
|
-
|
|
63
|
-
**User**: "Download this YouTube video: https://youtube.com/watch?v=abc123"
|
|
64
|
-
|
|
65
|
-
**Output**:
|
|
66
|
-
```
|
|
67
|
-
Downloading from YouTube...
|
|
68
|
-
|
|
69
|
-
Video: "How to Build Products Users Love"
|
|
70
|
-
Channel: Lenny's Podcast
|
|
71
|
-
Duration: 45:32
|
|
72
|
-
Quality: 1080p
|
|
73
|
-
|
|
74
|
-
Progress: ████████████████████ 100%
|
|
75
|
-
|
|
76
|
-
✓ Downloaded: how-to-build-products-users-love.mp4
|
|
77
|
-
✓ Saved thumbnail: how-to-build-products-users-love.jpg
|
|
78
|
-
✓ Size: 342 MB
|
|
79
|
-
|
|
80
|
-
Saved to: ~/Downloads/
|
|
81
|
-
```
|
|
82
|
-
|
|
83
|
-
**Inspired by:** Lenny's workflow from his newsletter
|
|
84
|
-
|
|
85
|
-
## Important Notes
|
|
86
|
-
|
|
87
|
-
⚠️ **Copyright & Fair Use**
|
|
88
|
-
- Only download videos you have permission to download
|
|
89
|
-
- Respect copyright laws and platform terms of service
|
|
90
|
-
- Use for personal, educational, or fair use purposes
|
|
91
|
-
- Don't redistribute copyrighted content
|
|
92
|
-
|
|
93
|
-
## Tips
|
|
94
|
-
|
|
95
|
-
- Specify quality if you need lower file size (720p vs 1080p)
|
|
96
|
-
- Use audio-only for podcasts or music to save space
|
|
97
|
-
- Download to a dedicated folder to stay organized
|
|
98
|
-
- Check file size before downloading on slow connections
|
|
99
|
-
|
|
100
|
-
## Common Use Cases
|
|
101
|
-
|
|
102
|
-
- **Education**: Save tutorials and courses for offline learning
|
|
103
|
-
- **Research**: Archive videos for reference
|
|
104
|
-
- **Content Creation**: Download your own content from platforms
|
|
105
|
-
- **Backup**: Save important videos before they're removed
|
|
106
|
-
- **Offline Viewing**: Watch videos without internet access
|
|
107
|
-
|