acclivity

pyComputeUkeleleChords

Jan 28th, 2024
133
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.10 KB | Software | 0 0
  1. # Compute fingering required for playing chords on a Ukelele
  2. # Mike Kerry - Jan 2024
  3.  
  4. scale = ["A", "Bb", "B", "C", "C#", "D", "Eb", "E", "F", "F#", "G", "Ab"]
  5. scale += scale
  6.  
  7. base_notes_open = ["G", "C", "E", "A"]      # Notes that open strings play
  8. base_note_offsets = [10, 3, 7, 0]           # Open string notes relative to A
  9.  
  10. chords = {"1,5,8": "", "1,5,8,10": "6", "1,5,8,11": "7", "1,5,8,12": "maj7",
  11.           "1,4,8": "m", "1,4,8,10": "m6",  "1,3,8,11": "m7"}
  12.  
  13. strings = [0, 0, 0, 0]
  14. lastcombo = ""
  15. lastfullkey = ""
  16. high_fret = 4                   # Highest fret wwe want to use
  17. chord_list = []
  18. for off1 in range(high_fret + 1):
  19.     for off2 in range(high_fret + 1):
  20.         for off3 in range(high_fret + 1):
  21.             for off4 in range(high_fret + 1):
  22.                 strings[0] = scale[base_note_offsets[0] + off1]
  23.                 strings[1] = scale[base_note_offsets[1] + off2]
  24.                 strings[2] = scale[base_note_offsets[2] + off3]
  25.                 strings[3] = scale[base_note_offsets[3] + off4]
  26.  
  27.                 for first_note in strings:
  28.                     first_note_index = scale.index(first_note)
  29.                     intervals = []      # compute a list of intervals from one string to all strings
  30.                     for second_note in strings:
  31.                         second_note_index = scale.index(second_note)
  32.                         interval = (second_note_index + 12 - first_note_index) % 12
  33.                         intervals.append(interval)
  34.                     intervals = list(set(intervals))        # drop duplicate intervals
  35.                     intervals.sort()                        # e.g. for major we want 1, 5, 8 not 5, 1, 8 etc.
  36.                     interval_key = ""
  37.                     for a in intervals:
  38.                         interval_key += str(a + 1)          # count notes from 1, not 0
  39.                         interval_key += ","
  40.                     interval_key = interval_key[:-1]        # drop the final comma
  41.  
  42.                     if interval_key in chords:              # Does this set of intervals make any desired chord?
  43.                         combo = f"{off1},{off2},{off3},{off4}"
  44.                         fullkey = f"{first_note}{chords[interval_key]}"
  45.                         if combo == lastcombo and fullkey == lastfullkey:
  46.                             continue            # ignore duplicates
  47.                         lastcombo = combo
  48.                         lastfullkey = fullkey
  49.                         chord_list.append([fullkey, combo])
  50.  
  51. chord_list.sort()
  52.  
  53. # Print sorted results
  54. for item in chord_list:
  55.     offsets = item[1]
  56.     offlist = offsets.split(',')
  57.     outline = f"{item[0]: <8} {item[1]: <10} "
  58.     notes = []
  59.     notes_str = ""
  60.     for x, off in enumerate(offlist):
  61.         off = int(off)
  62.         idx = base_note_offsets[x] + off
  63.         notes.append(scale[idx])
  64.         notes_str += scale[idx]
  65.         notes_str += " "
  66.     notes_str += "            "
  67.     outline += notes_str[:12]
  68.     if notes[0] in notes[1:] and item[1][0] != '0':
  69.         outline += "   or  x,"
  70.         outline += item[1][2:]
  71.  
  72.     print(outline)
  73.  
Add Comment
Please, Sign In to add comment