Page 1 of 1

Conflicts with Informal Questions code

Posted: Fri Nov 25, 2011 3:41 pm
by Bainespal
The code for Informal Questions on Hugo by Example would be useful in my project. I was just adding it to my source file, but some conflicts with the optional VERBSTUBS library came up.

The routines DoYes and DoNo are already defined in Verbstubs.h. Unfortunately, simply changing "routine" from the code on the website to "replace" doesn't work; it produces a bunch of compiler errors.

Here's the first error that appears in my compiler window when I try to "replace" the Verbstubs routines with the once from Informal Questions:

Code: Select all

D:\Users\Paul\IF\Hugo\Projects\Holiday\holiday.hug:279:  Error:  Syntax error:  doyes
D:\Users\Paul\IF\Hugo\Projects\Holiday\holiday.hug:279:  Error:  Not an object or routine:  doyes
Many other errors follow, because the Compiler has been thrown off. These errors do not appear when I have "routine DoYes" and "routine DoNo" instead of "replace" -- only two errors for the routines already having been defined come up.

I'm wondering if Verbstubs.h isn't replaceable, for some reason.

By the way, the Informal Questions code is great; I appreciate the effort in putting up on HxE.

Posted: Fri Nov 25, 2011 3:53 pm
by Roody_Yogurt
My first guess is that you have the "Informal questions" code before verbstubs.h is included. If it is after "#include verbstubs.h" in holiday.hug, "replace DoYes" and "replace DoNo" should work.

Posted: Fri Nov 25, 2011 3:58 pm
by Roody_Yogurt
The only other issue that I can think of is, a game that uses verbstub.g won't need the grammar at the top of the Informal Questions page:

Code: Select all

verb "yes","y"
	*					DoYes
verb "no"
	*					DoNo
I will be curious if the problem ends up being neither of these things.

Posted: Fri Nov 25, 2011 4:50 pm
by Bainespal
I don't have the line "#include verbstubs.h" in my code. Instead, my code has "#set VERBSTUBS" near the top of my source file, above where I've typed in the Informal Questions code.

I started by modifying the "shell.hug" file, so near the top of my code it says this:

Code: Select all

! Uncomment the following to use a precompiled version of the Hugo Library:
! #set PRECOMPILED_LIBRARY

! Uncomment the following to include the HugoFix Debugging Library:
#set DEBUG

! Uncomment the following to include verb stub routines:
#set VERBSTUBS

Posted: Fri Nov 25, 2011 5:05 pm
by Roody_Yogurt
verblib.g has this bit of code:

Code: Select all

#ifset VERBSTUBS
#include "verbstub.g"
#endif
hugolib.h has this:

Code: Select all

#ifset VERBSTUBS
#include "verbstub.h"
#endif
So, yeah, those files are included by setting "#set VERBSTUBS" and is why you can't have the "replace DoYes" before "#include hugolib.h". I guess it's unlikely that you are defining routines that far up in the source file, though.

If you need to, send the troublesome file to roodyyogurt at gmail.com.

Posted: Fri Nov 25, 2011 6:04 pm
by Bainespal
I had been defining verb routines directly under the verb grammar definitions. I rearranged the code, and now it works fine.

Thank you. For the Informal Questions code, as well.

Posted: Fri Nov 25, 2011 6:14 pm
by Roody_Yogurt
No problem. Learning where it's not ok to define things is not very clear. Only within the last handful of months have I realized that I could define globals, arrays, and (some) constants pretty much anywhere I wanted. Maybe this whole thing calls for a HxE page.

Also, glad to hear that somebody is using the Informal Questions code! It was one of those things where I thought it was very possible I'd be the only one who likes those kinds of things.

Posted: Fri Nov 25, 2011 9:44 pm
by Bainespal
Roody_Yogurt wrote:Also, glad to hear that somebody is using the Informal Questions code! It was one of those things where I thought it was very possible I'd be the only one who likes those kinds of things.
I originally decided to look up the code on HxE because I wanted the parser to ask the player a question in a certain game state to clarify what the player meant, taking advantage of the situation to insert some conventional parser sarcasm. But now that I've included the extension, I want to clean up some of my NPC interactions with it. In a couple cases, I used the cumbersome YesOrNo routine, which has a very artificial effect. I also think I can integrated it with my ASK/TELL conversation system to make dialogue a little more natural; I can Perform a DoYes/DoNo from TELLing.

