Welcome to Doom9's Forum, THE in-place to be for everyone interested in DVD conversion.

Before you start posting please read the forum rules. By posting to this forum you agree to abide by the rules.

 

Go Back   Doom9's Forum > Capturing and Editing Video > VapourSynth

Reply
 
Thread Tools Search this Thread Display Modes
Old 7th March 2019, 02:10   #81  |  Link
asarian
Registered User
 
Join Date: May 2005
Posts: 1,462
Quote:
Originally Posted by poisondeathray View Post
It does look impressive

One thing that stands out is the left cheek blemish - it looks over enhanced. Was that temporally consistent on other frames ? (or are you still waiting for it to finish processing other frames? )
That left-cheek blemish was actually a small glitch, it seems, in the original video (only lasting 2 frames). So, good thing Oyster got rid of it.

As for still waiting, my poor i7 6700K is going to take 54 hours to complete the job.
__________________
Gorgeous, delicious, deculture!
asarian is offline   Reply With Quote
Old 31st March 2019, 19:46   #82  |  Link
Revan654
Registered User
 
Revan654's Avatar
 
Join Date: May 2004
Posts: 324
I've been trying to get Oyster to work, I always run into either Subsampling not support, which I can easily get around, But it's the whole Blocksize issue. I've tried many source but always run into the same issue. Anyone know what else needs to be added to get this to work?

Python exception: Analyze: the block size must be 4x4, 8x4, 8x8, 16x2, 16x8, 16x16, 32x16, or 32x32.

Example of the Script:

clip = core.fmtc.bitdepth( clip, bits = 32 )
clip = core.fmtc.resample( clip, css = "444" )
ref_s = Oyster.Basic(clip, short_time=True)
clip = Oyster.Deringing(clip, ref_s, block_step=2)
Revan654 is offline   Reply With Quote
Old 31st March 2019, 21:57   #83  |  Link
jackoneill
unsigned int
 
jackoneill's Avatar
 
Join Date: Oct 2012
Location: 🇪🇺
Posts: 760
Quote:
Originally Posted by Revan654 View Post
I've been trying to get Oyster to work, I always run into either Subsampling not support, which I can easily get around, But it's the whole Blocksize issue. I've tried many source but always run into the same issue. Anyone know what else needs to be added to get this to work?

Python exception: Analyze: the block size must be 4x4, 8x4, 8x8, 16x2, 16x8, 16x16, 32x16, or 32x32.

Example of the Script:

clip = core.fmtc.bitdepth( clip, bits = 32 )
clip = core.fmtc.resample( clip, css = "444" )
ref_s = Oyster.Basic(clip, short_time=True)
clip = Oyster.Deringing(clip, ref_s, block_step=2)
You have an old copy of MVTools or MVToolsSF. Update them to the latest and that error should go away.
__________________
Buy me a "coffee" and/or hire me to write code!
jackoneill is offline   Reply With Quote
Old 31st May 2020, 02:52   #84  |  Link
SoupRKnowva
Registered User
 
Join Date: Jun 2011
Posts: 6
I have a question about doing the process in a series of steps rather than all in one go.

When i run my script and set the output as the results of Oyster.Basic(), using "vspipe exmaple.vpy example_basic.rgb", when i import it again on the second part with core.raws.Source("example_basic.rgb"), I get an error "TypeError: Oyster.Destaircase: the sample type of ref has to be single precision!"

At first i thought the autoloader was using the wrong mvtools, so i removed the non _sf version. Same problem. I tried using example.raw instead of example.rgb, thinking maybe vspipe or the importer were doing something weird. same problem.

But if i feel the output of Basic() straight into Oyster.Destaircase, without saving it out, it works just fine.

Is there something I am missing with writing the file with vspipe or with the import with raws.source()?
SoupRKnowva is offline   Reply With Quote
Old 31st May 2020, 06:52   #85  |  Link
feisty2
I'm Siri
 
feisty2's Avatar
 
Join Date: Oct 2012
Location: void
Posts: 2,633
as the error suggested, the input must be of fp32 sample type, you have to specify the sample type in core.raws.Source
feisty2 is offline   Reply With Quote
Old 7th July 2020, 07:08   #86  |  Link
Cary Knoop
Cary Knoop
 
Cary Knoop's Avatar
 
Join Date: Feb 2017
Location: Newark CA, USA
Posts: 397
Oyster is great but the performance is highly impractical.
Using a GPU-based BM3D implementation would put this slowly into the world of practicality (Optimizing KNLMeans for CUDA instead of CL would probably help as well).

Any updates on a BM3D implementation in CUDA?
Cary Knoop is offline   Reply With Quote
Old 18th July 2020, 20:36   #87  |  Link
Cary Knoop
Cary Knoop
 
Cary Knoop's Avatar
 
Join Date: Feb 2017
Location: Newark CA, USA
Posts: 397
What is function of sstring in Oyster.py?

Code:
43      def FreqMerge(self, low, hi, sbsize, sstring):
44          hif    = self.MakeDiff(hi, self.DFTTest(hi, sbsize=sbsize, sstring=sstring, **dfttest_args))
45          clip   = self.MergeDiff(self.DFTTest(low, sbsize=sbsize, sstring=sstring, **dfttest_args), hif)
Does this perhaps refer to an older version of DFTTest?
Cary Knoop is offline   Reply With Quote
Old 19th July 2020, 02:01   #88  |  Link
feisty2
I'm Siri
 
feisty2's Avatar
 
Join Date: Oct 2012
Location: void
Posts: 2,633
things have been updated in the GitHub repo
feisty2 is offline   Reply With Quote
Old 19th July 2020, 02:37   #89  |  Link
Cary Knoop
Cary Knoop
 
Cary Knoop's Avatar
 
