Welcome to the Second Life Forums Archive

These forums are CLOSED. Please visit the new forums HERE

Notecard script help

Nitro Biedermann
Registered User
Join date: 26 Aug 2008
Posts: 8
10-18-2008 09:48
Ok, I have a notecard that I'm working on a scene rezzer script. Not concentrating on the rezzer part, but something else, this is my problem/question:

I have a notecard which contains the scene names and coordinate locations of all objects per scene. An example would be this:

From: someone
17:46] : | scene | Bedroom
[17:46] : | object | Lamp | <-1.20872, -0.33155, -3.33858>/<-0.00000, 0.00000, -0.00000>
[17:46] : | object | Night_Table | <-0.72021, -0.32541, -3.32856>/<0.00000, -90.00000, 0.00000>
[17:46] : | object | Bed | <-0.73903, 2.22778, -1.11857>/<0.00000, -90.00000, 0.00000>
[17:46] : | object | Dresser | <-0.85421, -3.56949, -0.58953>/<0.00000, -90.00000, 0.00000>
[17:46] : | object | Bedroom_Room1 | <0.05109, -0.06909, -0.11857>/<0.00000, -90.00000, 0.00000>
[17:46] : | object | PictureFrame1 | <-3.40343, 2.21217, -4.06382>/<0.00000, -90.00000, 0.00000>
[17:46] : | object | Bedroom_room1 | <-3.40343, -4.03227, -0.57366>/<0.00000, -90.00000, 90.00000>


This is just one bloc,, but there are multiple instances of this each with objects and scenes. I can rez objects just fine, but I want to add something more to this script.

My question is this: how would I go about reading in ONLY the scene name (not manually) from the notecard, and then assigning a numerical digit (integer) to the indivitual names so that when I click on the start object, it will randomly pick a start room based on the integer input.

Now, another script will tell if an integer value has been assigned for scene rezzing and then to prevent another click instance on the start object, it will lock it. Somehow, I am not sure, but when the object is locked, clicking it again will kill all the objects in a scene.

Is this even possible in SL? I am fairly new with coding and any help would be appreciated. Thanks in advance!
Qie Niangao
Coin-operated
Join date: 24 May 2006
Posts: 7,138
10-18-2008 16:42
From: Nitro Biedermann
My question is this: how would I go about reading in ONLY the scene name (not manually) from the notecard, and then assigning a numerical digit (integer) to the indivitual names so that when I click on the start object, it will randomly pick a start room based on the integer input.
I have to admit I got lost with what's supposed to happen later, but reading in the "scene" lines from the notecard seems pretty straightforward, using something like

line_list = llParseString2List(line_data, [" | "], []);

in the dataserver() event, testing whether "scene" == llList2String(line_list, 1), and if it does, appending llList2String(line_data, 2) --the name of the scene-- to a list of scenes, perhaps relying on the position of the scene in the list as the integer for identifying the scene.

Or... is that not even the question? :o
Nitro Biedermann
Registered User
Join date: 26 Aug 2008
Posts: 8
10-18-2008 18:22
Ok, after beating my brains out trying to get a script working, this is what I have. Comment documentation located at the headder. Thanks for any help. The code is pretty simple to understand, if someone needs more explaining, I'll provide it.


From: someone
//What does this script do? Basically, it reads in a notecard containing a list of the scene names. The script gets the length (how many lines) the notecard has, and then parses it into a random number generator and then theoritically will spit out the line in question from the notecard. This is then going to be hopefully used send to the TalkBackChan to rez a room on the first spawn of teh sphere upon click. To prevent continuous clicking of the sphere, safeguards are in place. listchk and diechk are edited with conditions as below.


string gName; // name of a notecard in the object's inventory
//integer gLine = 0; // current line number
integer gLine;
key gQueryID; // id used to identify dataserver queries

integer random;
integer listchk = 0;
integer diechk = 0;

default {
state_entry() {
gName = llGetInventoryName(INVENTORY_NOTECARD, 0); // select the first notecard in the object's inventory
//gQueryID = llGetNotecardLine(gName, gLine); // request first line
llGetNumberOfNotecardLines("SCENES.NAMES";); // get notecard number of lines
gQueryID = llGetNotecardLine(gName, random); // request notecard random line
}

dataserver(key query_id, string data) {

integer lines = (integer)data;
//llSay(0, "This notecard has " + data + " lines.";);
integer random = (integer) llFrand (lines); // random number gen, max is how many lines notecard has

llSay(0, "random number:" + (string)random);


if (query_id == gQueryID) {
if (data != EOF && listchk==0) { // not at the end of the notecard



//llSay(0, (string)gLine+": "+data); // output the line

//++gLine; // increase line count
//gQueryID = llGetNotecardLine(gName, gLine); // request next line

listchk==1;
diechk==1;
}

else if (diechk==1) {
//llSay(CmdChan, "DIE";);
//llSay(MyChan, "DIE";);
//Scene = "";
llSetTimerEvent(0.0);
//getRefPos();
return;
}

}
}
}



