Difference between revisions of "NexUI"

From Second Life Wiki
Jump to navigation Jump to search
Line 135: Line 135:
<lsl>
<lsl>
list uiSlider1( integer Mode, key kTexture ){
list uiSlider1( integer Mode, key kTexture ){
if( llDetectedTouchFace( 0 ) == -1 ) return [-1];
if( llDetectedTouchFace( 0 ) != 0 ) return [];
if( Mode == 0 ){ // START //
if( Mode == 0 ){ // START //
      
      
Line 153: Line 153:
     else if( ST.y < 0.02 ) ST.y = 0.0;
     else if( ST.y < 0.02 ) ST.y = 0.0;
     return [ST.y];
     return [ST.y];
} return [-1]; }
} return []; }
</lsl>
</lsl>


Line 167: Line 167:
|-
|-
| return list uiSlider1( 1, key kTexture )
| return list uiSlider1( 1, key kTexture )
| Returns list with value of 0.0 - 1.0 of slider.
| Returns list with value [Range], 0.0 - 1.0 of slider. Empty list on error.
|-
|-
| return list uiSlider1( 2, key kTexture )
| return list uiSlider1( 2, key kTexture )
| Returns list with value of 0.0 - 1.0 of slider.
| Returns list with value [Range], 0.0 - 1.0 of slider. Empty list on error.
|}
<div style="float:right;font-size: 80%;">
By Nexii Malthus</div>
|}
 
 
<!--############# TURN #############-->
 
{|cellspacing="0" cellpadding="3" border="1" style="border: 1px solid #aaaaaa; margin: 1em 1em 1em 0pt; background-color: #ffffff; border-collapse: collapse" width="80%"
!style="color: #000000; background-color: #aaaaff;" height="20px"|
Turn
|-
|
Turn component, imagine a turntable, or the iPod menu.
 
<lsl>
list uiTurn( integer Mode ){
    integer Face = llDetectedTouchFace( 0 );
    if( Face != 0 ) return [];
   
    if( Mode == 0 ){
       
    } else if( Mode == 1 ){
        vector ST = llDetectedTouchST( 0 );
       
        vector Scale = < 0.97, 0.97, 0.0 >;
        vector Offset = < 0.0, 0.0, 0.0 >;
        float Turn = llAtan2( 0.5 - ST.y, 0.5 - ST.x );
       
        llMessageLinked( LINK_THIS, Smoother, llDumpList2String( [Lnk,PRIM_TEXTURE,0,"9ab6a2f8-8f26-0edc-53ba-db786618ce49",Scale,Offset,Turn], "|" ), "" );
        if( ++Smoother > 3 ) Smoother = 0;
        return [Turn];
    } else if( Mode == 2 ){
        vector ST = llDetectedTouchST( 0 );
        return [llAtan2( 0.5 - ST.y, 0.5 - ST.x )];
    } return [];}
</lsl>
 
{|cellspacing="0" cellpadding="6" border="1" style="border: 1px solid #aaaaaa; margin: 1em 1em 1em 0pt; background-color: #e0e0ff; border-collapse: collapse"
!style="background-color: #d0d0ee" | Input
!style="background-color: #d0d0ee" | Description
|-
| integer Mode
| Mode of uiFunction, 0 - Touch Start, 1 - Touch, 2 - Touch End
|-
!style="background-color: #d0d0ee" | Output
!style="background-color: #d0d0ee" | Description
|-
| return list uiTurn( 1 )
| Returns list with value [Angle], angle in radians, -PI to 0 to PI, or when multiplied by RAD_TO_DEG it is -180 to 0 to 180. Empty list on error.
|-
| return list uiTurn( 2 )
| Returns list with final value [Angle]. Empty list on error.
|}
|}
<div style="float:right;font-size: 80%;">
<div style="float:right;font-size: 80%;">
Line 188: Line 241:
<lsl>
<lsl>
list uiCND( integer Mode ){
list uiCND( integer Mode ){
if( llDetectedTouchFace( 0 ) == -1 ) return [-1];
if( llDetectedTouchFace( 0 ) != 0 ) return [];
if( Mode == 0 ){ // START //
if( Mode == 0 ){ // START //
     tData1 = [ llDetectedTouchPos(0), llDetectedTouchNormal(0), llDetectedTouchBinormal(0) ];
     tData1 = [ llDetectedTouchPos(0), llDetectedTouchNormal(0), llDetectedTouchBinormal(0) ];
Line 194: Line 247:
} else if( Mode == 1 ){ // TOUCH //
} else if( Mode == 1 ){ // TOUCH //
     vector ST2 = llDetectedTouchST( 0 );
     vector ST2 = llDetectedTouchST( 0 );
     if( ST1 == <-1,-1,0> || ST2 == <-1,-1,0> ) return [-1];
     if( ST1 == <-1,-1,0> || ST2 == <-1,-1,0> ) return [];
     if( llVecDist( ST1, ST2 ) > 0.01 ){
     if( llVecDist( ST1, ST2 ) > 0.01 ){
         llSetLinkColor( Lnk, < 0.0, 0.0, 1.0 >, 0 ); llSetLinkAlpha( Lnk, 0.2, 0 );
         llSetLinkColor( Lnk, < 0.0, 0.0, 1.0 >, 0 ); llSetLinkAlpha( Lnk, 0.2, 0 );
Line 208: Line 261:
     }
     }
} else if( Mode == 2 ){ // END //
} else if( Mode == 2 ){ // END //
     key nKey = llDetectedKey( 0 ); vector tPos = llDetectedTouchPos( 0 );
     tData2 = [ llDetectedTouchPos( 0 ), llDetectedTouchNormal( 0 ), llDetectedTouchBinormal( 0 ) ];
    tData2 = [ tPos, llDetectedTouchNormal( 0 ), llDetectedTouchBinormal( 0 ) ];
     vector ST2 = llDetectedTouchST( 0 );
     vector ST2 = llDetectedTouchST( 0 );
      
      
     if( ST1 == <-1,-1,0> || ST2 == <-1,-1,0> )
     if( ST1 == <-1,-1,0> || ST2 == <-1,-1,0> )
         return [-1];
         return [];
      
      
     if( llVecDist( ST1, ST2 ) < 0.01 ){
     if( llVecDist( ST1, ST2 ) < 0.01 ){
Line 233: Line 285:
         return [1] + tData1 + tData2;
         return [1] + tData1 + tData2;
     }
     }
} return [-1]; }
} return []; }
</lsl>
</lsl>


