void ApplicationCommandManager::registerCommand (const ApplicationCommandInfo& newCommand)
{
    // zero isn't a valid command ID!
    jassert (newCommand.commandID != 0);

    // the name isn't optional!
    jassert (newCommand.shortName.isNotEmpty());

    if (auto* command = getMutableCommandForID (newCommand.commandID))
    {
        // Trying to re-register the same command ID with different parameters can often indicate a typo.
        // This assertion is here because I've found it useful catching some mistakes, but it may also cause
        // false alarms if you're deliberately updating some flags for a command.
        jassert (newCommand.shortName == getCommandForID (newCommand.commandID)->shortName
                  && newCommand.categoryName == getCommandForID (newCommand.commandID)->categoryName
                  && newCommand.defaultKeypresses == getCommandForID (newCommand.commandID)->defaultKeypresses
                  && (newCommand.flags & (ApplicationCommandInfo::wantsKeyUpDownCallbacks | ApplicationCommandInfo::hiddenFromKeyEditor | ApplicationCommandInfo::readOnlyInKeyEditor))
                       == (getCommandForID (newCommand.commandID)->flags & (ApplicationCommandInfo::wantsKeyUpDownCallbacks | ApplicationCommandInfo::hiddenFromKeyEditor | ApplicationCommandInfo::readOnlyInKeyEditor)));

        *command = newCommand;
    }
    else
    {
        ApplicationCommandInfo* const newInfo = new ApplicationCommandInfo (newCommand);
        newInfo->flags &= ~ApplicationCommandInfo::isTicked;
        commands.add (newInfo);

        keyMappings->resetToDefaultMapping (newCommand.commandID);

        triggerAsyncUpdate();
    }
}
String ApplicationCommandManager::getNameOfCommand (const CommandID commandID) const noexcept
{
    if (auto* ci = getCommandForID (commandID))
        return ci->shortName;

    return {};
}
String ApplicationCommandManager::getNameOfCommand (const CommandID commandID) const noexcept
{
    if (const ApplicationCommandInfo* const ci = getCommandForID (commandID))
        return ci->shortName;

    return String();
}
String ApplicationCommandManager::getDescriptionOfCommand (const CommandID commandID) const noexcept
{
    const ApplicationCommandInfo* const ci = getCommandForID (commandID);

    return ci != nullptr ? (ci->description.isNotEmpty() ? ci->description : ci->shortName)
                         : String::empty;
}
String ApplicationCommandManager::getDescriptionOfCommand (const CommandID commandID) const noexcept
{
    if (auto* ci = getCommandForID (commandID))
        return ci->description.isNotEmpty() ? ci->description
                                            : ci->shortName;

    return {};
}
void ApplicationCommandManager::registerCommand (const ApplicationCommandInfo& newCommand)
{
    // zero isn't a valid command ID!
    jassert (newCommand.commandID != 0);

    // the name isn't optional!
    jassert (newCommand.shortName.isNotEmpty());

    if (getCommandForID (newCommand.commandID) == 0)
    {
        ApplicationCommandInfo* const newInfo = new ApplicationCommandInfo (newCommand);
        newInfo->flags &= ~ApplicationCommandInfo::isTicked;
        commands.add (newInfo);

        keyMappings->resetToDefaultMapping (newCommand.commandID);

        triggerAsyncUpdate();
    }
    else
    {
        // trying to re-register the same command with different parameters?
        jassert (newCommand.shortName == getCommandForID (newCommand.commandID)->shortName
                  && (newCommand.description == getCommandForID (newCommand.commandID)->description || newCommand.description.isEmpty())
                  && newCommand.categoryName == getCommandForID (newCommand.commandID)->categoryName
                  && newCommand.defaultKeypresses == getCommandForID (newCommand.commandID)->defaultKeypresses
                  && (newCommand.flags & (ApplicationCommandInfo::wantsKeyUpDownCallbacks | ApplicationCommandInfo::hiddenFromKeyEditor | ApplicationCommandInfo::readOnlyInKeyEditor))
                       == (getCommandForID (newCommand.commandID)->flags & (ApplicationCommandInfo::wantsKeyUpDownCallbacks | ApplicationCommandInfo::hiddenFromKeyEditor | ApplicationCommandInfo::readOnlyInKeyEditor)));
    }
}
String ApplicationCommandManager::getNameOfCommand (const CommandID commandID) const noexcept
{
    const ApplicationCommandInfo* const ci = getCommandForID (commandID);

    return ci != nullptr ? ci->shortName : String::empty;
}