/ proof-of-concept / cymbalsim
Sign in
proof-of-concept / cymbalsim
Add a hammered crash preset
The 16 inch crash with bell, with 160 Gaussian dents of 0.4 mm on the bow laid out on a sunflower spiral, so that the design has no symmetry. The dents shift the low modes by a few percent and split the pairs; the residual stresses of hammering are not modeled, which THEORY.md now says.
Jeremy Magland <jmagland@flatironinstitute.org> committed commit 0b5066005304 parent 7c1c648 Browse files
3 changed files+54−2
README.mdmodified+1−1View file
@@ -19,7 +19,7 @@ The sidebar holds the run controls at its top, then the design script, the strik
1919
2020 **Run mode.** The select at the top chooses the linear or the full model. In linear mode the modes of the current design are computed as soon as the script compiles (a progress bar shows the slices), and Synthesize produces the sound; after the first synthesis, a change of the strike or the listener parameters re-synthesizes automatically. In full mode Start begins the GPU run; Pause halts it, Stop ends it and keeps the audio and movie, and Continue extends a finished run after the duration has been raised.
2121
22-**Design script.** Pick a preset from the dropdown (a flat steel rectangle, an aluminum square, a bowed rectangle, a flat bronze disc, a tapered 16 inch crash, a 20 inch ride, the same crash with a bow and a bell, a steel ellipse, a thunder sheet) and edit it freely; the script is compiled as you type (or with Ctrl+Enter) and the view shows the resulting stress-free shape. Errors are reported under the script, and a summary lists the bounding box, the material, the thickness range, the mass, the grid, the profile's peak-to-peak height and largest slope (with a warning above the shallow-shell range), the loss constants with the coincidence frequency, and the estimated decay. Revert restores the selected preset.
22+**Design script.** Pick a preset from the dropdown (a flat steel rectangle, an aluminum square, a bowed rectangle, a flat bronze disc, a tapered 16 inch crash, a 20 inch ride, the same crash with a bow and a bell, that crash hammered, a steel ellipse, a thunder sheet) and edit it freely; the script is compiled as you type (or with Ctrl+Enter) and the view shows the resulting stress-free shape. Errors are reported under the script, and a summary lists the bounding box, the material, the thickness range, the mass, the grid, the profile's peak-to-peak height and largest slope (with a warning above the shallow-shell range), the loss constants with the coincidence frequency, and the estimated decay. Revert restores the selected preset.
2323
2424 The script fills in a struct named `design`. All lengths are meters. The outline, the thickness, and the profile are numbers or function handles `@(x, y, r, theta)` of the point relative to the center of the bounding box, its distance from the center, and its angle from the x axis; the handles are applied to whole grid matrices, so they use elementwise operators. A script is self-contained: nothing is in scope but numbl's own functions, so a script defines the shapes it needs as ordinary MATLAB functions at the bottom of the file, and the unit constants at the top.
2525
THEORY.mdmodified+1−1View file
@@ -124,6 +124,6 @@ With a GPU, a Playwright test runs one step of the WGSL kernel from a smooth ran
124124
125125 The linear model is linear: it has no pitch glide, no wash, and a hard hit is only a loud one. It is the right tool for the tone, the modes and the decay of a design, and for a first listen, and the full model is the right tool for the sound of a hard hit; the two agree for a light one. The modal truncation at the cutoff frequency removes the highest partials, which the grid places poorly anyway; the linear interpolation of the acceleration table during the first two milliseconds slightly blurs the attack.
126126
127-The von Karman model assumes moderate rotations, so it is not valid for displacements that are large compared with the plate size; a strike that moves a 400 mm cymbal by a few millimeters is well within its range. The Marguerre treatment of the profile is a shallow-shell approximation, adequate for a bow of a few millimeters on a sheet and for a gentle cymbal bow, but strained by the bell of a real cymbal, whose slope is several times the range in which the approximation holds; the curved preset uses a flatter bell than a real cymbal, and the interface reports the largest slope of a design. A deep bell also behaves as a stiff cup that shifts the bell modes up in ways the shallow shell does not capture. The thickness field is treated as a slowly varying coefficient in a thin-plate model, which is appropriate for a lathed taper but not for a step or a groove on the scale of the grid. The hammering of a real cymbal, which leaves residual stresses and a slightly non-axisymmetric shape, is absent unless the script adds it. The losses are derived from physical constants, but two of those constants are themselves empirical: the loss factor of the metal and, to a lesser degree, its thermal constants are typical published values rather than measurements of a particular alloy after hammering, and the loss factor is the one knob a user has on the decay. The radiation loss is that of a plate in a rigid wall, consistent with the listener model but an overstatement at low frequency for a plate in free air, where the two faces partly cancel; the losses to the air's viscosity and to the support other than the felt are absent; and the full model carries the losses only through the two-parameter fit to an average, so its decay agrees with the modal one on average and not mode by mode. Grid dispersion lowers the high partials by the amounts given in Section 2, and the staircase edge places the low frequencies within a few percent and splits modes that would be degenerate on a true disc.
127+The von Karman model assumes moderate rotations, so it is not valid for displacements that are large compared with the plate size; a strike that moves a 400 mm cymbal by a few millimeters is well within its range. The Marguerre treatment of the profile is a shallow-shell approximation, adequate for a bow of a few millimeters on a sheet and for a gentle cymbal bow, but strained by the bell of a real cymbal, whose slope is several times the range in which the approximation holds; the curved preset uses a flatter bell than a real cymbal, and the interface reports the largest slope of a design. A deep bell also behaves as a stiff cup that shifts the bell modes up in ways the shallow shell does not capture. The thickness field is treated as a slowly varying coefficient in a thin-plate model, which is appropriate for a lathed taper but not for a step or a groove on the scale of the grid. The hammering of a real cymbal leaves residual stresses and a non-axisymmetric shape; the hammered crash preset adds the shape, a field of shallow dents on the bow, which splits the mode pairs and mixes the modes, but the residual stresses are absent. The losses are derived from physical constants, but two of those constants are themselves empirical: the loss factor of the metal and, to a lesser degree, its thermal constants are typical published values rather than measurements of a particular alloy after hammering, and the loss factor is the one knob a user has on the decay. The radiation loss is that of a plate in a rigid wall, consistent with the listener model but an overstatement at low frequency for a plate in free air, where the two faces partly cancel; the losses to the air's viscosity and to the support other than the felt are absent; and the full model carries the losses only through the two-parameter fit to an average, so its decay agrees with the modal one on average and not mode by mode. Grid dispersion lowers the high partials by the amounts given in Section 2, and the staircase edge places the low frequencies within a few percent and splits modes that would be degenerate on a true disc.
128128
129129 The plate is free: nothing supports it, and neither the thread a sheet hangs from nor the stand a cymbal sits on is modeled, so the losses and the low modes a support adds are absent. Air loading, which lowers the frequencies of a thin plate slightly and adds radiation damping, is not included. The plate is unbaffled in reality, so the sound from its two faces partly cancels at low frequencies, and the Rayleigh integral overestimates the low-frequency level; an accurate treatment would require solving the exterior acoustic problem, which is outside the scope of this simulator. Finally, single precision limits the dynamic range of the tail of the full model's sound to roughly 100 dB below the peak, and the linear model, in double precision, has no such limit but no more physics.
src/presets.tsmodified+52−0View file
@@ -189,6 +189,57 @@ v = 0.5 * height * (1 + cos(pi * d / radius)) .* (d < radius);
189189 end
190190 `;
191191
192+const crashHammered16 = `% The 16 inch crash with bell, hammered: 160 shallow dents of 0.4 mm on
193+% the bow, laid out on a sunflower spiral so that no two align. A hammered
194+% cymbal is no longer axisymmetric, so its degenerate mode pairs split and
195+% its modes mix, which is part of what makes a cymbal sound like one. The
196+% dents here are what a script can express, a change of the rest shape;
197+% the residual stresses of real hammering are not modeled.
198+inch = 0.0254; mm = 1e-3;
199+D = 16*inch; R = D/2;
200+bellR = 55*mm; bellH = 8*mm; bowH = 10*mm;
201+tCenter = 1.2*mm; tEdge = 0.7*mm;
202+nDents = 160; dentR = 12*mm; dentDepth = 0.4*mm;
203+
204+design.name = '16 inch hammered crash';
205+design.material.E = 110e9;
206+design.material.nu = 0.34;
207+design.material.rho = 8800;
208+design.material.lossFactor = 2e-4; % internal friction of the metal (typical published value)
209+design.material.alpha = 18e-6; % thermal expansion [1/K] } for the thermoelastic damping
210+design.material.cp = 370; % specific heat [J/(kg K)] }
211+design.material.k = 40; % conductivity [W/(m K)] }
212+design.bounds.width = D;
213+design.bounds.height = D;
214+design.inside = @(x, y, r, theta) r <= R;
215+design.thickness = @(x, y, r, theta) tCenter + (tEdge - tCenter) * ramp(bellR, R, r);
216+design.profile = @(x, y, r, theta) bowH * (1 - (r/R).^2) + dome(r, bellR, bellH) + dents(x, y, bellR + dentR, R - dentR, nDents, dentR, dentDepth);
217+
218+function v = ramp(a, b, x)
219+v = min(max((x - a) ./ (b - a), 0), 1);
220+end
221+
222+function v = dome(d, radius, height)
223+% A cosine dome of the given height and base radius, with zero slope both at
224+% its rim and at its apex; d is the distance from its center.
225+v = 0.5 * height * (1 + cos(pi * d / radius)) .* (d < radius);
226+end
227+
228+function v = dents(x, y, r0, r1, n, rd, depth)
229+% n hammer marks between the radii r0 and r1: Gaussian dents of 1/e radius
230+% rd, placed on a sunflower spiral (equal area per mark, golden-angle
231+% spacing) so that the pattern has no symmetry.
232+v = 0 * x;
233+ga = pi * (3 - sqrt(5));
234+for k = 1:n
235+ rk = sqrt(r0^2 + (r1^2 - r0^2) * (k - 0.5) / n);
236+ tk = k * ga;
237+ dx = x - rk * cos(tk); dy = y - rk * sin(tk);
238+ v = v - depth * exp(-(dx.^2 + dy.^2) / rd^2);
239+end
240+end
241+`;
242+
192243 const ellipse = `% An elliptical steel plate. The outline is any test on the point;
193244 % an ellipse inscribed in the bounding box here. The degenerate mode pairs
194245 % of a disc split on an ellipse, which the mode browser shows.
@@ -236,6 +287,7 @@ export const PRESETS: Preset[] = [
236287 { id: "crash-16", label: "16 inch flat crash", source: crash16 },
237288 { id: "ride-20", label: "20 inch flat ride", source: ride20 },
238289 { id: "crash-bell-16", label: "16 inch crash with bell", source: crashBell16 },
290+ { id: "crash-hammered-16", label: "16 inch hammered crash", source: crashHammered16 },
239291 { id: "ellipse", label: "Steel ellipse", source: ellipse },
240292 { id: "thunder-sheet", label: "Thunder sheet", source: thunderSheet },
241293 ];
↑↓ move↵openescclose