Go Back   Cockos Incorporated Forums > REAPER Forums > REAPER for Video Editing/Mangling

Reply
 
Thread Tools Display Modes
Old 10-30-2018, 12:20 PM   #1
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default How to mirror in video processor - kaleidoscope

How to mirror in video processor?
gfx_blit gives only x,y,w,h. Tried negative numbers for w and h, but no luck. Anybody knows how to do it?

Last edited by sonicowl; 11-01-2018 at 02:44 AM.
sonicowl is offline   Reply With Quote
Old 10-31-2018, 01:11 AM   #2
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

Quote:
Originally Posted by sonicowl View Post
How to mirror in video processor?
gfx_blit gives only x,y,w,h. Tried negative numbers for w and h, but no luck. Anybody knows how to do it?
You don't have to mirror in the video processor. Just double click the video item to open the properties. Then click in video properties (down on the right side) and transform the video like you want. Mirroring, flipping etc.

Hope that helps.
Eli
Eliseat is offline   Reply With Quote
Old 10-31-2018, 07:36 AM   #3
Justin
Administrator
 
Justin's Avatar
 
Join Date: Jan 2005
Location: NYC
Posts: 15,721
Default

Try this:
Code:
input_info(0,w,h);
gfx_blit(0,0, 0,0,project_w,project_h,w,0,-w,h);
For more power you can also use gfx_deltablit() to do transformations, e.g.
Code:
input_info(0,w,h);
gfx_deltablit(0, 0,0, project_w,project_h,
             w,0, // starting source coordinates
            -w/project_w,0, // source delta-X/delta-Y with respect to output X
            0,h/project_h   // source delta-X/delta-Y with respect to output Y
            );

Last edited by Justin; 10-31-2018 at 07:43 AM.
Justin is offline   Reply With Quote
Old 10-31-2018, 07:54 AM   #4
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

Quote:
Originally Posted by Justin View Post
Try this:
Code:
input_info(0,w,h);
gfx_blit(0,0, 0,0,project_w,project_h,w,0,-w,h);
For more power you can also use gfx_deltablit() to do transformations, e.g.
Code:
input_info(0,w,h);
gfx_deltablit(0, 0,0, project_w,project_h,
             w,0, // starting source coordinates
            -w/project_w,0, // source delta-X/delta-Y with respect to output X
            0,h/project_h   // source delta-X/delta-Y with respect to output Y
            );
Saved for the love of video processor.
Eliseat is offline   Reply With Quote
Old 10-31-2018, 01:01 PM   #5
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

Thank you both.
I will learn this video processor coding... so much you can do with it. But it will take time.
I would like to make kaleidoscope effect, so my first step was to figure out mirroring. But before I dive into it further, I better ask... Justin, do you maybe already have kaleidoscope preset made and can share it?
sonicowl is offline   Reply With Quote
Old 10-31-2018, 02:12 PM   #6
EpicSounds
Human being with feelings
 
EpicSounds's Avatar
 
Join Date: Jul 2009
Posts: 7,570
Default

I did basic 4-quadrant kaleidoscope effect with the flip options in source properties but it wasn't quick or fun. A preset would be great.
__________________
REAPER Video Tutorials, Tips & Tricks and more at The REAPER Blog
EpicSounds is online now   Reply With Quote
Old 10-31-2018, 03:24 PM   #7
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

Here is some info on how to do kaleidoscope, with code in C. Too much for my abilities atm. https://github.com/timbz/KaleidoscopeGenerator
sonicowl is offline   Reply With Quote
Old 10-31-2018, 07:12 PM   #8
wwwmaze
Human being with feelings
 
Join Date: Oct 2009
Posts: 99
Default

I couldn't find out how to bit blit triangles so here's my quick take using rectangles:

----
see below

Last edited by wwwmaze; 11-01-2018 at 04:21 AM. Reason: updated version
wwwmaze is offline   Reply With Quote
Old 11-01-2018, 02:42 AM   #9
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

@wwwmaze: Your preset works so nicely. Patterns are so much fun. Thank you so much.

How about radial kaleidoscope effect like this?
https://youtu.be/q2fIWB8o-bs?t=221
Would this be achieved by creating vertical stripes, and then using spherical projection to make it a circle?

EDIT: Yes, after testing a bit, it is possible to get somewhat half circle kaleidoscope by adding Justin's radial transform. Probably below script could be modified to get proper 360° circle in the center?

