Ahoy Matey, ships are working

Ahoy Matey, ships are working

Postby roguan on Mon Oct 04, 2010 3:04 pm

Okeedokee. Ships. A great UO Demo feature (read bug).

Here's how to get them working.

If you want the solution, skip down a ways. I'm going to describe the problem.

A ship is a multi. Multis in the decompiled demo can be found in the rundir/multi.txt.q file. This actually lists the components of the multi with the locations, and what scripts are attached to each component.

The idea is, when the multi (or boat) is loaded, the script for each appropriate piece is loaded. In the following image, it should be clear that 5 scripts should be loaded into the boat multi, but are not.

Image

This is, in short, why boats don't work.

We need to modify two scripts to make boats work.
shipdeed.m.q
shipplank.m.q

In shipdeed.m.q, after the include, and before the first declared function (Q5SF), insert the following:
Code: Select all
function void attachScriptToComponent(object user, object shipComponent)
{
  if(getName(shipComponent) == "a tiller man")
  {
    attachScript(shipComponent, "shiptillerman");
  }
  if(getName(shipComponent) == "a hatch")
  {
    attachScript(shipComponent, "shiphold");
  }
  if(getName(shipComponent) == "a mast")
  {
    attachScript(shipComponent, "shipdecay");
  }
  if(getObjType(shipComponent) == 0x3EB1)
  {
    attachScript(shipComponent, "shipplank");
    attachScript(shipComponent, "shipleftplank");
  }
  if(getObjType(shipComponent) == 0x3EB2)
  {
    attachScript(shipComponent, "shipplank");
    attachScript(shipComponent, "shiprightplank");
  }
  return();
}




Now, further down in shipdeed.m.q, about halfway, in the function "targetloc":
After the line that reads "object Q5AO = Q5SD(Q5SR, place);"
And before the line that reads "if(Q5AO == NULL())"
Add the following snippet:
Code: Select all
  list objectsNearShip;
  getObjectsInRange(objectsNearShip, place, 0x0A);
  integer numObjects;
  numObjects = numInList(objectsNearShip);
  integer objectCounter;
  for(objectCounter = 0x00; objectCounter < numObjects; objectCounter ++)
  {   
    if(getMultiSlaveId(objectsNearShip[objectCounter]) == Q5AO)
    {
      attachScriptToComponent(user, objectsNearShip[objectCounter]);
    }
  }


One more change. Open up shipplank.m.q. In the function Q5SA:
Find the line that reads "setZ(Q5CP, getZ(Q5CP) + getSurfaceHeight(Q5IB));"
And change that line so it reads "setZ(Q5CP, getZ(Q5CP) + getSurfaceHeight(Q5IB) + 0x04);"
That is, you are adding 4 to the Z height of your player when you teleport TO the gang plank on double-click.

There is one bug left to find and that is why you can't walk after moving the boat, although you are on the same Z height as before the boat moved..

Regardless, these changes allow you to board boats, lock them, unlock them, issue commands to the tillerman, dock the boats, undock the boats, use the keys, see the age of the ship, (probably) rename the ship... etc...
roguan
 
Posts: 17
Joined: Tue Sep 07, 2010 1:57 pm


Re: Ahoy Matey, ships are working

Postby Derrick on Mon Oct 04, 2010 3:26 pm

Nice.

I wonder if the root of this is a templates problem or if the item scripts for these objects should have included these scripts.

There are some similar troubles with walking on multi seen in some of the houses, for example the theif small house will not allow you to enter the steps. Related?
Derrick
Site Admin
 
Posts: 250
Joined: Tue Jun 17, 2008 2:33 pm


Re: Ahoy Matey, ships are working

Postby roguan on Mon Oct 04, 2010 4:30 pm

I think the root is actually in the demo.exe how the scripts are loaded and attached to the planks, hatches, and tillermans at runtime through the multi.txt.q file.

More to come regarding houses. Probably related.
roguan
 
