diff --git a/esm/defs.d b/esm/defs.d index 7d96aeb2a..9c4327d1a 100644 --- a/esm/defs.d +++ b/esm/defs.d @@ -25,6 +25,7 @@ module esm.defs; public import std.string; public import monster.util.string; +import monster.monster; /* * Types and definitions related to parsing esm and esp files @@ -135,3 +136,50 @@ align(1) struct ENAMstruct static assert(ENAMstruct.sizeof==24); } + +// Common stuff for all the load* structs +template LoadTT(T) +{ + LoadState state; + char[] name, id; + + MonsterObject *proto; + static MonsterClass mc; + + void makeProto(char[] clsName = null) + { + // Use the template type name as the Monster class name if none + // is specified. + if(clsName == "") + { + clsName = typeid(T).toString; + + // Remove the module name + int i = clsName.rfind('.'); + if(i != -1) + clsName = clsName[i+1..$]; + } + + // Set up a prototype object + if(mc is null) + mc = MonsterClass.find(clsName); + proto = mc.createObject(); + + proto.setString8("id", id); + proto.setString8("name", name); + + static if(is(typeof(data.weight) == float)) + { + proto.setFloat("weight", data.weight); + proto.setInt("value", data.value); + } + + static if(is(typeof(data.enchant)==int)) + proto.setInt("enchant", data.enchant); + + static if(is(typeof(data.health)==int)) + proto.setInt("health", data.health); + } +} + +template LoadT() { mixin LoadTT!(typeof(*this)); } diff --git a/esm/imports.d b/esm/imports.d index b6cfd1d22..69f1d33dc 100644 --- a/esm/imports.d +++ b/esm/imports.d @@ -1,8 +1,8 @@ module esm.imports; /* This is a file that imports common modules used by the load*.d - record loaders. It is really a cut down version of the start of - records.d. + record loaders. It is really a cut down version of what used to be + the start of records.d. This file MUST NOT import records.d - directly or indirectly - because that will trigger a nice three page long list of template @@ -41,4 +41,7 @@ import esm.loadscpt; import esm.loadsoun; import esm.loadspel; import esm.loadench; + +import monster.monster; } + diff --git a/esm/loadacti.d b/esm/loadacti.d index 85ca7b6de..7dd731678 100644 --- a/esm/loadacti.d +++ b/esm/loadacti.d @@ -36,10 +36,8 @@ import esm.imports; struct Activator { - char[] id; - LoadState state; + mixin LoadT!(); - char[] name; Script *script; MeshIndex model; @@ -48,6 +46,8 @@ struct Activator model = getMesh(); name = getHNString("FNAM"); script = getHNOPtr!(Script)("SCRI", scripts); + + makeProto(); }} } ListID!(Activator) activators; diff --git a/esm/loadalch.d b/esm/loadalch.d index 3e6006fc1..150f0de72 100644 --- a/esm/loadalch.d +++ b/esm/loadalch.d @@ -30,9 +30,6 @@ import esm.imports; struct Potion { - char[] id; - LoadState state; - align(1) struct ALDTstruct { float weight; @@ -43,7 +40,7 @@ struct Potion ALDTstruct data; - char[] name; + mixin LoadT!(); MeshIndex model; IconIndex icon; @@ -69,6 +66,8 @@ struct Potion readHExact(&effects.array[$-1], effects.array[$-1].sizeof); } + makeProto(); + proto.setInt("autoCalc", data.autoCalc); }} } ListID!(Potion) potions; diff --git a/esm/loadappa.d b/esm/loadappa.d index 3d8a5ac1d..f2ee09217 100644 --- a/esm/loadappa.d +++ b/esm/loadappa.d @@ -30,9 +30,6 @@ import esm.imports; struct Apparatus { - char[] id, name; - LoadState state; - enum AppaType : int { MortarPestle = 0, @@ -50,6 +47,8 @@ struct Apparatus static assert(AADTstruct.sizeof == 16); } + mixin LoadT!(); + AADTstruct data; MeshIndex model; IconIndex icon; @@ -62,6 +61,11 @@ struct Apparatus readHNExact(&data, data.sizeof, "AADT"); script = getHNOPtr!(Script)("SCRI", scripts); icon = getIcon(); + + makeProto(); + + proto.setFloat("quality", data.quality); + proto.setInt("type", data.type); }} } ListID!(Apparatus) appas; diff --git a/esm/loadarmo.d b/esm/loadarmo.d index 6e0bfee22..fe1d74d63 100644 --- a/esm/loadarmo.d +++ b/esm/loadarmo.d @@ -116,8 +116,7 @@ struct Armor AODTstruct data; - char[] name, id; - LoadState state; + mixin LoadT!(); PartReferenceList parts; @@ -138,6 +137,11 @@ struct Armor parts.load(); enchant = getHNOPtr!(Enchantment)("ENAM", enchants); + + makeProto(); + + proto.setInt("type", data.type); + proto.setInt("armor", data.armor); }} } ListID!(Armor) armors; diff --git a/esm/loadbody.d b/esm/loadbody.d index 24f2b3019..2673d4fbd 100644 --- a/esm/loadbody.d +++ b/esm/loadbody.d @@ -74,8 +74,8 @@ struct BodyPart BYDTstruct data; - char[] name, id; - LoadState state; + mixin LoadT; + MeshIndex model; void load() @@ -83,6 +83,9 @@ struct BodyPart model = getMesh(); name = getHNString("FNAM"); readHNExact(&data, data.sizeof, "BYDT"); + + // don't need to run makeProto here yet, no BodyPart monster + // class. }} } diff --git a/esm/loadbook.d b/esm/loadbook.d index 822ed3e76..4d040b8c5 100644 --- a/esm/loadbook.d +++ b/esm/loadbook.d @@ -44,7 +44,9 @@ struct Book IconIndex icon; Script *script; Enchantment *enchant; - char[] name, text, id; + + mixin LoadT; + char[] text; LoadState state; @@ -57,6 +59,11 @@ struct Book icon = getIcon(); text = getHNOString("TEXT"); enchant = getHNOPtr!(Enchantment)("ENAM", enchants); + + makeProto(); + + proto.setInt("skillID", data.skillID); + proto.setBool("isScroll", data.isScroll != 0); }} } ListID!(Book) books; diff --git a/esm/loadbsgn.d b/esm/loadbsgn.d index a8c865d5b..f02637882 100644 --- a/esm/loadbsgn.d +++ b/esm/loadbsgn.d @@ -30,9 +30,9 @@ import esm.imports; struct BirthSign { - LoadState state; + char[] description; - char[] id, name, description; + mixin LoadT; TextureIndex texture; @@ -48,6 +48,8 @@ struct BirthSign description = getHNOString("DESC"); powers.load(); + + // No monster class equivalent yet }} } ListID!(BirthSign) birthSigns; diff --git a/esm/loadclas.d b/esm/loadclas.d index 2009c7860..5e2fe7749 100644 --- a/esm/loadclas.d +++ b/esm/loadclas.d @@ -72,8 +72,9 @@ struct Class static assert(CLDTstruct.sizeof == 60); } - LoadState state; - char[] id, name, description; + mixin LoadT; + + char[] description; CLDTstruct data; void load() @@ -85,6 +86,8 @@ struct Class esFile.fail("Unknown bool value"); description = esFile.getHNOString("DESC"); + + // no makeProto yet } } ListID!(Class) classes; diff --git a/esm/loadclot.d b/esm/loadclot.d index e70ffdecb..6a953025f 100644 --- a/esm/loadclot.d +++ b/esm/loadclot.d @@ -50,15 +50,15 @@ struct Clothing Type type; float weight; short value; - short enchantPoints; + short enchant; static assert(CTDTstruct.sizeof == 12); } CTDTstruct data; - LoadState state; - char[] id, name; + mixin LoadT; + PartReferenceList parts; MeshIndex model; @@ -78,6 +78,9 @@ struct Clothing parts.load(); enchant = getHNOPtr!(Enchantment)("ENAM", enchants); + + makeProto(); + proto.setInt("type", data.type); }} } ListID!(Clothing) clothes; diff --git a/esm/loadcont.d b/esm/loadcont.d index a088b0807..d372db90e 100644 --- a/esm/loadcont.d +++ b/esm/loadcont.d @@ -69,9 +69,6 @@ struct Container Unknown = 8 } - char[] id, name; - LoadState state; - MeshIndex model; Script *script; @@ -79,6 +76,8 @@ struct Container Flags flags; InventoryList inventory; + mixin LoadT!(); + void load() {with(esFile){ model = getMesh(); @@ -100,6 +99,9 @@ struct Container script = getHNOPtr!(Script)("SCRI", scripts); inventory.load(); + + makeProto(); + proto.setFloat("weight", weight); }} } diff --git a/esm/loaddoor.d b/esm/loaddoor.d index 22bc806a1..65f21c02a 100644 --- a/esm/loaddoor.d +++ b/esm/loaddoor.d @@ -30,13 +30,12 @@ import esm.imports; struct Door { - LoadState state; - char[] id, name; - MeshIndex model; Script *script; Sound* openSound, closeSound; + mixin LoadT!(); + void load() {with(esFile){ model = getMesh(); @@ -44,6 +43,8 @@ struct Door script = getHNOPtr!(Script)("SCRI", scripts); openSound = getHNOPtr!(Sound)("SNAM", sounds); closeSound = getHNOPtr!(Sound)("ANAM", sounds); + + makeProto(); }} } ListID!(Door) doors; // Break on through diff --git a/esm/loadligh.d b/esm/loadligh.d index 4ff11c8d2..ce583a9b3 100644 --- a/esm/loadligh.d +++ b/esm/loadligh.d @@ -29,9 +29,6 @@ import esm.imports; struct Light { - char[] id; - LoadState state; - enum Flags : uint { Dynamic = 0x001, @@ -59,14 +56,14 @@ struct Light LHDTstruct data; - char[] name; - - MeshIndex model; - IconIndex icon; + mixin LoadT!(); Sound* sound; Script* script; + MeshIndex model; + IconIndex icon; + void load() {with(esFile){ model = getMesh(); @@ -77,6 +74,14 @@ struct Light script = getHNOPtr!(Script)("SCRI", scripts); sound = getHNOPtr!(Sound)("SNAM", sounds); + + // Stash the data in the Monster object prototype + + makeProto(); + + proto.setUint("flags", data.flags); + proto.setFloat("lifetime", data.time); + proto.setInt("radius", data.radius); }} } ListID!(Light) lights; diff --git a/esm/loadweap.d b/esm/loadweap.d index 744f928c2..46d46f473 100644 --- a/esm/loadweap.d +++ b/esm/loadweap.d @@ -71,8 +71,7 @@ struct Weapon WPDTstruct data; - LoadState state; - char[] name, id; + mixin LoadT!(); MeshIndex model; IconIndex icon; @@ -87,6 +86,11 @@ struct Weapon script = getHNOPtr!(Script)("SCRI", scripts); icon = getOIcon(); enchant = getHNOPtr!(Enchantment)("ENAM", enchants); + + makeProto(); + + proto.setFloat("speed", data.speed); + proto.setFloat("reach", data.reach); }} } ListID!(Weapon) weapons; diff --git a/monster/compiler/assembler.d b/monster/compiler/assembler.d index e21cc4cbc..e3fc00dc1 100644 --- a/monster/compiler/assembler.d +++ b/monster/compiler/assembler.d @@ -393,6 +393,8 @@ struct Assembler addi(i); } + void cloneObj() { cmd(BC.Clone); } + // Copy the topmost int on the stack void dup() { cmd(BC.Dup); } diff --git a/monster/compiler/bytecode.d b/monster/compiler/bytecode.d index 037fcb55e..09c6f64a2 100644 --- a/monster/compiler/bytecode.d +++ b/monster/compiler/bytecode.d @@ -69,6 +69,12 @@ enum BC // giving the class index (in the file lookup // table) + Clone, // Clones an object - create a new object of + // the same class, then copy variable values + // and state from the old object to the + // new. Replaces the object index on the stack + // with the new index. + Jump, // Jump to given position (int) JumpZ, // Pop a value, if it is zero then jump to diff --git a/monster/compiler/expression.d b/monster/compiler/expression.d index a239d90ab..5791dd6f5 100644 --- a/monster/compiler/expression.d +++ b/monster/compiler/expression.d @@ -1004,6 +1004,7 @@ class VariableExpr : MemberExpression isNext(toks, TT.Identifier) || isNext(toks, TT.Singleton) || isNext(toks, TT.State) || + isNext(toks, TT.Clone) || isNext(toks, TT.Const); } @@ -1146,6 +1147,9 @@ class VariableExpr : MemberExpression if(name.type == TT.Const) fail("Cannot use const as a variable", name.loc); + if(name.type == TT.Clone) + fail("Cannot use clone as a variable", name.loc); + // These are special cases that work both as properties // (object.state) and as non-member variables (state=...) inside // class functions / state code. Since we already handle them diff --git a/monster/compiler/properties.d b/monster/compiler/properties.d index f5ede0ec9..2db8fa86f 100644 --- a/monster/compiler/properties.d +++ b/monster/compiler/properties.d @@ -159,6 +159,8 @@ class ClassProperties : SimplePropertyScope { super("ClassProperties"); + insert("clone", "owner", { tasm.cloneObj(); }); + // For testing purposes. Makes 'singleton' an alias for the // first variable in the data segment. This might actually not // be far from how the end result would work - the singleton diff --git a/monster/vm/mclass.d b/monster/vm/mclass.d index 4c3e5e4f9..277b882da 100644 --- a/monster/vm/mclass.d +++ b/monster/vm/mclass.d @@ -537,6 +537,41 @@ final class MonsterClass return top; } + // Create a new object based on an existing object + MonsterObject* createClone(MonsterObject *source) + { + requireCompile(); + + assert(source.tree.length == tree.length); + assert(source.thread.topObj == source, + "createClone can only clone the topmost object"); + + // Create a new thread + CodeThread *trd = threads.getNew(); + + // Loop through the objects in the source tree, and clone each + // of them + MonsterObject* otree[] = source.tree.dup; + foreach(i, ref obj; otree) + { + obj = obj.cls.getClone(obj); + obj.tree = otree[0..i+1]; + obj.thread = trd; + } + + // Pick out the top object + MonsterObject* top = otree[$-1]; + assert(top !is null); + + // Initialize the thread + trd.initialize(top); + + // Set the same state + trd.setState(source.thread.getState(), null); + + return top; + } + // Free an object and its thread void deleteObject(MonsterObject *obj) { @@ -757,6 +792,46 @@ final class MonsterClass // Point to the static data segment obj.sdata = sdata; + obj.extra = null; + + // Call the custom native constructor + if(constType != FuncType.Native) + { + fstack.pushNConst(obj); + if(constType == FuncType.NativeDDel) + dg_const(); + else if(constType == FuncType.NativeDFunc) + fn_const(); + else if(constType == FuncType.NativeCFunc) + c_const(); + fstack.pop(); + } + + return obj; + } + + // Clone an existing object + MonsterObject *getClone(MonsterObject *source) + { + assert(source !is null); + assert(source.cls is this); + assert(source.data.length == data.length); + assert(source.sdata.ptr is sdata.ptr); + + requireCompile(); + + MonsterObject *obj = objects.getNew(); + + // Set the class + obj.cls = this; + + // TODO: Fix memory management here too. + // Copy the data segment from the source + obj.data = source.data.dup; + + // Point to the static data segment + obj.sdata = sdata; + obj.extra = null; // Call the custom native constructor if(constType != FuncType.Native) diff --git a/monster/vm/mobject.d b/monster/vm/mobject.d index 51d6bde6d..2a98bbc72 100644 --- a/monster/vm/mobject.d +++ b/monster/vm/mobject.d @@ -69,6 +69,7 @@ struct MonsterObject // the MonsterClass. MonsterObject* tree[]; + /******************************************************* * * * Functions for object handling * @@ -98,6 +99,16 @@ struct MonsterObject cls.deleteObject(this); } + // Create a clone of this object. Note that this will always clone + // and return the top object (thread.topObj), regardless of which + // object in the list it is called on. In other words, the class + // mo.cls is not always the same as mo.clone().cls. + MonsterObject *clone() + { + auto t = thread.topObj; + return t.cls.createClone(t); + } + /******************************************************* * * * Casting / polymorphism functions * diff --git a/monster/vm/vm.d b/monster/vm/vm.d index 6c5e49011..f82e1c11c 100644 --- a/monster/vm/vm.d +++ b/monster/vm/vm.d @@ -480,6 +480,10 @@ struct CodeThread .createObject()); break; + case BC.Clone: + stack.pushObject(stack.popObject().clone()); + break; + case BC.Jump: code.jump(code.getInt); break; diff --git a/mscripts/gameobjects/activator.mn b/mscripts/gameobjects/activator.mn new file mode 100644 index 000000000..06290635c --- /dev/null +++ b/mscripts/gameobjects/activator.mn @@ -0,0 +1,25 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (activator.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +class Activator : GameObject; + diff --git a/mscripts/gameobjects/apparatus.mn b/mscripts/gameobjects/apparatus.mn new file mode 100644 index 000000000..1cfa677af --- /dev/null +++ b/mscripts/gameobjects/apparatus.mn @@ -0,0 +1,28 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (apparatus.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +// Covers all alchemy apparatus - mortars, retorts, etc +class Apparatus : InventoryItem; + +float quality; +int type; diff --git a/mscripts/gameobjects/armor.mn b/mscripts/gameobjects/armor.mn new file mode 100644 index 000000000..0719a4533 --- /dev/null +++ b/mscripts/gameobjects/armor.mn @@ -0,0 +1,28 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (armor.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +// Covers all weapons and projectile weapons you can carry (like +// arrows and throwable items.) +class Armor : Repairable; + +int type, armor; diff --git a/mscripts/gameobjects/book.mn b/mscripts/gameobjects/book.mn new file mode 100644 index 000000000..13133d3bb --- /dev/null +++ b/mscripts/gameobjects/book.mn @@ -0,0 +1,28 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (book.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +class Book : EnchantItem; + +bool isScroll; + +int skillID; // Skill that is enhanced by reading this book, if any diff --git a/mscripts/gameobjects/clothing.mn b/mscripts/gameobjects/clothing.mn new file mode 100644 index 000000000..08bd4bba0 --- /dev/null +++ b/mscripts/gameobjects/clothing.mn @@ -0,0 +1,27 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (clothing.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +// All items that can be repaired (weapons and armor) +class Clothing : EnchantItem; + +int type; diff --git a/mscripts/gameobjects/container.mn b/mscripts/gameobjects/container.mn new file mode 100644 index 000000000..10bad5ee7 --- /dev/null +++ b/mscripts/gameobjects/container.mn @@ -0,0 +1,26 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (container.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +class Container : LockedObject; + +float weight; // Not sure, might be max total weight allowed? diff --git a/mscripts/gameobjects/equipitem.mn b/mscripts/gameobjects/enchantitem.mn similarity index 83% rename from mscripts/gameobjects/equipitem.mn rename to mscripts/gameobjects/enchantitem.mn index 0565e3eae..bc92262cd 100644 --- a/mscripts/gameobjects/equipitem.mn +++ b/mscripts/gameobjects/enchantitem.mn @@ -4,7 +4,7 @@ Email: < korslund@gmail.com > WWW: http://openmw.snaptoad.com/ - This file (equipitem.mn) is part of the OpenMW package. + This file (enchantitem.mn) is part of the OpenMW package. OpenMW is distributed as free software: you can redistribute it and/or modify it under the terms of the GNU General Public License @@ -21,7 +21,7 @@ */ -// Anything that can be equiped, like clothes, armor and weapons. -class EquipItem : InventoryItem; +// Items that can be enchanted +class EnchantItem : InventoryItem; int enchant; diff --git a/mscripts/gameobjects/gameobject.mn b/mscripts/gameobjects/gameobject.mn index 5122ac951..432aa59a0 100644 --- a/mscripts/gameobjects/gameobject.mn +++ b/mscripts/gameobjects/gameobject.mn @@ -40,6 +40,8 @@ float r1, r2, r3; float scale; +char[] name, id; + // Various variables that are currently unused. Most of the strings // will be replaced by object references at some point. diff --git a/mscripts/gameobjects/light.mn b/mscripts/gameobjects/light.mn index 924703c90..aa3f171b3 100644 --- a/mscripts/gameobjects/light.mn +++ b/mscripts/gameobjects/light.mn @@ -26,5 +26,6 @@ class Light : InventoryItem; // Time left in seconds (for carried lights) float lifetime; -// Is this a carryable light? -bool carry; +int radius; +uint flags; + diff --git a/mscripts/gameobjects/potion.mn b/mscripts/gameobjects/potion.mn new file mode 100644 index 000000000..5f0f4f02c --- /dev/null +++ b/mscripts/gameobjects/potion.mn @@ -0,0 +1,26 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (potion.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +class Potion : InventoryItem; + +int autoCalc; diff --git a/mscripts/gameobjects/repairable.mn b/mscripts/gameobjects/repairable.mn new file mode 100644 index 000000000..12a253226 --- /dev/null +++ b/mscripts/gameobjects/repairable.mn @@ -0,0 +1,27 @@ +/* + OpenMW - The completely unofficial reimplementation of Morrowind + Copyright (C) 2008 Nicolay Korslund + Email: < korslund@gmail.com > + WWW: http://openmw.snaptoad.com/ + + This file (repairable.mn) is part of the OpenMW package. + + OpenMW is distributed as free software: you can redistribute it + and/or modify it under the terms of the GNU General Public License + version 3, as published by the Free Software Foundation. + + This program is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + version 3 along with this program. If not, see + http://www.gnu.org/licenses/ . + + */ + +// All items that can be repaired (weapons and armor) +class Repairable : EnchantItem; + +int health; diff --git a/mscripts/gameobjects/weapon.mn b/mscripts/gameobjects/weapon.mn index 19da4455c..e21b31c57 100644 --- a/mscripts/gameobjects/weapon.mn +++ b/mscripts/gameobjects/weapon.mn @@ -21,11 +21,11 @@ */ -// Weapons (This is just an example, it's not used for anything yet.) -class Weapon : EquipItem; +// Covers all weapons and carry-able projectiles. +class Weapon : Repairable; float speed, reach; +// Not set yet. bool magical, silver; -bool isTwohanded; - +bool twoHanded; diff --git a/scene/celldata.d b/scene/celldata.d index 3de23504b..f60059b38 100644 --- a/scene/celldata.d +++ b/scene/celldata.d @@ -39,7 +39,8 @@ import sound.audio; import scene.player; -// Generic version of a "live" object +// Generic version of a "live" object. Do we even need this at all? +// No, I don't think so. struct GenLive(T) { // Instance of class GameObject or a derived class (depending on @@ -259,16 +260,13 @@ class CellData private: static - MonsterClass gameObjC, doorC, lightC, lockedC; + MonsterClass gameObjC; void setup() { if(gameObjC !is null) return; - gameObjC = new MonsterClass("GameObject"); - doorC = new MonsterClass("Door"); - lightC = new MonsterClass("Light"); - lockedC = new MonsterClass("LockedObject"); + gameObjC = MonsterClass.find("GameObject"); } void loadReferences() @@ -329,24 +327,20 @@ class CellData { LiveLight ls; ls.m = m; - ls.obj = lightC.createObject; + ls.obj = m.proto.clone(); mo = ls.obj; - mo.setFloat("lifetime", m.data.time); bool carry = (m.data.flags&Light.Flags.Carry) != 0; - mo.setBool("carry", carry); - if(carry) lights.insert(ls); else statLights.insert(ls); } - else if(Container *c = it.getContainer()) { LiveContainer ls; ls.m = c; - ls.obj = lockedC.createObject; + ls.obj = c.proto.clone(); mo = ls.obj; containers.insert(ls); container = true; @@ -356,7 +350,7 @@ class CellData { LiveDoor ls; ls.m = d; - ls.obj = doorC.createObject; + ls.obj = d.proto.clone(); mo = ls.obj; doors.insert(ls); door = true; @@ -416,7 +410,7 @@ class CellData { LiveWeapon ls; ls.m = m; - ls.obj = gameObjC.createObject; + ls.obj = m.proto.clone(); mo = ls.obj; weapons.insert(ls); }