Select Field: Dynamic Options from Page Model Method

Is there anybody out there with an example of a page model method that returns valid options for the select field (https://getkirby.com/docs/reference/panel/fields/select#dynamic-options)?

$result = array();
// implement me...
array_push($result, ['value' => 0, 'text' => 'Nothing found']);
return $result;

This implementation yields the following error:

get_class() expects parameter 1 to be object, array given

Thanks!

1 Like

You need a flat array of key/value pairs:

Example

class AlbumPage extends Page
{
    public function cover()
    {
        return $this->content()->get('cover')->toFile() ?? $this->image();
    }
    public function options() {
        return ['single' => 'Single', 'repeat' => 'Repeat'];
    }
}

In blueprint:

fields:
  selectfield:
    type: select
    options: query
    query: page.options

Your array, however, returns an array of arrays

Array
(
    [0] => Array
        (
            [value] => 0
            [text] => Nothing found
        )

)

Thank you very much. I was looking way to far :upside_down_face:

Although, this looks correctly in the panel, it seems not to work as expected.

The options from you example translate in this JSON payload:

As you can see, textand value is identical.

That was finally the reason why I was experimenting with other constructs such as my proposed array and with Collection or Structure objects.

Hm :thinking:

@steirico have you found a solution for this? I am running into the same issue.

I’m not absolutely certain about my solution.

I think, I finally solved the problem by defining a custom route that calls the desired page method. Then I made the select field using that route as described in Dynamic API URLs.

Hope that helps.

Thx for sharing. Sounds like a weird workaround…that I am going to implement aswell :smile:

I had the same issue.
I got something like this working in Kirby 3.6. Maybe it will help someone.

In the PageModel:

public function myOptions() {
    return [
        new \Kirby\Toolkit\Obj(['value' => 'key1', 'text' => 'lorem']),
        new \Kirby\Toolkit\Obj(['value' => 'key2', 'text' => 'ipsum']),
    ];
}

In the blueprint:

exampleField:
    label: Lorem
    type: select
    options: query
    query:
        fetch: page.myOptions
        text: "{{ arrayItem.value.text() }}"
        value: "{{ arrayItem.value.value() }}"

– I bet there is a simpler way to do this, but it seems preferable to setting up a custom route.

BTW In my real world app, my PageModel function returned an array of complex PHP class instances. In that case I had to use different “templates” in the blueprint to get it to work. Something like this:

text: "{{ item.value.methodReturningLabel() }}"
value: "{{ item.value.methodReturningKey() }}"   

– so “item” rather than ”arrayItem”.