Join Date: Feb 2017
Location: Newark CA, USA
Posts: 397
Quote:
Originally Posted by feisty2 View Post
things have been updated in the GitHub repo
Got it, thanks!
Cary Knoop is offline   Reply With Quote
Old 23rd January 2023, 10:18   #90  |  Link
Emulgator
Big Bit Savings Now !
 
Emulgator's Avatar
 
Join Date: Feb 2007
Location: close to the wall
Posts: 1,266
2023, Oyster in VapourSynth R61:
I would welcome a helping tip towards replacement of depreciated function calls
I tried, but I am a VS noob, and I would welcome a full documentation...

I have hacked at Oyster.py but I get "SyntaxError: Invalid syntax for"
core = import core

Split in 2 parts (forum 16000 chars limit)

Code:
from vapoursynth import core
import math

fmtc_args                      = dict(fulls=True, fulld=True)
msuper_args                    = dict(hpad=0, vpad=0, sharp=2, levels=0)
manalyze_args                  = dict(search=3, truemotion=False, trymany=True, levels=0, badrange=-24, divide=0, dct=0)
mrecalculate_args              = dict(truemotion=False, search=3, smooth=1, divide=0, dct=0)
mdegrain_args                  = dict(thscd1=16711680.0, thscd2=255.0)
nnedi_args                     = dict(field=1, dh=True, nns=4, qual=2, etype=1, nsize=0)
dfttest_args                   = dict(smode=0, sosize=0, tbsize=1, tosize=0, tmode=0)

class core:
      def __init__(self):
          self.core            = vs.core()
          self.MSuper          = self.core.mvsf.Super
          self.MAnalyze        = self.core.mvsf.Analyze
          self.MRecalculate    = self.core.mvsf.Recalculate
          self.MDegrain        = self.core.mvsf.Degrain
          self.RGB2OPP         = self.core.bm3d.RGB2OPP
          self.OPP2RGB         = self.core.bm3d.OPP2RGB
          self.BMBasic         = self.core.bm3d.VBasic
          self.BMFinal         = self.core.bm3d.VFinal
          self.Aggregate       = self.core.bm3d.VAggregate
          self.DFTTest         = self.core.dfttest.DFTTest
          self.KNLMeansCL      = self.core.knlm.KNLMeansCL
          self.NNEDI           = self.core.nnedi3.nnedi3
          self.Resample        = self.core.fmtc.resample
          self.Expr            = self.core.std.Expr
          self.MakeDiff        = self.core.std.MakeDiff
          self.MergeDiff       = self.core.std.MergeDiff
          self.Crop            = self.core.std.CropRel
          self.CropAbs         = self.core.std.CropAbs
          self.Transpose       = self.core.std.Transpose
          self.BlankClip       = self.core.std.BlankClip
          self.AddBorders      = self.core.std.AddBorders
          self.StackHorizontal = self.core.std.StackHorizontal
          self.StackVertical   = self.core.std.StackVertical
          self.MaskedMerge     = self.core.std.MaskedMerge
          self.ShufflePlanes   = self.core.std.ShufflePlanes
          self.SetFieldBased   = self.core.std.SetFieldBased

      def FreqMerge(self, low, hi, sbsize, slocation):
          hif                  = self.MakeDiff(hi, self.DFTTest(hi, sbsize=sbsize, slocation=slocation, **dfttest_args))
          clip                 = self.MergeDiff(self.DFTTest(low, sbsize=sbsize, slocation=slocation, **dfttest_args), hif)
          return clip

      def Pad(self, src, left, right, top, bottom):
          w                    = src.width
          h                    = src.height
          clip                 = self.Resample(src, w+left+right, h+top+bottom, -left, -top, w+left+right, h+top+bottom, kernel="point", **fmtc_args)
          return clip

      def NLMeans(self, src, d, a, s, h, rclip, color):
          def duplicate(src):
              if d > 0:
                 blank         = self.Expr(src[0], "0.0") * d
                 clip          = blank + src + blank
              else:
                 clip          = src
              return clip
          pad                  = self.AddBorders(src, a+s, a+s, a+s, a+s)
          pad                  = duplicate(pad)
          if rclip is not None:
             rclip             = self.AddBorders(rclip, a+s, a+s, a+s, a+s)
             rclip             = duplicate(rclip)
          nlm                  = self.KNLMeansCL(pad, d=d, a=a, s=s, h=h, channels="YUV" if color else "Y", wref=1.0, rclip=rclip)
          clip                 = self.Crop(nlm, a+s, a+s, a+s, a+s)
          return clip[d:clip.num_frames - d]

      def ThrMerge(self, flt, src, ref=None, thr=0.0009765625, elast=None):
          ref                  = src if ref is None else ref
          elast                = thr / 2 if elast is None else elast
          BExp                 = ["x {thr} {elast} + z - 2 {elast} * / * y {elast} z + {thr} - 2 {elast} * / * +".format(thr=thr, elast=elast)]
          BDif                 = self.Expr(src, "0.0")
          PDif                 = self.Expr([flt, src], "x y - 0.0 max")
          PRef                 = self.Expr([flt, ref], "x y - 0.0 max")
          PBLD                 = self.Expr([PDif, BDif, PRef], BExp)
          NDif                 = self.Expr([flt, src], "y x - 0.0 max")
          NRef                 = self.Expr([flt, ref], "y x - 0.0 max")
          NBLD                 = self.Expr([NDif, BDif, NRef], BExp)
          BLDD                 = self.MakeDiff(PBLD, NBLD)
          BLD                  = self.MergeDiff(src, BLDD)
          UDN                  = self.Expr([flt, ref, BLD], ["x y - abs {thr} {elast} - > z x ?".format(thr=thr, elast=elast)])
          clip                 = self.Expr([flt, ref, UDN, src], ["x y - abs {thr} {elast} + < z a ?".format(thr=thr, elast=elast)])
          return clip

      def GenBlockMask(self, src):
          clip                 = self.BlankClip(src, 24, 24, color=0.0)
          clip                 = self.AddBorders(clip, 4, 4, 4, 4, color=1.0)
          clip                 = self.StackHorizontal([clip, clip, clip, clip])
          clip                 = self.StackVertical([clip, clip, clip, clip])
          clip                 = self.Resample(clip, 32, 32, kernel="point", **fmtc_args)
          clip                 = self.Expr(clip, ["x 0.0 > 1.0 0.0 ?"])
          clip                 = self.StackHorizontal([clip, clip, clip, clip, clip, clip, clip, clip])
          clip                 = self.StackVertical([clip, clip, clip, clip, clip, clip])
          clip                 = self.StackHorizontal([clip, clip, clip, clip, clip, clip])
          clip                 = self.StackVertical([clip, clip, clip, clip, clip])
          clip                 = self.StackHorizontal([clip, clip, clip, clip, clip, clip])
          clip                 = self.StackVertical([clip, clip, clip, clip, clip])
          clip                 = self.CropAbs(clip, src.width, src.height, 0, 0)
          return clip