Code:
input_info(0,w,h);
y=tab=0; 
tabsz=60;
loop(tabsz,
  x=0;
  loop(tabsz,
    dx = x/tabsz-.5;
    dy = 1-y/tabsz;
    ang = atan2(dx,dy);
    dist = (sqr(dx)+sqr(dy));
    z= ((ang-$pi/2)*w*.5)/$pi;
    z<0?z+=w;
    tab[]=z;
    tab[1] = h-(dist*h/(.5^2+1))*2;
    
    tab+=2;
    x+=1;
  );
  y+=1;
);
tab=0;
gfx_mode=0x100;
gfx_fillrect(0,0,project_w,project_h);
gfx_xformblit(0, 0,0,project_w,project_h,tabsz,tabsz,tab,0);

Last edited by sonicowl; 11-01-2018 at 03:23 AM.
sonicowl is offline   Reply With Quote
Old 11-01-2018, 04:06 AM   #10
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

Here is a quick test with kaleidoscope, no music.
sonicowl is offline   Reply With Quote
Old 11-01-2018, 04:11 AM   #11
wwwmaze
Human being with feelings
 
Join Date: Oct 2009
Posts: 99
Default

Quote:
Originally Posted by sonicowl View Post

EDIT: Yes, after testing a bit, it is possible to get somewhat half circle kaleidoscope by adding Justin's radial transform. Probably below script could be modified to get proper 360° circle in the center?
Ah yes using circular segments could work, I will have a look later.

Meanwhile I modified the preset to specify window width+height. Set num tiles x/y to 1 and angle to 0° if you are interested in what that means.

Code:
//@param1:x 'window x' 0.25 0 1 0.5 0.001
//@param2:y 'window y' 0.25 0 1 0.5 0.001
//@param3:w 'window w' 0.5 0 1 0.5 0.001
//@param4:h 'window h' 0.5 0 1 0.5 0.001

//@param6:numX 'num tiles x' 4 1 100 50 1
//@param7:numY 'num tiles y' 4 1 100 50 1
//@param9:ang 'angle' 45 0 360 180 1
//@param11:bg 'bg' 0 0 1 0.5 0.01
tileW=(project_w/numX)|0; tileH=(project_h/numY)|0;

gfx_set(bg,bg,bg);
gfx_fillrect(0,0,project_w,project_h);

input_info(0,inW,inH);
gfx_dest = fs = gfx_img_resize(fs, project_w, project_h);
gfx_fillrect(0,0,project_w,project_h);
gfx_rotoblit(0,$pi/180*ang,   0,0,tileW,tileH,    (x*inW)|0, (y*inH)|0, (w*inW)|0, (h*inH)|0);

gfx_dest=-1;
i=0;
loop(numX,
  curXd=tileW*i;
  i%2 ? (
    curWd=tileW;
    curXs=tileW;
    curWs=-tileW;
  ):(
    curWd=tileW+1;
    curXs=0;
    curWs=tileW;
  );
  j=0;
  loop(numY,
    curYd=tileH*j;
    j%2 ? (
      curHd=tileH;
      curYs=tileH;
      curHs=-tileH;
    ):(
      curHd=tileH+1;
      curYs=0;
      curHs=tileH;
    );
    gfx_blit(fs,0,  curXd,curYd,curWd,curHd,   curXs,curYs,curWs,curHs);
    j+=1;
  );
  i+=1;
);

Last edited by wwwmaze; 11-01-2018 at 04:19 AM.
wwwmaze is offline   Reply With Quote
Old 11-01-2018, 04:41 AM   #12
wwwmaze
Human being with feelings
 
Join Date: Oct 2009
Posts: 99
Default

Quote:
Originally Posted by sonicowl View Post
Here is a quick test with kaleidoscope, no music.
Nice! Made me think of lord of the rings

Here's my test:
wwwmaze is offline   Reply With Quote
Old 11-01-2018, 04:46 AM   #13
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

Quote:
Originally Posted by wwwmaze View Post
Ah yes using circular segments could work, I will have a look later.

Meanwhile I modified the preset to specify window width+height. Set num tiles x/y to 1 and angle to 0° if you are interested in what that means.

Thank you.
You get amazing effect by setting width to zero, and automate window x on any photo - those horizontal lines that come from extreme stretching, like in Photoshop, when you take vertical selection of one pixel wide, and stretch it horizontally to fill the canvas - but they move here. Great for quickly getting animated backgrounds.
sonicowl is offline   Reply With Quote
Old 11-01-2018, 05:02 AM   #14
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

