Group { name rebuild_frames selected true xpos -421 ypos 16 addUserKnob {20 User} addUserKnob {26 text1 l "" +STARTLINE T "1) Hit 'Reset' before beginning"} addUserKnob {22 reset l Reset T "n = nuke.thisNode()\['inputframe']\nkt = nuke.thisNode()\['kt']\nko = nuke.thisNode()\['ko']\np = nuke.thisNode()\['passthrough']\nkf = nuke.thisNode()\['kf']\nkl = nuke.thisNode()\['kl']\nn.clearAnimated()\nkt.clearAnimated()\nko.clearAnimated()\nn.setAnimated()\nf = nuke.thisNode().firstFrame()\nl = nuke.thisNode().lastFrame() \nn.animation(0).setKey(f,f)\nn.animation(0).setKey(l,l)\np.setValue(0)\nkf.setValue(f)\nkl.setValue(l)\n\ndef rebuild():\n\n\tk = nuke.thisNode()\['inputframe']\n\n\tif(k.isAnimated()):\n\t\t\t\t\n\t\ttOriginalCurve = k.animation(0)\n\t\t\t\t\t\n\t\ttKeys = tOriginalCurve.keys()\n\n\t\ti = 0\n\n\t\t\n\t\tkt = nuke.thisNode()\['kt']\n\t\tko = nuke.thisNode()\['ko']\n\t\tkv = nuke.thisNode()\['verbose'].value()\n\t\tkt.clearAnimated()\n\t\tko.clearAnimated()\n\t\tkt.setAnimated()\n\t\tko.setAnimated()\n\n\t\tfor tKey in tKeys:\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\ttFrame = tKey.x \n\t\t\ttFrameY = tKey.y\n\n\t\t\tif (kv):\n\n\t\t\t\tprint(\"key \" + str(i) + \" has x value \" + str(tFrame) + \", y value \" + str(tFrameY))\n\n\t\t\tko.setValueAt( i, tFrame )\n\n\t\t\tkt.setValueAt( tFrame, i )\n\n\t\t\ti = i+1\n\n\t\tkoKeys = ko.animation(0).keys()\n\n\t\tfor tKey in koKeys:\t\n\n\t\t\ttKey.interpolation = nuke.LINEAR\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\n\t\tktKeys = kt.animation(0).keys()\n\n\t\tfor tKey in ktKeys:\t\n\n\t\t\ttKey.interpolation = nuke.LINEAR\n\n\tp = nuke.thisNode()\['passthrough']\n\tp.setValue(1)" +STARTLINE} addUserKnob {26 ""} addUserKnob {26 text2 l "" +STARTLINE T "2) Add keys on frames that are good\n Remove keys on frames to be rebuilt "} addUserKnob {22 addall l "Keyframe all" T "n = nuke.thisNode()\['inputframe']\nn.setAnimated()\nf = nuke.thisNode().firstFrame()\nl = nuke.thisNode().lastFrame() \n\nn.animation(0).setKey(f,f)\nn.animation(0).setKey(l,l)\n\nfor i in range( f, l, 1 ):\n\tn.setValueAt(i, i)" +STARTLINE} addUserKnob {3 inputframe l Frame} inputframe {{curve x1001 1001 x1100 1100}} addUserKnob {22 addkey l "Add Key" -STARTLINE T "n = nuke.thisNode()\['inputframe']\nn.setAnimated()\nt = nuke.frame()\nn.animation(0).setKey(t,t)\n"} addUserKnob {22 deletekey l "Delete key" -STARTLINE T "n = nuke.thisNode()\['inputframe']\nt = nuke.frame()\n#n.animation(0).removeKeyAt(t)\nn.removeKeyAt(t)\nrebuild()"} addUserKnob {26 text3 l "" +STARTLINE T "(Do not manually change value of 'Frame' - leave it as frame number)"} addUserKnob {26 ""} addUserKnob {4 method l "Optical Flow Method" t "Oflow is faster but Kronos gives a better result usually." M {OFlow Kronos}} addUserKnob {26 ""} addUserKnob {26 text4 l "" +STARTLINE T "3) Hit 'Rebuild' to rebuild 'bad' frames"} addUserKnob {22 rebuild l Rebuild! T rebuild() +STARTLINE} addUserKnob {6 verbose +STARTLINE} addUserKnob {20 about l About} addUserKnob {26 credit l "" -STARTLINE T "FRAME REBUILDER v1.2\n\nRebuilds broken or missing frames using Optical Flow.\nAssumes that many of the frames are good, but that bad frames are littered throughout. \n\nhttps://richardfrazer.com/tools-tutorials/rebuilding-bad-frames-using-oflow/\n\nv1.1 by Richard Frazer\nv1.2 by Richard Frazer with update by Daniel Mark Miller \n (option between OFlow and Kronos methods)\nv1.3 by Richard Frazer - using OFlow2 class\n"} addUserKnob {26 ""} addUserKnob {3 kt +INVISIBLE} kt 1328 addUserKnob {3 ko +INVISIBLE} ko 0.01529052036 addUserKnob {3 passthrough +INVISIBLE} addUserKnob {3 kf +INVISIBLE} kf 1001 addUserKnob {3 kl +INVISIBLE} kl 1100 } Input { inputs 0 name Input1 xpos 475 ypos -625 } Dot { name Dot3 xpos 509 ypos -547 } set Nfcd8da0 [stack 0] TimeWarp { lookup {{parent.kt}} time "" name TimeWarp5 xpos 475 ypos -480 } set Nfcddd50 [stack 0] Kronos { input.first {{parent.kf}} input.last {{parent.kl}} retimedChannels all timing2 Frame timingFrame2 {{parent.ko}} motionEstimation Regularized name Kronos2 xpos 557 ypos -406 } push $Nfcddd50 OFlow2 { input.first {{parent.kf}} input.last {{parent.kl}} timing2 Frame timingFrame2 {{parent.ko}} name OFlow3 selected true xpos 413 ypos -401 } Switch { inputs 2 which {{parent.method i}} name Switch2 xpos 475 ypos -341 } push $Nfcd8da0 Dot { name Dot2 xpos 685 ypos -490 } Dot { name Dot1 xpos 685 ypos -300 } Switch { inputs 2 which {{parent.passthrough}} name Switch1 xpos 475 ypos -276 } Output { name Output1 xpos 475 ypos -215 } end_group