LPMuds.net

Lib Discussion => Dead Souls Support => Topic started by: capo on February 18, 2008, 09:13:02 am

Title: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 09:13:02 am
As most of you know I have been wracking my brain, as limited as it is, to create a forging/crafting system that allows for the following:

Players to forge weapons and armor, in relation to their forging skill, the type of components and requisits needed to create the weapon and armor..

For instance a player with a level 3 forge skill, a hunk of iron, and the knowledge of swords can pump out an iron sword with an accuracy of say... 3.

I was also looking to create a menu driven system (which admittedly I will fill in after I get the daemon working right) that handles all of this.

Right now I am kind of stuck, I've been working on it for a couple of weeks and I was hoping that you all could help put me back on the right path.

This is what I have so far:

forge.c in /lib/daemon

Code: [Select]

#include <lib.h>
#include <save.h>
#include <privs.h>
#include "include/forge.h"

inherit LIB_DAEMON;

private mapping Forges = ([]);

static void create() {
    daemon::create();

    if( unguarded((: file_size(SAVE_FORGES __SAVE_EXTENSION__) :)) > 0 )
        unguarded((: restore_object(SAVE_FORGES) :));

    if (!Forges) Forges = ([]);
}

static private void validate() {
    if( !((int)master()->valid_apply(({ PRIV_ASSIST }))) )
        error("Illegal attempt to modify forge data");
}

string array GetForgeRequisites(string str){
    return Forges[str]->requisites;
}

string array GetForgeComponents(string str){
    return Forges[str]->components;
}

void AddForge(string file, int player) {
    class forge res;

    string forge, requisite, components, test_string;
    int x;

    res = new(class forge);
    res->requisites = ({});
    res->components = ({});
    validate();
    if( !file_exists(file) ) error("No such file: " + file);
    forge = last_string_element(file,"/");

    foreach(string line in explode(read_file(file),"\n")){
        test_string = first_string_element(line," ");
        if(!test_string || !sizeof(test_string)) test_string = line;

        switch(test_string) {

        case "REQUISITE":
            requisite = replace_string(line, "REQUISITE ", "");
            res->requisites += ({requisite});
            break;

        case "COMPONENT":
            component = replace_string(line, "COMPONENT ", "");
            res->components += ({component});
            break;

        case "FORGE":
            forge = replace_string(line, "FORGE ", "");
            if( Forges[forge] ) error(forge+": Forge item already exists");
            break;

        default:
            break;
        }
    }

    Forges[forge] = res;
    save_object(SAVE_FORGES);
}

void RemoveForge(string forge) {
    validate();
    map_delete(Forges, forge);
    if(!Forges[forge])
        save_object(SAVE_FORGES);
}


This produces the following errors:

Quote
> update forge
/daemon/forge.c line 15: Undefined variable 'SAVE_FORGES'
   
/daemon/forge.c line 15: syntax error
   
/daemon/forge.c line 18: Illegal LHS
   
/daemon/forge.c line 18: syntax error
   
/daemon/forge.c line 40: Illegal LHS
   
/daemon/forge.c line 40: syntax error
   
---
2008.02.18-09.10
*Error in loading object '/daemon/forge'
Object: /secure/sefun/sefun at /secure/sefun/load_object.c:14

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 138
'load_object' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
'CATCH' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
Trace written to /log/catch


Here is a shell, that at least guides through the menu... for the forge verb:

Code: [Select]
#include <lib.h>
#include <daemons.h>
#include <position.h>
#include <privs.h>
#include <config.h>

inherit LIB_DAEMON;
inherit LIB_VERB;

string process_input( string str, string from );
int MainWeaponMenu();
int MainArmorMenu();
int sword();

static void create()
{
    verb::create();
    SetVerb("forge");
    SetRules("","STR");
    SetErrorMessage("Syntax: forge <%^BOLD%^%^RED%^armor%^RESET%^> or (%^BOLD%^%^CYAN%^weapon%^RESET%^)");
    SetHelp("Syntax: forge <%^BOLD%^%^RED%^armor%^RESET%^> or (%^BOLD%^%^CYAN%^weapon%^RESET%^)\n"
      "This command allows you to forge weapons and armor\n\n");
}

mixed can_forge()
{
  return "forge <%^BOLD%^%^RED%^armor%^RESET%^> or (%^BOLD%^%^CYAN%^weapon%^RESET%^)\n";
}

