FIRE-34771: Remove BVH save option from poser
parent
3e7f970c48
commit
7d1a2e1cce
|
|
@ -8056,17 +8056,6 @@
|
|||
<key>Value</key>
|
||||
<integer>0</integer>
|
||||
</map>
|
||||
<key>FSPoserSaveBvhFileAlso</key>
|
||||
<map>
|
||||
<key>Comment</key>
|
||||
<string>Whether to save a BVH file as well when saving a pose.</string>
|
||||
<key>Persist</key>
|
||||
<integer>1</integer>
|
||||
<key>Type</key>
|
||||
<string>Boolean</string>
|
||||
<key>Value</key>
|
||||
<integer>0</integer>
|
||||
</map>
|
||||
<key>FSPoserTrackpadSensitivity</key>
|
||||
<map>
|
||||
<key>Comment</key>
|
||||
|
|
|
|||
|
|
@ -45,14 +45,12 @@ namespace
|
|||
{
|
||||
constexpr char POSE_INTERNAL_FORMAT_FILE_MASK[] = "*.xml";
|
||||
constexpr char POSE_INTERNAL_FORMAT_FILE_EXT[] = ".xml";
|
||||
constexpr char POSE_EXTERNAL_FORMAT_FILE_EXT[] = ".bvh";
|
||||
constexpr char POSE_SAVE_SUBDIRECTORY[] = "poses";
|
||||
constexpr std::string_view POSE_PRESETS_HANDS_SUBDIRECTORY = "hand_presets";
|
||||
constexpr char XML_LIST_HEADER_STRING_PREFIX[] = "header_";
|
||||
constexpr char XML_LIST_TITLE_STRING_PREFIX[] = "title_";
|
||||
constexpr char XML_JOINT_TRANSFORM_STRING_PREFIX[] = "joint_transform_";
|
||||
constexpr std::string_view POSER_ADVANCEDWINDOWSTATE_SAVE_KEY = "FSPoserAdvancedWindowState";
|
||||
constexpr std::string_view POSER_ALSOSAVEBVHFILE_SAVE_KEY = "FSPoserSaveBvhFileAlso";
|
||||
constexpr std::string_view POSER_TRACKPAD_SENSITIVITY_SAVE_KEY = "FSPoserTrackpadSensitivity";
|
||||
} // namespace
|
||||
|
||||
|
|
@ -160,12 +158,6 @@ bool FSFloaterPoser::postBuild()
|
|||
mToggleAdvancedPanelBtn->setValue(true);
|
||||
}
|
||||
|
||||
mAlsoSaveBvhCbx = getChild<LLCheckBoxCtrl>("also_save_bvh_checkbox");
|
||||
if (gSavedSettings.getBOOL(POSER_ALSOSAVEBVHFILE_SAVE_KEY))
|
||||
{
|
||||
mAlsoSaveBvhCbx->set(true);
|
||||
}
|
||||
|
||||
mTrackpadSensitivitySlider = getChild<LLSliderCtrl>("trackpad_sensitivity_slider");
|
||||
mTrackpadSensitivitySlider->setValue(gSavedSettings.getF32(POSER_TRACKPAD_SENSITIVITY_SAVE_KEY));
|
||||
|
||||
|
|
@ -232,7 +224,6 @@ void FSFloaterPoser::onOpen(const LLSD& key)
|
|||
void FSFloaterPoser::onClose(bool app_quitting)
|
||||
{
|
||||
gSavedSettings.setBOOL(POSER_ADVANCEDWINDOWSTATE_SAVE_KEY, mToggleAdvancedPanelBtn->getValue().asBoolean());
|
||||
gSavedSettings.setBOOL(POSER_ALSOSAVEBVHFILE_SAVE_KEY, mAlsoSaveBvhCbx->getValue());
|
||||
|
||||
LLFloater::onClose(app_quitting);
|
||||
}
|
||||
|
|
@ -317,57 +308,9 @@ void FSFloaterPoser::onClickPoseSave()
|
|||
refreshPoseScroll(mPosesScrollList);
|
||||
setUiSelectedAvatarSaveFileName(filename);
|
||||
// TODO: provide feedback for save
|
||||
|
||||
bool alsoSaveAsBvh = mAlsoSaveBvhCbx->getValue().asBoolean();
|
||||
if (alsoSaveAsBvh)
|
||||
savePoseToBvh(avatar, filename);
|
||||
}
|
||||
}
|
||||
|
||||
bool FSFloaterPoser::savePoseToBvh(LLVOAvatar* avatar, const std::string& poseFileName)
|
||||
{
|
||||
if (poseFileName.empty())
|
||||
return false;
|
||||
|
||||
if (!mPoserAnimator.isPosingAvatar(avatar))
|
||||
return false;
|
||||
|
||||
bool writeSuccess = false;
|
||||
|
||||
try
|
||||
{
|
||||
std::string pathname = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, POSE_SAVE_SUBDIRECTORY);
|
||||
if (!gDirUtilp->fileExists(pathname))
|
||||
{
|
||||
LL_WARNS("Poser") << "Couldn't find folder: " << pathname << " - creating one." << LL_ENDL;
|
||||
LLFile::mkdir(pathname);
|
||||
}
|
||||
|
||||
std::string fullSavePath =
|
||||
gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, POSE_SAVE_SUBDIRECTORY, poseFileName + POSE_EXTERNAL_FORMAT_FILE_EXT);
|
||||
|
||||
llofstream file;
|
||||
file.open(fullSavePath.c_str());
|
||||
if (!file.is_open())
|
||||
{
|
||||
LL_WARNS("Poser") << "Unable to save pose!" << LL_ENDL;
|
||||
return false;
|
||||
}
|
||||
|
||||
writeSuccess = mPoserAnimator.writePoseAsBvh(&file, avatar);
|
||||
|
||||
file.close();
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
LL_WARNS("Posing") << "Exception caught in SaveToBVH: " << e.what() << LL_ENDL;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool FSFloaterPoser::savePoseToXml(LLVOAvatar* avatar, const std::string& poseFileName)
|
||||
{
|
||||
if (poseFileName.empty())
|
||||
|
|
|
|||
|
|
@ -192,7 +192,6 @@ class FSFloaterPoser : public LLFloater
|
|||
void onClickPoseSave();
|
||||
void onPoseFileSelect();
|
||||
bool savePoseToXml(LLVOAvatar* avatar, const std::string& posePath);
|
||||
bool savePoseToBvh(LLVOAvatar* avatar, const std::string& posePath);
|
||||
void onClickBrowsePoseCache();
|
||||
void onPoseMenuAction(const LLSD& param);
|
||||
void loadPoseFromXml(LLVOAvatar* avatar, const std::string& poseFileName, E_LoadPoseMethods loadMethod);
|
||||
|
|
|
|||
|
|
@ -808,113 +808,3 @@ bool FSPoserAnimator::isAvatarSafeToUse(LLVOAvatar* avatar) const
|
|||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool FSPoserAnimator::writePoseAsBvh(llofstream* fileStream, LLVOAvatar* avatar)
|
||||
{
|
||||
if (!fileStream || !avatar)
|
||||
return false;
|
||||
|
||||
*fileStream << "HIERARCHY" << std::endl;
|
||||
auto startingJoint = getPoserJointByName("mPelvis");
|
||||
writeBvhFragment(fileStream, avatar, startingJoint, 0);
|
||||
*fileStream << "MOTION" << std::endl;
|
||||
*fileStream << "Frames: 1" << std::endl;
|
||||
*fileStream << "Frame Time: 1" << std::endl;
|
||||
writeBvhMotion(fileStream, avatar, startingJoint);
|
||||
*fileStream << std::endl;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool FSPoserAnimator::writeBvhFragment(llofstream* fileStream, LLVOAvatar* avatar, const FSPoserJoint* joint, S32 tabStops)
|
||||
{
|
||||
if (!joint)
|
||||
return false;
|
||||
|
||||
auto position = getJointPosition(avatar, *joint);
|
||||
|
||||
switch (joint->boneType())
|
||||
{
|
||||
case WHOLEAVATAR:
|
||||
*fileStream << "ROOT " + joint->jointName() << std::endl;
|
||||
*fileStream << "{" << std::endl;
|
||||
*fileStream << getTabs(tabStops + 1) + "OFFSET " + vec3ToXYZString(position) << std::endl;
|
||||
*fileStream << getTabs(tabStops + 1) + "CHANNELS 6 Xposition Yposition Zposition Xrotation Yrotation Zrotation" << std::endl;
|
||||
break;
|
||||
|
||||
default:
|
||||
*fileStream << getTabs(tabStops) + "JOINT " + joint->jointName() << std::endl;
|
||||
*fileStream << getTabs(tabStops) + "{" << std::endl;
|
||||
*fileStream << getTabs(tabStops + 1) + "OFFSET " + vec3ToXYZString(position) << std::endl;
|
||||
*fileStream << getTabs(tabStops + 1) + "CHANNELS 3 Xrotation Yrotation Zrotation" << std::endl;
|
||||
break;
|
||||
}
|
||||
|
||||
size_t numberOfBvhChildNodes = joint->bvhChildren().size();
|
||||
if (numberOfBvhChildNodes > 0)
|
||||
{
|
||||
for (size_t index = 0; index != numberOfBvhChildNodes; ++index)
|
||||
{
|
||||
auto nextJoint = getPoserJointByName(joint->bvhChildren()[index]);
|
||||
writeBvhFragment(fileStream, avatar, nextJoint, tabStops + 1);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
*fileStream << getTabs(tabStops + 1) + "End Site" << std::endl;
|
||||
*fileStream << getTabs(tabStops + 1) + "{" << std::endl;
|
||||
*fileStream << getTabs(tabStops + 2) + "OFFSET " + vec3ToXYZString(position) << std::endl; // I don't understand this node
|
||||
*fileStream << getTabs(tabStops + 1) + "}" << std::endl;
|
||||
}
|
||||
|
||||
*fileStream << getTabs(tabStops) + "}" << std::endl;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool FSPoserAnimator::writeBvhMotion(llofstream* fileStream, LLVOAvatar* avatar, const FSPoserJoint* joint)
|
||||
{
|
||||
if (!joint)
|
||||
return false;
|
||||
|
||||
auto rotation = getJointRotation(avatar, *joint, SWAP_NOTHING, NEGATE_NOTHING, true);
|
||||
auto position = getJointPosition(avatar, *joint, true);
|
||||
|
||||
switch (joint->boneType())
|
||||
{
|
||||
case WHOLEAVATAR:
|
||||
*fileStream << vec3ToXYZString(position) + " " + rotationToYZXString(rotation);
|
||||
break;
|
||||
|
||||
default:
|
||||
*fileStream << " " + rotationToYZXString(rotation);
|
||||
break;
|
||||
}
|
||||
|
||||
size_t numberOfBvhChildNodes = joint->bvhChildren().size();
|
||||
for (size_t index = 0; index != numberOfBvhChildNodes; ++index)
|
||||
{
|
||||
auto nextJoint = getPoserJointByName(joint->bvhChildren()[index]);
|
||||
writeBvhMotion(fileStream, avatar, nextJoint);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string FSPoserAnimator::vec3ToXYZString(const LLVector3& val)
|
||||
{
|
||||
return std::to_string(val[VX]) + " " + std::to_string(val[VY]) + " " + std::to_string(val[VZ]);
|
||||
}
|
||||
|
||||
std::string FSPoserAnimator::rotationToYZXString(const LLVector3& val)
|
||||
{
|
||||
return std::to_string(val[VY] * RAD_TO_DEG) + " " + std::to_string(val[VZ] * RAD_TO_DEG) + " " + std::to_string(val[VX] * RAD_TO_DEG);
|
||||
}
|
||||
|
||||
std::string FSPoserAnimator::getTabs(S32 numOfTabstops)
|
||||
{
|
||||
std::string tabSpaces;
|
||||
for (S32 i = 0; i < numOfTabstops; i++)
|
||||
tabSpaces += "\t";
|
||||
|
||||
return tabSpaces;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -476,14 +476,6 @@ public:
|
|||
/// <param name="avatar">The avatar whose pose should flip left-right.</param>
|
||||
void flipEntirePose(LLVOAvatar* avatar);
|
||||
|
||||
/// <summary>
|
||||
/// Determines whether the supplied PoserJoint for the supplied avatar is being posed.
|
||||
/// </summary>
|
||||
/// <param name="avatar">The avatar having the joint to which we refer.</param>
|
||||
/// <param name="joint">The joint being queried for.</param>
|
||||
/// <returns>True if this is joint is being posed for the supplied avatar, otherwise false.</returns>
|
||||
bool writePoseAsBvh(llofstream* fileStream, LLVOAvatar* avatar);
|
||||
|
||||
private:
|
||||
/// <summary>
|
||||
/// Translates a rotation vector from the UI to a Quaternion for the bone.
|
||||
|
|
@ -527,41 +519,6 @@ public:
|
|||
/// <returns>True if the avatar is safe to manipulate, otherwise false.</returns>
|
||||
bool isAvatarSafeToUse(LLVOAvatar* avatar) const;
|
||||
|
||||
/// <summary>
|
||||
/// Recursively writes a fragment of a BVH file format representation of the supplied joint, then that joints BVH child(ren).
|
||||
/// </summary>
|
||||
/// <param name="fileStream">The stream to write the fragment to.</param>
|
||||
/// <param name="avatar">The avatar owning the supplied joint.</param>
|
||||
/// <param name="joint">The joint whose fragment should be written, and whose child(ren) will also be written.</param>
|
||||
/// <param name="tabStops">The number of tab-stops to include for formatting purpose.</param>
|
||||
/// <returns>True if the fragment wrote successfully, otherwise false.</returns>
|
||||
bool writeBvhFragment(llofstream* fileStream, LLVOAvatar* avatar, const FSPoserJoint* joint, S32 tabStops);
|
||||
|
||||
/// <summary>
|
||||
/// Writes a fragment of the 'single line' representing an animation frame within the BVH file respresenting the positions and/or rotations.
|
||||
/// </summary>
|
||||
/// <param name="fileStream">The stream to write the position and/or rotation to.</param>
|
||||
/// <param name="avatar">The avatar owning the supplied joint.</param>
|
||||
/// <param name="joint">The joint whose position and/or rotation should be written.</param>
|
||||
/// <returns></returns>
|
||||
bool writeBvhMotion(llofstream* fileStream, LLVOAvatar* avatar, const FSPoserJoint* joint);
|
||||
|
||||
/// <summary>
|
||||
/// Generates a string with the supplied number of tab-chars.
|
||||
/// </summary>
|
||||
std::string static getTabs(S32 numOfTabstops);
|
||||
|
||||
/// <summary>
|
||||
/// Transforms a rotation such that llbvhloader.cpp can resolve it to something vaguely approximating the supplied angle.
|
||||
/// When I say vague, I mean, it's numbers, buuuuut.
|
||||
/// </summary>
|
||||
std::string static rotationToYZXString(const LLVector3& val);
|
||||
|
||||
/// <summary>
|
||||
/// Transforms the supplied vector into a string of three numbers, format suiting to writing into a BVH file.
|
||||
/// </summary>
|
||||
std::string static vec3ToXYZString(const LLVector3& val);
|
||||
|
||||
/// <summary>
|
||||
/// Maps the avatar's ID to the animation registered to them.
|
||||
/// Thus we start/stop the same animation, and get/set the same rotations etc.
|
||||
|
|
|
|||
|
|
@ -1463,15 +1463,6 @@ width="565">
|
|||
name="save_file_options"
|
||||
left_pad="2"
|
||||
width="235">
|
||||
<check_box
|
||||
name="also_save_bvh_checkbox"
|
||||
height="16"
|
||||
label="Write BVH when saving"
|
||||
follows="left|top"
|
||||
left="0"
|
||||
tool_tip="When you save your pose, also write a BVH file, which can be uploaded via the 'Build' menu to pose yourself or others in-world"
|
||||
top_pad="5"
|
||||
width="134" />
|
||||
<slider
|
||||
decimal_digits="2"
|
||||
can_edit_text="true"
|
||||
|
|
|
|||
Loading…
Reference in New Issue