Wolf GetUp v1
實驗目標:
1.扣分制
2.快速進入站立瞬間
3.站立瞬間不限制視線方向 (視線瞄準將由站立處理)
4.Size 在 1-5之前隨機,Size會影響mass和JointDrive
5.ML為Release19,Unity為2021.3.11f1
實驗設計:
1.弱點觸地
AddReward(-0.0001f * wolfBodies[i].damageCoef);life -= 0.005f * wolfBodies[i].damageCoef;
2.
//Set: judge.endEpisode = true
//Set: judge.episodeLength = 10f
if(life <= 0f)
{
if(inferenceMode)
{
}
else
{
// ===Train Get Up===
float survivedTime = Time.fixedTime - arrivedMoment;
if(survivedTime < judge.episodeLength )
{
AddReward( (survivedTime - judge.episodeLength) * 0.1f );
}
judge.outLife++;
judge.Reset();
return;
}
}
else if(wolfRoot.localPosition.y < -10f)
{
if(inferenceMode)
{
}
else
{
//===Train Get Up===
float survivedTime = Time.fixedTime - arrivedMoment;
if(survivedTime < judge.episodeLength )
{
AddReward( (survivedTime - judge.episodeLength) * 0.1f );
}
judge.outY++;
//===All Required===
judge.Reset();
return;
}
}
else if(targetDistance > 500f)
{
judge.Reset();
}
targetSmoothPosition = targetPositionBuffer.GetSmoothVal();
headDir = targetSmoothPosition - stageBase.InverseTransformPoint(wolfHeadRb.position);
spineDir = targetSmoothPosition - stageBase.InverseTransformPoint(wolfSpine.position);
rootDir = targetSmoothPosition - stageBase.InverseTransformPoint(wolfRootRb.position);
lookAngle = Mathf.InverseLerp(180f, 0f, Vector3.Angle(wolfHead.right * -1f, headDir));
upAngle = Mathf.InverseLerp(180f, 0f, Vector3.Angle(wolfHead.up * -1f, Vector3.up));
spineLookAngle = Mathf.InverseLerp(180f, 30f, Vector3.Angle(wolfSpine.right * -1f, spineDir));
spineUpAngle = Mathf.InverseLerp(180f, 30f, Vector3.Angle(wolfSpine.up * -1f, Vector3.up));
rootLookAngle = Mathf.InverseLerp(180f, 30f, Vector3.Angle(wolfRoot.forward, rootDir));
rootUpAngle = Mathf.InverseLerp(180f, 30f, Vector3.Angle(wolfRoot.up, Vector3.up));
leftThighAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfLeftThigh.right, Vector3.up));
leftCalfAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfLeftCalf.right, Vector3.up));
rightThighAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfRightThigh.right, Vector3.up));
rightCalfAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfRightCalf.right, Vector3.up));
leftUpperArmAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfLeftUpperArm.right, Vector3.up));
leftForeArmAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfLeftForeArm.right, Vector3.up));
rightUpperArmAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfRightUpperArm.right, Vector3.up));
rightForeArmAngle = Mathf.InverseLerp(180f, 60f, Vector3.Angle(wolfRightForeArm.right, Vector3.up));
avgVelocity = velocityBuffer.GetSmoothVal();
flatVelocity = avgVelocity;
flatVelocity.y = 0f;
velocityCoef = Mathf.InverseLerp(0f, 10f, flatVelocity.magnitude );
// Reward -1 + angles
lastReward = (upAngle + spineUpAngle + rootUpAngle) * 0.00033f
+ (lookAngle + spineLookAngle + rootLookAngle) * 0.000133f
+ (leftThighAngle + leftCalfAngle + rightThighAngle + rightCalfAngle + leftUpperArmAngle + leftForeArmAngle + rightUpperArmAngle + rightForeArmAngle) * 0.00005f
+ (1f - velocityCoef) * 0.00018f
+ (1f - exertionRatio) * 0.00002f - 0.002f;
totalReward += lastReward;
AddReward( lastReward );
if(hasLanding && !weaknessOnGround && velocityCoef < 0.2f && upAngle > 0.9f && spineUpAngle > 0.9f && rootUpAngle > 0.9f
&& leftThighAngle > 0.9f && leftCalfAngle > 0.9f && rightThighAngle > 0.9f && rightCalfAngle > 0.9f && leftUpperArmAngle > 0.9f && leftForeArmAngle > 0.9f && rightUpperArmAngle > 0.9f && rightForeArmAngle > 0.9f)
{
//===Train Get Up===
AddReward(1f);
judge.survived++;
judge.Reset();
return;
}
大致來說
0.扣分制
1.鼓勵頭胸腹朝上向量
2.鼓勵頭胸腹視線向量
3.鼓勵四肢大腿和小腿朝上向量
4.鼓勵抑制速度
5.鼓勵抑制exertion
6.在抑制速度、頭胸腹朝上,四肢朝上滿足條件時達成
實驗時間:
Step: 5e7
Time Elapsed: 82480s (22.9hr)
//幸好想起來,以後忘記或遺失時間數據,可以去看TensorBoard的紀錄
實驗結果:
實驗結果為成功,狼可以效率受身,但是動作不太帥氣,是一種前後腳都大外八的策略
這裡原因可能有三
1.InverseLerp角過大
原本覺得對四足動物來說,受身的完成,腳是否直立沒那麼重要,因此把InverseLerp角從45度改為60度
但現在看來可能導致狼覺得大外八很好,內縮分數也不會更高,因而不會試圖內縮
2.這個動作物理上看來的確很合理,因而指出當前關節設計的缺陷
當前關節在所有活動角度都能有一樣的出力能力
但通常現實生物是主要旋轉軸力量很大,而側翼展開或其他旋轉軸力量則弱很多
導致不會使用那個動作,例如大部分的人可能都有辦法半蹲,但是可能沒幾個人用出一字馬
但是在Unity試圖實現這個效果有點不切實際
雖然Unity的關節也能切軸,但也很難重現拮抗肌的不對等
例如鱷魚的咬合力超級強,張開嘴巴的力量卻非常弱
人類的手腕向下非常有力,向上卻很弱
所以關於這個問題,決定回歸紅蓮玩偶的根源--是為了製造能自律演化的角色
因此是否和現實概念接近的生物身體能力相近並不是主要考量
反而演化能力和效率才是優先項目
因此決定除非出現很適合模擬不對等關節的新系統或設計
否則就維持當前的關節設計
3.DamageCoef係數不佳
像獸醫學妹說的,動物起身常常是利用重心變化來在地上滾動
但是我設定DamageCoef無意識的沿用的人類的比例
因此可能導致狼很討厭用身體和頭部觸地
才變成像人類一樣傾向四腳開開
但人類四腳開開,被打飛是像在空翻或側翻一樣的帥氣動作
狼四腳開開只像是個被捲入暴風的松鼠
考慮四足動物帥氣的受身,應該是身體滾一滾之後,霎那間站起來,也許應該反而要讓身體的DamageCoef數值略低於大腿和小腿才對
嗯~~不過四足動物還太欠缺數據,所以優先走會凸顯問題的路線好了
下個實驗將進行狼靜立
1.獎勵瞄準方向
2.獎勵抑制全身速度和角速度
3.獎勵四足觸地
4.使用ClampReward機制