mixed can_forge_str(string str)
{
    int pos = this_player()->GetPosition();
    if( (int)this_player()->GetParalyzed() ) {
        return "You cannot move!";
    }
    if( pos == POSITION_SITTING || pos == POSITION_LYING &&
      !RACES_D->GetLimblessCombatRace(this_player()->GetRace()) ){
        return "You cannot teach in that position!";
    }
    if(!str || str == "" || str != "weapon" || str != "armor")
           {
     write("forge <%^BOLD%^%^RED%^armor%^RESET%^> or (%^BOLD%^%^CYAN%^weapon%^RESET%^)\n");
     return 1;
       }
    return 1;
}

mixed do_forge_str(string str)
{
    switch( str ) {
      case "armor" :
        MainArmorMenu();
        break;
      case "weapon" :
        MainWeaponMenu();
        break;
      default :
        GetHelp( "" );
    }
    return 1;
}

string process_input( string str, string from )
{
    switch (str)
      {
    case "q" :
    case "x" :
        switch( from ) {
          case "sword" : sword(); break;
          case "MainWeaponMenu":
          case "MainArmorMenu":
            write("You abort the forging process.\n");
            return " ";
        }
        break;
    case "y" : write("You abort the forging process.\n");return " ";
    default :
        write("'"+ str +"' is not a valid menu option.\n");
        call_other( this_object(), from );
      }
    return "(Menu fun finished.)";
    }

varargs mixed MainWeaponMenu(string str) {
    string tmp;
tmp =  "\t-------------------------------------------------------\n";
    tmp += "\t-You know how to forge the following types of weapon: -\n";
    tmp += "\t-------------------------------------------------------\n";
    tmp += "\n\t          sword                   \n";
    this_player()->eventPrint(tmp, "foo");

    input_to( (: process_input :), 0, "MainWeaponMenu" );
    return 1;
}

varargs mixed MainArmorMenu(string str) {
    string tmp;
tmp =  "\t------------------------------------------------------\n";
    tmp += "\t-You know how to forge the following types of armor: -\n";
    tmp += "\t------------------------------------------------------\n";
    tmp += "\n\t          helmets, platemail, gee wiz               \n";
    this_player()->eventPrint(tmp, "foo");

    input_to( (: process_input :), 0, "MainWeaponMenu" );
    return 1;
}

static int sword(string str) {
   string tmp;
   object thing;
   thing = new("/domains/foo/silver_sword.c");
   thing->eventMove(this_player());
   this_player()->eventPrint(tmp, "foo");
 
   input_to( (: process_input :), 0, "MainWeaponMenu" );
    return 1;
 }
   

 string GetHelp(string str) {
    return ("Syntax: <forge>\n\n");
}



Again... I appreciate all the help you all offer, I really do.  Thanks!
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 09:52:34 am
As an aside, I was attempting to make a template of each forgeable item that had the following:

Item name: Steel Sword
Component: steel ore
Requisit: forge level 3
Title: Re: Forge Daemon/Verb... assistance needed
Post by: detah on February 18, 2008, 09:54:36 am
Lets debug from the top.
I see several errors in this segment:
Code: [Select]
if( unguarded((: file_size(SAVE_FORGES __SAVE_EXTENSION__) :)) > 0 )
        unguarded((: restore_object(SAVE_FORGES) :));

1) file_size takes 1 arg. you have 2. Did you mean to call that arg SAVE_FORGES_SAVE_EXTENSION_ ? If so, that would be legal. But I dont see your forge.h so I dont know what you have for defs.
2) unguarded takes a function only as an arg. I think it will puke if it tries to find the numeric equivalent of 'unguarded()>0'. I recommend the following:
Code: [Select]
if(file_size(SAVE_FORGES)) >0 {
    unguarded(stuff)
}
3) Im not sure that you need an unguarded here at all. It all depends on how you have your variables saved in the daemon. You might want to handle all that on the item side? Then here you just need to check if any variables have been set.

