Panel Support Screen Hooks

1 views Markdown

The twenty-one placement points of the support screens: the ticket detail, the reply form, the list rows and the department forms.

Overview

The placement points of the support screens live here: every part of the ticket detail, the list rows and the department forms.

A few points on the ticket detail hand you a privilege flag. It is not a gate: the core disables its own buttons with it, but it does not stop your output. If you show something that needs the privilege, do the check yourself.

Reference

A badge or button in the ticket title

uiadmin.tickets_detail.header_actions
admin/tickets/detail the title area

Appears in the title row of the ticket detail. It suits a case number in another system or a shortcut of your own.

Parameters 1
$ticketarrayThe active ticket record.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_detail.header_actions', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

The top of the side column

uiadmin.ticket_detail.sidebar_top
admin/tickets/detail top of the side column

Appears in the side column of the ticket detail, above the first card.

Parameters 2
$ticketarrayThe active ticket record.
$opPrivboolWhether the viewer holds the operation privilege. ? This is information, not a gate: when false the core disables its own buttons but does not stop your output. If you show something that needs the privilege, check it yourself.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.sidebar_top', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Adding an operation to the side column

uiadmin.ticket_detail.sidebar_actions
admin/tickets/detail an operation box

Appears among the operation boxes in the side column. It puts a ticket operation of your own beside the built-in ones.

Parameters 2
$ticketarrayThe active ticket record.
$opPrivboolWhether the viewer holds the operation privilege. ? This is information, not a gate: when false the core disables its own buttons but does not stop your output. If you show something that needs the privilege, check it yourself.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.sidebar_actions', 10, function ($ticket, $opPriv) {
    // Yetki bilgisi kapi DEGIL: kendiniz sinayin.
    if (!$opPriv) return null;

    return '<div class="operation-box"><button onclick="acmeEscalate('
         . (int) ($ticket['id'] ?? 0) . ')">Acme</button></div>';
});

A row on the ticket details card

uiadmin.ticket_detail.details_card.meta
admin/tickets/detail the details card

Appears among the fields of the ticket details card. Add metadata of your own beside the core fields.

Parameters 1
$ticketarrayThe active ticket, with its mail source, department and reference in it.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.details_card.meta', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Above the conversation

uiadmin.ticket_detail.conversation.before
admin/tickets/detail above the conversation

Appears immediately above the reply thread. It suits context or a warning from another system.

Parameters 1
$ticketarrayThe active ticket record.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.conversation.before', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

The top of the reply form

uiadmin.ticket_detail.reply_form.top
admin/tickets/detail top of the reply form

Appears above the box staff write their reply in. It suits a warning that should be seen before writing.

Parameters 2
$ticketarrayThe active ticket record.
$opPrivboolWhether the viewer holds the operation privilege. ? This is information, not a gate: when false the core disables its own buttons but does not stop your output. If you show something that needs the privilege, check it yourself.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.reply_form.top', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

The reply form toolbar

uiadmin.ticket_detail.reply_form.toolbar
admin/tickets/detail the form toolbar

Appears in the toolbar of the reply form. Put your own insert or template button here.

Parameters 1
$ticketarrayThe active ticket record.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.reply_form.toolbar', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Below the reply editor

uiadmin.ticket_detail.reply_editor.after
admin/tickets/detail below the editor

Appears immediately below the text editor. It suits an extra option or a confirmation box before sending.

Parameters 1
$ticketarrayThe active ticket record.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.reply_editor.after', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Below the canned replies

uiadmin.ticket_detail.canned_replies.after
admin/tickets/detail the language is separate

Appears below the canned reply options. The place to add a template source of your own.

Parameters 2
$ticketarrayThe active ticket record.
$client_langstringThe active interface language. Canned replies load in the customer’s language, and since the template does not hold that value the interface language is passed instead. The two may differ.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.canned_replies.after', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

The bottom of the internal note form

uiadmin.ticket_detail.note_form.bottom
admin/tickets/detail the internal note form

Appears below the internal note box. Notes are never shown to the customer.

Parameters 1
$ticketarrayThe active ticket record.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.ticket_detail.note_form.bottom', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

A new tab on the ticket detail

