Files
test2/source/blender/io/usd/intern/usd_utils.cc

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

60 lines
1.6 KiB
C++
Raw Normal View History

/* SPDX-FileCopyrightText: 2024 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
#include "usd_utils.hh"
#include "BLI_array.hh"
#include "BLI_string_ref.hh"
#include "BLI_string_utf8.h"
#include <pxr/base/tf/stringUtils.h>
#include <pxr/base/tf/unicodeUtils.h>
namespace blender::io::usd {
std::string make_safe_name(const StringRef name, bool allow_unicode)
{
if (name.is_empty()) {
return "_";
}
/* Create temporary buffer with exact amount of space required. */
const bool has_leading_digit = std::isdigit(name[0]);
Array<char, 64> storage(name.size() + (has_leading_digit ? 1 : 0));
MutableSpan<char> buf(storage);
/* Insert a leading '_' to account for names starting with digits. */
size_t offset = 0;
bool first = true;
if (has_leading_digit) {
buf[0] = '_';
offset = 1;
first = false;
}
if (!allow_unicode) {
buf.take_back(name.size()).copy_from(name);
offset += name.size();
return pxr::TfMakeValidIdentifier({buf.data(), offset});
}
for (auto cp : pxr::TfUtf8CodePointView{name}) {
constexpr pxr::TfUtf8CodePoint cp_underscore = pxr::TfUtf8CodePointFromAscii('_');
const bool cp_allowed = first ? (cp == cp_underscore || pxr::TfIsUtf8CodePointXidStart(cp)) :
pxr::TfIsUtf8CodePointXidContinue(cp);
if (!cp_allowed) {
offset += BLI_str_utf8_from_unicode(uint32_t('_'), buf.data() + offset, buf.size() - offset);
}
else {
offset += BLI_str_utf8_from_unicode(cp.AsUInt32(), buf.data() + offset, buf.size() - offset);
}
first = false;
}
return {buf.data(), offset};
}
} // namespace blender::io::usd