I assume SAVE_FORGES is a pathname/filename to a .o file? Are variables only written to this file is they contain some value? I guess I do not understand what SAVE_FORGES looks like. That is important in determining how to access the info there. If SAVE_FORGES is a .c which has SetMaterials()="steel", etc in it, then your file_size fun doesnt make any sense. OTOH, if its a .o file, then you will need something (on the level of a playerfile.o) then you will still never have an empty file, which means the above file_size check is pretty pointless. Just not sure where you want to go with this.
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 18, 2008, 09:56:33 am
Quote
/daemon/forge.c line 15: Undefined variable 'SAVE_FORGES'

Edit /secure/include/save.h and add the SAVE_FORGES define to it, then:

update /secure/daemon/master.c

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 11:23:13 am

This is my forge.h file...

Code: [Select]
#ifndef l_forge_h
#define l_forge_h

class forge {
    string name;
    string *requisites;
}

#endif /* l_forge_h */
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 11:25:08 am

Great, one step forward... one step back.. Crat's update lead me to these errors in forge.c in /lib/daemon after updating the save.h file to reflect the correct directory where the templates will be stored.

The errors now:

Quote
> update forge
/daemon/forge.c: File not found.
> dchat :rubs his head
<dchat> Capo rubs his head
> update forge
/daemon/forge.c line 29: No class in scope has no member 'components'
   
/daemon/forge.c line 40: Class 'forge' has no member 'components'
   
/daemon/forge.c line 40: Bad assignment ( unknown vs array ).
   
/daemon/forge.c line 57: Undefined variable 'component'
   
/daemon/forge.c line 57: Illegal lvalue
   
/daemon/forge.c line 58: Class 'forge' has no member 'components'
   
---
2008.02.18-11.23
*Error in loading object '/daemon/forge'
Object: /secure/sefun/sefun at /secure/sefun/load_object.c:14

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 138
'load_object' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
'CATCH' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
Trace written to /log/catch
/daemon/forge.c line 29: No class in scope has no member 'components'
   
/daemon/forge.c line 40: Class 'forge' has no member 'components'
   
/daemon/forge.c line 40: Bad assignment ( unknown vs array ).
   
/daemon/forge.c line 57: Undefined variable 'component'
   
/daemon/forge.c line 57: Illegal lvalue
   
/daemon/forge.c line 58: Class 'forge' has no member 'components'
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 18, 2008, 11:35:12 am
I am in the process of removing the class data type from
Dead Souls. It is confusing and intentionally limited. I
suggest you use mappings instead, for complex data
types with explicit index handles.

See: help mappings

And also: http://dead-souls.net/ds-creator-faq.html#2.51

If you're determined to use classes, though, the Lima lib
has some docs on them: http://dead-souls.net/code/libs/lima-1.0b5/lib/help/wizard/coding/classes

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 01:12:08 pm
Giving mappings a try I have this now:

Code: [Select]
#include <lib.h>
#include <save.h>
#include <privs.h>
#include "include/forge.h"

inherit LIB_DAEMON;

private mapping Forges = ([]);

static void create() {
    daemon::create();

    if( unguarded((: file_size(SAVE_FORGES __SAVE_EXTENSION__) :)) > 0 )
        unguarded((: restore_object(SAVE_FORGES) :));

    if (!Forges) Forges = ([]);
}

static private void validate() {
    if( !((int)master()->valid_apply(({ PRIV_ASSIST }))) )
        error("Illegal attempt to modify forge data");
}

string array GetForgeRequirements(string str){
    return Forges[str]->requirements;
}

string array GetForgeComponents(string str){
    return Forges[str]->components;
}

void AddForge(string file, int player) {
   
    string forge, requirements, components, test_string;
    int x, y, z;

    mapping Forges = ([requirements:y, components:z]);
   
    validate();
    if( !file_exists(file) ) error("No such file: " + file);
    forge = last_string_element(file,"/");

    foreach(string line in explode(read_file(file),"\n")){
        test_string = first_string_element(line," ");
        if(!test_string || !sizeof(test_string)) test_string = line;

        switch(test_string) {

        case "REQUIREMENT":
            requirement = replace_string(line, "REQUIREMENT ", "");
            return Forges["requirements"];
            break;

        case "COMPONENT":
            component = replace_string(line, "COMPONENT ", "");
            return Forges["components"];
            break;

        case "FORGE":
            forge = replace_string(line, "FORGE ", "");
            if( Forges[forge] ) error(forge+": Forge item already exists");
            break;

        default:
            break;
        }
    }

    save_object(SAVE_FORGES);
}

