// Update a sound in the displayed buttons, sound list, and sound file
  // soundClip - An object storing information about the added or updated sound
  public void updateSound(SoundInfo soundClip) {

    // Add the sound to the project
    SoundInfo newSound = soundManager.addSound(soundClip);

    if (newSound != null) {
      // Add a new button to the GUI
      addSound(newSound);
    }

    if (soundManager.getProjectModified()) {

      if (newSound == null) {
        // An existing sound was updated
        // Update the button label and tooltip
        for (int s = 0; s < soundList.size(); s++) {
          BoardButton button = soundList.get(s);
          if (button.getKeyCode() == soundClip.getKeyCode()) {
            button.updateButtonText();
            break;
          }
        }
      }

      // Update the GUI
      frame.setProjectModified();
      refreshSoundBoard();
    }
  }
  // Clears all the buttons from the GUI
  private void clearBoard() {

    // Remove all the old buttons and refresh the panel
    for (int i = 0; i < soundList.size(); i++) {
      BoardButton curr = soundList.get(i);
      remove(curr.getButton());
    }
    refreshSoundBoard();

    // Refresh the list of sound board buttons
    soundList = new ArrayList<BoardButton>();
  }
  // Removes a sound from the interface and sound list
  // keyCode - The keyboard key code associated with the sound
  public void deleteSound(int keyCode) {
    soundManager.deleteSound(keyCode);

    // Search the sound buttons for the button to remove
    for (int s = 0; s < soundList.size(); s++) {
      BoardButton button = soundList.get(s);
      if (button.getKeyCode() == keyCode) {
        // Remove the button from the interface
        remove(button.getButton());
        soundList.remove(s);

        // Update the GUI
        frame.setProjectModified();
        refreshSoundBoard();

        break;
      }
    }
  }
  // Constructor
  // frame - The frame containing this panel
  public CueMasherPanel(CueMasherFrame frame) {
    // Listens to the keyboard
    addKeyListener(new ToggleSound());

    // Tweak focus so keyboard listener works
    addFocusListener(new PanelFocusListener());
    setFocusable(true);

    this.frame = frame;
    this.frame.setMinimumSize(new Dimension(500, 500));

    soundManager = new ProjectFileManager();
    dialogManager = new SoundDialogManager(this);

    soundList = new ArrayList<BoardButton>();

    // Create a button for the spacebar
    space = new StopButton(soundManager);
    add(space.getButton());

    editingMode = false;
  }
  // Set the positions and sizes of the buttons and display the panel
  public void paintComponent(Graphics page) {
    super.paintComponent(page);

    // Calculate the button width and height so the buttons span the screen
    int screenWidth = getWidth();
    int screenHeight = getHeight();
    int[] buttonWidth = new int[5];
    buttonWidth[0] = (screenWidth - (BUTTON_SPACE * 13)) / 13;
    buttonWidth[1] = buttonWidth[0];
    buttonWidth[2] = (screenWidth - (BUTTON_SPACE * 11)) / 11;
    buttonWidth[3] = (screenWidth - (BUTTON_SPACE * 11)) / 10;
    buttonWidth[4] = (screenWidth - (BUTTON_SPACE * 11)) / 10;
    int buttonHeight = (screenHeight - (BUTTON_SPACE * 7)) / 6;

    int xPos;
    int yPos;
    // Subtract 1 from this int every time a sound button is placed where it belongs
    // When it equals zero all sounds have been placed
    int keysToMap = soundList.size();
    ArrayList<BoardButton> copy = (ArrayList<BoardButton>) soundList.clone();

    // For each string in the rows array, check if any of the key strings for the sound match
    for (int j = 0; j < rows.length; j++) {
      int i = 0;

      // For each string in the rows array, check each sound object to see if it is played with a
      // key in that row
      while ((copy.size() > 0) && (i < soundList.size())) {
        int index = 0;
        if (soundList.get(i).getKeyName().indexOf("N") != -1) {
          if (j == 4) index = rows[j].indexOf(soundList.get(i).getKeyName().substring(1));
          else index = -1;
        } else {
          if (j != 4)
            // Get where the key string is in the rows array
            index = rows[j].indexOf(soundList.get(i).getKeyName());
          else index = -1;
        }
        // If the key string doesn't exist, the key is not in this row and the button won't be
        // placed
        if (index != -1) {
          // Place the button based on the corresponding key's position on the keyboard
          xPos = ((buttonWidth[j] + BUTTON_SPACE) * index) + BUTTON_SPACE;
          yPos = ((buttonHeight + BUTTON_SPACE) * j) + BUTTON_SPACE;

          JButton curr = soundList.get(i).getButton();
          // Set the button's size and position to the size and position calculated
          curr.setSize(new Dimension(buttonWidth[j], buttonHeight));
          curr.setLocation(xPos, yPos);
          // Decrement the number of sounds left to map
          copy.remove(soundList.get(i));
          keysToMap -= 1;
        }

        // Increment the index of the sound to check
        i++;
      }
    }

    // Set the x-position, y-position, and size of the spacebar key
    // It will span the bottom of the screen and be the same height as the other buttons
    JButton btnSpace = space.getButton();
    xPos = 10;
    yPos = ((buttonHeight + BUTTON_SPACE) * 5) + BUTTON_SPACE;
    btnSpace.setSize(new Dimension(screenWidth - (BUTTON_SPACE * 2), buttonHeight));
    btnSpace.setLocation(xPos, yPos);
  }