En ^ Ru
AVS by UnConeD
61119
The Superscope
http://forums.winamp.com/showthread.php?threadid=61119 SuperScope
- основной рендерер, который также точки или линии между этими точками. Вы
должны написать код, который, в конечном счете, вычислит координаты x, y для
каждой точки, которая будет нарисована. X располагается от -1 до 1, и это
горизонтальная координата, Y в диапазоне от -1 до 1, и это вертикальная
координата.
Примеры:
(0,0) - центр экрана
AVS
(-1,-1) - верхний левый угол
(0,1)
- центр нижней границы основания
(0.8,0.9) - точка около нижнего правого
угла
Переменная n используется, чтобы установить число точек, которые
вычисляются на каждом фрейме. Большое значение n означает медленный пресет, так
что не используйте огромные числа, если в этом нет особой необходимости.
Переменная i отличается для каждой точки, и является процентом, который говорит,
какую точку вы рисуете.
Например:
- первая точка: i=0 (0%)
- последняя точка: i=1 (100%)
-
50-я точка superscope из 150 точек: i=0.33333... (33%)
Переменная v также отличается для каждой точки, и содержит текущую звуковую
величину для этой точки (или oscilloscope, или spectrum данные, в зависимости от
вашего выбора). Если Вы кликните кнопку "help", то сможете увидеть все функции,
которые можно использовать. Экспериментируйте с ними, если Вы не знаете точно,
что они делают.
Теперь сделаем базовую суперобласть [UnConeD - Basic SuperScope.avs]:
Init: n=300; t=0; tpi=acos(-1)*2;
Beat: t=t+rand(200)/50;
Frame:
t=t-0.05; rad=sin(t)/2+0.5;
Point: x=cos(i*tpi)*(rad+v/5);
y=sin(i*tpi)*(rad+v/5);
Поначалу это может показаться очень сложным, но давайте посмотрим на всё
это шаг за шагом:
Init - Сначала мы устанавливаем n в 300, чтобы superscope рисовал 300
различных точек. Мы также устанавливаем переменную t в 0. Затем мы устанавливаем
переменную tpi как арккосинус -1 в квадрате. Если Вы знаете математику, то это
означает 2Pi (6.28). Не беспокойтесь, это лишь уловка, чтобы Вам не пришлось
самостоятельно набирать число pi, являющееся очень полезным числом.
On Beat - Переменная t на каждом бите будет увеличена на случайное целое
число из диапазона 0-200, разделённое на 50. Так, чтобы получить случайное
десятичное число от 0.00 до 4.00.
Per Frame - Каждый фрейм мы немного уменьшаем величину t. Мы также
вычисляем радиус (rad), беря синус t и масштабируя его в бит (scaling it a bit).
Если Вы знаете, что синус - это волна (repetive wave-shape), и что t уменьшается
понемногу на каждом фрейме, то Вы поймете, что величина радиуса будет медленно
пульсировать от 0 до 1 и обратно, кроме каждого бита, когда t резко изменится и
величина радиуса подскочит.
Per Point - Здесь мы делаем фактические точки. В нашем уравнении x и y -
координаты точки на круге. Круг имеет радиус rad плюс текущая величина
sound-value, разделенная на 5. Чтобы удостовериться, что мы проходим полный
круг, умножаем i (диапазон 0-1) на 2pi, и таким образом получаем диапазон
0-6.28.
Теперь Вы имеете superscope, которые рисует спектр или круг осциллографа с
прыгающим радиусом. Другой аспект супервозможностей - цвет. Вы или можете
использовать скучный выбор цвета внизу (color-selector), или написать
собственные уравнения для переменных red, green и blue. Они находятся в
диапазоне 0-1 и содержат величину для каждого цвета.
Давайте приправлять наши супервозможности, добавляя уравнения к "on
beat":
cr=rand(100)/100; cg=rand(100)/100; cb=rand(100)/100;
И в "per
frame":
red=cr; green=cg; blue=cb;
Что происходит здесь? Каждый такт (beat) мы устанавливаем cr, cg и cb в
случайную величину из диапазона 0-1. Каждый фрейм (frame) назначаем эту тройку
на red, green и blue. Мы не могли назначить их непосредственно "on beat"? Нет.
AVS перезагружает их на каждом фрейме, с цветом, определенным в
color-selector.
Таким образом, Вы имеете ваш собственный, изменяющий цвет, пресет
superscope. Он выглядит лучше, если удалить t-changing on beat и комбинировать с
фильтром Trans / Water [UnConeD - Basic SuperScope Water.avs].
61847
Тригонометрия:
Возьмём круг с радиусом 1, так называемый "unit-circle", и выберем
случайную точку на этом круге. Мы можем уникально описать эту точку углом между
радиусом и осью X, например 90 градусов. Однако математически радианы
используются вместо градусов. Не вдаваясь в теорию, нужно только помнить, что
360 градусов = 2*PI. Так, предположим, что мы имеем точку, лежащую в N радианах
на нашем единичном круге. Тогда координата X будет даваться cos(N), а Y
координата sin(N). Это определение косинуса и синуса.
Если хотите рисовать круг, возьмите каждую величину A от 0 до 2*PI, и
нарисуйте график (cos(A),sin(A)). Соотношение синуса и косинуса довольно легко
увидеть на прямоугольном треугольнике. Нарисуйте круг, используя начало (0,0)
как центр. Возьмите точку на этом круге, соедините точку с центром,
спроектируйте точку на ось X. Появляется прямоугольный треугольник.
Sin и Cos также имеют другое использование. Поскольку они - координаты
точек, лежащих на круге, они являются периодическими. Точка, перемещающаяся по
кругу, в конечном счете достигнет своего отправного пункта. Это означает, что
эти величины повторяются через некоторое время (2*PI, если быть точным). Таким
образом, вы можете использовать синус и косинус как источник для
пульсирующих/волновых scope или movement.
Тангенс (tan) определяется как sin разделенный на cos. Он ранжируется от
минус бесконечности до плюс бесконечности в диапазоне от -PI/2 до PI/2, и
повторяется непосредственно каждое PI. Обычно Вы не будете нуждаться в
математических использованиях этих функций, но будете использовать их
характеристики, например повторяемость.
64660
Grid size используется всегда, независимо от полярных или прямоугольных
координат. Идея в том, что dynamic movement является очень тяжелым эффектом.
Пересчитывать каждую пиксел-координату на каждом фрейме было бы невозможно, и
именно поэтому экран разделен на сетку. AVS вычисляет позицию для каждого
пересечения на сетке, и использует интерполяцию (усреднение от одной величины к
другой), чтобы достигнуть гладкого эффекта.
Обычно низкого grid size бывает достаточно, но иногда Вы будете хотеть
установить его повыше. Удостоверьтесь, что Вы не делаете его излишне большим,
потому что большая сетка - это медленный пресет. Вы должны также помнить, что
horizontal gridsize и vertical gridsize могут не совпадать. Gridsizes 2x20 или
40x3 вполне приемлемы.
Что касается прямоугольных координат, то это означает использовать x,y
координаты (декартовские, cartesian), вместо d,r (полярные, polar). В полярных
координатах, точка определена её расстоянием до центра "d" и углом между
вертикальной линией и линией, соединяющей точку с центром (отметьте, что AVS
помещает 0 rotation вертикально, вместо горизонтально, как это обычно делается).
Polar coordinate-movements имеют тенденцию производить более круглые формы, чем
horizontal/vertical movements. Прямоугольные координаты - хороший способ сделать
улучшенные эффекты.
70899
> geozop
Обычно находил, что при использовании пресета movement, он не перемещается
достаточно быстро, вращение на достаточно приличном расстоянии, или сталкивался
с чем-то другим, что меня не устраивает, даже при том, что всё оно было порой
весьма близко. К сожалению, мы не видим математических уравнений, которые
заключены в пресетах. Некоторые уравнения движения достаточно легко выяснить
(типа shift rotate left), но другие (как blocky partial out) от меня ускользают.
Предполагаю, что и другие AVS-конструкторы имеют подобные проблемы. Таким
образом, думаю, что тема перепроектирования этих движений может быть полезна
всем.
Некоторые из Trans - Movement, которые я уже "расшифровал" (user
defined):
big swirl out (большой
водоворот):
d=d-sin(d)/25;
r=r-0.2*(d-0.5);
medium swirl (средний
водоворот):
d=d+0.001;
r=r-0.025*cos(d*16);
sunburster (солнечный взрыв):
[нахожу, что работает лучше чем
стандартный пресет, поскольку имеет up-and-left движение, в дополнение к
sunbursting]
d=d-(sin(d)*0.1*abs(sin(r*18)));
r=r+0.004;
swirling around both ways at once (одновременное кружение):
[в четыре
раза больше чем в medium swirl, с бит смещением (bit of an
offset)]
d=d+0.001;
r=r-0.1*cos(d*16+0.75);
bubbling outward (пузырение наружу):
[такой же шаблон, как с sunburster,
но движение центра не выглядело достаточно хорошо без r
movement]
d=d-0.025*pow(1.33*sin(d*2*1.57)-0.25,4);
r=r-log
(0.01+d)/100;
5 pointed distro:
[сходство хорошее, но не настолько точно, как я
хотелось бы]
d=d-0.1*sin(d)*abs(sin(r*2.5+1.57));
r=r+0.005;
Думаю, что blocky partial out можно сделать, используя rect coordinates...
Slight fuzzify, вероятно, можно сделать как пресет swirl to center, за
исключением того, что swirls будут иметь ширину только несколько пикселов, а не
одну треть экрана.
> UnConeD
tunneling (туннелирование):
[Это приблизительное туннельное движение.
Реальный "tunnel", кажется, имеет точку вращения немного слева от центра, но за
исключением этого очень похоже.]
df=d-.16; df=if(below(df, 0.02),0.02,
df);
d=d-sqr(df)*.23; r=r+0.035;
Ключевые момент для расшифровки движений заключается в создании пресета,
который будет содержать:
- Effect List (Input: ignore / Output: replace)
Simple ->
Oscilloscope Dots
Movement (Оригинал)
- Effect List (Input: ignore
/ Output: subtractive blend 1)
Simple -> Oscilloscope
Dots
Movement (Ваше собственное)
Теперь Вы будете видеть различие между этими двумя движениями. Чем ярче
картинка, тем хуже Вы сделали. Также Вы должны видеть ваше движение как "черный
слой" над оригиналом.
> Montana
tunneling movement:
d=sin(d); r=0.05+r;
> UnConeD
Я нашёл своё решение экспериментально. Вы нашли более короткий, хороший
вариант. Если сравнить эти два graphs (поставьте формулу в superscope), то
увидете, что мой сильно напоминает волну синуса около 0-1. Проверял ваше решение
с уловкой two-effect-list, и, кажется, что rotation factor немного слишком
высок.
> Montana
Отрегулируйте 0.05 до необходимой
величины.
>
BlurPak2k1
Похожий эффект:
d=sin(d); d=atan(d);
> UnConeD
Думаю, что пока невозможно сделать blocky partial out. AVS не обеспечивает
width/height в movement, таким образом можно заставить его работать только в
одном разрешении. Конечно, можно сделать нечто близкое, но реальная идея в
получении точной копии.
> Montana
blur>> не действительно, d=sin(d) имеет move "tunnel-like"
depth, в то время как d=atan(d) сокращает всю картинку в 2-4 части,
> TasZ69
bleedin':
d=atan(d)*1.05;
r=.01+r;
> Warrior of the
Light
bleedin':
t=cos(d*3.14);
r=r+(0.07*t);
d=d*(0.98+t*0.10);
> StevenRoy
Сделать Blocky Partial Out возможно. Недавно экспериментировал с очень
похожими эффектами в Movement code. Уловка в использовании дополнительных
переменных, чтобы фактически ПОДСЧИТАТЬ пикселы (вместо sw и sh).
Например:
nr=equal(y,
yy); // "New Row" is
0 when y
changes.
nx=nr*((nx+1)*3);
// Either increment or reset nx (from 0 to
3)
ny=(ny+bnot(nr))*3; // Increment
ny (from 0 to 3) when y
changes
yy=y;
// This is how we tell when it changes.
vx=if(nx,vx,x);
// Save X and Y coordinates for each 4x4
square's
vy=if(ny-1,vy,y);
// upper left pixel.
insq=(nx*2) | ((ny-1)*2); // "In square" is 0 if we're in one of the
2x2 squares.
x=if(insq,x,(vx*7)/8); // If we are,
perform the magic!
y=if(insq,y,(vy*7)/8);
Конечно, это всё ещё не в точности как BPO, но это лучшее приближение,
которое я могу придумать сегодня. Эта pixel-counting уловка весьма неочевидна
(особенно для not dynamic Movement). Даже попал в искушение оставить её в
секрете, чтобы использовать в пресете (для компиляции, конечно), и затем поиметь
толпу народа, размышляющего: "Как, чёрт возьми, он сделал
это?"
> jheriko
Movement хорошо подходит для изготовления любой сложности raytraces в
реальном времени (обеспечивает маленькое время подгрузки). Также, существуют
другие изящные уловки, которые Вы можете реализовать с пиксельной точностью,
чего dynamic movement не позволит из-за его ужасного разрешения. См. "Jheriko -
There is no Spoon".
StevenRoy, очень не хочу умалять ваше фантастическое открытие, но почему бы
не использовать sw и sh? Подсчёт пикселов - хорошая идея, но здесь больше работы
(code) при не очевидной выгоде (для меня). И готов держать пари, что кто-то уже
делал подсчёт прежде, так как это весьма тривиально.
Другое хорошее место для подсчёта пикселов находится в Dynamic Movement,
хотя полезность несколько отличается: Вы можете "считать" текущую позицию в
сетке и использовать для access (g) megabuf в любых целях (возможно для создания
более быстрого Whittaker solver).
Перевод: А.Панов.
http://avs.chat.ru
Panow©
En ^ Ru
61119
A superscope is basically a renderer that draws either dots, or the lines
between these dots. You have to write code that, at the end, outputs a set of
x,y coordinates for each point to be drawn. X ranges from -1 to 1 and is the
horizontal coordinate, Y ranges from -1 to 1 and is the vertical coordinate.
Some examples:
(0,0) - the center of the AVS screen
(-1,-1) - the top-left of the AVS
screen
(0,1) - the center of the bottom border of the AVS screen
(0.8,0.9)
- a point near the bottom right
The variable n is used to set the number of points to calculate each frame.
Higher n means slower presets, so don't use huge numbers if it's not
needed.
The variable i is different for each point and is a percentage that tells
you which point you're drawing. For example:
- first point: i=0 (0%)
-
last point: i=1 (100%)
- the 50th point of a 150 point superscope:
i=0.33333... (33%)
The variable v is also different for each point and contains the current
sound value for this point (either oscilloscope- or spectrumdata, depending on
your choice).
If you click the 'help' button, you'll see all the functions you can use.
Experiment with them if you don't know what they do exactly.
So now we'll make a basic superscope:
Init:
n=300;t=0;tpi=acos(-1)*2;
Beat: t=t+rand(200)/50
Frame:
t=t-0.05;rad=sin(t)/2+0.5
Point:
x=cos(i*tpi)*(rad+v/5);y=sin(i*tpi)*(rad+v/5)
This will seem very complex at first, but let's look at it step by
step:
Init - First we set n to 300, so that the superscope draws 300 different
points. We also set the variable t to 0. Then, we set the variable tpi to twice
the arc-cosine of -1. If you do the math, that means 2 times Pi (6.28....).
Don't worry, it's just a trick to prevent you from having to type the number pi
yourself, which is a useful number.
On Beat - Every beat, the variable t will be increased by a random integer
number from 0-200, divided by 50. So that means a random decimal number from
0.00 to 4.00.
Per Frame - Every frame we decrease the t value slightly. We also calculate
rad by taking the sine of t and scaling it a bit. If you know that a sine is a
repetive wave-shape and that t is decreased slightly each frame, then you'll
understand that the rad value will slowly pulse from 0 to 1 and back, except
every beat. Then t gets modified drastically and the rad value jumps.
Per Point - Here we do the actual points. In our equation x and y are
coordinates of a point on a circle. The circle has radius rad plus the current
sound-value divided by 5. To make sure we traverse a full circle, we multiply i
(range 0-1) with 2 times pi, so we get a range of 0-6.28...
Now you have a superscope that draws a spectrum or oscilloscope circle with
a jumpy radius.
Another aspect of the superscope is colour. You can either use the (boring)
color selector at the bottom, or you can write your own equations for the
variables red, green and blue. They range from 0-1 and contain the value for
their color. Let's spice up our superscope by adding this to the "on beat"
equation:
cr=rand(100)/100;cg=rand(100)/100;cb=rand(100)/100;
And this to "per frame":
red=cr;green=cg;blue=cb;
What's going on here? Every beat we set cr, cg and cb to a random value in
the range 0-1. Every frame, we assign these three to red, green and blue.
Couldn't we just assign them directly 'on beat'? Nope... AVS resets them every
frame with the color defined by the color-selector at the bottom.
So there you have your own groovy, color-changing superscope. It looks neat
if you remove the t-changing on beat and combine it with a Trans / Water
filter.
61847
Trigonometry
Given a circle with radius 1 (the so called 'unit-circle'). We take a
random point on this circle. We can describe this point uniquely by the angle of
the radius through this point and the X-axis, for example 90?, 140?, ...
Mathematically however, radians are used instead of degrees. Without going into
much theory, you should just remember that 360? = 2*PI. So suppose we have a
point lying at N radians on our unit circle. Then the X coordinate will be given
by cos(N), and the Y coordinate by sin(N). That's the definition of cosine and
sine.
So if you want to draw a circle, take every value A from 0 to 2*PI, and
plot the points (cos(A), sin(A)). Easy.
The relationship of sine and cosing
with right-angled triangles is pretty easy to see. Draw a circle using the
origin (0,0) as center. Take a point on this circle, connect the point with the
center, project the point on the X axis. Voil?: a right-angled triangle appears
Sin and cos have other uses as well. Because they are coordinates of points
lying on a circle, they are periodic. A point traveling along a circle will
eventually arrive at its starting point. This means that their values are
repetive after a while (2*PI to be exact). So you can use sine and cosine as a
source for a pulsing/wavy scope or movement.
The tangent tan is defined as sin divided by cos. It ranges from negative
infinity to positive infinity in -PI/2 to PI/2, and repeates itself every PI.
Usually you won't need the actual mathematical uses of these functions, but
you'll rather be using their characteristics (e.g. repetiveness).
64660
Grid size is always used, regardless of polar or rectangular coordinates.
The idea behind it is that the dynamic movement is a very heavy effect.
Recalculating every pixel-coordinate each frame would be impossible, so that's
why the screen is divided into a grid. AVS calculates a position for each
intersection on the grid, and uses interpolation (averaging from one value to
the other) to achieve a smooth effect.
Usually a pretty low grid size will suffice, but sometimes you'll want to
set it higher. Make sure that you don't make it unnecessarily big, because
bigger grid = slower preset. You should also remember that the horizontal
gridsize and vertical gridsize don't need to match. Gridsizes of 2x20 or 40x3
are acceptable.
As for rectangular coordinates, it means to use x,y (cartesian) coordinates
instead of d,r (polar). In polar coordinates, a point is defined by its distance
to the center "d", and the angle between the vertical line and the line
connecting the point to the center (note that AVS puts 0 rotation vertically
instead of horizontally, as is normally done). Polar coordinate-movements tend
to produce more circular movements, instead of horizontal/vertical movements.
Rectangular coordinates is the way to go when you want to do advanced effects
though.
70899
> geozop
I have usually found that when using a preset movement, it doesn't quite
move fast enough, rotate enough at a certain distance, or something that doesn't
quite make it useful for what I need; even though it was quite close.
Unfortunately, it does not tell you the math/equations that are the presets. If
those were known
Some movements are easy enough to figure out the equations (such as shift
rotate left), but others (like blocky partial out) elude me. I assume other AVS
creators have similar problems, so I thought a topic for reverse-engineering
these movement could help everyone.
Some that I have "decoded":
big swirl out:
d=d-sin(d)/25;
r=r-0.2*(d-0.5)
medium swirl:
d=d+0.001;
r=r-0.025*cos(d*16)
sunburster:
d=d-(sin(d)*0.1*abs(sin(r*18)));
r=r+0.004
(I find
that this works better than the preset, because ther preset has an up-and-left
movement, in addition to the sunbursting)
swirling around both ways at
once:
d=d+0.001;
r=r-0.1*cos(d*16+0.75)
(four times more than medium
swirl, with a bit of an offset)
bubbling
******ds:
d=d-0.025*pow(1.33*sin(d*2*1.57)-0.25,4);
r=r-log(0.01+d)/100
(same
thing as with sunburster, but the movement of the center did not look good
without the r movement)
5 pointed
distro:
d=d-0.1*sin(d)*abs(sin(r*2.5+1.57));
r=r+0.005
(it's a good
likeness, but it's not as exact as I'd like)
I think blocky partial out can be done using rect coordinates... Slight
fuzzify looks like it could be done like the swirl to center preset, except that
the swirls are only a few pixels wide, rather than a third of the
screen.
> UnConeD
This one approximates the tunnel movement. The real 'tunnel' seems to have
its rotation point slightly to the left of the center, but other than that it's
near perfect.
df=d-.16;df=if(below(df,0.02),0.02,df);
d=d-sqr(df)*.23;r=r+0.035
A tip for decoding the movements is to create a preset that contains
this:
-Effect List (Input: ignore / Output: replace)
Simple -> Oscilloscope
Dots
Movement (Original)
-Effect List (Input: ignore / Output: subtractive
blend 1)
Simple -> Oscilloscope Dots
Movement (Your own)
Now you will see the difference between the two movements. The brighter the
picture, the worse you're doing. You should also see your movement as a 'black
layer' over the original. It can help you decode the movement.
> Montana
unconed, whatta hell u talking about
tunneling
movement is
d=sin(d);r=0.05+r
> UnConeD
I was "watta hell" talking about another solution for the tunnel which I
found experimentally. You found a shorter one, nice. If you compare the two
graphs (pop the formula in a superscope and plot them), you'll see that mine
strongly resembles a sine-wave near 0-1.
I checked your solution with the
two-effect-list trick though and it seems the rotation factor is slightly too
high.
> BlurPak2k1
well i sound this out too.
but d=sin(d);
and d=atan(d); have simular effect as well.
> UnConeD
By the way I think it's (sorta) impossible to do blocky partial out for
now. I remember AVS not providing width/height in the movement, so you could
only make it work on one resolution.
Of course you can make something close,
but the real idea here is to get exact copies right?
> TasZ69
Bleedin
d=atan(d)*1.05;
r=.01+r;
I'm
pretty sure this is it. i've got a slight problem remembering it right
now.
> Warrior of the Light
the code for bleedin' is:
t = cos(d * $PI);
r = r + (0.07 * t);
d
= d * (0.98 + t * 0.10);
> StevenRoy
Oh, it's
possible to do a "Blocky Partial Out". I've recently experimented with some very
similar effects in Movement code. The trick is to use extra variables to
actually COUNT the pixels (instead of relying on sw and sh). For example:
nr=equal(y,yy); // "New Row" is 0 when y changes.
nx=nr*((nx+1)&3);
// Either increment or reset nx (from 0 to 3)
ny=(ny+bnot(nr))&3; //
Increment ny (from 0 to 3) when y changes
yy=y; // This is how we tell when
it changes.
vx=if(nx,vx,x); // Save X and Y coordinates for each 4x4
square's
vy=if(ny-1,vy,y); // upper left pixel.
insq=(nx&2)|((ny-1)&2); // "In square" is 0 if we're in one of the
2x2 squares.
x=if(insq,x,(vx*7)/8); // If we are, perform the
magic!
y=if(insq,y,(vy*7)/8);
Well, it's still not -exactly- like the BPO, but it's the best
approximation I can come up with this late at night.
This pixel-counting trick is so unobvious (especially for something like a
Movement that isn't dynamic!), I was -so- tempted to keep it a secret, just so
that I could use it in a preset (for the compilation, of course) and then have a
bunch of people thinking "How the heck did he do that?" ...I love when people
think that!
> jheriko
I love movement. Good for making arbitrarily complex raytraces in realtime
(given a small loading time) Also there are other nifty tricks you can do with
its per-pixel accuracy which dynamic movement forbids with its terrible
resolution. See 'Jheriko - There is no Spoon'.
StevenRoy: I hate to belittle
your fantastic discovery, but why not use sw and sh? Counting those pixels is a
good idea, but more work (code) for no obvious benefit (to me). I'd also be
willing to bet someone has done the counting trick before since it is quite
trivial.
BTW: Another good place to 'count pixels' is in a Dynamic Movement,
althought the utility is somewhat different: you can 'count' the current
position in the grid and use it to access (g)megabuf for whatever reason.
(Creating a faster Whittaker solver maybe )
Anyway, maybe someone should lock
this age-old thread now that the problems are solved and it is outdated?