示例#1
0
std::string FormatTag(std::string const& src, json::Value& data) {
  if (src.empty()) return src;
  if (src[0] == '$' && src.back() == '$') return src;
  size_t slash = src.find('/');
  if (slash == std::string::npos) return src;
  auto list = Strings::list(src.substr(0, slash));
  if (!list) {
    Logger::log("StringList not found: %s", src.substr(0, slash).c_str());
    return src;
  }
  size_t at = src.find('@', slash);
  std::string text = src.substr(slash + 1, at == std::string::npos ? at : at - slash - 1);
  if (!list.has(text)) {
    Logger::log("String not found: %s", src.substr(0, at).c_str());
    return src;
  }
  text = list[text];
  if (at != std::string::npos) {
    size_t quest = src.find('?', at);
    if (quest == std::string::npos) quest = src.length();
    FormatFlags flags = FormatTags;
    PowerTag* context = nullptr;
    AttributeMap values = GameAffixes::defaultMap();
    if (quest > at + 1) {
      flags = FormatHTML;
      context = PowerTags::get(src.substr(at + 1, quest - at - 1));
      if (!context) {
        Logger::log("PowerTag not found: %s", src.substr(at + 1, quest - at - 1).c_str());
      }
    } else {
      values["value"] = AttributeValue("%");
      values["value1"] = AttributeValue("%");
      values["value2"] = AttributeValue("%");
      values["value3"] = AttributeValue("%");
    }
    std::map<std::string, std::string> replace;
    if (quest < src.length()) {
      std::vector<std::string> parts = split(src.substr(quest + 1), '&');
      for (auto& p : parts) {
        size_t eq = p.find('=');
        if (eq == std::string::npos) continue;
        std::string key = p.substr(0, eq);
        std::string value = p.substr(eq + 1);
        if (!testString(key, isalnum)) {
          size_t pos = text.find(key);
          if (pos == std::string::npos) continue;
          std::string rval = fmtstring("@%d", replace.size() + 1);
          replace.emplace(rval, value);
          text.replace(pos, key.length(), rval);
          continue;
        }
        if (testString(value, isdigit)) {
          values.emplace(key, atof(value.c_str()));
          continue;
        }
        size_t ss = value.find('/');
        if (ss == std::string::npos) {
          values[key] = AttributeValue(value);
        } else {
          std::string listname = value.substr(0, ss);
          if (!testString(listname, isalpha)) {
            values[key] = AttributeValue(value); continue;
          }
          auto sublist = Strings::list(listname);
          if (!sublist) {
            Logger::log("StringList not found: %s", listname.c_str());
            continue;
          }
          std::string subtext = value.substr(ss + 1);
          if (!sublist.has(subtext)) {
            Logger::log("String not found: %s", value.c_str());
            continue;
          }
          values[key] = AttributeValue(sublist[subtext]);
        }
      }
    }
    text = FormatDescription(text, flags, values, context);
    for (auto& kv : replace) {
      size_t pos = text.find(kv.first);
      if (pos == std::string::npos) continue;
      text.replace(pos, kv.first.length(), kv.second);
    }
  }
  return text;
}