void RemoveForge(string forge) {
    validate();
    map_delete(Forges, forge);
    if(!Forges[forge])
        save_object(SAVE_FORGES);
}

With these bugs:


 update forge
/daemon/forge.c line 26: No class in scope has no member 'requirements'
   
/daemon/forge.c line 30: No class in scope has no member 'components'
   
---
2008.02.18-13.11
*Error in loading object '/daemon/forge'
Object: /secure/sefun/sefun at /secure/sefun/load_object.c:14

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 138
'load_object' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
'CATCH' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
Trace written to /log/catch
/daemon/forge.c line 26: No class in scope has no member 'requirements'
   
/daemon/forge.c line 30: No class in scope has no member 'components'
   
---
2008.02.18-13.11
*Error in loading object '/daemon/forge'
Object: /secure/cmds/creators/update at line 151

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 151
'CATCH' at /secure/cmds/creators/update at line 151
Trace written to /log/catch
/daemon/forge: Error in update
*Error in loading object '/daemon/forge'
Title: Re: Forge Daemon/Verb... assistance needed
Post by: quixadhal on February 18, 2008, 02:00:23 pm
I am in the process of removing the class data type from
Dead Souls. It is confusing and intentionally limited.

Aren't classes supported at the driver level?  Of course, if you remove the mudlib support for them the driver functions will just never be called.

You might also take a peek at the LDMUD driver, as it supports structs as an LPC data type.  That's really what most of us want to use them as anyways.

DGD has something called an LWO (Lightweight Object) which is also similar, although it gets treated a little differently and play into their statedump/persistence system.
Title: Re: Forge Daemon/Verb... assistance needed
Post by: wodan on February 18, 2008, 02:24:41 pm
I am in the process of removing the class data type from
Dead Souls. It is confusing and intentionally limited. I
suggest you use mappings instead, for complex data
types with explicit index handles.

See: help mappings

And also: http://dead-souls.net/ds-creator-faq.html#2.51

If you're determined to use classes, though, the Lima lib
has some docs on them: http://dead-souls.net/code/libs/lima-1.0b5/lib/help/wizard/coding/classes

-Crat

So you're giving up some type safety and speed for ehm, what?

Wodan.
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 18, 2008, 02:34:25 pm
Quote
Aren't classes supported at the driver level?

They are. I'm not removing driver support for them. I am converting classes,
as I run into them, into mappings in the lib.


Quote
So you're giving up some type safety and speed for ehm, what?

For preference, really. I'm not arguing anything about classes
being inferior in any *technical* way. Rather, my experience with them
is that they serve to obscure code, endifficult troubleshooting, and
add yet another meaning to a word already quite overloaded with them.

I don't like them and they get in my way, so the advantage is that
I'm happier, not that the lib is somehow more efficient without them.

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 03:49:34 pm

Hmm... Interesting.  Any thoughts on how I messed this up?
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 18, 2008, 06:16:39 pm
Quote
Hmm... Interesting.  Any thoughts on how I messed this up?

Code: [Select]
#ifndef l_forge_h
#define l_forge_h

class forge {
    string name;
    string *requisites;
}

#endif /* l_forge_h */

Quote
/daemon/forge.c line 26: No class in scope has no member 'requirements'
   
/daemon/forge.c line 30: No class in scope has no member 'components'

It looks like maybe you're trying to use elements in the
class that the class doesn't support.

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 08:00:18 pm

Updated forge.h to:

Code: [Select]
#ifndef l_forge_h
#define l_forge_h

mapping forge {
    string name;
    string *requirements;
    string *components
}

#endif /* l_forge_h */


I now get:

Quote
> update forge
/daemon/include/forge.h line 4: syntax error
   
---
2008.02.18-19.59
*Error in loading object '/daemon/forge'
Object: /secure/sefun/sefun at /secure/sefun/load_object.c:14

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 138
'load_object' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
'CATCH' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
Trace written to /log/catch
/daemon/include/forge.h line 4: syntax error
   
---
2008.02.18-19.59
*Error in loading object '/daemon/forge'
Object: /secure/cmds/creators/update at line 151

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 151
'CATCH' at /secure/cmds/creators/update at line 151
Trace written to /log/catch
/daemon/forge: Error in update
*Error in loading object '/daemon/forge'

>
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 18, 2008, 08:09:31 pm
Code: [Select]
#ifndef l_forge_h
#define l_forge_h