Line 247: Line 299:
|-
|-
| return list uiCND( 2 )
| return list uiCND( 2 )
| Returns list of values, if on error returns one item of '-1', [[ClickAndDrag|else same return data as my script.]]
| Returns list of values, Click [0,World Pos,Normal,Bi-Normal], Drag [1,Pos1,N1,BN1,Pos2,N2,BN2], if on error returns empty list.
|}
|}
<div style="float:right;font-size: 80%;">
<div style="float:right;font-size: 80%;">
By Nexii Malthus</div>
By Nexii Malthus</div>
|}
|}

Revision as of 11:42, 29 November 2008

User Interface Project

A project to try create an efficient, flexible and innovative User Interface in LSL. Without being complex to use or using a ridicolous amount of constants, providing direct results that can be returned and used by the scripter directly in a Master script for efficiency, or used via automation of a UI master to a link-message protocol sent to scripts written by the original scripter.

The User Interface Project is to create a UI that can be used in-world as well as on the HUD, providing pseudo-dynamic graphical feedback to the user(s).

Setup

Rez a object to serve as root, recommended as the menu-background of the UI.

new script, name as 'uiMaster'. This is the default basic setup: <lsl> default{

   state_entry(){
       uiInit();
       llMinEventDelay( 0.10 );
   }
   
   touch_start( integer dn ){
       integer lLink = llDetectedLinkNumber( 0 );
       string lName = llGetLinkName( lLink );
       integer x = llListFindList( uiNm, [lName] );
       if( ~x ) Lnk = llList2Integer( uiLnk, x );
       
       if( lName == "My UI Element #1" ){
           // uiFunction( 0 );
       }
   }
   
   touch( integer dn ){
       integer lLink = llDetectedLinkNumber( 0 );
       string lName = llGetLinkName( lLink );
       integer x = llListFindList( uiNm, [lName] );
       if( ~x ) Lnk = llList2Integer( uiLnk, x );
       
       if( lName == "My UI Element #1" ){
           // uiFunction( 1 );
       }
   }
   
   touch_end( integer dn ){
       integer lLink = llDetectedLinkNumber( 0 );
       string lName = llGetLinkName( lLink );
       integer x = llListFindList( uiNm, [lName] );
       if( ~x ) Lnk = llList2Integer( uiLnk, x );
       
       if( lName == "My UI Element #1" ){
           // variable = uiFunction( 2 );
       }
   }

} </lsl>

