# Ipelets written in Lua

Ipelets written in Lua have access to the entire Ipe user interface, and can in principle do anything that Ipe can do.

An ipelet is a Lua script that is placed in Ipe's ipelet directory.

The script needs to define three global variables, namely `label`, `about`, and either `run` or `methods` (or both).

- `label` is a string containing the label (that is, the name) of the ipelet. It is shown in the Ipelet menu.

- `about` is a string containing an 'about' or copyright notice for the ipelet. Ipe displays this in the "About the ipelets" box.

- `run` is used if the ipelet contains only a single method. When the ipelet is invoked, the function `run` is called by Lua.

- `methods` is used if the ipelet contains more than one method. It is an array with an entry for each method. Each entry is a table with keys `label` (defining the label of the method) and `run` (a Lua function that will be called by Ipe to execute this method). If an entry does not have a `run` field, then the global `run` method is called instead.

If an ipelet defines no `label` variable, then the ipelet is not added to the Ipelet menu. Such ipelets can be used to customize Ipe.

When Ipe invokes an ipelet, the Lua method is called with two arguments: the first argument model is the active Ipe user interface, the second is the index of the method being invoked.

The "global" environment of the ipelet is a private environment for this ipelet only, so there is no need to fear polluting the global namespace - you can use names here freely. The commonly used names have been imported from Ipe's global namespace already, and you can access any others you may need through `_G`.

It is important that the ipelet does not directly modify the document. This would mess up the undo stack, and could cause Ipe to crash on undo or redo. Instead, to modify the document the ipelet needs to create an undo item `t` and call `model:register(t)`.

If all the ipelet does is to create a new object `obj`, then it can simply call

    model:creation("create new object", obj)

The following are some useful methods and data structures:

    model.doc     -- the document
    model.pno     -- current page number
    model.vno     -- current view number

    model:page()  -- returns current page

    model:register(t) -- register undo item and execute its redo method
    model:creation("label", obj)  -- register undo item for object creation

    model.attributes   -- attributes currently set in user interface
    model.snap         -- currently active snap settings

Look at the existing ipelets for inspiration.