Feedback

Please leave feedback and comments. I am always interested to hear how people get on using these LScripts!

Wednesday, 14 March 2012

LScript - Motion_SpotlightTrick


LScript (Layout) to anti-aliase shadow maps used on Spotlights. It works by implementing an old school technique of spinning (Spinning Light Trick) a light across a frame time inorder to offset sample positions. It helps reduce glitches and improves overall image quality. Apply it to a Spotlight in its Motion Options, enable motion blur and see what happens when you render.

Changes

  • Must have motionblur enabled with more than 1 pass
  • Attach to a spotlight
  • Enable shadow maps

Compatible with Newtek LightWave 9.6 and above.

// LScript Item Animation - www.StephenCulley.co.uk
//
// web   address: http://www.stephenculley.co.uk
// email address: email@stephenculley.co.uk

/*  
    LScript Item Animation - SpotlightTrick

    Motion_SpotlightTrick.ls

*/

@version 2.2
@warnings
@script motion
@name *Spotlight Trick

    // Title
    sTitle = "*Spotlight Trick";

    // Version
    sVersion = "v1.1";

    // Item
    Item = nil;

    // Variable
    bH = false;
    bP = false;
    bB = true;
    nAmount = 360.0;
    nSoftEdge = 0.0;   

create : id
{
    // Description
    setdesc(sTitle);
 
    // Info
    info("*Spotlight Trick - Motion blur must be enabled.");

    // Item
    Item = id; // Item
}

destroy
{
}

process: ma, frame, time
{     
    // Variables
    vPosition = ma.get(POSITION,time);
    vRotation = ma.get(ROTATION,time);
    vnForward = normalize3D(Item.getForward(time));

    if(Camera().blurLength(time) <> 0.0)
      {
      // Map Range
      n01 = maprange01(frame * (1 / Scene().fps),(frame + 1) * (1 / Scene().fps),time);

      // Position
      if(nSoftEdge <> 0.0){vPosition -= vnForward * ((10 / Camera().blurLength(time)) * nSoftEdge * n01);} 

      // Rotation
      nDegree = linear1D(0.0,(1 / Camera().blurLength(time)) * nAmount.0,n01);
      if(bH){vRotation.x += nDegree;} // H
      if(bP){vRotation.y += nDegree;} // P
      if(bB){vRotation.z += nDegree;} // B  
      } 

// ma

  ma.set(POSITION,vPosition);
  ma.set(ROTATION,vRotation);

}

// INTERPOLATION

linear1D: n1,n2,i // i = interpolation point (0-1)
{
    return(n1 * (1 - i) + n2 * i);     
}

// MAP RANGE

maprange01: n1,n2,i

{    
    if(n2-n1 == 0.0){return(0.0);}
  else
    {return((1/(n2-n1)) * (i-n1));}
}

// VECTOR 3D

magnitude3D: v // n
{
    // Vector
    return(sqrt((v.x * v.x) + (v.y * v.y) + (v.z * v.z)));
}

normalize3D: v // v
{
    // Vector normalize to 0 - 1
    nMagnitude = magnitude3D(v);
    if(nMagnitude <> 0) nMagnitude = 1 / nMagnitude;
    return(v * nMagnitude);
}

load: what,io
{
    if(what == SCENEMODE)   // processing an ASCII scene file
    {
        if(io.read().asStr() == sTitle + " " + sVersion)
            {
            bH = io.read().asInt(); // H
            bP = io.read().asInt(); // P
            bB = io.read().asInt(); // B
            nAmount = io.read().asNum(); // Amount           
            nSoftEdge = io.read().asNum(); // Soft Edge           
            }
    }
}

save: what,io
{
    if(what == SCENEMODE)
    {
        // Header
        io.writeln(sTitle + " " + sVersion);

        io.writeln(bH); // H
        io.writeln(bP); // P
        io.writeln(bB); // B
        io.writeln(nAmount); // Amount
        io.writeln(nSoftEdge); // Soft Edge
    }
}

options
{
    if(reqisopen())
        {
        reqend();
        return;
        }

    reqbegin(sTitle + " " + sVersion);

    ctrl_c0 = ctlcheckbox("Spin H", bH);
    ctrl_c1 = ctlcheckbox("Spin P", bP);
    ctrl_c2 = ctlcheckbox("Spin B (Antialiase Shadow Map)", bB);
    ctrl_c3 = ctlangle("Amount",nAmount);   
    ctlsep();
    ctrl_c4 = ctlpercent("Soft Edge",nSoftEdge);   

    // Developer
    ctlsep();
    ctrl_dev0 = ctltext("","developer: Stephen Culley","http://www.stephenculley.co.uk");

    // Refresh
    ctlrefresh(ctrl_c0,"refresh_c0"); // H
    ctlrefresh(ctrl_c1,"refresh_c1"); // P
    ctlrefresh(ctrl_c2,"refresh_c2"); // B
    ctlrefresh(ctrl_c3,"refresh_c3"); // Amount
    ctlrefresh(ctrl_c4,"refresh_c4"); // Soft Edge

    reqopen();
}

refresh_c0:value // H
{
    bH = value;
}

refresh_c1:value // P
{
    bP = value;
}

refresh_c2:value // B
{
    bB = value;
}

refresh_c3:value // Amount
{
    nAmount = value;
}

refresh_c4:value // Soft Edge
{
    nSoftEdge = value;
}


All scripts available at my Google Drive at
https://drive.google.com/open?id=1cR_q2GVUAJHumic1-A3eXV16acQnVTWs

No comments:

Post a Comment