Posts: 17
Joined: Tue Sep 07, 2010 1:57 pm


Re: Ahoy Matey, ships are working

Postby Batlin on Mon Oct 04, 2010 9:54 pm

Great job.

I've got two questions though.

In the Process Monitor I see : NAME INVALID. Was that before or after fixing the scripts? If before, why is the error NAME INVALID? Those script exists in the end, so why do they generate this error? Any idea?

In case of 0x3EB1 and 0x3EB2, why are you attaching the "shipplank" script? I'm asking because the left and rightplank scripts include the shipplank themselves.

Anyways, I'm still amazed by your work, as if you're an ex OSI employee :)
<Derrick> RunUO AI is kind of a functional prototype, which i have hacked into something resembling OSI behavior, but only by complitcating everything
Batlin
Site Admin
 
Posts: 306
Joined: Wed Apr 08, 2009 6:35 am


Re: Ahoy Matey, ships are working

Postby roguan on Tue Oct 05, 2010 5:53 am

Batlin wrote:In the Process Monitor I see : NAME INVALID. Was that before or after fixing the scripts? If before, why is the error NAME INVALID? Those script exists in the end, so why do they generate this error? Any idea?


This one befuddles me even now. I did some troubleshooting. For example, I renamed "shipdecay" in the multi.txt.q file to "shipdecayd" and the file being searched for showed up as "shipdecayd". This implies that the multi.txt.q is actually being used for multi creation. The next step was to eliminate the possibility that the path was invalid, maybe a DOS path? So, I changed my run directory to "rundir = c:\rundir"
Sure enough, procmon showed that, upon ship creation, "C:\rundir\scripts\shipdecay.m.q" was being loaded with NAME INVALID. Because this is basically the only time multis are loaded during runtime, I assume there is a special block of code in the .exe which takes care of loading these files. It could be that the function in the .exe is just wrong.

Batlin wrote:In case of 0x3EB1 and 0x3EB2, why are you attaching the "shipplank" script? I'm asking because the left and rightplank scripts include the shipplank themselves.


This is just a mistake, I think. I wasn't sure of the architecture. That is, if attaching shipleftplank calls creation() for both scripts, or only shipleftplank. shipplank does some extra stuff, such as registering the plank to "myhousedoors" which is necessary before key creation. I don't think it hurts anything.

Batlin wrote:Anyways, I'm still amazed by your work, as if you're an ex OSI employee :)

I hope you deem my coding skills a bit better than this ;)
roguan
 
Posts: 17
Joined: Tue Sep 07, 2010 1:57 pm


Re: Ahoy Matey, ships are working

Postby Kaivan on Thu Oct 07, 2010 12:17 pm

Looking at that first block of code where certain scripts are attached, I seem to recall a piece of code that is called when attempting to place a house that seems rather out of place. The piece of code is this function:

Code: Select all
void Q4WV(object Q5AO, location Q5CV)
{
  return();
}


If I recall correctly, this code call seems to be in exactly the right spot where you would want to begin attaching scripts to pieces of the house in order to actually enable a player to use the house. Given this, I would like to throw two questions out there:

1. Do you think that this empty function is where scripts are attached to the correct objects?

2. If you do think that function is where the scripts belong, do you think that a similar looking function with respect to input values should exist for ships as well?

Also, on a somewhat related subject, how likely do you think it is of us adding our own scripts into the demo? I've messed around with some scripts already and I've been able to get unreferenced scripts to work (namely the dyetub_god script) in the demo by modifying sdb.txt, and I was thinking that by adding the script name and any strings that are used in the script to sdb.txt we should be able to get the demo to load our own compiled scripts. Thoughts?
Kaivan
 
Posts: 13
Joined: Thu Apr 23, 2009 1:27 am


Re: Ahoy Matey, ships are working

Postby roguan on Thu Oct 07, 2010 1:21 pm