Here is a test with extreme stretch, and automating x position. At minimal setting it seems to be more than 1pixel wide, but still gives an effect.
sonicowl is offline   Reply With Quote
Old 11-01-2018, 05:24 AM   #15
sonicowl
Human being with feelings
 
sonicowl's Avatar
 
Join Date: Oct 2015
Posts: 739
Default

Kaleidoscope is fun... just one parameter animated. Same static image used as in above two clips.
sonicowl is offline   Reply With Quote
Old 11-01-2018, 05:50 AM   #16
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

YEAAAAHHH! This is just amazing.

And it works so nicely. Seems the possibilities of video processor are really endless. Thank you so much!
Eliseat is offline   Reply With Quote
Old 11-01-2018, 05:54 AM   #17
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

And now imagine how cool it would be to use Justins new meter levels or spectrograms to mangle them thru the kaleidoscope.
Eliseat is offline   Reply With Quote
Old 11-29-2018, 12:18 PM   #18
wwwmaze
Human being with feelings
 
Join Date: Oct 2009
Posts: 99
Default

I finally managed to finish the triangular shaped kaleidoscope (its not that straightforward):


Hope it works for you guys. Have fun

PHP Code:
// Kaleidoscope (triangle base)
// v0.1

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.

//@param1:preview 'preview' 0 0 1 0 1

//@param3:cxn 'center x' 0.5 0 1 0.5 0.01
//@param4:cyn 'center y' 0.5 0 1 0.5 0.01
//@param5:lenn 'length' 0.25 0 1 0.5 0.01
//@param6:rot 'rotate' 0 0 360 180 1
//@param7:sc 'scale' 1 0.01 5 2.5 0.01

//@param9:bg 'graylevel background' 0.5 0 1 0.5 0.01

///@param11:debug 'debug' 0 0 3 2 1

