Welcome to the Second Life Forums Archive

These forums are CLOSED. Please visit the new forums HERE

Reading a config from a notecard

Bobby Dayton
Test Pilot for Airfix
Join date: 15 Nov 2003
Posts: 206
01-17-2005 06:59
I am having tgwo problems. The ideaa is to read the config (3 lines) from a notecard.
I am using llGetNotecardLine along with dataserve. My first problem is that dataserve is also being used for a llRequestAgentData. I believe I have to use a queryid key to tell which call is which. Not quite sure how that goes. But the other part of the problem seems to be reading the card. I wrote a notecard with 3 lines containing Line1 line2 and Line3. I used an example bit of code as follows. Might have an odd typo as I cant get at actual code as I am at work. The output is

Line # 0 : line1
Line # 1 : line1
Line # 2 : line2
Line # 3 : line3

It sometimes counts further. So I am not sure if I have to put some form of EOF caracter on the notecard. But why am I getting the first line twice every time.

Sorry if it's a newby question but I am just getting to grips with LSL...Slowly.

state_entry()
{
lineCounter = 0
dataRequestID = llGetNotecardLine(notecardName, lineCounter);
}
dataserver(key queryid, string data)
{
if (dataRequestID)
{
if (data != EOF)
{
dataRequestID = llGetNotecardLine(notecardName, lineCounter);
lineCounter += 1;
llSay(0, "Line #" + (string)lineCounter + ": " + data);
}
else
{
state default;
}
}
}
Christopher Omega
Oxymoron
Join date: 28 Mar 2003
Posts: 1,828
01-17-2005 08:26
From: Bobby Dayton
I am having tgwo problems. The ideaa is to read the config (3 lines) from a notecard.
I am using llGetNotecardLine along with dataserve. My first problem is that dataserve is also being used for a llRequestAgentData. I believe I have to use a queryid key to tell which call is which.

Your hunch is correct. In order to differentiate between two different function calls that trigger the dataserver event, you must first save the key returned by the function call to a global variable and compare it to the key passed to the dataserver event. If the key in the dataserver event matches the one in the global variable for the function call, then the dataserver data is for that function call.

Here's an example:
CODE

key agentDataId;
key notecardDataId;
default {
state_entry() {
agentDataId = llRequestAgentData(llGetOwner(), DATA_BORN);
notecardDataId = llGetNotecardLine("myNote", 0);
}
dataserver(key queryId, string data) {
if (queryId == notecardDataId) {
notecardDataId = ""; // Prevent a bug.
// data contains the first line in myNote.
} else if (queryId == agentDataId) {
agentDataId = ""; // Prevent a bug.
// data contains the date the owner was born.
}
}
}


From: someone

Not quite sure how that goes. But the other part of the problem seems to be reading the card. I wrote a notecard with 3 lines containing Line1 line2 and Line3. I used an example bit of code as follows. Might have an odd typo as I cant get at actual code as I am at work. The output is

Line # 0 : line1
Line # 1 : line1
Line # 2 : line2
Line # 3 : line3

It sometimes counts further. So I am not sure if I have to put some form of EOF caracter on the notecard. But why am I getting the first line twice every time.

Sorry if it's a newby question but I am just getting to grips with LSL...Slowly.

state_entry()
{
lineCounter = 0
dataRequestID = llGetNotecardLine(notecardName, lineCounter);
}
dataserver(key queryid, string data)
{
if (dataRequestID)
{
if (data != EOF)
{
dataRequestID = llGetNotecardLine(notecardName, lineCounter);
lineCounter += 1;
llSay(0, "Line #" + (string)lineCounter + ": " + data);
}
else
{
state default;
}
}
}

Hmm... I cant be sure with the code you posted. It doesnt say what state the script is in, and it calls state default, which is not shown. Keep in mind that when you post a code example it makes it alot easier on replyers when the code actually compiles. :)

Right now I see two problems with your code. The line "if (dataRequestID)" actually is saying if (dataRequestID != NULL_KEY). dataRequestID will never be NULL_KEY, so this will always evaluate to TRUE.

Also, there's a known bug with the dataserver event where it can erroniously trigger twice with the same data and key. That's why I set my key globals to "" in the previous code, to prevent that.

Here's an example of a reader script that should do what you want:
CODE

string notecardName = "myNote";
integer lineCounter = 0;
// Stores query ID of the current call to llGetNotecardLine.
key curNotecardRead;
default {
// ...
}

state readNotecard {
state_entry() {
lineCounter = 0;
curReadId = llGetNotecardLine(notecardName, lineCounter);
}
dataserver(key query, string data) {
if (query == curReadId) { // Then data is for notecard.
curReadId = ""; // Prevent repeat bug.
if (data != EOF) { // This isn't the end of the notecard.
llSay(0, "Line #" + (string)lineCounter + ": " + data);
lineCounter++; // Shorthand for lineCounter += 1;
curReadId = llGetNotecardLine(notecardName, lineCounter);
} else { // Reached end of notecard.
// Do stuff that's supposed to happen after reading the notecard here.
}
}
}
}


Hope this helps!
==Chris
Bobby Dayton
Test Pilot for Airfix
Join date: 15 Nov 2003
Posts: 206
01-17-2005 09:17
Thanks Chris, that explains a lot. I was not able to post actual code as I was at work.
However now at home I can post the whole example I was trying to use and getting the error on the first two lines.

CODE

string notecardName = "My Notecard";
integer lineCounter;
key dataRequestID;

default
{
state_entry()
{
llSay(0, "Ready. Click to start.");
}
touch_start(integer num_detected)
{
state readNotecard;
}
}

state readNotecard
{
state_entry()
{
lineCounter = 0;
dataRequestID = llGetNotecardLine(notecardName, lineCounter);
}
dataserver(key queryid, string data)
{
//Check to make sure this is the request we are making.
//Remember that when data comes back from the dataserver,
//it goes to *all* scripts in your prim.
//So you have to make sure this is the data you want, and
//not data coming from some other script.
if (dataRequestID)
{
//If we haven't reached the end of the file
//Display the incoming data, then request the next line #
if (data != EOF)
{
dataRequestID = llGetNotecardLine(notecardName, lineCounter);
lineCounter += 1;
llSay(0, "Line #" + (string)lineCounter + ": " + data);
}
else
{
state default;
}
}
}
}


I am still interested in why it had the error. I thought it was lack of EOF.