This guide explains how to create custom gathering patterns for the Fuzzy Macro.
What are Patterns?
Patterns define the movement your character performs while gathering in fields. They determine how efficiently you collect pollen from flowers. Patterns are Python scripts located in settings/patterns/.
When gathering is active, the macro:
Navigates to your selected field
Positions at the start location
Executes your pattern repeatedly
Collects pollen while moving
Pattern File Structure
Patterns are .py files that execute within the macro's gather function context. Basic structure:
# Size conversion (standard for all patterns)if sizeword.lower()=="xs": size =0.5elif sizeword.lower()=="s": size =1elif sizeword.lower()=="l": size =2elif sizeword.lower()=="xl": size =2.5else: size =1.5# Default: M# Pattern movement logicself.keyboard.walk(tcfbkey,0.5* size)for _ inrange(width):self.keyboard.walk(tclrkey,0.17)self.keyboard.walk(afcfbkey,0.5* size)
File Naming:
Use lowercase with underscores: my_pattern.py
Avoid spaces or special characters
Name should be descriptive: zigzag_tight.py, circle_large.py
Available Variables
When your pattern executes, these variables are available in the namespace:
Movement Keys
Why use inverted keys?
Using tcfbkey instead of fwdkey respects user's "Invert Forward/Back" setting
Using tclrkey instead of leftkey respects user's "Invert Left/Right" setting
This makes your pattern work correctly regardless of user preferences
Camera Controls
Pattern Settings
Macro Methods
Walk Method Details:
Pattern Examples
Example 1: Simple E Pattern (e_lol. py)
This pattern traces an "E" shape, ideal for rectangular fields.
How it works:
Moves back slightly to position
Walks right to form top of "E"
Zigzags down and back to form top section
Walks right to form middle of "E"
Zigzags down and back to form bottom section
Example 2: Bambe Pattern (bambe.py)
A complex pattern with tight movements, good for dense fields.
How it works:
Positions character at specific start point
Performs serpentine pattern moving left
Performs serpentine pattern moving right
Repeats for each width increment
Example 3: Bowl Pattern with Camera Rotation (bowl.py)
Advanced pattern using camera rotation and diagonal movements.
Advanced features:
Camera rotation to change perspective
Diagonal walking with multiWalk()
Digital Bee compatibility with sleep delays
Custom drift compensation
Complex multi-directional sweeps
Best Practices
1. Always Include Size Handling
Every pattern must convert the size setting:
You can customize the multipliers for your pattern's needs:
2. Scale All Movements by Size
3. Use Width for Repetitions
4. Use Inverted Keys for Pattern Logic
5. Test Multiple Sizes
Always test your pattern with different size settings:
XS: Very tight, small areas
S: Small fields or dense gathering
M: Default, balanced coverage
L: Large fields, spread out
XL: Very large fields, maximum coverage
6. Add Clear Comments
7. Handle Special Cases
8. Keep Patterns Efficient
9. Consider Field Coverage
Good patterns should:
Cover most of the field area
Avoid revisiting the same spots too much
Work in fields of different shapes
Adapt to size/width settings
10. Document Pattern Behavior
Add a header comment explaining your pattern:
Testing & Debugging
Testing Patterns
1. Enable a Test Field
In the macro GUI:
Select a field to use your pattern
Set gathering time to 1-2 minutes (quick tests)
Enable only that field
Disable other tasks
2. Watch the Pattern Execute
Start the macro
Observe if the pattern covers the field well
Look for:
Missed areas
Overlapping paths
Drift over time
Getting stuck
3. Adjust Size Scaling
If pattern is too large/small, adjust size multipliers:
tcfbkey # True camera forward/backward key (affected by invert_fb)
afcfbkey # Alternate forward/backward key (opposite of tcfbkey)
tclrkey # True camera left/right key (affected by invert_lr)
afclrkey # Alternate left/right key (opposite of tclrkey)
# Base keys (unaffected by inversions)
fwdkey # "w" - forward
backkey # "s" - backward
leftkey # "a" - left
rightkey # "d" - right
rotleft # "," - rotate camera left
rotright # "." - rotate camera right
rotup # "pageup" - rotate camera up
rotdown # "pagedown" - rotate camera down
zoomin # "i" - zoom in
zoomout # "o" - zoom out
sc_space # "space" - space key
size # Float: Calculated from sizeword (XS=0.5, S=1, M=1.5, L=2, XL=2.5)
sizeword # String: "XS", "S", "M", "L", or "XL" from GUI
width # Integer: 1-8, number of pattern repetitions from GUI
self.keyboard.walk(key, duration) # Walk in direction for duration seconds
self.keyboard.multiWalk([keys], duration) # Walk multiple directions simultaneously
self.keyboard.press(key) # Press key once
sleep(seconds) # Sleep for specified time
# Walk forward for 1.5 seconds
self.keyboard.walk("w", 1.5)
# Walk diagonally (forward + left) for 2 seconds
self.keyboard.multiWalk(["w", "a"], 2.0)
# Press rotate right (single tap)
self.keyboard.press(".")
if sizeword.lower() == "xs":
size = 0.5
elif sizeword.lower() == "s":
size = 1
elif sizeword.lower() == "l":
size = 2
elif sizeword.lower() == "xl":
size = 2.5
else:
size = 1.5
# Move back to start position
self.keyboard.walk(afcfbkey, 0.5 * size)
# Top horizontal line
for _ in range(width):
self.keyboard.walk(tclrkey, 0.17)
self.keyboard.walk(tclrkey, 0.17)
# Downward zigzag (first half of E)
for _ in range(width):
self.keyboard.walk(tcfbkey, 0.5 * size)
self.keyboard.walk(afclrkey, 0.17)
self.keyboard.walk(afcfbkey, 0.5 * size)
self.keyboard.walk(afclrkey, 0.17)
# Middle horizontal line
self.keyboard.walk(tcfbkey, 0.5 * size)
for _ in range(width):
self.keyboard.walk(tclrkey, 0.17)
self.keyboard.walk(tclrkey, 0.17)
# Downward zigzag (second half of E)
for _ in range(width):
self.keyboard. walk(afcfbkey, 0.5 * size)
self.keyboard.walk(afclrkey, 0.17)
self.keyboard.walk(tcfbkey, 0.5 * size)
self.keyboard.walk(afclrkey, 0.17)
# Tighter pattern
if sizeword.lower() == "xs":
size = 0.25
elif sizeword. lower() == "s":
size = 0.5
# ...
# Or add additional scaling
size = size / 5.5 # Make pattern much tighter
# ✅ GOOD - Scales with size
self.keyboard.walk(tcfbkey, 0.5 * size)
# ❌ BAD - Ignores user's size setting
self.keyboard.walk(tcfbkey, 0.5)
# ✅ GOOD - Respects width setting
for _ in range(width):
self.keyboard.walk(tcfbkey, 1.0 * size)
self.keyboard.walk(tclrkey, 0.5 * size)
# ❌ BAD - Hardcoded repetitions
for _ in range(5):
self.keyboard.walk(tcfbkey, 1.0 * size)
# ✅ GOOD - Respects invert settings
self.keyboard.walk(tcfbkey, 1.0) # Forward (respects Invert F/B)
self.keyboard.walk(tclrkey, 0.5) # Left (respects Invert L/R)
# ❌ BAD - Ignores invert settings
self.keyboard.walk(fwdkey, 1.0) # Always forward
self.keyboard.walk(leftkey, 0.5) # Always left
# Position character at pattern start point
self.keyboard.walk(afcfbkey, 0.5 * size)
# Top horizontal line of E shape
for _ in range(width):
self.keyboard.walk(tclrkey, 0.17)
# Downward vertical sweep with lateral movement
for _ in range(width):
self.keyboard.walk(tcfbkey, 0.5 * size)
self.keyboard.walk(afclrkey, 0.17)
# For Digital Bee users - add pause after camera rotations
digistops = False # User can change this at top of pattern
if digistops:
sleep(0.8)
# Field-specific adjustments
passivefdc = 0.3 # Passive field drift compensation
# Adjust for different field shapes
if "bamboo" in field_name: # Would need to pass field name
size *= 1.2 # Bamboo is larger
# ✅ GOOD - Continuous movement
self.keyboard.walk("w", 2.0)
self.keyboard.walk("a", 1.0)
# ❌ BAD - Unnecessary stops
self.keyboard.walk("w", 1.0)
sleep(0.5)
self.keyboard.walk("w", 1.0)
sleep(0.5)
"""
Pattern: Spiral Outward
Description: Starts at center and spirals outward in expanding squares
Best for: Square fields (Clover, Dandelion, Sunflower)
Width: Controls number of spiral loops
Size: Controls distance between spiral rings
Author: YourName
"""
# Pattern code here...
# Pattern is too large
size = size * 0.8 # Make pattern 20% smaller
# Pattern is too small
size = size * 1.2 # Make pattern 20% larger
# Pattern needs different proportions
size_horizontal = size * 1.0
size_vertical = size * 0.7 # Make vertical movements shorter
XS → Should work in very tight spaces
S → Should work in small areas
M → Should be balanced (most common)
L → Should cover large areas
XL → Should maximize coverage
# Error: NameError: name 'tcfbkey' is not defined
# Fix: Check spelling, use correct variable names
# Error: TypeError: unsupported operand type(s)
# Fix: Ensure size is defined, check math operations
# Error: SyntaxError
# Fix: Check for missing colons, parentheses, quotes
# Add debug prints to see what's happening
print(f"Size: {size}, Width: {width}")
print(f"Moving forward for {1.0 * size} seconds")
self.keyboard.walk(tcfbkey, 1.0 * size)
print("Forward movement complete")
# Macro automatically converts . ahk files to .py
ahkPatterns = [x for x in os.listdir(patterns_dir) if ".ahk" in x]
for pattern in ahkPatterns:
python = ahkPatternToPython(ahk)
# Saves as .py file with same name