% Feta (not the Font-En-Tja) music font -- Accidentals % This file is part of LilyPond, the GNU music typesetter. % % Copyright (C) 1997--2022 Han-Wen Nienhuys % Copyright (C) 2013--2022 Janek WarchoĊ‚ % % The LilyPond font is free software: you can redistribute it and/or modify % it under the terms of the GNU General Public License as published by % the Free Software Foundation, either version 3 of the License, or % (at your option) any later version, or you can redistribute it under % the SIL Open Font License. % % LilyPond is distributed in the hope that it will be useful, % but WITHOUT ANY WARRANTY; without even the implied warranty of % MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the % GNU General Public License for more details. % % You should have received a copy of the GNU General Public License % along with LilyPond. If not, see . % % The stems of the natural are brushed (at least, in Barenreiter SCS) % % general parameters: save stem_thickness, stem_end_thickness_multiplier; save beam_thickness, beam_slant; stem_thickness# := 0.09 staff_space# + 0.5 stafflinethickness#; stem_end_thickness_multiplier := 10/7; beam_slant := 1.266 stafflinethickness; beam_thickness := 0.485 staff_space - stafflinethickness; def draw_natural (expr arrowup, arrowdown, figured_bass) = save depth, height, width, breapth; save full_width, full_height; save offset; save hole_highest_point; save upstem_factor, downstem_factor; save upstem_end_thickness, downstem_end_thickness; save half_height, half_box_height; save beam_direction, r_stem_top_path, l_stem_bottom_path; pair beam_direction; path r_stem_top_path, l_stem_bottom_path; upstem_factor = downstem_factor = stem_end_thickness_multiplier; if figured_bass: full_height# := number_design_size + 2 figbass_y#; full_width# := .7 figbass_width#; offset# := .5 number_design_size; width# := figbass_width#; hole_highest_point := 0.2 staff_space + stafflinethickness; else: full_height# := 3 staff_space#; full_width# := 2/3 staff_space#; offset# := 0; width# := full_width#; hole_highest_point := 0.5 (staff_space - stafflinethickness); fi; define_pixels (offset); half_height# := 0.5 full_height#; define_pixels (half_height); define_whole_pixels (full_width); depth# := half_height# - offset#; height# := half_height# + offset#; breapth# := 0; if arrowup: % synchronized with point z4 of the arrow height# := half_height# % y1 + .1 staff_space# + .5 stafflinethickness# % upshift + .85 staff_space# + stafflinethickness#; % htip breapth# := .3 staff_space# - .5 stem_thickness#; % to look nice, arrowed stems must be less brushed upstem_factor := 0.5 (1 + upstem_factor); fi; if arrowdown: % synchronized with point z4 of the arrow depth# := half_height# % y3 + .1 staff_space# + .5 stafflinethickness# % upshift + .85 staff_space# + stafflinethickness#; % htip width# := width# + .3 staff_space# - .5 stem_thickness#; % to look nice, arrowed stems must be less brushed downstem_factor := 0.5 (1 + downstem_factor); fi; set_char_box (breapth#, width#, depth#, height#); d := d - feta_space_shift; upstem_end_thickness# = upstem_factor * stem_thickness#; downstem_end_thickness# = downstem_factor * stem_thickness#; define_whole_blacker_pixels (upstem_end_thickness, downstem_end_thickness); define_whole_blacker_pixels (stem_thickness); if odd (upstem_end_thickness - stem_thickness): upstem_end_thickness := upstem_end_thickness - 1; fi; if odd (downstem_end_thickness - stem_thickness): downstem_end_thickness := downstem_end_thickness - 1; fi; half_box_height := hole_highest_point + beam_thickness %% correction for the fact that x11 != x12. %% ideally y2 should be calculated from y11 %% and beam_thickness, but the brushed stems %% would cause a cyclic dependency: %% y2 -> x11 -> y14 -> y13 -> y12 -> y2 + 0.5 stem_thickness * beam_slant / full_width; %% stems: pickup pencircle scaled stem_thickness; penpos1 (upstem_end_thickness, 0); penpos3 (downstem_end_thickness, 0); penpos2 (stem_thickness, 0); penpos4 (stem_thickness, 0); x2r = w - (w - full_width) / 2; x4l = (w - full_width) / 2; x3 = x2; x1 = x4; y1 = half_height + offset; y3 = -half_height + offset; top y2 = vround (half_box_height + offset); bot y4 = vround (-half_box_height + offset) + feta_space_shift; l_stem_bottom_path := z4r{z4r - z1r} .. bot z4 .. z4l{z1l - z4l}; r_stem_top_path := z2r{z2r - z3r} .. top z2 .. z2l{z3l - z2l}; fill simple_serif (z1l, z1r, -30) -- l_stem_bottom_path -- cycle; fill simple_serif (z3l, z3r, 30) -- r_stem_top_path -- cycle; %% beams: beam_direction = (full_width, beam_slant); z11 = z3l + whatever * (z2l - z3l); y11 = vround (hole_highest_point + offset); z12 = directionpoint -beam_direction of r_stem_top_path; z13 = z12 + whatever * beam_direction; x13 = x1; z14 = z11 + whatever * beam_direction; x14 = x1; z21 = z4r + whatever * (z1r - z4r); y21 = vround (-hole_highest_point + offset) + feta_space_shift; z22 = directionpoint -beam_direction of l_stem_bottom_path; z23 = z22 + whatever * beam_direction; x23 = x3; z24 = z21 + whatever * beam_direction; x24 = x3; fill z11 -- z12 -- z13 -- z14 -- cycle; fill z21 -- z22 -- z23 -- z24 -- cycle; if arrowup: fill draw_arrow (z1, upstem_end_thickness, z1l - z4l, stafflinethickness / 2, false) -- cycle; fi; if arrowdown: fill draw_arrow (z3, downstem_end_thickness, z2r - z3r, stafflinethickness / 2, true) -- cycle; fi; %% debugging: penlabels (1, 2, 3, 4); labels (11, 12, 13, 14, 21, 22, 23, 24); draw_staff_if_debugging (-2, 2); enddef; fet_beginchar ("natural", "natural"); draw_natural (false, false, false); fet_endchar; fet_beginchar ("figured bass natural", "natural.figbass"); draw_natural (false, false, true); fet_endchar; fet_beginchar ("arrowed natural (arrow up)", "natural.arrowup"); draw_natural (true, false, false); fet_endchar; fet_beginchar ("arrowed natural (arrow down)", "natural.arrowdown"); draw_natural (false, true, false); fet_endchar; fet_beginchar ("arrowed natural (arrows up and down)", "natural.arrowboth"); draw_natural (true, true, false); fet_endchar;