mapping forge {
    string name;
    string *requirements;
    string *components
}

#endif /* l_forge_h */

This is the way to define a class. However, you're
using the keyword mapping, instead. Mappings
are not defined in the same manner as classes.

Note also you're missing a semicolon.

-Crat

Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 18, 2008, 09:09:11 pm
I noticed the missing semi colon and replaced it, I forgot to update that here.. sorry.

What is the proper way to define mappings in this .h file?
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 18, 2008, 09:43:32 pm
I'm not sure you gain much by defining it in an .h file.

I'd keep it in the body of the .c file.

For how to use mappings, see: help mappings

And also: http://dead-souls.net/ds-creator-faq.html#2.51

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 19, 2008, 05:13:18 pm

Hmm.  So confused!
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 19, 2008, 05:26:58 pm
It's because jenny's variables get saved, but
ExternalDesc is a function for her, and so
it winds up getting set to 0 whenever she
is cloned. It's a fairly unusual situation. Most
npc's don't save state.

It'll be fixed in the next release. ExternalDesc in
/lib/events/look.c will be static.

Thanks for the heads up!

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 19, 2008, 05:28:14 pm
Erm...I should get around to fixing that edit thing, huh.

The correct reply was this:

:(

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 19, 2008, 07:40:34 pm

Hah.  I was going to say, that response made me even more confused.

I feel as if I properly defined the mapping in the .c file, do I need anything at all in the .h file?  Do I even really need it?

Ugh.
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 20, 2008, 08:22:00 am
Quote
Hmm.  So confused!

I'm not really a fan of debugging someone's entire
file to get it to work, but in this case it's easier than
pointing out the problems piecemeal, since that
would take another couple of weeks.

Code: [Select]
#include <lib.h>
#include <save.h>
#include <privs.h>

#ifndef SAVE_FORGES
#define SAVE_FORGES DIR_SECURE_SAVE "/forges"
#endif

inherit LIB_DAEMON;

/* This is NOT an example of how to make a forge daemon.
 * This is an example of how to initialize a mapping
 * such that it does not error and such that it
 * makes some logical sense.
 *
 * I don't know exactly how you're visualizing the data for
 * your forges, or how they're supposed to work. I'm setting up
 * a sample mapping here that assumes you'll be storing the
 * data in the form of "what are the components for finished
 * products?" and "how much of those components are required?"
 * Here you see that a knife requires 50 steel, 10 wood, and 5 leather.
 * The units are just to illustrate quantity handling, I have no
 * idea (nor really do I want to know) the nature of your amounts.
 *
 * Therefore a query for "knife" in GetForgeRequirements() would return this:
 * ([ "steel" : 50, "wood" : 10, "leather" : 5 ])
 *
 * Internally to the object, that mapping above lives here:
 * Forges["requirements"]["knife"]
 *
 * Another way to write it is:
 * Forges["requirements"]["knife"] = ([ "steel" : 50, "wood" : 10, "leather" : 5 ]);
 *
 * I don't understand the idea behind the components element, but
 * I'm including it here since your original data set includes it.
 *
 */

private mapping Forges = ([
  "requirements" : ([ "knife" : ([ "steel" : 50, "wood" : 10, "leather" : 5 ]) ]),
  "components" : ({ "steel", "iron", "bronze", "copper", "wood", "leather" }),
]);

static void create() {
    daemon::create();

    if( unguarded((: file_size(SAVE_FORGES __SAVE_EXTENSION__) :)) > 0 )
        unguarded((: restore_object(SAVE_FORGES) :));

    if (!Forges) Forges = ([]);
}

static private void validate() {
    if( !((int)master()->valid_apply(({ PRIV_ASSIST }))) )
        error("Illegal attempt to modify forge data");
}

mixed GetForgeRequirements(string str){
    if(!Forges["requirements"][str]) return 0;
    return Forges["requirements"][str];
}

string array GetForgeComponents(string str){
    return Forges["components"];
}

/* I haven't really messed with the function below because I
 * don't want to get involved in how you're parsing
 * your config files. You'll eventually need to work out
 * string manipulation, it might as well be now.
 * I've only poked at it so it doesn't error.
 *
 * You'll need to go over the logic of it because it's
 * not doing what I think you want it to. For example,
 * it doesn't seem to be actually setting anything
 * in the Forges mapping.
 */

void AddForge(string file, int player) {
    string forge, requirements, components, test_string;
    int x, y, z;

    validate();
    if( !file_exists(file) ) error("No such file: " + file);
    forge = last_string_element(file,"/");

    foreach(string line in explode(read_file(file),"\n")){
        test_string = first_string_element(line," ");
        if(!test_string || !sizeof(test_string)) test_string = line;

        switch(test_string) {

        case "REQUIREMENT":
            requirements = replace_string(line, "REQUIREMENT ", "");
            return Forges["requirements"];
            break;

        case "COMPONENT":
            components = replace_string(line, "COMPONENT ", "");
            return Forges["components"];
            break;

        case "FORGE":
            forge = replace_string(line, "FORGE ", "");
            if( Forges[forge] ) error(forge+": Forge item already exists");
            break;

        default:
            break;
        }
    }

    save_object(SAVE_FORGES);
}

void RemoveForge(string forge) {
    validate();
    map_delete(Forges, forge);
    if(!Forges[forge])
        save_object(SAVE_FORGES);
}

You know I like you and want to encourage you, etc, so
I won't beat around the bush with excessive courtesy.

The main problem is that you're leaping directly into relatively
complicated data manipulation with very little groundwork
leading up to it. It's like skipping multiplication in school
and heading straight for algebra.

That's fine if you're up to the challenge of brute forcing
stuff into your brain without doing the homework first, but
chances are you're going to wind up with code that
doesn't update and you have no idea what it would look
like in a working form, because you don't understand
the principles behind how the working structure would operate.

I'm presenting your code to you in a form that updates, not
because it fixes your problem, but because it at least now
provides you a stepping stone toward understanding how
mappings work in relation to your forge idea.

At this point, you need to study why it does what it does, figure
out why the Set function doesn't change anything, and
make it so that it does.

-Crat

Title: Re: Forge Daemon/Verb... assistance needed
Post by: detah on February 20, 2008, 03:09:59 pm
file_size(SAVE_FORGES __SAVE_EXTENSION__)
Why does this work? Does it?
man file_size is pretty clear that it takes only one arg.
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 20, 2008, 04:22:04 pm
Quote
file_size(SAVE_FORGES __SAVE_EXTENSION__)
Why does this work? Does it?
man file_size is pretty clear that it takes only one arg.

It's one string argument.

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 20, 2008, 05:08:21 pm
Thanks Crat, I appreciate your input..  my confusion is, in part, that I wasnt sure how to use a daemon to do this.  I do understand, in part, that the data for each object that can be forged needs to be stored somewhere setting that up.

I was, and am, a little confused on where ALL of the data for say "knife" should be stored.  Should it be stored in the verb with a shell in the daemon? Is it better to store it all in the daemon?

Does that make sense too?
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 20, 2008, 05:13:59 pm
Quote
Is it better to store it all in the daemon?


That's really the point of a daemon...a central repository of
mud-wide data and arbiter of related calculations.

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 20, 2008, 05:35:26 pm

That was my feeling, but I've had a lot of different advice from people and in many ways I've gotten all backwards on how to do this.

Thanks for the answer, I work a lot better seeing an actual example than I do talking theory or application.  I never did very well, in any field, the other way.   :-\
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 20, 2008, 05:43:56 pm

Now that I have an understanding of what to put in the daemon, this is what I am thinking...

In the daemon I'll store everything for each object that can be forged....then in the forge skill/verb I can create an ifcheck that checks for the requisit associated skill.. ie.. forging swords for swords AND then tie in sword to sword.c from /lib/domains/standard/weap...

Is that the best way to go?
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 20, 2008, 06:20:10 pm
Quote
In the daemon I'll store everything for each object that can be forged....then in the forge skill/verb I can create an ifcheck that checks for the requisit associated skill.. ie.. forging swords for swords AND then tie in sword to sword.c from /lib/domains/standard/weap...

Is that the best way to go?

Assuming I understand you, yes, it sounds like you've got the right idea there.

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: capo on February 22, 2008, 03:30:00 pm
Ok, I undstand what's going on here.. however.. in trying to make two different types of forgeable weapons I came across this syntax error and I cant quite beat it:

Code: [Select]
#include <lib.h>
#include <save.h>
#include <privs.h>

#ifndef SAVE_FORGES
#define SAVE_FORGES DIR_SECURE_SAVE "/forges"
#endif

inherit LIB_DAEMON;

/*
 * Therefore a query for "knife" in GetForgeRequirements() would return this:
 * ([ "steel" : 50, "wood" : 10, "leather" : 5 ])
 *
 * Internally to the object, that mapping above lives here:
 * Forges["requirements"]["knife"]
 *
 * Another way to write it is:
 * Forges["requirements"]["knife"] = ([ "steel" : 50, "wood" : 10, "leather" : 5 ]);
 *
 */

private mapping Forges = ([
  "components" : ([ "silver sword" : ([ "steel" : 10, "silver" : 5 ])]),
                 ([ "emerald dagger" : ([ "steel" : 5, "emerald" : 1 ])])


                 ]);

static void create() {
    daemon::create();

    if( unguarded((: file_size(SAVE_FORGES __SAVE_EXTENSION__) :)) > 0 )
        unguarded((: restore_object(SAVE_FORGES) :));

    if (!Forges) Forges = ([]);
}

static private void validate() {
    if( !((int)master()->valid_apply(({ PRIV_ASSIST }))) )
        error("Illegal attempt to modify forge data");
}

mixed GetForgeComponents(string str){
    if(!Forges["components"][str]) return 0;
    return Forges["components"][str];
}




Quote
> update forge.c
/daemon/forge.c line 28: syntax error
   
/daemon/forge.c line 36: Illegal LHS
   
/daemon/forge.c line 36: syntax error
   
---
2008.02.22-15.27
*Error in loading object '/daemon/forge'
Object: /secure/sefun/sefun at /secure/sefun/load_object.c:14

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 138
'load_object' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
'CATCH' at /secure/sefun/sefun at /secure/sefun/load_object.c:14
Trace written to /log/catch
/daemon/forge.c line 28: syntax error
   
/daemon/forge.c line 36: Illegal LHS
   
/daemon/forge.c line 36: syntax error
   
---
2008.02.22-15.27
*Error in loading object '/daemon/forge'
Object: /secure/cmds/creators/update at line 151

'<fake>' at /secure/save/creators/c/capo (/<driver>) at line 0
'cmdAll' at /secure/save/creators/c/capo (/lib/command.c) at line 162
'cmd' at /secure/cmds/creators/update at line 110
'eventUpdate' at /secure/cmds/creators/update at line 151
'CATCH' at /secure/cmds/creators/update at line 151
Trace written to /log/catch
/daemon/forge: Error in update
*Error in loading object '/daemon/forge'
Title: Re: Forge Daemon/Verb... assistance needed
Post by: cratylus on February 22, 2008, 03:39:00 pm
Code: [Select]
private mapping Forges = ([
  "components" : ([ "silver sword" : ([ "steel" : 10, "silver" : 5 ]) ]),
                 ([ "emerald dagger" : ([ "steel" : 5, "emerald" : 1 ]) ])
 ]);

Mappings require both a key and a value per element. Here you have this as a
first element:

Code: [Select]
"components" : ([ "silver sword" : ([ "steel" : 10, "silver" : 5 ]) ])
But the next element is:

Code: [Select]
([ "emerald dagger" : ([ "steel" : 5, "emerald" : 1 ]) ])
Where's the key for it?

You probably meant to have this as your mapping:

Code: [Select]
private mapping Forges = ([
  "components" : ([
                  "silver sword" : ([ "steel" : 10, "silver" : 5 ]) ,
                  "emerald dagger" : ([ "steel" : 5, "emerald" : 1  ])
         ]) /*end  components */
 ]); /*end Forges */

-Crat
Title: Re: Forge Daemon/Verb... assistance needed
Post by: detah on February 22, 2008, 03:54:17 pm
*del the solo key components. It serves no purpose.
*house the various traits for each item inside of one mapping as a value. Then you can add as many things to it as you wish

Code: [Select]
private mapping Forges =
([ item1: ([silver: 10, req: 8]), item2: ([gold: 10, req: 17]) ])
Title: Re: Forge Daemon/Verb... assistance needed
Post by: detah on February 22, 2008, 03:58:36 pm
*shoot*
I wanted to mention.
Make sure that each key is unique. If you have two silver swords, name them each something distinct. Latter keys:values will overwrite earlier keys with the same name.