new scripts (4 total), name as 'uiSlave:0', 'uiSlave:1', 'uiSlave:2' and 'uiSlave:3', which serve to speed up feedback significantly of the pseudo dynamic graphics.

<lsl> integer x;

default{

   state_entry(){
       x = (integer)llList2String( llParseString2List( llGetScriptName(), [":"], [] ), 1 );
       state Main;
   }

}

state Main{

   link_message( integer sn, integer n, string str, key k ){
       if( n == x ){
           list t = llParseString2List( str, ["|"], [] );
           llSetLinkPrimitiveParams( (integer)llList2String(t,0), 
               [(integer)llList2String(t,1),
                (integer)llList2String(t,2),
                    (key)llList2String(t,3),
                 (vector)llList2String(t,4),
                 (vector)llList2String(t,5),
                  (float)llList2String(t,6)] );
       }
   }

} </lsl>

uiFunctions

Initialization

Initializes UI Elements into lists. Goes through all child prims to identify them as being a UI element by their prim description. And includes them into global lists of link number, name and their UI type for:

  • use in other functions
  • debug
  • saving time from re-searching entire linksets again and;
  • preventing objects having hard-coded scripts which would defy the point of flexibility.

<lsl> uiInit(){

   integer y = llGetNumberOfPrims();
   while( --y-1 ){
       list Dat = llGetObjectDetails( llGetLinkKey( y ), [OBJECT_NAME,OBJECT_DESC] );
       string lDesc = llList2String( Dat, 1 );
       if( llGetSubString( lDesc, 0, 2 ) == "UI_" ){
           uiLnk = (uiLnk = []) + uiLnk + y;
           uiNm = (uiNm = []) + uiNm + llList2String( Dat, 0 );
           uiType = (uiType = []) + uiType + lDesc;
       }
   }

} </lsl>

Process Description
uiInit Initializes by assorting all the child prims
By Nexii Malthus


Slider

Slider script.

<lsl> list uiSlider1( integer Mode, key kTexture ){ if( llDetectedTouchFace( 0 ) != 0 ) return []; if( Mode == 0 ){ // START //

} else if( Mode == 1 ){ // TOUCH //

   vector Scale = < 1.0, 0.5, 0.0 >;
   vector Offset; vector ST = llDetectedTouchST( 0 );
   if( ST.y > 0.98 ){Offset.y = -0.25;ST.y = 1.0;}
   else if( ST.y < 0.02 ){Offset.y = 0.25;ST.y = 0.0;}
   else Offset.y = 0.25 - ST.y/2;
   
   llMessageLinked( LINK_THIS, Smoother, llDumpList2String( [Lnk,PRIM_TEXTURE,0,kTexture,Scale,Offset,0], "|" ), "" );
   if( ++Smoother > 3 ) Smoother = 0;
   return [ST.y];

} else if( Mode == 2 ){ // END //

   vector ST = llDetectedTouchST( 0 );
   if( ST.y > 0.98 ) ST.y = 1.0;
   else if( ST.y < 0.02 ) ST.y = 0.0;
   return [ST.y];

} return []; } </lsl>

Input Description
integer Mode Mode of uiFunction, 0 - Touch Start, 1 - Touch, 2 - Touch End
Output Description
return list uiSlider1( 1, key kTexture ) Returns list with value [Range], 0.0 - 1.0 of slider. Empty list on error.
return list uiSlider1( 2, key kTexture ) Returns list with value [Range], 0.0 - 1.0 of slider. Empty list on error.
By Nexii Malthus


Turn

Turn component, imagine a turntable, or the iPod menu.

<lsl> list uiTurn( integer Mode ){

   integer Face = llDetectedTouchFace( 0 );
   if( Face != 0 ) return [];
   
   if( Mode == 0 ){
       
   } else if( Mode == 1 ){
       vector ST = llDetectedTouchST( 0 );
       
       vector Scale = < 0.97, 0.97, 0.0 >;
       vector Offset = < 0.0, 0.0, 0.0 >;
       float Turn = llAtan2( 0.5 - ST.y, 0.5 - ST.x );
       
       llMessageLinked( LINK_THIS, Smoother, llDumpList2String( [Lnk,PRIM_TEXTURE,0,"9ab6a2f8-8f26-0edc-53ba-db786618ce49",Scale,Offset,Turn], "|" ), "" );
       if( ++Smoother > 3 ) Smoother = 0;
       return [Turn];
   } else if( Mode == 2 ){
       vector ST = llDetectedTouchST( 0 );
       return [llAtan2( 0.5 - ST.y, 0.5 - ST.x )];
   } return [];}