Posted: Sat Nov 26, 2011 2:33 pm
by Roody_Yogurt
Of course, the same idea can be applied to things other than "YES" and "NO" answers in the game. Looking at HxE and my own files, I am reminded that I still haven't polished a library contribution I meant to add at some point. It's called "opportune.h", and it's basically a simplified version of "Informal Questions" (in fact, some of the IQ code has been left in there as someone might still want it).

The point of this library is for all of the times you want to have a 1 turn window open for somebody to do something. Of course, there are other ways to handle it, but the purpose of this method is to keep your code clean and easy to read.

The code so far:

Code: Select all


global current_opp

! A fuse so that each question is only answerable for one turn
! opp_window = short for "opportunity window"
! changed the name of the fuse so it'd sound more
! dual-purpose
fuse opp_window
{}
 
event opp_window
{
	if not self.tick
		current_opp = 0
}

!\    ! the old code in case someone wants any questions
! a question class so to help organize our questions
class Question
{}
 
question egress
{
	long_desc
		"Are you sure you're mentally and otherwise prepared to meet up with an egress?"
}

Started like:
NewQuestion(egress)
\!

routine NewQuestion(question)
{
	current_opp = question
	run question.long_desc
	Activate (opp_window, 2)
}

routine NewOpp(opportunity)
{
	current_opp = opportunity
	Activate (opp_window, 2)
}

class opp
{}

! some sample opportunities
opp busted
{}

opp takealook
{}
So, in my WIP, it is possible to have an object hit you in the face (I think I say "chin"). I set the "busted" opportunity, then in my chin object, I have this code:

Code: Select all

object chin "chin"
{
     article "your"
     noun "chin"
     part_of you
     long_desc
        {
	if current_opp = busted
		"Aw, it'll be okay."
	else
	"It is your chin."
	return true
	}
}
Now, after somebody does the chin-smashing action, if they look at their chin right away, they get the reassuring "Aw, it'll be okay."

So yeah, there are a lot of uses for something like this (I hope).

Posted: Sat Nov 26, 2011 7:49 pm
by Bainespal
I like that code!

I'm keeping track of sequences of interactions using a property called "room_state", which I've given to most of the rooms in the game. I increment room_state to reflect the current position in an interaction with an NPC or to keep track of changes that the PC has made on the environment. Its been working for me, but it gets messy and chaotic some times, especially when trying to account for alternate actions that shouldn't advance room_state to a value reserved for the sequence that actually moves the game forward.

I don't think this code could replace my room_state system, but it could make certain portions of interaction sequences that I've implemented much cleaner and easier to debug.

What if I wanted to make an "opp" that lasted for more than one turn? Maybe the NewOpp routine could be written with an additional local variable, allowing for the length of the fuse to be customized:

Code: Select all

routine NewOpp(opportunity, length)
{
   current_opp = opportunity
   Activate (opp_window, length)
}
Just an untested spur-of-the-moment thought.

Posted: Sat Nov 26, 2011 8:15 pm
by Roody_Yogurt
I haven't yet run into a situation where I'd need something like that. You could do something like this, though:

Code: Select all

routine NewOpp(opportunity)
{
	current_opp = opportunity
	Activate (opp_window, (2 + opportunity.extra_turns))
}

property extra_turns alias size ! just picked a random property to alias to

class opp
{}

opp busted
{
	extra_turns 1 ! would run for 2 turns total
}

Posted: Mon Nov 28, 2011 12:45 pm
by Roody_Yogurt
I did end up turning this whole thing into a library extension afterall, which you can find here.

It's always rough figuring out how much explanation I should put inside the file in comments, and how much I should put externally. As you can see, I opted mainly for the former this time around.

Posted: Sun Mar 04, 2012 7:46 pm
by Roody_Yogurt
Instead of working on my game, I've been cleaning up code on an older game (Baby Uncle New Year) so I can upload the source to Hugo By Example. When possible, I'm trying to delete messy code and replace them with library contribution inclusions. One such library contribution is opportune.h.

Anyhow, it turns out there were a couple big-ish bugs in it, so a new version has been uploaded.

Posted: Thu Oct 18, 2012 4:06 pm
by Roody_Yogurt
I recently update "opportune.h" to allow for multiple opportunities with varying lengths of time. It's called Multiopportune.h. In doing so, I realized that most of the things this could be applied to would be better off handled by regular fuses, so I reverted opportune.h to its original one-turn window.

So, in review: Multiopportune, bad. Fuses, good. Opportune, good.