在任意點評估樣條曲線的最佳/最正確的方法是什麼?貝塞爾樣條評估的正確性
我繪製了我的評估結果,並將它們與使用UI庫所得到的結果進行了比較,結果發現我的結果已關閉。
我使用中心段的三次方程式,而曲線的第一段使用二次方程式。
我認爲我有這個問題的原因是因爲在其評估的X座標的變化(位移)和我目前在不斷評估其踏下導致輸入之間存在一些差異座標x和輸出之一(我目前忽略)
我可以根據需要提供代碼。 (我使用Qt作爲檢查正確性的一種方式,以防萬一)
在任意點評估樣條曲線的最佳/最正確的方法是什麼?貝塞爾樣條評估的正確性
我繪製了我的評估結果,並將它們與使用UI庫所得到的結果進行了比較,結果發現我的結果已關閉。
我使用中心段的三次方程式,而曲線的第一段使用二次方程式。
我認爲我有這個問題的原因是因爲在其評估的X座標的變化(位移)和我目前在不斷評估其踏下導致輸入之間存在一些差異座標x和輸出之一(我目前忽略)
我可以根據需要提供代碼。 (我使用Qt作爲檢查正確性的一種方式,以防萬一)
原來是數學和編程的結合。
我已經擴展了自己對於正在實施的特定曲線類型的知識,現在我可以更好地解釋我想要實現的目標以及我的問題。對於這可能造成的任何混淆抱歉。
我正在實施FCurve,需要能夠以任意輸入值「評估」它。 FCurves是代表函數的樣條(對於任何給定的輸入,它們返回一個唯一的輸出)
當評估我的舊樣條實現時,我得到的評估結果不正確,因爲我的評估代碼沒有考慮曲線,除了FCurves稍微更具限制性之外。
我目前使用的方法來獲得確切的評估值,一直填滿一組沿着線段具有不同「t」的「線段樣本」,然後遍歷它以找到最接近的匹配並進行線性它們之間的插值。我稍後會回到它並試圖找到一個聰明的方式,以獲取多少樣本真正需要以最小的誤差來評估分段,但現在這個工作非常好。
所有這些都是因爲應用上述公式(立方貝塞爾)時,從輸入「x」和「t」中獲得不同的「x」值是相當常見的。
下面是代碼,我最終評估時,它與位:
const uint32_t sampleCount = 20;
Vec2 samples[sampleCount];
fillSegmentSamples(x, &samples[0], sampleCount);
uint32_t best = 0;
for(uint32_t i = 0; i < sampleCount; i++)
{
if(samples[i].x > x)
break;
best = i;
}
uint32_t nxt = best + 1;
if(nxt >= sampleCount)
{
best--;
nxt--;
}
float t = (x - samples[best].x)/(samples[nxt].x - samples[best].x);
y = lerp(samples[best].y, samples[nxt].y, t);
之前,我跑以下的等價物,這是錯誤的,因爲它沒有做任何的形式的補償x軸移動。(注意,在這種情況下, 「T」 會從 「X」 中提取)
Vec2 samples[1];
fillSegmentSamples(x, &samples[0], 1);
y = samples[0].y;
這是兩個問題/答案,幫助我明白髮生了什麼事情不對:
他們沒有專門針對fcurves,但弧長給了我一個修復這個問題的提示。
乾杯!
「我有這個問題的原因」什麼問題? //「如果需要,我可以提供代碼」當然需要! //「我使用Qt來檢查......」只有Qt?基礎語言是什麼? – DYangu
@Dangangu謝謝你的回覆。它確實是一個數學問題,而不是一個程序化的問題,這就是爲什麼我沒有包含代碼,也沒有在首位指定語言。儘管我很樂意提供它。 我現在已經證實,問題來自於對曲線進行「常數階躍評估」,而沒有考慮曲線的導數。如果我要考慮弧長,它可能會工作,但不能完全解決如何做到這一點。我會更新該帖子,如果我這樣做。乾杯。 –
是的,請。提供一些代碼和錯誤輸出。我仍不清楚你的錯誤是什麼。 – DYangu