sample notecard named SCENES.NAMES:
From: someone
Bedroom
Dance
adfadsf
asdfasdfasf
asdfasdfasdf
adsfadsfadsf
Qie Niangao
Coin-operated
Join date: 24 May 2006
Posts: 7,138
10-19-2008 08:20
Maybe this will give you a start.

The script in the rezzing object:

CODE

string DIE_STRING = "die";
string SCENE_TOKEN = "scene";
string OBJECT_TOKEN = "object";

list scenes;
list objectSceneStartIndices;
list objects;
list positions;
list rotations;

integer notecardLineNumber;
string notecardName;
key notecardQueryID;

integer notecardRead;
integer dieChannel;

readNextNotecardLine()
{
notecardQueryID = llGetNotecardLine(notecardName, notecardLineNumber++);
}

default
{
state_entry()
{
notecardName = llGetInventoryName(INVENTORY_NOTECARD, 0);
readNextNotecardLine();
}
touch_start(integer total_number)
{
if (dieChannel) // non-zero if anything is rezzed
llWhisper(dieChannel, DIE_STRING);
dieChannel = -500000000 - (integer)llFrand(1000000000);
// choose a random scene:
integer sceneIndex = (integer)llFrand(llGetListLength(scenes));
llWhisper(0, "Rezzing " + llList2String(scenes, sceneIndex));
integer objectIndex = llList2Integer(objectSceneStartIndices, sceneIndex);
integer objectEndIndex = llList2Integer(objectSceneStartIndices, sceneIndex + 1);
for (; objectIndex < objectEndIndex; objectIndex++)
llRezObject
( llList2String(objects, objectIndex)
// assuming the positions are offsets from the rezzer:
, llGetPos() + (llList2Vector(positions, objectIndex) * llGetRot())
, ZERO_VECTOR // velocity
, llList2Rot(rotations, objectIndex) * llGetRot()
, dieChannel
);
}
dataserver(key queryid, string data)
{
if (queryid != notecardQueryID)
return; // Triggered by a different script
if (EOF == data)
{
objectSceneStartIndices += llGetListLength(objects);
notecardRead = TRUE;
return;
}
readNextNotecardLine();
list dataList = llParseString2List(data, [" | "], []);
string lineTypeToken = llList2String(dataList, 1);
if (SCENE_TOKEN == lineTypeToken)
{
scenes += llList2String(dataList, 2);
objectSceneStartIndices += llGetListLength(objects);
}
else
if (OBJECT_TOKEN == lineTypeToken)
{
string objectName = llList2String(dataList, 2);
if (INVENTORY_OBJECT != llGetInventoryType(objectName))
{
llSay(DEBUG_CHANNEL, "skipping missing object: " + objectName);
return;
}
objects += objectName;
positions += (vector)llList2String(dataList, 3);
rotations += llEuler2Rot((vector)llList2String(dataList, 4));
}
else
llWhisper(DEBUG_CHANNEL, "unknown token \"" + lineTypeToken
+ "\" in line:\n" + data
+ " in notecard " + notecardName);
}
}


Sample notecard:

17:46] : | scene | Bedroom
[17:46] : | object | Lamp | <-1.20872, -0.33155, -3.33858>/<-0.00000, 0.00000, -0.00000>
[17:46] : | object | Night_Table | <-0.72021, -0.32541, -3.32856>/<0.00000, -90.00000, 0.00000>
17:46] : | scene | Livingroom
[17:46] : | object | Couch | <-1.20872, -0.33155, -3.33858>/<-0.00000, 0.00000, -0.00000>

(with this data, the rezzer needs to contain Lamp, Night_Table, and Couch objects)

Script in the rezzed objects:

CODE

string DIE_STRING = "die"; // As rezzer llWhisper() to us.

default
{
on_rez(integer start_param)
{
llListen
( start_param // on channel passed from rezzer
, "" // from anything (unless we knew the name of rezzer)
, NULL_KEY // from anything (unless we knew the key of rezzer)
, DIE_STRING
);
}
listen(integer channel, string name, key id, string message)
{
// Only listening for command to die
llDie();
//llOwnerSay("sayanara");
}
}


(Note: To recover formatting between the php tags, press the "Quote" button and copy from the draft reply text.)
Nitro Biedermann
Registered User
Join date: 26 Aug 2008
Posts: 8
10-19-2008 10:01
Ok I figured it out myself.

I however have another small problem. I have a string that is set in the dataserver, but however, I am unable to call the string outside of the dataserver as it is somehow blank. How would I go about calling it outside of the dataserver?
Qie Niangao
Coin-operated
Join date: 24 May 2006
Posts: 7,138
10-19-2008 11:48
Possibly a global variable (defined at top-level scope) needs to be set to the string value in the dataserver() event handler?