class internal:
      def super(core, src, pel):
          src                  = core.Pad(src, 128, 128, 128, 128)
          clip                 = core.Transpose(core.NNEDI(core.Transpose(core.NNEDI(src, **nnedi_args)), **nnedi_args))
          if pel == 4:
             clip              = core.Transpose(core.NNEDI(core.Transpose(core.NNEDI(clip, **nnedi_args)), **nnedi_args))
          return clip

      def basic(core, src, super, radius, pel, sad, short_time, color):
          plane                = 4 if color else 0
          src                  = core.Pad(src, 128, 128, 128, 128)
          supersoft            = core.MSuper(src, pelclip=super, rfilter=4, pel=pel, chroma=color, **msuper_args)
          supersharp           = core.MSuper(src, pelclip=super, rfilter=2, pel=pel, chroma=color, **msuper_args)
          if short_time:
             constant          = 0.0001989762736579584832432989326
             me_sad            = [constant * math.pow(sad, 2.0) * math.log(1.0 + 1.0 / (constant * sad))]
             me_sad           += [sad]
             vmulti            = core.MAnalyze(supersoft, radius=radius, chroma=color, overlap=4, blksize=8, **manalyze_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=2, blksize=4, thsad=me_sad[0], **mrecalculate_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=1, blksize=2, thsad=me_sad[1], **mrecalculate_args)
          else:
             constant          = 0.0000139144247313257680589719533
             me_sad            = constant * math.pow(sad, 2.0) * math.log(1.0 + 1.0 / (constant * sad))
             vmulti            = core.MAnalyze(supersoft, radius=radius, chroma=color, overlap=64, blksize=128, **manalyze_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=32, blksize=64, thsad=me_sad, **mrecalculate_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=16, blksize=32, thsad=me_sad, **mrecalculate_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=8, blksize=16, thsad=me_sad, **mrecalculate_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=4, blksize=8, thsad=me_sad, **mrecalculate_args)
             vmulti            = core.MRecalculate(supersoft, vmulti, chroma=color, overlap=2, blksize=4, thsad=me_sad, **mrecalculate_args)
          clip                 = core.MDegrain(src, supersharp, vmulti, thsad=sad, plane=plane, **mdegrain_args)
          clip                 = core.Crop(clip, 128, 128, 128, 128)
          return clip

      def deringing(core, src, ref, radius, h, sigma, \
                    mse, hard_thr, block_size, block_step, group_size, bm_range, bm_step, ps_num, ps_range, ps_step, \
                    lowpass, color, matrix):
          c1                   = 0.1134141984932795312503328847998
          c2                   = 2.8623043756241389436528021745239
          strength             = [h]
          strength            += [h * math.pow(c1 * h, c2) * math.log(1.0 + 1.0 / math.pow(c1 * h, c2))]
          strength            += [None]
          def loop(flt, init, src, n):
              strength[2]      = n * strength[0] / 4 + strength[1] * (1 - n / 4)
              window           = int(32 / math.pow(2, n))
              flt              = init if n == 4 else flt
              dif              = core.MakeDiff(src, flt)
              dif              = core.NLMeans(dif, 0, window, 1, strength[2], flt, color)
              fnl              = core.MergeDiff(flt, dif)
              n               -= 1
              return fnl if n == -1 else loop(fnl, init, src, n)
          ref                  = core.FreqMerge(src, ref, block_size // 2 * 2 + 1, lowpass)
          dif                  = core.MakeDiff(src, ref)
          dif                  = core.BMBasic(dif, ref, radius=radius, th_mse=mse[0], hard_thr=hard_thr, sigma=sigma, \
                                              block_size=block_size, block_step=block_step, group_size=group_size, bm_range=bm_range, bm_step=bm_step, \
                                              ps_num=ps_num, ps_range=ps_range, ps_step=ps_step, matrix=matrix)
          dif                  = core.Aggregate(dif, radius, 1)
          ref                  = core.MergeDiff(ref, dif)
          refined              = loop(None, ref, src, 4)
          bm3d                 = core.BMFinal(refined, ref, radius=radius, th_mse=mse[1], sigma=sigma, \
                                              block_size=block_size, block_step=block_step, group_size=group_size, bm_range=bm_range, bm_step=bm_step, \
                                              ps_num=ps_num, ps_range=ps_range, ps_step=ps_step, matrix=matrix)
          bm3d                 = core.Aggregate(bm3d, radius, 1)
          bm3d                 = core.FreqMerge(refined, bm3d, block_size // 2 * 2 + 1, lowpass)
          clip                 = loop(None, bm3d, refined, 4)
          return clip

      def destaircase(core, src, ref, radius, sigma, \
                      mse, hard_thr, block_size, block_step, group_size, bm_range, bm_step, ps_num, ps_range, ps_step, \
                      thr, elast, lowpass, matrix):
          mask                 = core.GenBlockMask(core.ShufflePlanes(src, 0, vs.GRAY))
          ref                  = core.FreqMerge(src, ref, block_size // 2 * 2 + 1, lowpass)
          ref                  = core.ThrMerge(src, ref, thr=thr, elast=elast)
          dif                  = core.MakeDiff(src, ref)
          dif                  = core.BMBasic(dif, ref, radius=radius, th_mse=mse[0], hard_thr=hard_thr, sigma=sigma, \
                                              block_size=block_size, block_step=block_step, group_size=group_size, bm_range=bm_range, bm_step=bm_step, \
                                              ps_num=ps_num, ps_range=ps_range, ps_step=ps_step, matrix=matrix)
          dif                  = core.Aggregate(dif, radius, 1)
          ref                  = core.MergeDiff(ref, dif)
          dif                  = core.MakeDiff(src, ref)
          dif                  = core.BMFinal(dif, ref, radius=radius, th_mse=mse[1], sigma=sigma, \
                                              block_size=block_size, block_step=block_step, group_size=group_size, bm_range=bm_range, bm_step=bm_step, \
                                              ps_num=ps_num, ps_range=ps_range, ps_step=ps_step, matrix=matrix)
          dif                  = core.Aggregate(dif, radius, 1)
          ref                  = core.MergeDiff(ref, dif)
          clip                 = core.MaskedMerge(src, ref, mask, first_plane=True)
          return clip

      def deblocking(core, src, ref, radius, h, sigma, \
                     mse, hard_thr, block_size, block_step, group_size, bm_range, bm_step, ps_num, ps_range, ps_step, \
                     lowpass, color, matrix):
          mask                 = core.GenBlockMask(core.ShufflePlanes(src, 0, vs.GRAY))
          cleansed             = core.NLMeans(ref, radius, block_size, math.ceil(block_size / 2), h, ref, color)
          dif                  = core.MakeDiff(ref, cleansed)
          dif                  = core.BMBasic(dif, cleansed, radius=radius, th_mse=mse[0], hard_thr=hard_thr, sigma=sigma, \
                                              block_size=block_size, block_step=block_step, group_size=group_size, bm_range=bm_range, bm_step=bm_step, \
                                              ps_num=ps_num, ps_range=ps_range, ps_step=ps_step, matrix=matrix)
          dif                  = core.Aggregate(dif, radius, 1)
          cleansed             = core.MergeDiff(cleansed, dif)
          dif                  = core.MakeDiff(ref, cleansed)
          dif                  = core.BMFinal(dif, cleansed, radius=radius, th_mse=mse[1], sigma=sigma, \
                                              block_size=block_size, block_step=block_step, group_size=group_size, bm_range=bm_range, bm_step=bm_step, \
                                              ps_num=ps_num, ps_range=ps_range, ps_step=ps_step, matrix=matrix)
          dif                  = core.Aggregate(dif, radius, 1)
          cleansed             = core.MergeDiff(cleansed, dif)
          ref                  = core.FreqMerge(cleansed, ref, block_size // 2 * 2 + 1, lowpass)
          src                  = core.FreqMerge(cleansed, src, block_size // 2 * 2 + 1, lowpass)
          clip                 = core.MaskedMerge(src, ref, mask, first_plane=True)
          return clip
__________________
"To bypass shortcuts and find suffering...is called QUALity" (Die toten Augen von Friedrichshain)
"Data reduction ? Yep, Sir. We're working on that issue. Synce invntoin uf lingöage..."

Last edited by Emulgator; 23rd January 2023 at 10:44.
Emulgator is offline   Reply With Quote
Old 23rd January 2023, 10:20   #91  |  Link
Emulgator
Big Bit Savings Now !
 
Emulgator's Avatar
 
Join Date: Feb 2007
Location: close to the wall
Posts: 1,266
Code:
def Super(src, pel=4):
    if not isinstance(src, vs.VideoNode):
       raise TypeError("Oyster.Super: src has to be a video clip!")
    elif src.format.sample_type != vs.FLOAT or src.format.bits_per_sample < 32:
       raise TypeError("Oyster.Super: the sample type of src has to be single precision!")
    elif src.format.subsampling_w > 0 or src.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Super: subsampled stuff not supported!")
    if not isinstance(pel, int):
       raise TypeError("Oyster.Super: pel has to be an integer!")
    elif pel != 2 and pel != 4:
       raise RuntimeError("Oyster.Super: pel has to be 2 or 4!")
    core                       = import core
    src                        = core.SetFieldBased(src, 0)
    colorspace                 = src.format.color_family
    if colorspace == vs.RGB:
       src                     = core.RGB2OPP(src, 1)
    clip                       = internal.super(core, src, pel)
    del core
    return clip

def Basic(src, super=None, radius=6, pel=4, sad=2000.0, short_time=False):
    if not isinstance(src, vs.VideoNode):
       raise TypeError("Oyster.Basic: src has to be a video clip!")
    elif src.format.sample_type != vs.FLOAT or src.format.bits_per_sample < 32:
       raise TypeError("Oyster.Basic: the sample type of src has to be single precision!")
    elif src.format.subsampling_w > 0 or src.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Basic: subsampled stuff not supported!")
    if not isinstance(super, vs.VideoNode) and super is not None:
       raise TypeError("Oyster.Basic: super has to be a video clip or None!")
    elif super is not None:
       if super.format.sample_type != vs.FLOAT or super.format.bits_per_sample < 32 or super.format.subsampling_w > 0 or super.format.subsampling_h > 0:
          raise RuntimeError("Oyster.Basic: corrupted super clip!")
    if not isinstance(radius, int):
       raise TypeError("Oyster.Basic: radius has to be an integer!")
    elif radius < 1:
       raise RuntimeError("Oyster.Basic: radius has to be greater than 0!")
    if not isinstance(pel, int):
       raise TypeError("Oyster.Basic: pel has to be an integer!")
    elif pel != 1 and pel != 2 and pel != 4:
       raise RuntimeError("Oyster.Basic: pel has to be 1, 2 or 4!")
    if not isinstance(sad, float) and not isinstance(sad, int):
       raise TypeError("Oyster.Basic: sad has to be a real number!")
    elif sad <= 0.0:
       raise RuntimeError("Oyster.Basic: sad has to be greater than 0!")
    if not isinstance(short_time, bool):
       raise TypeError("Oyster.Basic: short_time has to be boolean!")
    core                       = import core
    color                      = True
    rgb                        = False
    colorspace                 = src.format.color_family
    if colorspace == vs.RGB:
       src                     = core.RGB2OPP(src, 1)
       rgb                     = True
    if colorspace == vs.GRAY:
       color                   = False
    src                        = core.SetFieldBased(src, 0)
    super                      = core.SetFieldBased(super, 0) if super is not None else None
    clip                       = internal.basic(core, src, super, radius, pel, sad, short_time, color)
    clip                       = core.OPP2RGB(clip, 1) if rgb else clip
    del core
    return clip

def Deringing(src, ref, radius=6, h=6.4, sigma=16.0, \
              mse=[None, None], hard_thr=3.2, block_size=8, block_step=1, group_size=32, bm_range=24, bm_step=1, ps_num=2, ps_range=8, ps_step=1, \
              lowpass=None):
    if not isinstance(src, vs.VideoNode):
       raise TypeError("Oyster.Deringing: src has to be a video clip!")
    elif src.format.sample_type != vs.FLOAT or src.format.bits_per_sample < 32:
       raise TypeError("Oyster.Deringing: the sample type of src has to be single precision!")
    elif src.format.subsampling_w > 0 or src.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Deringing: subsampled stuff not supported!")
    if not isinstance(ref, vs.VideoNode):
       raise TypeError("Oyster.Deringing: ref has to be a video clip!")
    elif ref.format.sample_type != vs.FLOAT or ref.format.bits_per_sample < 32:
       raise TypeError("Oyster.Deringing: the sample type of ref has to be single precision!")
    elif ref.format.subsampling_w > 0 or ref.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Deringing: subsampled stuff not supported!")
    if not isinstance(radius, int):
       raise TypeError("Oyster.Deringing: radius has to be an integer!")
    elif radius < 1:
       raise RuntimeError("Oyster.Deringing: radius has to be greater than 0!")
    if not isinstance(h, float) and not isinstance(h, int):
       raise TypeError("Oyster.Deringing: h has to be a real number!")
    elif h <= 0:
       raise RuntimeError("Oyster.Deringing: h has to be greater than 0!")
    if not isinstance(mse, list):
       raise TypeError("Oyster.Deringing: mse parameter has to be an array!")
    elif len(mse) != 2:
       raise RuntimeError("Oyster.Deringing: mse parameter has to contain 2 elements exactly!")
    for i in range(2):
        if not isinstance(mse[i], float) and not isinstance(mse[i], int) and mse[i] is not None:
           raise TypeError("Oyster.Deringing: elements in mse must be real numbers or None!")
    if not isinstance(lowpass, list) and lowpass is not None:
       raise TypeError("Oyster.Deringing: lowpass has to be a list or None!")
    core                       = import core
    rgb                        = False
    color                      = True
    mse[0]                     = sigma * 160.0 + 1200.0 if mse[0] is None else mse[0]
    mse[1]                     = sigma * 120.0 + 800.0 if mse[1] is None else mse[1]
    lowpass                    = [0.0,sigma, 0.48,1024.0, 1.0,1024.0] if lowpass is None else lowpass
    matrix                     = None
    colorspace                 = src.format.color_family
    if colorspace == vs.RGB:
       rgb                     = True
       matrix                  = 100
       src                     = core.RGB2OPP(src, 1)
       ref                     = core.RGB2OPP(ref, 1)
    if colorspace == vs.GRAY:
       color                   = False
    src                        = core.SetFieldBased(src, 0)
    ref                        = core.SetFieldBased(ref, 0)
    clip                       = internal.deringing(core, src, ref, radius, h, sigma, \
                                                    mse, hard_thr, block_size, block_step, group_size, bm_range, bm_step, ps_num, ps_range, ps_step, \
                                                    lowpass, color, matrix)
    clip                       = core.OPP2RGB(clip, 1) if rgb else clip
    del core
    return clip

def Destaircase(src, ref, radius=6, sigma=16.0, \
                mse=[None, None], hard_thr=3.2, block_size=8, block_step=1, group_size=32, bm_range=24, bm_step=1, ps_num=2, ps_range=8, ps_step=1, \
                thr=0.03125, elast=0.015625, lowpass=None):
    if not isinstance(src, vs.VideoNode):
       raise TypeError("Oyster.Destaircase: src has to be a video clip!")
    elif src.format.sample_type != vs.FLOAT or src.format.bits_per_sample < 32:
       raise TypeError("Oyster.Destaircase: the sample type of src has to be single precision!")
    elif src.format.subsampling_w > 0 or src.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Destaircase: subsampled stuff not supported!")
    if not isinstance(ref, vs.VideoNode):
       raise TypeError("Oyster.Destaircase: ref has to be a video clip!")
    elif ref.format.sample_type != vs.FLOAT or ref.format.bits_per_sample < 32:
       raise TypeError("Oyster.Destaircase: the sample type of ref has to be single precision!")
    elif ref.format.subsampling_w > 0 or ref.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Destaircase: subsampled stuff not supported!")
    if not isinstance(radius, int):
       raise TypeError("Oyster.Destaircase: radius has to be an integer!")
    elif radius < 1:
       raise RuntimeError("Oyster.Destaircase: radius has to be greater than 0!")
    if not isinstance(mse, list):
       raise TypeError("Oyster.Destaircase: mse parameter has to be an array!")
    elif len(mse) != 2:
       raise RuntimeError("Oyster.Destaircase: mse parameter has to contain 2 elements exactly!")
    for i in range(2):
        if not isinstance(mse[i], float) and not isinstance(mse[i], int) and mse[i] is not None:
           raise TypeError("Oyster.Destaircase: elements in mse must be real numbers or None!")
    if not isinstance(thr, float) and not isinstance(thr, int):
       raise TypeError("Oyster.Destaircase: thr has to be a real number!")
    elif thr < 0 or thr > 1:
       raise RuntimeError("Oyster.Destaircase: thr has to fall in [0, 1]!")
    if not isinstance(elast, float) and not isinstance(elast, int):
       raise TypeError("Oyster.Destaircase: elast has to be a real number!")
    elif elast < 0 or elast > thr:
       raise RuntimeError("Oyster.Destaircase: elast has to fall in [0, thr]!")
    if not isinstance(lowpass, list) and lowpass is not None:
       raise TypeError("Oyster.Destaircase: lowpass has to be a list or None!")
    core                       = import core
    rgb                        = False
    mse[0]                     = sigma * 160.0 + 1200.0 if mse[0] is None else mse[0]
    mse[1]                     = sigma * 120.0 + 800.0 if mse[1] is None else mse[1]
    lowpass                    = [0.0,sigma, 0.48,1024.0, 1.0,1024.0] if lowpass is None else lowpass
    matrix                     = None
    colorspace                 = src.format.color_family
    if colorspace == vs.RGB:
       rgb                     = True
       matrix                  = 100
       src                     = core.RGB2OPP(src, 1)
       ref                     = core.RGB2OPP(ref, 1)
    src                        = core.SetFieldBased(src, 0)
    ref                        = core.SetFieldBased(ref, 0)
    clip                       = internal.destaircase(core, src, ref, radius, sigma, \
                                                      mse, hard_thr, block_size, block_step, group_size, bm_range, bm_step, ps_num, ps_range, ps_step, \
                                                      thr, elast, lowpass, matrix)
    clip                       = core.OPP2RGB(clip, 1) if rgb else clip
    del core
    return clip

def Deblocking(src, ref, radius=6, h=6.4, sigma=16.0, \
               mse=[None, None], hard_thr=3.2, block_size=8, block_step=1, group_size=32, bm_range=24, bm_step=1, ps_num=2, ps_range=8, ps_step=1, \
               lowpass=[0.0,0.0, 0.12,1024.0, 1.0,1024.0]):
    if not isinstance(src, vs.VideoNode):
       raise TypeError("Oyster.Deblocking: src has to be a video clip!")
    elif src.format.sample_type != vs.FLOAT or src.format.bits_per_sample < 32:
       raise TypeError("Oyster.Deblocking: the sample type of src has to be single precision!")
    elif src.format.subsampling_w > 0 or src.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Deblocking: subsampled stuff not supported!")
    if not isinstance(ref, vs.VideoNode):
       raise TypeError("Oyster.Deblocking: ref has to be a video clip!")
    elif ref.format.sample_type != vs.FLOAT or ref.format.bits_per_sample < 32:
       raise TypeError("Oyster.Deblocking: the sample type of ref has to be single precision!")
    elif ref.format.subsampling_w > 0 or ref.format.subsampling_h > 0:
       raise RuntimeError("Oyster.Deblocking: subsampled stuff not supported!")
    if not isinstance(radius, int):
       raise TypeError("Oyster.Deblocking: radius has to be an integer!")
    elif radius < 1:
       raise RuntimeError("Oyster.Deblocking: radius has to be greater than 0!")
    if not isinstance(h, float) and not isinstance(h, int):
       raise TypeError("Oyster.Deblocking: h has to be a real number!")
    elif h <= 0:
       raise RuntimeError("Oyster.Deblocking: h has to be greater than 0!")
    if not isinstance(mse, list):
       raise TypeError("Oyster.Deblocking: mse parameter has to be an array!")
    elif len(mse) != 2:
       raise RuntimeError("Oyster.Deblocking: mse parameter has to contain 2 elements exactly!")
    for i in range(2):
        if not isinstance(mse[i], float) and not isinstance(mse[i], int) and mse[i] is not None:
           raise TypeError("Oyster.Deblocking: elements in mse must be real numbers or None!")
    if not isinstance(lowpass, list):
       raise TypeError("Oyster.Deblocking: lowpass has to be a list!")
    core                       = import core
    rgb                        = False
    color                      = True
    mse[0]                     = sigma * 160.0 + 1200.0 if mse[0] is None else mse[0]
    mse[1]                     = sigma * 120.0 + 800.0 if mse[1] is None else mse[1]
    matrix                     = None
    colorspace                 = src.format.color_family
    if colorspace == vs.RGB:
       rgb                     = True
       matrix                  = 100
       src                     = core.RGB2OPP(src, 1)
       ref                     = core.RGB2OPP(ref, 1)
    if colorspace == vs.GRAY:
       color                   = False
    src                        = core.SetFieldBased(src, 0)
    ref                        = core.SetFieldBased(ref, 0)
    clip                       = internal.deblocking(core, src, ref, radius, h, sigma, \
                                                     mse, hard_thr, block_size, block_step, group_size, bm_range, bm_step, ps_num, ps_range, ps_step, \
                                                     lowpass, color, matrix)
    clip                       = core.OPP2RGB(clip, 1) if rgb else clip
    del core
    return clip
__________________
"To bypass shortcuts and find suffering...is called QUALity" (Die toten Augen von Friedrichshain)
"Data reduction ? Yep, Sir. We're working on that issue. Synce invntoin uf lingöage..."

Last edited by Emulgator; 23rd January 2023 at 10:43.
Emulgator is offline   Reply With Quote
Old 23rd January 2023, 10:46   #92  |  Link
ChaosKing
Registered User
 
Join Date: Dec 2005
Location: Germany
Posts: 1,744
First vs.core() is old syntax. Now it's simply vs.core (you still need to have import vapoursynth as vs)

Never saw something like this core = import core (no a python pro here) but I think you can also replace it with vs.core.

Oh in case you didn't know, scripts/plugins by feisty2 are very very very slow
__________________
AVSRepoGUI // VSRepoGUI - Package Manager for AviSynth // VapourSynth
VapourSynth Portable FATPACK || VapourSynth Database || https://github.com/avisynth-repository

Last edited by ChaosKing; 23rd January 2023 at 10:50.
ChaosKing is offline   Reply With Quote
Old 23rd January 2023, 10:53   #93  |  Link
Emulgator
Big Bit Savings Now !
 
Emulgator's Avatar
 
Join Date: Feb 2007
Location: close to the wall
Posts: 1,266
Thanks, that helped ! Getting futher.
Now next comes up:

2023-01-23 10:50:22.589
Failed to evaluate the script:
Python exception: name 'vs' is not defined

Traceback (most recent call last):
File "src\cython\vapoursynth.pyx", line 2832, in vapoursynth._vpy_evaluate
File "src\cython\vapoursynth.pyx", line 2833, in vapoursynth._vpy_evaluate
File "C:/_SOFT/! Vapoursynth/VapourSynth64PortableFatpack_2021_10_16/userscripts/Haley A.vpy", line 49, in
ref_s = Oyster.Basic(clip, short_time=True)
File "C:\_SOFT\! Vapoursynth\VapourSynth64PortableFatpack_2021_10_16\Scripts\Oyster.py", line 233, in Basic
if not isinstance(src, vs.VideoNode):
NameError: name 'vs' is not defined

P.S. Slooow: Yes, I heard.. Hoping for some newer HW to deliver someting like >0,05fps ;-)

At the same time trying to get Dogway's Oyster rewrite for AviSynth+ 3.7.3 to run, unsuccessful so far as well..
__________________
"To bypass shortcuts and find suffering...is called QUALity" (Die toten Augen von Friedrichshain)
"Data reduction ? Yep, Sir. We're working on that issue. Synce invntoin uf lingöage..."

Last edited by Emulgator; 23rd January 2023 at 11:26.
Emulgator is offline   Reply With Quote
Old 24th January 2023, 11:03   #94  |  Link
ChaosKing
Registered User
 
Join Date: Dec 2005
Location: Germany
Posts: 1,744
I got Oyster to work.
I think you are using an older version of Oyster. Download the newest version from his github page https://github.com/IFeelBloated/Oyster
It also needs the latest version (r10) of mvtools-sf https://github.com/IFeelBloated/vapoursynth-mvtools-sf

Delete libmvtools_sf_em64t.dll (it's the old one. Otherwise there will be a namespace conflict and only one of the plugins will be loaded)


All you have to fix is line 14 in Oyster.py
Code:
self.core            = vs.get_core()
to
self.core            = vs.core
Code:
import vapoursynth as vs
import Oyster

core = vs.core

clip = core.lsmas.LWLibavSource(source=r"F:\video.mkv")

clip = core.fmtc.bitdepth( clip, bits = 32 )
clip = core.fmtc.resample( clip, css = "444" )

ref_s = Oyster.Basic(clip, short_time=True)
clip = Oyster.Deringing(clip, ref_s, block_step=2)

clip.set_output()
This took about a minute to display one frame (720x480) in vsedit

p.s. If you make changes to a python script (Oyster.py) make sure to restart vsedit!
__________________
AVSRepoGUI // VSRepoGUI - Package Manager for AviSynth // VapourSynth
VapourSynth Portable FATPACK || VapourSynth Database || https://github.com/avisynth-repository

Last edited by ChaosKing; 24th January 2023 at 11:10.
ChaosKing is offline   Reply With Quote
Old 24th January 2023, 11:05   #95  |  Link
kedautinh12
Registered User
 
Join Date: Jan 2018
Posts: 1,636
Dogway's Oyster don't work cause W.I.P
kedautinh12 is online now   Reply With Quote
Old 25th January 2023, 03:02   #96  |  Link
Emulgator
Big Bit Savings Now !
 
Emulgator's Avatar
 
Join Date: Feb 2007
Location: close to the wall
Posts: 1,266
Chaosking, you are a hero. Indeed r10-prerelease was needed.
Many thanks ! This is with your fatpack 2021 10 16:
Script loaded, no fault comments, i9-11900K CPU breathing hot air @ 100%,
waiting for the first frame to emerge...
10...48...128GB RAM used up, then 69GB...then 29GB, then 14GB
And here it is ! 1 frame deringing only like 3 minutes...

Lets see if I can move this to my R61 portable.
__________________
"To bypass shortcuts and find suffering...is called QUALity" (Die toten Augen von Friedrichshain)
"Data reduction ? Yep, Sir. We're working on that issue. Synce invntoin uf lingöage..."

Last edited by Emulgator; 25th January 2023 at 03:09.
Emulgator is offline   Reply With Quote
Old 25th January 2023, 21:06   #97  |  Link
Selur
Registered User
 
Selur's Avatar
 
Join Date: Oct 2001
Location: Germany
Posts: 6,904
Small question seeing:
Code:
          self.core            = vs.core()
          self.MSuper          = self.core.mvsf.Super
          self.MAnalyze        = self.core.mvsf.Analyze
          self.MRecalculate    = self.core.mvsf.Recalculate
          self.MDegrain        = self.core.mvsf.Degrain
          self.RGB2OPP         = self.core.bm3d.RGB2OPP
          self.OPP2RGB         = self.core.bm3d.OPP2RGB
          self.BMBasic         = self.core.bm3d.VBasic
          self.BMFinal         = self.core.bm3d.VFinal
          self.Aggregate       = self.core.bm3d.VAggregate
          self.DFTTest         = self.core.dfttest.DFTTest
          self.KNLMeansCL      = self.core.knlm.KNLMeansCL
          self.NNEDI           = self.core.nnedi3.nnedi3
          self.Resample        = self.core.fmtc.resample
          self.Expr            = self.core.std.Expr
          self.MakeDiff        = self.core.std.MakeDiff
          self.MergeDiff       = self.core.std.MergeDiff
          self.Crop            = self.core.std.CropRel
          self.CropAbs         = self.core.std.CropAbs
          self.Transpose       = self.core.std.Transpose
          self.BlankClip       = self.core.std.BlankClip
          self.AddBorders      = self.core.std.AddBorders
          self.StackHorizontal = self.core.std.StackHorizontal
          self.StackVertical   = self.core.std.StackVertical
          self.MaskedMerge     = self.core.std.MaskedMerge
          self.ShufflePlanes   = self.core.std.ShufflePlanes
          self.SetFieldBased   = self.core.std.SetFieldBased
Woud it speed things up to use:
BM3DCUDA instead of BM3D ?
NNEDI3CL instead of NNEDI3? (or at least znedi3?)
__________________
Hybrid here in the forum, homepage
Selur is offline   Reply With Quote
Old 26th January 2023, 00:18   #98  |  Link
ChaosKing
Registered User
 
Join Date: Dec 2005
Location: Germany
Posts: 1,744
You can replace nnedi3 with:
Code:
self.NNEDI           = self.core.nnedi3cl.NNEDI3CL
I removed RGB2OPP() and replaced bm3d with
Code:
vs.core.bm3dcuda_rtc.BM3Dv2(dif, cleansed, radius=radius, sigma=sigma, \
                                              block_step=block_step, bm_range=bm_range, \
                                              ps_num=ps_num, ps_range=ps_range)
I had to remove some parameters since they are not present in bm3dcuda. Not sure if I replaced it correctly, but at least it looks very similar (not much tested)

For this example it is twice as fast for me.
Code:
ref_s = Oyster.Basic(clip, short_time=True)
clip = Oyster.Deringing(clip, ref_s, block_step=2)
With radius=2 it is actually usable now with ~15sec for a single frame
Code:
import Oystergpu as Oy
ref_s = Oy.Basic(clip, short_time=True, radius=2)
clip = Oy.Deringing(clip, ref_s, block_step=2, radius=2)
Download here
https://gist.github.com/theChaosCode...cb54994eacf9ca

EDIT
Just found this https://github.com/AmusementClub/vs-nlm-cuda

EDIT2
Replaced knlm with nlm_cuda
__________________
AVSRepoGUI // VSRepoGUI - Package Manager for AviSynth // VapourSynth
VapourSynth Portable FATPACK || VapourSynth Database || https://github.com/avisynth-repository

Last edited by ChaosKing; 26th January 2023 at 00:34.
ChaosKing is offline   Reply With Quote
Old 26th January 2023, 09:00   #99  |  Link
Dogway
Registered User
 
Join Date: Nov 2009
Posts: 2,097
Quote:
Originally Posted by kedautinh12 View Post
Dogway's Oyster don't work cause W.I.P
I've been following the thread and decided to finish the filter for AVS+
The main problem with Deringing is the use of NLMeans, which loops KNLMeansCL several times, maybe not in VS but in AVS that causes an out of resources error when used more than twice (1 loop in 2 dif calls), and I have 32Gb of RAM.

Aside of that for BM3D I found that radius doesn't make a big difference, and blockstep=1 is only a slightly bit sharper than with 2, but at the expense of magnitudes times slower.

The main trick I did to speed it up was to remake FreqMerge() using GuidedBlur() (at half res) instead of DFTTest which is known to be slow.

Here are my tests using oyster_Deblocking, and some further custom filtering to recover back some structure.

src

blockstep = 1..........................................................blockstep = 2
_______
Structure sharpen......................................................Recover smearing
_______
Code:
ConverttoYUV444().ConvertBits(32)
clp   = last
sup   = oyster_Super(clp)
ref_s = oyster_Basic(clp, sup, short_time=true)
dbl   = oyster_Deblocking (clp, radius=4, ref_s, block_step=1)

dbl

# De-smearing
ex_lfr(clp,LFR=130)
# Re-structure
ex_unsharp(0.4, Fc=400, th=0, safe=true)

# Recover some saturation
ex_vibrance(1.15)
__________________
i7-4790K@Stock::GTX 1070] AviSynth+ filters and mods on GitHub + Discussion thread
Dogway is offline   Reply With Quote
Old 26th January 2023, 10:38   #100  |  Link
ChaosKing
Registered User
 
Join Date: Dec 2005
Location: Germany
Posts: 1,744
Quote:
Originally Posted by Dogway View Post
Aside of that for BM3D I found that radius doesn't make a big difference, and blockstep=1 is only a slightly bit sharper than with 2, but at the expense of magnitudes times slower.

ex_vibrance(1.15)[/CODE]
In the deringing function bm3d basic is called, then It's "refined" with loop(None, ref, src, 4), so called x4 again and finally bm3d final.
So bm3d is called at least 6 times. Combine this with radius=6 und you know why it takes 3 minutes to process a single frame. feisty2 makes zero compromises


Missed the dfttest part: dfttest could be replaced with neo_dfttest or https://github.com/AmusementClub/vs-dfttest2

EDIT: Oh you're right NLMeans is called 4 times, not bm3d. Well never code when tired xD
__________________
AVSRepoGUI // VSRepoGUI - Package Manager for AviSynth // VapourSynth
VapourSynth Portable FATPACK || VapourSynth Database || https://github.com/avisynth-repository

Last edited by ChaosKing; 26th January 2023 at 11:23.
ChaosKing is offline   Reply With Quote
Reply

Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT +1. The time now is 13:19.


Powered by vBulletin® Version 3.8.11
Copyright ©2000 - 2023, vBulletin Solutions Inc.