1% Drum head: a triangular net of beads under tension, pinned at the rim,
2% struck by a soft mallet. Units are SI. The net stands in for a membrane
3% with areal density sigma and tension T; its fundamental is near
4% 2.405/(2*pi*R)*sqrt(T/sigma).
6R = 0.15; % radius (m)
7a = 0.01; % bead spacing (m)
8sigma = 0.25; % areal density (kg/m^2)
9T = 2000; % membrane tension (N/m)
10strain = 0.02; % spring stretch at rest. Smaller is closer to a real
11 % membrane and more nonlinear, but stiffer in-plane, so
12 % the time step shrinks.
14[pos, tri, rim] = bp_hexdisk(R, a);
15E = bp_edges(tri);
16f0 = T * a / sqrt(3); % spring tension that gives membrane tension T
17k = f0 / (strain * a); % spring stiffness
19sys.pos = pos;
20sys.mass = sigma * (sqrt(3)/2) * a^2; % lattice area per bead
21sys.pinned = rim;
22sys.springs = bp_springs(pos, E, k, f0);
23sys.dashpots = [E, 1e-4 * ones(size(E, 1), 1)]; % damping that grows with frequency
24sys.friction = 1e-4; % damping that does not
26% A soft mallet: a 1 ms raised-cosine push on the beads within 3 cm.
27hit.t = 0;
28hit.beads = bp_near(pos, [0.05 0 0], 0.03);
29hit.force = [0 0 -0.4]; % peak force per bead (N)
30hit.duration = 1e-3;
31sys.hits = hit;
32% For more strikes, make sys.hits a struct array, e.g.
33% sys.hits(2) = struct('t', 0.5, 'beads', bp_near(pos, [0 0.06 0], 0.02), ...
34% 'force', [0 0 -0.6], 'duration', 1e-3);
35% (every hit in the array needs the same fields). A hit may instead give an
36% instant velocity: struct('t', 0, 'beads', idx, 'velocity', [0 0 -3]).
38sys.listen = struct('beads', bp_near(pos, [-0.04 0.03 0], 0), 'dir', [0 0 1]);
39sys.duration = 2;
41fprintf('%d beads (%d pinned), %d springs\n', size(pos, 1), numel(rim), size(E, 1));
42fprintf('expected fundamental: %.1f Hz\n', 2.405 / (2*pi*R) * sqrt(T / sigma));