When building the bird shape, I was using a lot of clunky code to convert the different ways to represent a shape’s segments (straight lines between points! an arc! a cubic bezier curve!) into one type.
I had a lot of code like this:
CurveDrawer::new(
vec![
vec![
self.neck_for_head(body),
CurveSegment::new_simple_point(beak_mustache_bottom),
],
neck_front.clone(),
]
.concat(), // a list of curve segments
false, // if it's an opened or closed shape
)
So I defined a trait that converts something into segments and wrote a macro that called the trait’s methods. I wrote another trait to convert a list of segments into the curve drawer (to_cd_open) and another to attach a style to it (to_drawn_shape).
curve_segments![
self.neck_for_head(body),
beak_mustache_bottom,
neck_front,
].to_cd_open()
.to_drawn_shape(self.style)
That’s a lot cuter!
The days are darker and colder, and the interesting winter birds aren’t here yet. But I dragged myself outside for a bit of birding.
I started at this berry-filled tree that the robins had taken over, and where cute white-throated sparrows are usually hopping in the leaf litter below. Today, the area had no birds. I heard chickadees yelling their alarm call, as well as the sounds of a large quantity of house sparrows. I followed the chirps to a small tree containing 50 sparrows. With winter, birds are starting to form larger flocks, chattering and hopping around the newly bare trees.

I walked by the churning tree, and the birds didn’t fly off. I must not register as a predator? Oh, no. It’s because I’m not as big a threat as the huge hawk sitting in the tree right above me. Gasp.
The juvenile red-tailed hawk and I watched each other for a few minutes, and then it took off (gasp) to a small tree on the other side of the tracks. I waited for a minute, and then the sparrows flew to the berry tree area, and I walked back there as it filled up with birds. A few minutes later, the hawk flew back to its big tree, and the berry tree area was once again deserted. Ebbs and flows.