AviSynth 模拟Mplayer的遮标滤镜(Delogo)

       MedacoderNT 转码系统最近加入遮标(Delogo)功能,遮标功能是为了去掉原有影片上的水印等标志,相信有不少人有这样的转码需求。NT转码系统的前端解码采用了Mencoder/Mplayer及AviSynth等,来解码不同格式的影片,由于遮标滤镜要放到其他滤镜之前,所以这个滤镜的实现要放到解码器里,Mencoder/Mplayer自带了一个简单的遮标滤镜,其原理是用水印周围的像素颜色插值模糊来替换水印,遮标效果还凑合。

      Mencoder解码时直接用自带滤镜即可,而AviSynth就需要模拟一个类似Mencoder的遮标,由于对AviSynth不熟,在网上搜索良久才找到一段代码,修改调试后,达到了Mencoder类似的效果(在搜索时也发现AviSynth有几个Delogo滤镜,但都需要提供用于遮标的图片,比较麻烦,跟Mencoder不统一,遂不予采用),现记录于此:

 

      function Delogo(clip c, int x, int y, int width, int height) { top = c.crop(x, y-2, width, 2) bottom = c.crop(x, y+height, width, 2) mask = StackVertical(top,bottom).Blur(0.5,1.38).BilinearResize(width,height) c = c.Layer(mask, "add", 255, x, y) return c }

 

      该代码解释:参数c是指滤镜应用的电影片段,后面几个参数指出了源水印的位置及大小,主要功能就是用水印周围的像素颜色构建出一个模糊的色块来遮住源水印。

 

      进一步考虑,有的影片的水印是动态变化的,比如前10分钟水印在左上角,接下来10分钟在右上角。此时就需要给遮标滤镜增加时间间隔控制。对于Mencoder/Mplayer,可以通过patch代码,增加时间控制即可,而AviSynth就有点麻烦了,由于滤镜的执行在不同的时间段里执行的位置不同,需要通过运行时函数及ConditionalReader来达到这个要求。通过摸索,下面这段代码可以工作。

DirectShowSource("G:/resource/video/Godsend_720.wmv") ConvertToRGB32() ScriptClip("Delogo(last, delogox, delogoy, delogow,delogoh)") ConditionalReader("x.txt", "delogox", false) ConditionalReader("y.txt", "delogoy", false) ConditionalReader("w.txt", "delogow", false) ConditionalReader("h.txt", "delogoh", false) ConvertToYV12()

 

      这段代码通过ConditionalReader读取水印的位置参数的配置文件,位置参数是随时间间隔的不同而变化的,这样就达到遮住动态水印的效果。代码中之所以用ScriptClip函数来执行遮标滤镜,因为该函数对每帧执行时都会重新取得各参数的值,参数随时间的变化才可以起作用。参数配置文件 "x.txt"示例如下,其他参数与此类似。

 

Type int Default 0 R 100 400 260 R 401 1000 320 R 1001 6000 400

 

    该配置文件指定了100帧~400帧 时x的值为260,及其他帧间隔的值。 外面传进的参数是时间间隔,这里需要帧间隔,可通过影片帧率来转换。

 

你可能感兴趣的:(音视频处理)