function gfx_line(x,y,x2,y2,tlocal(i,n,dx,dy,dxn,dyn) (
  
dx=(x2-x); dy=(y2-y);
  
n=abs(dx)+abs(dy);
  
dxn=dx/ndyn=dy/n;
  
i=0;
  
loop(n,
    
gfx_fillrect(x+i*dxn,y+i*dyn,t,t);
    
i+=1;
  );
  
gfx_fillrect(x2,y2,1,1);
);
function 
pt(x,yinstance(x,y) (
  
this.x=x;
  
this.y=y;
);
function 
pRot(cx,cy,alocal(tx,tyinstance(x,y) (
  
tx=x-cx;
  
ty=y-cy;
  
x=tx*cos(a)-ty*sin(a);
  
y=tx*sin(a)+ty*cos(a);
  
x+=cx;
  
y+=cy;
);

!
initdone ? (
  
sqrt3div6=sqrt(3)/6;
  
lrot=lcxn=lcyn=llenn=-1;
  
initdone=1;
);


lcxn!=cxn || lcyn!=cyn || llenn!=lenn || lrot!=rot || lsc!=sc || lproject_w!=project_w || lproject_h!=project_h ? (
  
cx=(cxn*project_w)|0;
  
cy=(cyn*project_h)|0;
  
lenNoSc=lenn*max(project_w,project_h);
  
  
trApoNoSc=(sqrt3div6*lenNoSc)|1// apothem/height of center
  
trHnoSc=trApoNoSc*3;
  
lenNoSc=(trApoNoSc/sqrt3div6)|1;
  
wslenNoSc=(sqrt(2*((4*trApoNoSc)^2))+2)|1;
  
  
p1.pt(cx-(lenNoSc-1)/2cy+trApoNoSc);
  
p2.pt(cx+(lenNoSc-1)/2cy+trApoNoSc);
  
p3.pt(cxcy-trApoNoSc*2);
  
  
rotrad=$pi/180*rot;
  
p1.pRot(cx,cy,rotrad);
  
p2.pRot(cx,cy,rotrad);
  
p3.pRot(cx,cy,rotrad);
  
  
linew=(max(project_w,project_h)/200)|1;
  
  
trApo=(sqrt3div6*lenNoSc*sc)|1;
  
trH=trApo*3;
  
len=(trApo/sqrt3div6)|1;
  
wslen=(sqrt(2*((4*trApo)^2))+2)|1;
  
  
startX=(wslen-len)/2;
  
l1.a=-2*trH/len;
  
l1.b=wslen/2+trApo-l1.a*startX;
  
l2.a=-l1.a;
  
l2.b=wslen/2+trApo-l2.a*(wslen+len)/2;
  
l3.b=wslen/2+trApo;
  
  
minX=min(p1.xmin(p2.x,p3.x)) -cx+project_w/2;
  
maxX=max(p1.xmax(p2.x,p3.x)) -cx+project_w/2;
  
minY=min(p1.ymin(p2.y,p3.y)) -cy+project_h/2;
  
maxY=max(p1.ymax(p2.y,p3.y)) -cy+project_h/2;
  
rotoDx=max(0,max(-minX,maxX-project_w));
  
rotoDy=max(0,max(-minY,maxY-project_h));
  
  
rwsw=project_w+2*rotoDx;
  
rwsh=project_h+2*rotoDy;
  
  
lcxn=cxnlcyn=cynllenn=lennlrot=rotlsc=sclproject_w=project_wlproject_h=project_h;
);



input=0;
colorspace='RGBA';

preview ? (
  
gfx_blit(input);
  
gfx_set(1,0,0);
  
gfx_fillrect(cx-(linew-1)/2,cy-(linew-1)/2,linew,linew); 
  
gfx_line(p1.x,p1.y,p2.x,p2.y,linew);
  
gfx_line(p2.x,p2.y,p3.x,p3.y,linew);
  
gfx_line(p3.x,p3.y,p1.x,p1.y,linew);
):(
  
gfx_set(bg);
  
// add margins to work with rotoblit()
  
gfx_dest ws1 gfx_img_resize(ws1,rwsw,rwsh,1);
  
gfx_blit(input,0,rotoDx,rotoDy,project_w,project_h);
  
  
// rotate
  
gfx_dest ws2 gfx_img_resize(ws2,rwsw,rwsh,1);
  
gfx_rotoblit(ws1,-rotrad,  0,0,rwsw,rwsh,  0,0,rwsw,rwsh0, -rwsw/2+cx+rotoDx, -rwsh/2+cy+rotoDy);
  
  
// crop to square (scaled)
  
gfx_dest ws3 gfx_img_resize(ws3,wslen,wslen,1);
  
gfx_blit(ws2,00,0,wslen,wslenrwsw/2-(wslenNoSc-1)/2,rwsh/2-(wslenNoSc-1)/2,wslenNoSc,wslenNoSc);
  
  
// set alpha (create triangle)
  
code="
  _1>wslen-1 ? (_2+=1;_1=0;);
  _2>wslen-1 ? _2=0;
  _2>l3.b || _2<l1.a*(_1+1)+l1.b || _2<l2.a*_1+l2.b ? a=0;
  _1+=1;
  "
;
  
gfx_evalrect(0,0,wslen,wslen,code);
  
  
// create template of 6 rotated/mirrored triangles
  
gfx_dest templates gfx_img_resize(templates,3*len,2*trH);
  
// upper left
  
gfx_blit(ws3,00,0,len,trH,  startX,(wslen-1)/2-2*trApo,len,trH);
  
  
// upper mid
  
gfx_dest rotTr gfx_img_resize(rotTr,wslen,wslen,1);
  
gfx_rotoblit(ws3,$pi/3,00wslenwslen 00wslenwslen,  0,   00);
  
gfx_dest mirrTr gfx_img_resize(mirrTr,wslen,wslen,1);
  
gfx_deltablit(rotTr0,0wslen,wslen,  wslen-1,0,  -1,00,1);

  
gfx_dest=templates;
  
gfx_blit(mirrTr,0len,0,len,trH,   startX, (wslen-1)/2-trApo+1len,trH);
  
gfx_evalrect(len,0,len,1,"a=255"); // remove some rotating artefacts (sporadic for some triangle length)
  
  // upper right
  
gfx_dest rotTr gfx_img_resize(rotTr,wslen,wslen,1);
  
gfx_rotoblit(ws3,$pi*2/3,00wslenwslen 00wslenwslen,  0,   00);
  
  
gfx_dest=templates;
  
gfx_blit(rotTr,02*len,0,len,trH,  startX,(wslen-1)/2-2*trApo+1,len,trH);
  
gfx_evalrect(2*len,trH-1,len,1,"a=255;"); // remove artefacts
  
  // create lower 3 triangles (mirror along x)
  
gfx_deltablit(templates0,trH3*len,trH,  0,trH-1,  1,00,-1);
  
  
  
// build image
  
gfx_dest=-1;
  
gfx_set(bg);gfx_fillrect(0,0,project_w,project_w);
  
gfx_mode=gfx_mode|0x10000;
  
  
// !debug ? (
    
curX=-(len-1)/2;
    
curY=0;
    
curTr=lTr=0;
    while(
curY<=project_h) (
      
curTemX=(curTr%3)*len;
      
curTemY=(curTr/3)<1?0:trH;
      
gfx_blit(templates,0curX,curY,len,trHcurTemX,curTemY,len,trH);
      
curX+=(len-1)/2;
      
curTr=(curTr+1)%6;
      
curX>project_w ? (
        
curY+=trH;
        
curX=-(len-1)/2;
        
curTr=lTr=lTr?0:3;
      );
    );
  
// ):debug==1 ? gfx_blit(ws2,1,0,0,project_w,project_h) : debug==2 ? gfx_blit(ws3,1,0,0,wslen,wslen) : debug==3 ? gfx_blit(templates,1,0,0,3*len,2*trH);
); 

Last edited by wwwmaze; 11-29-2018 at 12:23 PM.
wwwmaze is offline   Reply With Quote
Old 11-29-2018, 03:46 PM   #19
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

wwwmaze, you are just THE video processor god!

So genius to make a preview. And it works just amazing. I love it. And I just got the hint with the cat in your preview gif. Its hard to see but recognizable. Testing with cats just makes more fun.

Many, many thanks for this great preset. You are the wind in the sail of the new video section. This makes a lot of people very happy. Me too.
Eliseat is offline   Reply With Quote
Old 11-29-2018, 03:50 PM   #20
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

Quote:
Originally Posted by sonicowl View Post
Kaleidoscope is fun... just one parameter animated. Same static image used as in above two clips.
Imagine this with the upcoming track level inputs in presets. You then can animated a level meter and mangle it in every weird way while the beat comes thru. This will make a lot of fun I think.
Eliseat is offline   Reply With Quote
Old 11-30-2018, 07:31 AM   #21
wwwmaze
Human being with feelings
 
Join Date: Oct 2009
Posts: 99
Default

Quote:
Originally Posted by Eliseat View Post
wwwmaze, you are just THE video processor god!

So genius to make a preview. And it works just amazing. I love it. And I just got the hint with the cat in your preview gif. Its hard to see but recognizable. Testing with cats just makes more fun.

Many, many thanks for this great preset. You are the wind in the sail of the new video section. This makes a lot of people very happy. Me too.
Haha thanks glad you like it Eli.
I wondered if you'd recognize Mr. Fluff I feel bad that poor kitty is getting morphed into his pals though
wwwmaze is offline   Reply With Quote
Old 12-21-2018, 03:00 PM   #22
daxliniere
Human being with feelings
 
daxliniere's Avatar
 
Join Date: Nov 2008
Location: London, UK
Posts: 2,581
Default

As a new video user, I'm finding there's quite a steep barrier to getting new video filters. Currently, I've found I need to trawl through threads and even then I'm not sure if the one I've found is the most up-to-date.

Do you think these could be added to a ReaPack repo? Video subsection, perhaps?
@cfillion @X-Raym (<--- I wish tagging worked on the forum)
__________________
Puzzle Factory Sound Studios, London [Website] [Instagram]
[AMD 5800X, 32Gb RAM, Win10x64, NVidia GTX1080ti, UAD2-OCTO, FireFaceUCX, REAPER x64]
[Feature request: More details in Undo History]
daxliniere is offline   Reply With Quote
Old 12-22-2018, 05:07 PM   #23
Eliseat
Human being with feelings
 
Eliseat's Avatar
 
Join Date: Mar 2018
Location: Cologne
Posts: 1,362
Default

Quote:
Originally Posted by daxliniere View Post
As a new video user, I'm finding there's quite a steep barrier to getting new video filters. Currently, I've found I need to trawl through threads and even then I'm not sure if the one I've found is the most up-to-date.

Do you think these could be added to a ReaPack repo? Video subsection, perhaps?
@cfillion @X-Raym (<--- I wish tagging worked on the forum)
Yes, of course. But if you take a closer look you will see that 80% of the presets available were created in the last few weeks. Video in Reaper was kind of a shadow project and got now a little bit pushed since wwwmaze made his fantastic contributions and since we have a separate sub forum for this. And of course since Justin jumped on the wave and makes us happy with lots of new stuff and optimizations.

Those user presets don't follow any plans and sometimes evolve inside a thread, so its impossible to declare final versions. Even the preset codes you can find now are already replacements as bugfixes and little optimizations took place. There is no catalog or something like that. And its kind of typical for Reaper that you have to find the stuff for yourself. Only thing I could offer was to make a thread with all presets I could find.

But - to tell you something positive - a lot of new presets will find their way in one of the next official releases. (blur, histogram, white balance, spectrogram for example). This will make lots of fun.


So I absolutely understand your enthusiasm and that you want everything right now, but there is actually more action in the video section than ever before since implementing.



Eliseat is offline   Reply With Quote
Old 12-22-2018, 06:21 PM   #24
daxliniere
Human being with feelings
 
daxliniere's Avatar
 
Join Date: Nov 2008
Location: London, UK
Posts: 2,581
Default

Oh, I don't want it right now, I just think it would be better in one place. But it sounds like this is already happening so I will continue to hang around. (Y)
__________________
Puzzle Factory Sound Studios, London [Website] [Instagram]
[AMD 5800X, 32Gb RAM, Win10x64, NVidia GTX1080ti, UAD2-OCTO, FireFaceUCX, REAPER x64]
[Feature request: More details in Undo History]
daxliniere is offline   Reply With Quote
Old 03-27-2022, 11:38 AM   #25
ashcat_lt
Human being with feelings
 
Join Date: Dec 2012
Posts: 7,271
Default

Quote:
Originally Posted by wwwmaze View Post
I finally managed to finish the triangular shaped kaleidoscope (its not that straightforward):

Hope it works for you guys. Have fun
I audiofied this.

Adds the value of the audio sample on your chosen audio channel to any of the meaningful parameters.

It requires the video sample peeker, but if you want more than 2 channels, use my 64 channel version (forum url in code) instead, and don't forget to match the gmem names in the code.

It does rectify and includes a simple global smoothing for out of the box satisfaction. There is no gain/range stuff. That would be controlled by the volume of whatever is on that audio channel. Honestly, if you want much more control, probably condition the audio signal using whatever plugs you want before it gets to the video peeker.

Code:
// Kaleidoscope (triangle base)
// v0.1

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
//@gmem=jsfx_to_video 
  // for more than 2 channels, use 64 channel video peeker and match gmem names
  // https://forums.cockos.com/showthread.php?t=247691


//@param1:preview 'preview' 0 0 1 0 1

//@param3:cxn_p 'center x' 0.5 0 1 0.5 0.01
//@param4:cyn_p 'center y' 0.5 0 1 0.5 0.01
//@param5:lenn_p 'length' 0.25 0 1 0.5 0.01
//@param6:rot_p 'rotate' 0 0 360 180 1
//@param7:sc_p 'scale' 1 0.01 5 2.5 0.01

//@param9:cxn_ch 'center x channel' 0 0 64 32 1
//@param10:cyn_ch 'center y channel' 0 0 64 32 1
//@param11:lenn_ch 'length channel' 0 0 64 32 1
//@param12:rot_ch 'rotate channel' 0 0 64 32 1
//@param13:sc_ch 'scale channel' 0 0 64 32 1
//@param14:smooth 'smoothing' 0 0 1 0.5 0.01

//@param16:bg 'graylevel background' 0 0 1 0.5 0.01

///@param17:debug 'debug' 0 0 3 2 1



bufplaypos = gmem[0];
bufwritecursor = gmem[1];
bufsrate = gmem[2];
bufstart = gmem[3];
bufend = gmem[4];
nch = gmem[5];

dt=max(bufplaypos - project_time,0);
dt*bufsrate < dotcount ? underrun_cnt+=1;
rdpos = bufwritecursor - ((dt*bufsrate - dotcount)|0)*nch;
rdpos < bufstart ? rdpos += bufend-bufstart;

i_smooth = 1 - smooth;


function getpt(channel, rect_)
  local (return)
  (channel > 0 && channel <= nch ?
    (return = gmem[rdpos + channel - 1];
     rect_ == -1 ? return = -abs(return);
     rect_ == 1 ? return = abs(return);
     rect_ == 2 ? return = 0.5 * (return + 1);
    );
   (rdpos += nch)>=bufend ? rdpos=bufstart;
   return;
);

function smooth (input)
  instance (last)
  (this.last = i_smooth * input + smooth * this.last;
  );
i=0;


function gfx_line(x,y,x2,y2,t) local(i,n,dx,dy,dxn,dyn) (
  dx=(x2-x); dy=(y2-y);
  n=abs(dx)+abs(dy);
  dxn=dx/n; dyn=dy/n;
  i=0;
  loop(n,
    gfx_fillrect(x+i*dxn,y+i*dyn,t,t);
    i+=1;
  );
  gfx_fillrect(x2,y2,1,1);
);
function pt(x,y) instance(x,y) (
  this.x=x;
  this.y=y;
);
function pRot(cx,cy,a) local(tx,ty) instance(x,y) (
  tx=x-cx;
  ty=y-cy;
  x=tx*cos(a)-ty*sin(a);
  y=tx*sin(a)+ty*cos(a);
  x+=cx;
  y+=cy;
);

!initdone ? (
  sqrt3div6=sqrt(3)/6;
  lrot=lcxn=lcyn=llenn=-1;
  initdone=1;
);

cxn = cxn_p + 0.5 * cx_a.smooth(getpt(cxn_ch, 1));
cyn = cyn_p + 0.5 * cy_a.smooth(getpt(cyn_ch, 1));
lenn = lenn_p + 0.5 * lenn_a.smooth(getpt(lenn_ch, 1));
rot = rot_p + 180 * rot_a.smooth(getpt(rot_ch, 2));
sc = sc_p + 0.5 * sc_a.smooth(getpt(sc_ch, 1));
////@param7:sc 'scale' 1 0.01 5 2.5 0.01

lcxn!=cxn || lcyn!=cyn || llenn!=lenn || lrot!=rot || lsc!=sc || lproject_w!=project_w || lproject_h!=project_h ? (
  cx=(cxn*project_w)|0;
  cy=(cyn*project_h)|0;
  lenNoSc=lenn*max(project_w,project_h);
  
  trApoNoSc=(sqrt3div6*lenNoSc)|1; // apothem/height of center
  trHnoSc=trApoNoSc*3;
  lenNoSc=(trApoNoSc/sqrt3div6)|1;
  wslenNoSc=(sqrt(2*((4*trApoNoSc)^2))+2)|1;
  
  p1.pt(cx-(lenNoSc-1)/2, cy+trApoNoSc);
  p2.pt(cx+(lenNoSc-1)/2, cy+trApoNoSc);
  p3.pt(cx, cy-trApoNoSc*2);
  
  rotrad=$pi/180*rot;
  p1.pRot(cx,cy,rotrad);
  p2.pRot(cx,cy,rotrad);
  p3.pRot(cx,cy,rotrad);
  
  linew=(max(project_w,project_h)/200)|1;
  
  trApo=(sqrt3div6*lenNoSc*sc)|1;
  trH=trApo*3;
  len=(trApo/sqrt3div6)|1;
  wslen=(sqrt(2*((4*trApo)^2))+2)|1;
  
  startX=(wslen-len)/2;
  l1.a=-2*trH/len;
  l1.b=wslen/2+trApo-l1.a*startX;
  l2.a=-l1.a;
  l2.b=wslen/2+trApo-l2.a*(wslen+len)/2;
  l3.b=wslen/2+trApo;
  
  minX=min(p1.x, min(p2.x,p3.x)) -cx+project_w/2;
  maxX=max(p1.x, max(p2.x,p3.x)) -cx+project_w/2;
  minY=min(p1.y, min(p2.y,p3.y)) -cy+project_h/2;
  maxY=max(p1.y, max(p2.y,p3.y)) -cy+project_h/2;
  rotoDx=max(0,max(-minX,maxX-project_w));
  rotoDy=max(0,max(-minY,maxY-project_h));
  
  rwsw=project_w+2*rotoDx;
  rwsh=project_h+2*rotoDy;
  
  lcxn=cxn; lcyn=cyn; llenn=lenn; lrot=rot; lsc=sc; lproject_w=project_w; lproject_h=project_h;
);



input=0;
colorspace='RGBA';

preview ? (
  gfx_blit(input);
  gfx_set(1,0,0);
  gfx_fillrect(cx-(linew-1)/2,cy-(linew-1)/2,linew,linew); 
  gfx_line(p1.x,p1.y,p2.x,p2.y,linew);
  gfx_line(p2.x,p2.y,p3.x,p3.y,linew);
  gfx_line(p3.x,p3.y,p1.x,p1.y,linew);
):(
  gfx_set(bg);
  // add margins to work with rotoblit()
  gfx_dest = ws1 = gfx_img_resize(ws1,rwsw,rwsh,1);
  gfx_blit(input,0,rotoDx,rotoDy,project_w,project_h);
  
  // rotate
  gfx_dest = ws2 = gfx_img_resize(ws2,rwsw,rwsh,1);
  gfx_rotoblit(ws1,-rotrad,  0,0,rwsw,rwsh,  0,0,rwsw,rwsh, 0, -rwsw/2+cx+rotoDx, -rwsh/2+cy+rotoDy);
  
  // crop to square (scaled)
  gfx_dest = ws3 = gfx_img_resize(ws3,wslen,wslen,1);
  gfx_blit(ws2,0, 0,0,wslen,wslen, rwsw/2-(wslenNoSc-1)/2,rwsh/2-(wslenNoSc-1)/2,wslenNoSc,wslenNoSc);
  
  // set alpha (create triangle)
  code="
  _1>wslen-1 ? (_2+=1;_1=0;);
  _2>wslen-1 ? _2=0;
  _2>l3.b || _2<l1.a*(_1+1)+l1.b || _2<l2.a*_1+l2.b ? a=0;
  _1+=1;
  ";
  gfx_evalrect(0,0,wslen,wslen,code);
  
  // create template of 6 rotated/mirrored triangles
  gfx_dest = templates = gfx_img_resize(templates,3*len,2*trH);
  // upper left
  gfx_blit(ws3,0, 0,0,len,trH,  startX,(wslen-1)/2-2*trApo,len,trH);
  
  // upper mid
  gfx_dest = rotTr = gfx_img_resize(rotTr,wslen,wslen,1);
  gfx_rotoblit(ws3,$pi/3,0, 0, wslen, wslen , 0, 0, wslen, wslen,  0,   0, 0);
  gfx_dest = mirrTr = gfx_img_resize(mirrTr,wslen,wslen,1);
  gfx_deltablit(rotTr, 0,0, wslen,wslen,  wslen-1,0,  -1,0, 0,1);

  gfx_dest=templates;
  gfx_blit(mirrTr,0, len,0,len,trH,   startX, (wslen-1)/2-trApo+1, len,trH);
  gfx_evalrect(len,0,len,1,"a=255"); // remove some rotating artefacts (sporadic for some triangle length)
  
  // upper right
  gfx_dest = rotTr = gfx_img_resize(rotTr,wslen,wslen,1);
  gfx_rotoblit(ws3,$pi*2/3,0, 0, wslen, wslen , 0, 0, wslen, wslen,  0,   0, 0);
  
  gfx_dest=templates;
  gfx_blit(rotTr,0, 2*len,0,len,trH,  startX,(wslen-1)/2-2*trApo+1,len,trH);
  gfx_evalrect(2*len,trH-1,len,1,"a=255;"); // remove artefacts
  
  // create lower 3 triangles (mirror along x)
  gfx_deltablit(templates, 0,trH, 3*len,trH,  0,trH-1,  1,0, 0,-1);
  
  
  // build image
  gfx_dest=-1;
  gfx_set(bg);gfx_fillrect(0,0,project_w,project_w);
  gfx_mode=gfx_mode|0x10000;
  
  // !debug ? (
    curX=-(len-1)/2;
    curY=0;
    curTr=lTr=0;
    while(curY<=project_h) (
      curTemX=(curTr%3)*len;
      curTemY=(curTr/3)<1?0:trH;
      gfx_blit(templates,0, curX,curY,len,trH, curTemX,curTemY,len,trH);
      curX+=(len-1)/2;
      curTr=(curTr+1)%6;
      curX>project_w ? (
        curY+=trH;
        curX=-(len-1)/2;
        curTr=lTr=lTr?0:3;
      );
    );
  // ):debug==1 ? gfx_blit(ws2,1,0,0,project_w,project_h) : debug==2 ? gfx_blit(ws3,1,0,0,wslen,wslen) : debug==3 ? gfx_blit(templates,1,0,0,3*len,2*trH);
);

Last edited by ashcat_lt; 03-27-2022 at 11:58 AM.
ashcat_lt is online now   Reply With Quote
Reply

Thread Tools
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 -7. The time now is 11:02 AM.


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