public String parse(String format) {
   StringBuffer buffer = new StringBuffer();
   Matcher m = formatPattern.matcher(format);
   while (m.find()) m.appendReplacement(buffer, getFormatSpecifierValue(m.group()));
   m.appendTail(buffer);
   return buffer.toString();
 }
  protected void setupScoreBoardValues() {
    new ScoreBoardValue(
        "%sbto", "ScoreBoard Timeout Owner", getScoreBoard(), ScoreBoard.EVENT_TIMEOUT_OWNER) {
      public String getValue() {
        return getScoreBoard().getTimeoutOwner();
      }
    };
    new ScoreBoardValue(
        "%sbip", "ScoreBoard Is In Period", getScoreBoard(), ScoreBoard.EVENT_IN_PERIOD) {
      public String getValue() {
        return String.valueOf(getScoreBoard().isInPeriod());
      }
    };
    new ScoreBoardValue(
        "%sbio", "ScoreBoard Is In Overtime", getScoreBoard(), ScoreBoard.EVENT_IN_OVERTIME) {
      public String getValue() {
        return String.valueOf(getScoreBoard().isInOvertime());
      }
    };
    new ScoreBoardValue(
        "%sbos", "ScoreBoard Is Score Official", getScoreBoard(), ScoreBoard.EVENT_OFFICIAL_SCORE) {
      public String getValue() {
        return String.valueOf(getScoreBoard().isOfficialScore());
      }
    };

    setupTeamValues("1", Team.ID_1);
    setupTeamValues("2", Team.ID_2);
    setupClockValues("p", Clock.ID_PERIOD);
    setupClockValues("j", Clock.ID_JAM);
    setupClockValues("l", Clock.ID_LINEUP);
    setupClockValues("t", Clock.ID_TIMEOUT);
    setupClockValues("i", Clock.ID_INTERMISSION);

    StringBuffer patternBuffer = new StringBuffer();
    Iterator<String> patterns = scoreBoardValues.keySet().iterator();
    while (patterns.hasNext()) patternBuffer.append(patterns.next() + "|");
    String specifiersRegex = patternBuffer.toString().replaceAll("[|]$", "");
    formatPattern = Pattern.compile(specifiersRegex);
    eventPattern = Pattern.compile("^\\s*(" + specifiersRegex + ")");
    conditionPattern =
        Pattern.compile("(" + specifiersRegex + ")(?:(" + comparatorRegex + ")(\\S+))?");
  }