</lsl>

Input Description
integer Mode Mode of uiFunction, 0 - Touch Start, 1 - Touch, 2 - Touch End
Output Description
return list uiTurn( 1 ) Returns list with value [Angle], angle in radians, -PI to 0 to PI, or when multiplied by RAD_TO_DEG it is -180 to 0 to 180. Empty list on error.
return list uiTurn( 2 ) Returns list with final value [Angle]. Empty list on error.
By Nexii Malthus


Click and Drag

Based on my Click and Drag script.

<lsl> list uiCND( integer Mode ){ if( llDetectedTouchFace( 0 ) != 0 ) return []; if( Mode == 0 ){ // START //

   tData1 = [ llDetectedTouchPos(0), llDetectedTouchNormal(0), llDetectedTouchBinormal(0) ];
   ST1 = llDetectedTouchST( 0 );

} else if( Mode == 1 ){ // TOUCH //

   vector ST2 = llDetectedTouchST( 0 );
   if( ST1 == <-1,-1,0> || ST2 == <-1,-1,0> ) return [];
   if( llVecDist( ST1, ST2 ) > 0.01 ){
       llSetLinkColor( Lnk, < 0.0, 0.0, 1.0 >, 0 ); llSetLinkAlpha( Lnk, 0.2, 0 );
       float relSize = 0.08;//0.084;
       vector selCentre = <1,1,0> - ((ST2+ST1)/2);
       vector selSize = (ST1-ST2); selSize = <llFabs(selSize.x),llFabs(selSize.y),0>;
       
       vector Scale = <relSize/selSize.x,relSize/selSize.y,0>;
       vector Offset = (selCentre-<0.5,0.5,0>);
       Offset = <Offset.x*Scale.x,Offset.y*Scale.y,0>;
       llMessageLinked( LINK_THIS, Smoother, llDumpList2String( [Lnk,PRIM_TEXTURE,0,kTextureDrag,Scale,Offset,0], "|" ), "" );
       if( ++Smoother > 3 ) Smoother = 0;
   }

} else if( Mode == 2 ){ // END //

   tData2 = [ llDetectedTouchPos( 0 ), llDetectedTouchNormal( 0 ), llDetectedTouchBinormal( 0 ) ];
   vector ST2 = llDetectedTouchST( 0 );
   
   if( ST1 == <-1,-1,0> || ST2 == <-1,-1,0> )
       return [];
   
   if( llVecDist( ST1, ST2 ) < 0.01 ){
       llSetLinkColor( Lnk, < 0.0, 1.0, 0.0 >, 0 ); llSetLinkAlpha( Lnk, 1.0, 0 );
       vector Scale = < 1.0, 1.0, 0>;
       vector Offset = < 1.0, 1.0, 0 > - ST1;
       llSetLinkPrimitiveParams( Lnk, [ PRIM_TEXTURE, 0, kTextureClick, Scale, Offset, 0 ]);
       llSetLinkAlpha( Lnk, 0.0, 0 );
       return [0] + tData1;
   } else {
       llSetLinkColor( Lnk, < 0.0, 0.0, 1.0 >, 0 ); llSetLinkAlpha( Lnk, 0.2, 0 );
       float relSize = 0.08;
       vector selCentre = <1,1,0> - ((ST2+ST1)/2);
       vector selSize = (ST1-ST2); selSize = <llFabs(selSize.x),llFabs(selSize.y),0>;
       vector Scale = <relSize/selSize.x,relSize/selSize.y,0>;
       vector Offset = (selCentre-<0.5,0.5,0>);Offset = <Offset.x*Scale.x,Offset.y*Scale.y,0>;
       llSetLinkPrimitiveParams( Lnk, [ PRIM_TEXTURE, 0, kTextureDrag, Scale, Offset, 0 ]);
       llSetLinkAlpha( Lnk, 0.0, 0 );
       return [1] + tData1 + tData2;
   }

} return []; } </lsl>

Input Description
integer Mode Mode of uiFunction, 0 - Touch Start, 1 - Touch, 2 - Touch End
Output Description
return list uiCND( 2 ) Returns list of values, Click [0,World Pos,Normal,Bi-Normal], Drag [1,Pos1,N1,BN1,Pos2,N2,BN2], if on error returns empty list.
By Nexii Malthus