protected String toUnderscoreFromCamel(String camelCase) {

    int lastUpper = -1;
    StringBuffer sb = new StringBuffer();
    for (int i = 0; i < camelCase.length(); i++) {
      char c = camelCase.charAt(i);

      if ('_' == c) {
        // Underscores should just be passed through
        sb.append(c);
        lastUpper = i;
      } else if (Character.isDigit(c)) {
        if (i > lastUpper + 1 && !digitsCompressed) {
          sb.append("_");
        }
        sb.append(c);
        lastUpper = i;

      } else if (Character.isUpperCase(c)) {
        if (i > lastUpper + 1) {
          sb.append("_");
        }
        sb.append(Character.toLowerCase(c));
        lastUpper = i;

      } else {
        sb.append(c);
      }
    }
    String ret = sb.toString();
    if (forceUpperCase) {
      ret = ret.toUpperCase();
    }
    return ret;
  }