@@ -7,6 +7,7 @@ Add black or colored borders, increasing frame size. This has several common use
77* Adjust the `aspect ratio `_ (make a 4:3 clip into 16:9 without stretching)
88* :doc: `Splice <splice >` a smaller resolution clip to a larger one without resizing
99* Together with :doc: `Crop <crop >`, shift a clip horizontally or vertically – see below.
10+ * Optionally filters the transient areas. (3.7.4-)
1011
1112See also: :doc: `letterbox `, which adds borders without changing frame size.
1213
@@ -16,7 +17,8 @@ Syntax and Parameters
1617
1718::
1819
19- AddBorders (clip clip, int left, int top, int right, int bottom, int "color", int "color_yuv")
20+ AddBorders (clip clip, int left, int top, int right, int bottom, int "color", int "color_yuv",
21+ string "resample", float "param1", float "param2", float "param3", int "r" )
2022
2123.. describe :: clip
2224
@@ -48,11 +50,82 @@ Syntax and Parameters
4850
4951.. describe :: color_yuv
5052
51- Specifies the border color using YUV values. Input clip must be YUV;
52- otherwise an error is raised. See the :ref: `YUV colors <yuv-colors >` for
53- more information.
54-
55-
53+ | Specifies the border color using YUV values. Input clip must be YUV;
54+ otherwise an error is raised.
55+ | Similar to ``color_yuv`` in :doc:`BlankClip <blankclip>`
56+
57+ .. describe :: resample
58+
59+ string resample = "gauss"
60+
61+ When `r ` radius is not zero, then determines which resampler is used in the transient filtering.
62+ All AviSynth :doc: `resizers <resize >` are allowed:
63+ ("point", "bilinear", "bicubic", "lanczos", "lanczos4", "blackman", "spline16", "spline36", "spline64",
64+ "gauss" and "sinc", "sinpow", "sinclin2" and "userdefined2").
65+
66+ Default is "gauss".
67+
68+ .. describe :: param1, param2, param3
69+
70+ These 'float' type parameters can be the additional parameters for the
71+ resampler. Some resizer algorithms would need and can be fine tuned with up to 3 parameters.
72+ Their default values depend on the selected chromaresample resizer kernel.
73+
74+ default (when "gauss"):
75+
76+ * param1 (p), param2(b), param3(s): p=10, b=2.71828182, s=0
77+
78+ for other resizer algoritms see in :doc: `resizers <resize >`.
79+
80+ .. describe :: r
81+
82+ int r = 0
83+
84+ The radius of the transient treatment in pixels. The value is meant as +/- around the border line.
85+
86+ When `r ` radius is not zero, transient filtering occurs.
87+ Even ``r=1 `` is giving sufficient protection for some next processing stages.
88+
89+ Why: by filtering the transient areas (boundary of the new borders), we can prevent
90+ artifacts e.g. ringing after a subsequent upscale.
91+
92+ This is how it works:
93+
94+ Eight crops are taken from around the transient areas:
95+
96+ - left and right rectangles, which cover +/- 10 (but at least ``r ``) pixels
97+ horizontally around the new border line.
98+ - top and bottom rectangles, which cover +/- 10 (but at least ``r ``) pixels
99+ vertically around the new border line.
100+ - four corners, top left, top right, bottom left, bottom right, dimension rules
101+ as seen above.
102+
103+ These eight rectangles are "resized", using the given resizer in convolution mode.
104+ No dimension is changed, just we'll get a blurred area.
105+
106+ Since 3.7.4 resizers can accept a ``force `` parameter, so we use it.
107+
108+ - left and right parts need only horizontal treatment.
109+ - top and bottom parts need only vertical treatment.
110+ - corners get both H and V processing.
111+
112+ Then, from this larger area only a central ``r `` (radius)-wide rectangle is copied over the transient area.
113+
114+ The left and right side will be overwritten by a ``r * original_height `` sized part.
115+ At the top and bottom an ``original_width * r `` sized rectangle will be copied back.
116+ And a ``r * r `` rectangle is copied over the corners.
117+
118+ The exact dimensions can be a bit different, e.g. if ``r `` is larger than the actually added left border.
119+ Then the radius is reduced accordingly.
120+
121+ The ``r `` radius is automatically adjusted with the video format subsampling requirements.
122+ AddBorders won't give error if e.g. for a YV12 ``r=1 `` is given: due to the chroma subampling it will be
123+ automatically promoted to 2.
124+
125+ Other notes:
126+
127+ This copy-paste of the up-to eight area is using a new :doc: `MultiOverlay <multioverlay >` filter.
128+
56129Examples
57130--------
58131
@@ -86,13 +159,75 @@ Examples
86159 on color format.
87160 * You can shift in sub-pixel increments with :doc: `Resize <resize >`.
88161
162+ * AddBorders with filtering
163+
164+ ::
165+
166+ # Add 20 black pixels around the clip, filters (blurs) 1 pixel with the default "gauss" method
167+ AddBorders(20, 20, 20, 20, r=1)
168+
169+ * AddBorders filtering test script
170+ ::
171+
172+ Function AddBordersHF(clip c, int left, int right, int flt_rad)
173+ {
174+ unflt=AddBorders(c, left, 0, right, 0)
175+ flt=GaussResize(unflt, unflt.width, unflt.height, p=10, b=2.71828, s=0, force=1)
176+ uf_internal=Crop(c, flt_rad, 0, c.width-flt_rad*2, c.height)
177+ return Overlay(flt, uf_internal, x=left+flt_rad, y=0)
178+ }
179+
180+ Function AddBordersVF(clip c, int top, int bottom, int flt_rad)
181+ {
182+ unflt=AddBorders(c, 0, top, 0, bottom)
183+ flt=GaussResize(unflt, unflt.width, unflt.height, p=10, b=2.71828, s=0, force=2)
184+ uf_internal=Crop(c, 0, flt_rad, 0, c.height - flt_rad*2)
185+ return Overlay(flt, uf_internal, x=0, y=top+flt_rad)
186+ }
187+
188+ Function Diff(clip src1, clip src2)
189+ {
190+ return Subtract(src1.ConvertBits(8),src2.ConvertBits(8)).Levels(120, 1, 255-120, 0, 255, coring=false)
191+ }
192+
193+ ColorBarsHD(2000,2000)
194+ UserDefined2Resize(width/10, height/10)
195+
196+ # filtering area, means +/- around the border boundaries
197+ r1=2
198+ r2=2
199+
200+ left=20
201+ top=20
202+ right=20
203+ bottom=20
204+
205+ std=AddBorders(left, top, right, bottom)
206+ a=last
207+ a=AddBordersHF(a, left, right, r1)
208+ a=AddBordersVF(a, top, bottom, r1).SubTitle("Scriptbased", align=5)
209+
210+ b=last
211+ b=AddBorders(b, left, top, right, bottom, param1=10, param2=2.71828, param3=0, r=r2).SubTitle("AVS 3.7.4", align=5)
212+
213+ d1 = Diff(a,b)
214+ d2 = Diff(std,a)
215+ d3 = Diff(std,b)
216+
217+ StackHorizontal(StackVertical(std, a, b), Stackvertical(d1, d2, d3))
218+
219+ LanczosResize(width*4, height*2, taps=16)
220+
221+
89222
90223Changelog
91224----------
92225
93226+-----------------+------------------------------------------------------------------+
94227| Version | Changes |
95228+=================+==================================================================+
229+ | 3.7.4 | Add filtering. resample, param1, param2, param3, r parameters |
230+ +-----------------+------------------------------------------------------------------+
96231| AviSynth+ 3.6.2 | Fix: AddBorders did not pass frame properties |
97232+-----------------+------------------------------------------------------------------+
98233| AviSynth+ 3.5.0 | New ``color_yuv `` parameter like in BlankClip |
0 commit comments