定义IN,tI_{N,t}IN,t表示没有经过jitter采样处理的第ttt帧原始画面,IJ,tI_{J,t}IJ,t表示jitter采样得到的第ttt帧画面;MVN,t,MVJ,tMV_{N,t},MV_{J,t}MVN,t,MVJ,t表示的意思类似,只不过从“画面”变成了“后向运动矢量”;JtJ_{t}Jt表示第ttt帧施加给相机的(pixel-wise)抖动量
值得注意的是,下面讨论的MVJ,tMV_{J,t}MVJ,t将jitter抖动也纳入了运动变化的考量范畴,换句话说,即使前后两帧(i−1,ii-1,ii−1,i)的相机位置和朝向完全没有变化,且画面中全部是静态物体,也会因为jitter抖动的缘故,MVJ,tMV_{J,t}MVJ,t的值也会呈现出非0的情况(当然了,MVN,tMV_{N,t}MVN,t的值全部为0)

IJ,t(p)=IN,t(p+Jt)⇔IN,t(p)=IJ,t(p−Jt)\begin{equation} I_{J,t}(p)=I_{N,t}(p+J_{t})\Leftrightarrow I_{N,t}(p)=I_{J,t}(p-J_{t})\end{equation}IJ,t(p)=IN,t(p+Jt)⇔IN,t(p)=IJ,t(p−Jt)
//for example, rendersize=(960,540), display size=(1920,1080)
//Curjitter in [-0.5,0.5],such as Halton sequence whose lenght is 32
m_temporalSRShader.SetFloats("renderSize", m_renderSize.x, m_renderSize.y);
m_temporalSRShader.SetFloats("displaySize", m_displaySize.x, m_displaySize.y);
m_temporalSRShader.SetVector("_curJitter", Curjitter);//J_{t}
m_temporalSRShader.SetVector("_prevJitter", Prevjitter); //J_{t-1}
void UpscaleMain(uint3 id : SV_DispatchThreadID)
{
int2 pos_sr = id.xy;
float2 ori_uv = float2(pos_sr + 0.5) / displaySize;
float2 new_uv = float2(ori_uv.x-_curJitter.x/renderSize.x, ori_uv.y-_curJitter.y/renderSize.y );
...
根据引擎生成的后向运动矢量定义,在时序信息可信(没有遮挡、高光、阴影、锯齿等)的前提下,我们有
IN,t(p)=IN,t−1(p−MVN,t(p))\begin{equation} I_{N,t}(p)=I_{N,t-1}(p-MV_{N,t}(p)) \end{equation}IN,t(p)=IN,t−1(p−MVN,t(p))
根据(1)(2)(1)(2)(1)(2)两式可得:
IJ,t(p−Jt)=IN,t−1(p−MVN,t(p))\begin{equation} I_{J,t}(p-J_t)=I_{N,t-1}(p-MV_{N,t}(p)) \end{equation}IJ,t(p−Jt)=IN,t−1(p−MVN,t(p))
IN,t−1(p−MVN,t(p))=IJ,t−1(p−MVN,t(p)−Jt−1)\begin{equation} I_{N,t-1}(p-MV_{N,t}(p))=I_{J,t-1}(p-MV_{N,t}(p)-J_{t-1}) \end{equation}IN,t−1(p−MVN,t(p))=IJ,t−1(p−MVN,t(p)−Jt−1)
结合(3)(4)(3)(4)(3)(4)两式可得
IJ,t(p−Jt)=IJ,t−1(p−(MVN,t(p)+Jt−1))⇔IJ,t(p−Jt)=IJ,t−1(p−(MVN,t(p)+Jt−1−Jt))\begin{equation} I_{J,t}(p-J_t)=I_{J,t-1}(p-(MV_{N,t}(p)+J_{t-1}))\Leftrightarrow I_{J,t}(p-J_t)=I_{J,t-1}(p-(MV_{N,t}(p)+J_{t-1}-J_t))\end{equation}IJ,t(p−Jt)=IJ,t−1(p−(MVN,t(p)+Jt−1))⇔IJ,t(p−Jt)=IJ,t−1(p−(MVN,t(p)+Jt−1−Jt))
根据(5)(5)(5)式和后向运动矢量的定义可知:
MVJ,t=MVN,t+Jt−1−Jt\begin{equation} MV_{J,t}=MV_{N,t}+J_{t-1}-J_{t} \end{equation}MVJ,t=MVN,t+Jt−1−Jt
又结合(1)(1)(1)式和后向运动矢量的定义可知
IN,t(p)=IJ,t−1(p−Jt−MVJ,t(p))\begin{equation} I_{N,t}(p)=I_{J,t-1}(p-J_t-MV_{J,t}(p))\end{equation}IN,t(p)=IJ,t−1(p−Jt−MVJ,t(p))
float2 pre_juv=new_uv-currentMV.SampleLevel(smpLinearClamp,ori_uv,1.0f).xy;
又根据(6)(6)(6)式和后向运动矢量定义可得
IN,t(p)=IN,t−1(p−Jt−MVJ,t(p)+Jt−1−Jt)\begin{equation} I_{N,t}(p)=I_{N,t-1}(p-J_t-MV_{J,t}(p)+J_{t-1}-J_t)\end{equation}IN,t(p)=IN,t−1(p−Jt−MVJ,t(p)+Jt−1−Jt)
float2 pre_njuv=ori_uv-currentMV.SampleLevel(smpLinearClamp,ori_uv,1.0f).xy-(_curJitter - _prevJitter)/renderSize;
float4 prev_rgba = prevYCoCgAHR.SampleLevel(smpLinearClamp, pre_njuv, 0);
如果MVJ,tMV_{J,t}MVJ,t将jitter抖动没有纳入了运动变化的考量范畴,换句话说,即使前后两帧(i−1,ii-1,ii−1,i)的相机位置和朝向完全没有变化,且画面中全部是静态物体,MVJ,tMV_{J,t}MVJ,t的值就是0了呢?
那可以看做MVJ,tMV_{J,t}MVJ,t和MVN,tMV_{N,t}MVN,t就没有区别了,只不过其和“未加抖动情况下渲染生成的motion vector”相比,会存在物体位移上的偏差(当然,两个对应位置上的值是完全一样的)
此时的情况就比较简单了,我这边直接给出代码,具体推导留给大家思考
void UpscaleMain(uint3 id : SV_DispatchThreadID)
{
int2 pos_sr = id.xy;
float2 ori_uv = float2(pos_sr + 0.5) / displaySize;
float2 cur_uv = ori_uv - _curJitter/renderSize;
float2 cur_rgb = currentColorLR.SampleLevel(smpLinearClamp, cur_uv, 0).xy; //sample color of frame T
float2 cur_mv = currentMotionLR.SampleLevel(smpLinearClamp, cur_uv, 0).xy; //sample motion of frame T
float2 pre_uv = ori_uv - cur_mv - _prevJitter / renderSize;
float2 pre_depth = prevDepthLR.SampleLevel(smpLinearClamp, pre_uv , 0).xy; //sample depth of frame T-1
float2 pre_mv = prevMotionLR.SampleLevel(smpLinearClamp, pre_uv , 0).xy;// //sample motion of frame T-1
float2 pre_sr_uv = ori_uv - cur_mv; //because of no jitter in Super-resolution result T-1
float4 pre_sr_rgba = prevColorSR.SampleLevel(smpLinearClamp, pre_sr_uv, 0); // sample color of Super-resolution result T-1 (recurrent)
}
157

被折叠的 条评论
为什么被折叠?



