docs/source/manuals/openmw-cs/tour.rst
A Tour through OpenMW CS: making a magic ring #############################################
In this first chapter we will create a mod that adds a new ring with a simple enchantment to the game. The ring will give its wearer a permanent Night Vision effect while being worn. You do not need previous Morrowind modding experience, but you should be familiar with the game itself. There will be no scripting necessary, we can achieve everything using just what the base game offers out of the box. Before continuing make sure that OpenMW is properly installed and playable.
Adding the ring to the game's records
In this first section we will define what our new ring is, what it looks like, and what it does. Getting it to work is the first step before we go further.
We will start by launching OpenMW CS, the location of the program depends on your operating system. You will be presented with a dialogue with three options: create a new game, create a new addon, edit a content file.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/opening-dialogue.png :alt: Opening dialogue with three option and setting button (the wrench)
The first option is for creating an entirely new game, that's not what we want. We want to edit an existing game, so choose the second option. When you save your addon you can use the third option to open it again.
You will be presented with another window where you get to choose the content to edit and the name of your project. Then we have to select at least the base game and optionally a number of other addons we want to depend on. The name of the project is arbitrary, it will be used to identify the addon later in the OpenMW launcher.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/new-project.png :alt: Creation dialogue for a new project, pick content modules and name
Choose Morrowind as your content file and enter Ring of Night Vision as the
name. We could also choose further content files as dependencies if we wanted
to, but for this mod the base game is enough.
Once the addon has been created you will be presented with a table. If you see a blank window rather than a table choose World → Objects from the menu.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/new-project.png :alt: The table showing all object records in the game.
Let's talk about the interface for a second. Every window in OpenMW CS has panels, these are often but not always tables. You can close a panel by clicking the small X on the title bar of the panel, or you can detach it by either dragging the title bar or clicking the icon with the two windows. A detached panel can be re-attached to a window by dragging it by the title bar on top of the window.
Now let's look at the panel itself: we have a filter text field, a very large table and a status bar. The filter will be very useful when we want to find an entry in the table, but for now it is irrelevant. The table you are looking at contains all objects in the game, these can be items, NPCs, creatures, whatever. Every object is an entry in that table, visible as a row. The columns of the table are the attributes of each object.
Morrowind uses something called a relational database for game data. If you are not familiar with the term, it means that every type of thing can be expressed as a table: there is a table for objects, a table for enchantments, a table for icons, one for meshes and so on. Properties of an entry must be simple values, like numbers or text strings. If we want a more complicated property we need to reference an entry from another table. There are a few exceptions to this though, some tables do have subtables. The effects of enchantments are one of those exceptions.
Enough talk, let's create the new ring now. Right-click anywhere in the objects
table, choose Add Record and the status bar will change into an input field.
We need to enter an ID (short for identifier) and pick the type. The
identifier is a unique name by which the ring can later be identified; I have
chosen ring_night_vision. For the type choose Clothing.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/add-record.png :alt: Enter the ID and type of the new ring
The table should jump right to our newly created record, if not read further below how to use filters to find a record by ID. Notice that the Modified column now shows that this record is new. Records can also be Base (unmodified), Modified and Deleted. The other fields are still empty since we created this record from nothing. We can double-click a table cell while holding Shift to edit it (this is a configurable shortcut), but there is a better way: right-click the row of our new record and chose Edit Record, a new panel will open.
We can right-click the row of our new record and select Edit Record, a new panel will open. Alternatively we can also define a configurable shortcut instead of using the context menu; the default is double-clicking while holding down the shift key.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/edit-record.png :alt: Edit the properties of the record in a separate panel
You can set the name, weight and coin value as you like, I chose Ring of Night Vision, 0.1 and 2500 respectively. Make sure you set the Clothing Type
to Ring. We could set the other properties manually as well, but unless you
have an exceptional memory for identifiers and never make typos that's not
feasible. What we are going to do instead is find the records we want in their
respective tables and assign them from there.
We will add an icon first. Open the Icons table the same way you opened the
Objects table: in the menu click Assets → Icons. If the window gets too
crowded remember that you can detach panels. The table is huge and not every
ring icon starts with :code:ring, so we have to use filters to find what we want.
Filters are a central element of OpenMW CS and a major departure from how the original Morrowind CS was used. In fact, filters are so important that they have their own table as well. We won't be going that far for now though. There are three types of filters: Project filters are part of the project and are stored in the project file, session filter are only valid until you exit the CS, and finally instant filter which are used only once and typed directly into the Filter field.
For this tutorial we will only use instant filters. We type the definition of
the filter directly into the filter field rather than the name of an existing
filter. To signify that we are using an instant filter the have to use ! as
the first character. Type the following into the field:
.. code::
!string("id", ".ring.")
A filter is defined by a number of queries which can be logically linked. For
now all that matters is that the string(<property>, <pattern>) query will check
whether <property> matches <pattern>. The pattern is a regular expression,
if you don't know about them you should learn their syntax. For now all that
matters is that . stands for any character and * stands for any amount,
even zero. In other words, we are looking for all entries which have an ID that
contains the word :code:ring somewhere in it. This is a pretty dumb pattern because
it will also match words like :code:ringmail, but it's good enough for now.
If you have typed the filter definition properly the text should change from red to black and our table will be narrowed down a lot. Browse for an icon you like and drag & drop its table row onto the Icon field of our new ring.
That's it, you have now assigned a reference to an entry in another table to the ring entry in the Objects table. Repeat the same process for the 3D model, you can find the Meshes table under Assets → Meshes.
Putting everything you have learned so far to practice we can add the final and
most important part to our new ring: the enchantment. You know enough to
perform the following steps without guidance: Open the Enchantments table
(Mechanics → Enchantments) and create a new entry with the ID Cats Eye.
Edit it so that it has Constant Effect enchantment type.
To add an effect to the enchantment right-click the Magic Effects table and
choose Add new row. You can edit the effects by right-clicking their table
cells. Set the effect to NightEye, range to Self, and both magnitudes to
50. The other properties are irrelevant.
Once you are done add the new enchantment to our ring. That's it, we now have a complete enchanted ring to play with. Let's take it for a test ride.
Launch OpenMW and in the launcher under Data Files check your addon. Load a game and open the console. We have only defined the ring, but we haven't placed any instance of it anywhere in the game world, so we have to create one. In the console type:
.. code::
player->AddItem "ring_night_vision" 1
The part in quotation marks is the ID of our ring, you have to adjust it if you chose a different ID. Exit the console and you should find a new ring in your inventory. Equip it and you will instantly receive the Night Vision effect for your character.
In this tutorial we have learned how to create a new addon, what tables are and how to create new records. We have also taken a very brief glimpse at the syntax of filters, a feature you will be using a lot when creating larger mods.
This mod is a pure addition, it does not change any of the existing records. However, if you want to actually present appealing content to the player rather than just offering abstract definitions you will have to change the game's content. In the next tutorial we will learn how to place the ring in the game world so the player can find it legitimately.
Adding the ring to the game's world
Now that we have defined the ring it is time add it to the game world so the player can find it legitimately. We will add the ring to a merchant, place it in a chest, and put it somewhere in plain sight. To this end we will have to actually modify the contents of the game.
The simplest way is probably to add it to the inventory of a shopkeeper. An obvious candidate is Arrille in Seyda Neen - he's quick to find in a new game and he's easy to find in the CS as his name comes early alphabetically.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/Ring_to_Arrille.png :alt: Putting the ring into Arrille's inventory
Open the CS and open the Objects table (World → Objects).
Scroll down to Arrille, or use a filter like :code:!string("ID","arrille").
Open another pane to edit him - either right click and select edit or use the shortcut (default is shift double-click). Scroll down to the inventory section and right click to add a new row. Type in the id of the ring (or find it in the object pane, and drag and drop). Set the number of rings for him to stock - with a negative number indicating that he will restock again to maintain that level.
However, it's an attractive item, so he will probably wear it rather than sell it. So set his stock level too high for him to wear them all (3 works, 2 might do).
Another possibility, again in Seyda Neen making it easy to access, would be for Fargoth to give it to the player in exchange for his healing ring.
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/Ring_to_Fargoth_1.png :alt: Editing Fargoth to give ring to player
Open the Topicinfo Table (Characters → Topic Infos). Use a filter :code:!string(Topic,ring)
and select the row with a response starting with :code:You found it!. Edit the record,
firstly by adding a bit more to the response, then by adding a line to the script
to give the ring to the player - the same as used earlier in the console
.. code::
player->AddItem "ring_night_vision" 1
.. figure:: https://gitlab.com/OpenMW/openmw-docs/raw/master/docs/source/manuals/openmw-cs/_static/images/chapter-1/Ring_to_Fargoth_2.png :alt: Editing Fargoth to give ring to player
For this example we will use the small chest intended for lockpick practice, located in the Census and Excise Office in Seyda Neen.
First we need the ID of the chest - this can be obtained either by clicking on it in the console in the game, or by applying a similar process in the CS -
World/Cells
Select Seyda Neen, Census and Excise Office
Right-click and select View
Use mouse wheel to zoom in/out, and mouse plus WASD keys to navigate
Click on the small chest
Either way, you should find the ID, which is :code:chest_small_02_lockprac.
Open the Objects table (World → Objects) and scroll down to find this item.
Alternatively use the Edit/Search facility, selecting ID rather than text,
enter lockprac into the search box, press Search,
which should return two rows, then select the Container one rather than the Instance
Right-click and Edit Record.
Right-click the Content section and select Add a row
Set the Item ID of the new row to be your new ring - simplest way is probably to open the Objects table if it's not already open, sort on the Modified column which should bring the ring, with its status of Added to the top, then drag and drop to the chest row.
Increase the Count to :code:1.
Save the addon, then test to ensure it works - e.g. start a new game and lockpick the chest.
Let's hide the Ring of Night vision in the cabin of the Ancient Shipwreck <https://en.uesp.net/wiki/Morrowind:Ancient_Shipwreck>_, a derelict vessel
southeast of Dagon Fel. Open the list of Cells (World → Cells) and find
:code:Ancient Shipwreck, Cabin.
This will open a visualization of the cabin. You can navigate around the scene just like you would when playing Morrowind. Use the WASD keys to move forward, backwards, and sideways. Click and drag with the left mouse button to change the direction you are looking. Navigate to the table in the cabin.
If you've closed the Objects table, reopen it via World → Objects. Navigate to your Ring of Night Vision (you can find it easily if you sort by the Modified column). Drag the ring from the Objects table onto the table in the Cell view.
Now let's move the ring to the precise location we want. Hover over the ring and click the middle mouse button. If you don't have a middle mouse button, you can select an alternative command by going to Edit → Preferences… (Windows, Linux) or OpenMW → Preferences… (macOS). Go to the Key Bindings section and choose Scene from the dropdown menu. Then click on the button for Primary Select and choose an alternative binding.
After you have switched to movement mode, you will see several arrows. Clicking and dragging them with the right mouse button will allow you to move the object in the direction you want.
If you'd like an easy way to test this, you can start OpenMW with the game arguments <https://wiki.openmw.org/index.php?title=Testing>_
:code:--start="Ancient Shipwreck, Cabin" --skip-menu. This will place you right in
the cell and allow you to pick up and equip the ring in order to check that it
works.
This is probably a suitable place to start talking about how navigation differs from TESCS in vanilla Morrowind.
There is advice in Scripting for Dummies, the definitive manual for Morrowind Scripting: "If you give your scripts a common tag, that will make it easier to jump between the different scripts of your project, e.g. start every script name with AA_Scriptname this will put them right at the beginning of the list and keep them neatly together."
This is valid for the rather poorer navigation facilities there, but it's not sensible for
the OpenMW CS. Some modders took it further, and started script names and object id with numbers,
typically :code:1, to bring the items even earlier in the default alphabetical sorts. In fact
the CS won't allow names/ids to start with numbers or to include :code:..
There are better options available:
Filtering, which isn't available at all in TESCS - put in a filter like
.. code::
!string("ID",".ring.")
to find all IDs which contain the string :code:ring
Sorting, which is available in some parts of TESCS, but not for scripts (other than script names being sorted in ascending order)- hence the recommendation Typically the Modified column is useful here - most items will have Base status, unchanged from the base game.
Added status will cover those items added in this addon.
Modified status will cover items from the base game which have been modified in this addon.
Click on the top of the column to toggle between ascending and descending order - thus between Added and Modified at the top. Or put your desired modified status into a filter then sort alphabetically on a different column.
Launch OpenMW and in the launcher under Data Files check your addon, if it's not already checked. Load a game and make your way to Seyda Neen - or start a new game.
Check whether Arrille has one (or more) for sale, and whether Fargoth give you one when you return his healing ring.