Kaivan wrote:Looking at that first block of code where certain scripts are attached, I seem to recall a piece of code that is called when attempting to place a house that seems rather out of place. The piece of code is this function:

Code: Select all
void Q4WV(object Q5AO, location Q5CV)
{
  return();
}


If I recall correctly, this code call seems to be in exactly the right spot where you would want to begin attaching scripts to pieces of the house in order to actually enable a player to use the house. Given this, I would like to throw two questions out there:

1. Do you think that this empty function is where scripts are attached to the correct objects?

2. If you do think that function is where the scripts belong, do you think that a similar looking function with respect to input values should exist for ships as well?


Hey Kaivan,
This function, Q4WV, is found in housedeed.m.q and, I believe serves as a stub simply.
If you look, for example, in housedeedthieftrain.m.q, the only function is Q4WV:

Code: Select all
// UO-C
include housedeed;

function void Q4WV(object Q5AO, location Q5CV)
{
  object Q63A;
  if(Q5AO != NULL())
  {
    setZ(Q5CV, getZ(Q5CV) + 0x07);
    setX(Q5CV, getX(Q5CV) - 0x02);
    setY(Q5CV, getY(Q5CV) + 0x01);
    Q63A = createGlobalObjectAt(0x1EC3, Q5CV);
    Q4X0(Q63A);
    setY(Q5CV, getY(Q5CV) - 0x03);
    setX(Q5CV, getX(Q5CV) + 0x03);
    Q63A = createGlobalObjectAt(0x1EC0, Q5CV);
    Q4X0(Q63A);
  }
  return();
}

This script creates two training dummies and attaches them to the house (Q5A0)

This function is being overloaded in a sort of Object Oriented way. This is the snippet from housedeed.m.q
Code: Select all
object Q5AO = Q4X5(Q65M, Q5CV); //Creates house multi Q5A0
  if(Q5AO == NULL())
  {
    string Q58D = Q592(Q5NG, "house", "valid terrain");
    barkTo(user, user, Q58D);
    return(Q5AO);
  }
  Q4WV(Q5AO, Q5CV); //Calls setup for specialized houses


So, if this empty function did not exist in housedeed.m.q , then the call to the function would not compile. Likewise, if the code from housedeedthieftrain.m.q was in housedeed.m.q instead, every house would come with thief training dummies.

All of the scripts which start with housedeed... (housedeedmiller, housedeedsmith, housedeedweaver...) contain Q4WV and use that function to create addons to the house.

Kaivan wrote:Also, on a somewhat related subject, how likely do you think it is of us adding our own scripts into the demo? I've messed around with some scripts already and I've been able to get unreferenced scripts to work (namely the dyetub_god script) in the demo by modifying sdb.txt, and I was thinking that by adding the script name and any strings that are used in the script to sdb.txt we should be able to get the demo to load our own compiled scripts. Thoughts?


I've done this, and I believe Derrick and Batlin have done this. I use a compiler created by Batlin which modifies the string database based on the changes you make in a script. This is basically what Batlin did with the gmcheat script, viewtopic.php?f=32&t=606

It's fun.
roguan
 
Posts: 17
Joined: Tue Sep 07, 2010 1:57 pm


Re: Ahoy Matey, ships are working

Postby Kaivan on Fri Oct 08, 2010 10:31 am

Ok, thank you for that information rougan. I hadn't done the due diligence on looking at that particular script, I just recall it from looking at the scripts for a short while. Thanks for the clarification :D

Also, thanks for the link to the gm script. I was aware that the compiler existed, but I hadn't done much with it in the past. I had just sort of realized that by playing around with sdb.txt you could get it to load unreferenced scripts, and apparently, you can get it to load custom scripts as indicated by the gm script. I guess I'll have to get my feet wet with this in the near future.
Kaivan
 
Posts: 13
Joined: Thu Apr 23, 2009 1:27 am



Return to UO Demo

Who is online

Users browsing this forum: No registered users and 1 guest