uiadmin.ticket_detail.tabs
admin/tickets/detail an object, not an array

Runs once the tabs of the ticket detail are built. You do not return HTML: you add the tab through the object’s method.

Parameters 2
$tabobjectThe tab object. Being an object, it changes for good without a by-link mark.
$ticketarrayThe full ticket record.
Return 1
voidThe return is not used. This point shows no HTML.
Listener
Hook::add('ui:admin.ticket_detail.tabs', 10, function ($tab, $ticket) {
    $tab->add('acme', 'Acme', Acme::renderTab((int) ($ticket['id'] ?? 0)));
});

The very bottom of the ticket page

uiadmin.tickets_detail.bottom
admin/tickets/detail end of the page

Appears at the very end of the page.

Parameters 1
$ticketarrayThe ticket record on screen.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_detail.bottom', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

A badge on a list row

uiadmin.tickets_list.row_badges
admin/tickets per row

Appears on every row of the ticket list. It puts a status badge of your own beside the core ones.

Parameters 1
$modelarrayThe row data: id, status, read mark, department and title. ? The hook runs per row, so a listener querying the database here produces hundreds of queries per page. Collect what you need beforehand.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_list.row_badges', 10, function ($model) {
    // SATIR BASINA calisir: burada sorgu yapmayin, onceden toplayin.
    if (!Acme::isEscalated((int) ($model['id'] ?? 0))) return null;

    return '<span class="badge bg-danger">Acme</span>';
});

The ticket list toolbar

uiadmin.tickets_list.toolbar
admin/tickets no parameters

Appears in the button group above the ticket list.

Parameters 0
It takes no parameters.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_list.toolbar', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Above the table on the ticket list

uiadmin.tickets_list.before_table
admin/tickets no parameters

Appears immediately above the ticket table.

Parameters 0
It takes no parameters.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_list.before_table', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

The department list toolbar

uiadmin.department_list.toolbar
admin/tickets/departments no parameters

Appears in the toolbar of the department list.

Parameters 0
It takes no parameters.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.department_list.toolbar', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Above the table on the department list

uiadmin.department_list.before_table
admin/tickets/departments no parameters

Appears immediately above the department table.

Parameters 0
It takes no parameters.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.department_list.before_table', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Above the ticket creation form

uiadmin.tickets_edit.before_content
admin/tickets the customer may be empty

Appears above the form staff use to open a ticket for a customer.

Parameters 1
$userarrayThe customer pre-selected for the form. It arrives empty when no customer is chosen yet.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_edit.before_content', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Below the ticket creation form

uiadmin.tickets_edit.bottom
admin/tickets the customer may be empty

Appears below the same form, at the bottom of the page.

Parameters 1
$userarrayThe customer pre-selected for the form. It arrives empty when no customer is chosen yet.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.tickets_edit.bottom', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Above the department form

uiadmin.department_edit.before_content
admin/tickets/departments empty when creating

Appears above the department add and edit form.

Parameters 1
$detailarrayThe department being edited. It is empty when creating: test before reaching for an id.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.department_edit.before_content', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Below the department form

uiadmin.department_edit.bottom
admin/tickets/departments empty when creating

Appears below the same form.

Parameters 1
$detailarrayThe department being edited. It is empty when creating: test before reaching for an id.
Return 1
string|nullThe HTML you return appears. With several listeners the outputs are appended one after another in priority order. Empty text, null and false are skipped, so return null when you have nothing to add. The output enters the page unescaped — clean anything coming from outside yourself.
Listener
Hook::add('ui:admin.department_edit.bottom', 10, function () {
    return '<div class="alert alert-info">Acme</div>';
});

Pitfalls

The privilege flag is not a gate

The privilege parameter on the ticket detail tells you whether the viewer holds it; it does not block your output on its own. If you would rather not show an operation button to somebody without the privilege, put the condition in your own listener. The real check stays in the operation on the server: hiding here is only visibility.

The row badge runs on every row

The list badge point is called separately for every ticket on the page. A listener doing a database query or an outside call inside it produces fifty queries on a fifty-row page and slows the list noticeably. Collect what you need once and read it from memory.

Was this helpful?

Thanks for your feedback!

Still Need Help?

Our support team is here around the clock for anything you can't find above.