Mail: [email protected] Phone: +1(424)231-4091

Creating Settings Page

Creating a module often requires creating a section where how the module works can be configured. NexoPOS 4.x comes with a settings API that aims to ease the creation of the settings for developers. Before proceeding with this guide, we believe you already know how to :

The settings API interacts with the Options API, but additionally, validates, stores, and fetches your settings for you.

# Creating A Settings Page Class

Every settings page must extend `App\Services\SettingsPage`. Within your module, you'll store your settings page on a folder named "Settings", "Forms" or any folder name that makes sense for you, as no convention has been decided for that at the moment. Typically here is how the class must looks like.

Here, we define the property "form" which is required as that's what we'll use to create our settings page.

A settings page usually consists of tabs and fields. So the structure of a settings page should include tabs having fields within. Here is a sample settings page.

[
    'tabs'  =>  [
        'general'   =>  [
            'fields'    =>  [], // <= an array of fields
            'label'     =>  __( 'My FooBar General Settings' )
        ],
    ]
]

The "$form" property should be assigned this multidimensional array that defines "tabs". The "tabs" entry has a key-value pair array where the key is a unique identifier for the tab. In our previous example, the unique identifier for our tab is "general", but it can be anything you want. Each tab has a "fields" that consist of an array of fields and a "label" entry, that is what the humans will see.

Additionally, the settings form supports "$labels" which is an array having: title and description as attributes, and an "identifier" that must be a unique identifier for the settings field. This is mostly used on the frontend for interacting with the settings page.

# Structure of a field

Most fields have a common way of being defined. Usually a field looks like this.

[
    'type'  =>  'text',
    'label' =>  __( 'My Field Name' ),
    'description'   =>  __( 'My field description' ),
    'validation'    =>  'required',
    'name'          =>  'my_field_name'
]

These are however not all the parameters that can be used for a field. So some field such as "select" requires more attributes that are explained on this list of supported attributes.

type

Every field definition must have a "type" that defines the type of the field. Supported types are :

  • text
  • textarea
  • number
  • select
  • media
  • switch
  • multiselect
  • checkbox
  • ckeditor
  • datetimepicker
  • password
  • email
  • tel
  • date

label

The label is what the user will see as the field name. This should be descriptive of what the field is about.

description

The description provides more hints on the field. This can be useful to explains how the field will be used.

validation

This is used to enforce validation for a field. All Laravel's validation strings a supported (on the backend). Validations based on an object are ignored on the frontend as well as validation that performs a check on the database.

name

This is the name of the field but also the name of the option. In case you create a settings page for your module, you should prefix all of your fields' names. For example, NexoPOS uses "ns_" as a prefix for all the settings created for the system, so it's a reserved prefix. However, you should note that your name value should never use a dot as a separator. For example "my.custom.field.name", is not allowed.

value

This is the desired value that needs to be displayed on the field. Usually, you'll need to use the options here to fetch the option from the database using "ns()->option->get( '[your field name]' )", where [your field name] must be replaced by the field name as you have defined above.

options

This is only used for "switch", "select" and "multiselect" field types. It consists of an array having an array as an option. Typically, it is designed like this.

[
    [
        'label' =>  __( 'Choose Me' ),
        'value' =>  'choose_me'
    ], [
        'label' =>  __( 'No choose me' ),
        'value' =>  'no_choose_me'
    ]
]

This can be shortened using an array helpers :

Using kvTojsOptions

Using toJsOptions

This should be used while converting a collection into options for a field. This function accepts as first parameters the collection, and as second an array which first index should be the "value" and second index should be the "label".

If you would like to have a look at a complete settings page, you can check this file from the source code of NexoPOS 4.x.

# Render A Vue Component

If you would like to completely change the layout of the settings and create a custom settings page that is actually a Vue component, it's also possible. To get started, you'll have to inject your Vue component. Once it's done, while defining your form, instead of providing a "fields" attribute, you'll provide the "component" attribute.

Let's suppose you've injected your view component as what follows :

You can see that our component registered name is "myCustomComponent". That is the name we'll use on the "component" attribute like this.

[
    'tabs'  =>  [
        'general'   =>  [
            'component'    =>  'myCustomComponent', // here
            'label'     =>  __( 'My FooBar General Settings' )
        ],
    ]
]

When the page will be rendered, NexoPOS will try to resolve the dynamic component and replace the body of the settings with that.

# How To Register A Settings Page

Once a settings page has been created as a class, it needs to be registered. This will ensure NexoPOS 4.x is aware of the setting page and able to handle it. In order to register a settings page, we need to register a filter for that within the module ServiceProvider "register" method like so :

Note here "my-foo-bar-settings" is the "identifier" on the settings page. In case the identifier doesn't match your modifiers, you must return the $class that is passed as a first parameter. Note also that the methods"addFilter" has here 4 arguments :

  • The hook identifier
  • The callback
  • The priority
  • The number of arguments for the callback (in our example 2).

# How To Render A Settings Page

Now it's time to render a settings page. What you'll need is to create a route that points to a controller method where we'll use the class we have created so far.