Áú»¢¶Ä²©

Crear un giny (tutorial)

Aquest ¨¦s un tutorial passa a passa que ensenya com crear un giny de tauler senzill. Podeu descarregar tots els fitxers d'aquest giny en un arxiu ZIP: lesson_gauge_chart.zip.

Qu¨¨ fareu

Durant aquest tutorial, primer creareu un giny ²ú¨¤²õ¾±³¦ "Hola, m¨®n!" i, a tot seguit, el convertireu a un giny m¨¦s avan?at que ensenya el valor d'un element com a gr¨¤fic gauge. Aix¨ª ¨¦s com es veur¨¤ el giny enllestit:

Part I - "Hola, m¨®n!"

En aquesta secci¨® aprendreu a crear els elements m¨ªnims de giny necessaris i afegir un nou giny a la interf¨ªcie Áú»¢¶Ä²©.

Afegir un giny buit a la interf¨ªcie Áú»¢¶Ä²©

  1. Creeu el directori lesson_gauge_chart al directori ³¾¨°»å³Ü±ô²õ de la vostra instal¡¤laci¨® de Áú»¢¶Ä²© (com ara zabbix/ui/modules).

Tots els ginys personalitzats es tracten com a ³¾¨°»å³Ü±ô²õ externs i s'han d'afegir al directori de ³¾¨°»å³Ü±ô²õ de Áú»¢¶Ä²© (per exemple, zabbix/ui/modules). El directori zabbix/ui/widgets ¨¦s reservat per als ginys integrats de Áú»¢¶Ä²© i s'actualitza juntament amb la interf¨ªcie d'usuari de Áú»¢¶Ä²©.

  1. Creeu el fitxer manifest.json amb metadades b¨¤siques del giny (veieu la descripci¨® dels ±è²¹°ù¨¤³¾±ð³Ù°ù±ð²õ admesos).

ui/modules/lesson_gauge_chart/manifest.json

{
           "manifest_version": 2.0,
           "id": "lesson_gauge_chart",
           "type": "widget",
           "name": "Gauge chart",
           "namespace": "LessonGaugeChart",
           "version": "1.0",
           "author": "Áú»¢¶Ä²© SIA"
       }
  1. A la interf¨ªcie Áú»¢¶Ä²© aneu a la secci¨® Administraci¨®¡úGeneral¡ú²Ñ¨°»å³Ü±ôs i premeu el bot¨® Escanejar directori.

  1. Cerqueu el nou m¨°dul Diagrama de mesura a la llista i canvieu l'estat del m¨°dul de "Desactivat" a "Actiu" (si no veieu el m¨°dul al llistat, reviseu la secci¨® de soluci¨® de problemes).

  1. Obriu el Tauler de control, canvieu-lo a mode d'edici¨® i afegiu-hi un nou giny. Al camp Tipus, trieu ³Ò°ù¨¤´Ú¾±³¦ de mesura.

  1. En aquest punt, la configuraci¨® del giny Diagrama de mesura nom¨¦s cont¨¦ camps de giny habituals: Nom i Interval d'actualitzaci¨®. Premeu Afegir per afegir el giny al tauler.

  1. Al tauler hauria d'apar¨¨ixer un giny en blanc. Premeu Desar els canvis a l'extrem superior dret per desar el tauler.

Afegir un nou giny

El fitxer view del giny s'ha d'ubicar al directori views (per a aquest tutorial, ui/modules/lesson_gauge_chart/views/). Si el fitxer t¨¦ un nom predeterminat widget.view.php, no cal que el registreu a manifest.json. Si el fitxer t¨¦ un nom diferent, especifiqueu-lo a la secci¨® actions/widget.lesson_gauge_chart.view de manifest.json.

  1. Afegiu un directori views al leson_gauge_chart.

  2. Creeu el fitxer widget.view.php dins del directori views.

ui/modules/lesson_gauge_chart/views/widget.view.php

<?php
       
       /**
        * Visualitzaci¨® del giny del gr¨¤fic de mesura.
        *
        * @var CView $this
        * @var array $data
        */
           
       (new CWidgetView($data))
           ->addItem(
               new CTag('h1', true, 'Hello, world!')
           )
           ->show();
  1. Recarregueu el tauler Áú»¢¶Ä²©. El giny ³Ò°ù¨¤´Ú¾±³¦ de mesura ara ensenyar¨¤ "Hola, m¨®n!".

Part II - ³Ò°ù¨¤´Ú¾±³¦ de mesura

Afegiu ±è²¹°ù¨¤³¾±ð³Ù°ù±ð²õ a una vista de configuraci¨® i empreu-los en una vista de giny

En aquesta secci¨®, aprendr¨¤s a afegir un camp de configuraci¨® del giny i a mostrar el valor introdu?t a la vista del giny com a text.

La configuraci¨® del giny consta d'un formulari (Áú»¢¶Ä²©\Widgets\CWidgetForm) i d'una vista de formulari de giny (widget.edit.php). Per afegir camps (Áú»¢¶Ä²©\Widgets\CWidgetField), heu de crear una classe WidgetForm, que ampliar¨¤ Áú»¢¶Ä²©\Widgets\CWidgetForm.

El formulari cont¨¦ el conjunt de camps (Áú»¢¶Ä²©\Widgets\CWidgetField) de diversos tipus, que s'empren per validar els valors introdu?ts per l'usuari. El camp de formulari (Áú»¢¶Ä²©\Widgets\CWidgetField) per a cada tipus d'element d'entrada converteix el valor en un format ¨²nic per emmagatzemar-lo a la base de dades.

El fitxer formulari del giny s'ha d'ubicar al directori includes (per a aquest tutorial, ui/modules/lesson_gauge_chart/includes/). Si el fitxer t¨¦ un nom predeterminat WidgetForm.php, no cal que el registreu a manifest.json. Si el fitxer t¨¦ un nom diferent, especifiqueu-lo a la secci¨® widget/form_class de manifest.json.

  1. Afegiu un directori includes al lesson_gauge_chart.

  2. Creeu el fitxer WidgetForm.php dins del directori includes.

ui/modules/lesson_gauge_chart/includes/WidgetForm.php

<?php
           
       namespace Modules\LessonGaugeChart\Includes;
           
       use Áú»¢¶Ä²©\Widgets\CWidgetForm;
           
       class WidgetForm extends CWidgetForm {
       }
  1. Afegiu un camp ¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨® al formulari de configuraci¨® del giny. Aquest ¨¦s un camp de text normal, on un usuari pot introduir qualsevol conjunt de car¨¤cters. Podeu utilitzar la classe CWidgetFieldTextBox per a aix¨°.

ui/modules/lesson_gauge_chart/includes/WidgetForm.php

<?php
       
       namespace Modules\LessonGaugeChart\Includes;
       
       use Áú»¢¶Ä²©\Widgets\CWidgetForm;
       
       use Áú»¢¶Ä²©\Widgets\Fields\CWidgetFieldTextBox;
       
       class WidgetForm extends CWidgetForm {
       
          public function addFields(): self {
             return $this
                ->addField(
                   new CWidgetFieldTextBox('description', _('Description'))
                );
          }
       }
  1. Al directori views, creeu un fitxer de visualitzaci¨® de configuraci¨® del giny widget.edit.php i afegiu una vista per al nou camp ¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨®. Per a la classe de camp CWidgetFieldTextBox, la vista ¨¦s CWidgetFieldTextBoxView.

ui/modules/lesson_gauge_chart/views/widget.edit.php

<?php
           
       /**
        * Visualitzaci¨® del formulari del giny del gr¨¤fic de mesura.
        *
        * @var CView $this
        * @var array $data
        */
           
       (new CWidgetFormView($data))
           ->addField(
               new CWidgetFieldTextBoxView($data['fields']['description'])
           )
           ->show();
  1. Aneu al Tauler i premeu la icona d'engranatge per obrir la configuraci¨® del giny.

  2. La configuraci¨® del giny ara cont¨¦ un camp nou de text (¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨®). Introdu?u qualsevol valor, per exemple, ¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨® del gr¨¤fic de calibre.

  1. Premeu Aplica a la configuraci¨® del giny. Premeu Desar els canvis per desar el tauler. El text nou no ¨¦s visible enlloc i el giny encara mostra "Hola, m¨®n!".

Per veure-ho al giny, cal recuperar el valor del camp ¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨® de la base de dades i passar a la vista del giny. Per fer-ho, heu de crear una classe d'acci¨®.

  1. Afegiu un directori actions al lesson_gauge_chart.

  2. Creeu un fitxer WidgetView.php dins del directori actions. La classe d'acci¨® WidgetView ampliar¨¤ la classe CControllerDashboardWidgetView.

Els valors dels camps de configuraci¨® del giny s'emmagatzemen a la propietat $fields_values de la classe d'acci¨®.

ui/modules/lesson_gauge_chart/actions/WidgetView.php

<?php
           
       namespace Modules\LessonGaugeChart\Actions;
           
       use CControllerDashboardWidgetView,
           CControllerResponseData;
           
       class WidgetView extends CControllerDashboardWidgetView {
           
           protected function doAction(): void {
               $this->setResponse(new CControllerResponseData([
                   'name' => $this->getInput('name', $this->widget->getName()),
                   'description' => $this->fields_values['description'],
                   'user' => [
                       'debug_mode' => $this->getDebugMode()
                   ]
               ]));
           }
       }
  1. Obriu el fitxer manifest.json i registreu WidgetView com a classe d'acci¨® a la secci¨® actions/widget.lesson_gauge_chart.view.

ui/modules/lesson_gauge_chart/manifest.json

{
            "manifest_version": 2.0,
            "id": "lesson_gauge_chart",
            "type": "giny",
            "name": "³Ò°ù¨¤´Ú¾±³¦ de mesura",
            "namespace": "LessonGaugeChart",
            "version": "1.0",
            "author": "Áú»¢¶Ä²© SIA",
            "actions": {
                "widget.lesson_gauge_chart.view": {
                    "class": "WidgetView"
                }
            }
       }
  1. Ara podeu emprar el valor del camp de descripci¨®, contingut a $data['description'], a la vista del giny. Obriu views/widget.view.php i substitu?u el text est¨¤tic "Hola, m¨®n!" amb $»å²¹³Ù²¹°Ú'»å±ð²õ³¦°ù¾±±è³¦¾±¨®'±Õ.

ui/modules/lesson_gauge_chart/views/widget.view.php

<?php
           
       /**
         * Visualitzaci¨® del giny del gr¨¤fic de mesura.
         *
         * @var CView $this
         * @var array $data
         */
           
       (nou CWidgetView($data))
            ->addItem(
                new CTag('h1', true, $data['description'])
            )
            ->show();
  1. Actualitzeu la p¨¤gina Tauler. Haur¨ªeu de veure el text de descripci¨® del giny en lloc de "Hola, m¨®n!".

Recuperar el valor d'un element mitjan?ant l'API

El giny hauria de mostrar el darrer valor d'un element triat per l'usuari. Per aix¨°, heu d'afegir la possibilitat de triar elements a la configuraci¨® del giny.

En aquesta secci¨® aprendreu a afegir un camp de selecci¨® d'elements al formulari del giny i a afegir la part visual d'aquest camp a la vista de configuraci¨®. Aleshores, el controlador de ginys podr¨¤ recuperar les dades de lelement i el seu valor mitjan?ant una petici¨® d'API. Un cop rebuda, el valor es pot mostrar a la vista del giny.

  1. Obriu includes/WidgetForm.php i afegiu el camp CWidgetFieldMultiSelectItem. Aix¨° us permetr¨¤ triar un element al formulari de configuraci¨®.

ui/modules/lesson_gauge_chart/includes/WidgetForm.php

<?php
       
       namespace Modules\LessonGaugeChart\Includes;
       
       use Áú»¢¶Ä²©\Widgets\{
           CWidgetField,
           CWidgetForm
       };
       
       use Áú»¢¶Ä²©\Widgets\Fields\{
           CWidgetFieldMultiSelectItem,
           CWidgetFieldTextBox
       };
       
       /**
        * Formulari de giny de gr¨¤fic de calibre.
        */
       classe WidgetForm amplia CWidgetForm {
       
           public function addFields(): self {
               return $this
                   ->addField(
                       (newCWidgetFieldMultiSelectItem('itemid', _('Item')))
                           ->setFlags(CWidgetField::FLAG_NOT_EMPTY | CWidgetField::FLAG_LABEL_ASTERISK)
                           ->setMultiple (false)
                   )
                   ->addField(
                       new CWidgetFieldTextBox('»å±ð²õ³¦°ù¾±±è³¦¾±¨®', _('¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨®'))
                   );
           }
       }
  1. Obriu views/widget.edit.php i afegiu el component visual de camp a la vista de configuraci¨®.

ui/modules/lesson_gauge_chart/views/widget.edit.php

<?php
       
       /**
        * Visualitzaci¨® del formulari del giny del gr¨¤fic de mesura.
        *
        * @var CView $this
        * @var array $data
        */
       
       (new CWidgetFormView($data))
           ->addField(
               new CWidgetFieldMultiSelectItemView($data['fields']['itemid'], $data['captions']['items']['itemid'])
           )
           ->addField(
               new CWidgetFieldTextBoxView($data['fields']['description'])
           )
           ->show();
  1. Torneu al tauler i feu clic a la icona d'engranatge del giny per obrir el formulari de configuraci¨® del giny.

  2. El formulari de configuraci¨® del giny ara cont¨¦ un camp d'entrada nou Element. Trieu l'equip "Servidor Áú»¢¶Ä²©" i l'element "C¨¤rrega mitjana (1 m de mitjana)".

  1. Feu clic a Aplicar al formulari de configuraci¨® del gint. Tot seguit, feu clic a Desar els canvis a l'extrem superior dret per desar el tauler.

  2. Obriu i modifiqueu actions/WidgetView.php.

A partir d'ara, l'identificador de l'element ser¨¤ disponible al controlador del giny a $this->fields_values['itemid']. El m¨¨tode del controlador doAction() recopila les dades de l'element (nom, tipus de valor, unitats) mitjan?ant el m¨¨tode API item.get i l'¨²ltim valor de l'element mitjan?ant el M¨¨tode de l'API history.get.

ui/modules/lesson_gauge_chart/actions/WidgetView.php

<?php
       
       namespace Modules\LessonGaugeChart\Actions;
       
       use API,
           CControllerDashboardWidgetView,
           CCollerResponseData;
       
       class WidgetView extendsCControllerDashboardWidgetView {
       
           protected function doAction(): void {
               $db_items = API::Item()->get([
                   'output' => ['itemid', 'value_type', 'nom', 'unitats'],
                   'itemids' => $this->fields_values['itemid'],
                   'webitems' => true,
                   'filtre' => [
                       'value_type' => [ITEM_VALUE_TYPE_UINT64, ITEM_VALUE_TYPE_FLOAT]
                   ]
               ]);
       
               $value = nul;
       
               if ($db_items) {
                   $element = $db_items[0];
       
                   $³ó¾±²õ³Ù¨°°ù¾±²¹ = API::History()->get([
                       'output' => API_OUTPUT_EXTEND,
                       'itemids' => $item['itemid'],
                       'history' => $item['value_type'],
                       'sortfield' => 'rellotge',
                       'sortorder' => ZBX_SORT_DOWN,
                       '±ô¨ª³¾¾±³Ù' => 1
                   ]);
       
                   si ($history) {
                       $value = convertUnitsRaw([
                           'valor' => $history[0]['valor'],
                           'unitats' => $item['unitats']
                       ]);
                   }
               }
       
               $this->setResponse(new CControllerResponseData([
                   'name' => $this->getInput('name', $this->widget->getName()),
                   'valor' => $value,
                   'description' => $this->fields_values['»å±ð²õ³¦°ù¾±±è³¦¾±¨®'],
                   'usuari' => [
                       'debug_mode' => $this->getDebugMode()
                   ]
               ]));
           }
       }
  1. Obriu views/widget.view.php i afegiu el valor de l'element a la vista del giny.

ui/modules/lesson_gauge_chart/views/widget.view.php

<?php
       
       /**
        * Visualitzaci¨® del giny del gr¨¤fic de mesura.
        *
        * @var CView $this
        * @var array $data
        */
       
       (new CWidgetView($data))
           ->addItem([
               new CTag('h1', true, $data['»å±ð²õ³¦°ù¾±±è³¦¾±¨®']),
               CDiv new($data['valor'] !== nul ? $data['valor']['valor'] : _('Sense dades'))
           ])
           ->show();
  1. Actualitzeu la p¨¤gina del tauler. El giny mostrar¨¤ el valor de l'element m¨¦s recent.

Afegeix ±è²¹°ù¨¤³¾±ð³Ù°ù±ð²õ de configuraci¨® avan?ats a una vista de configuraci¨®

En aquesta secci¨®, aprendreu a afegir una secci¨® de °ä´Ç²Ô´Ú¾±²µ³Ü°ù²¹³¦¾±¨® avan?ada desplegable/plegable amb ±è²¹°ù¨¤³¾±ð³Ù°ù±ð²õ opcionals com ara el color, els valors m¨ªnims i m¨¤xims, les unitats i el camp ¶Ù±ð²õ³¦°ù¾±±è³¦¾±¨® creat abans.

  1. Creeu un fitxer Widget.php al directori principal de widgets lesson_gauge_chart per crear una nova classe Widget.

La classe Widget ampliar¨¤ la classe base CWidget per afegir/substituir la configuraci¨® predeterminada del giny (en aquest cas - traduccions). JavaScript, que es proporciona tot seguit, mostra la cadena "Sense dades" en cas que manquin dades. La cadena "Sense dades" ¨¦s present als fitxers de traducci¨® de la interf¨ªcie d'usuari de Áú»¢¶Ä²©.

Si hi ha constants de giny, es recomana definir-les tamb¨¦ a la classe Widget.

ui/modules/lesson_gauge_chart/Widget.php

<?php
       
       namespace Modules\LessonGaugeChart;
       
       use Áú»¢¶Ä²©\Core\CWidget;
       
       class Widget extends CWidget {
       
           public const UNIT_AUTO = 0;
           public const UNIT_STATIC = 1;
       
           public function getTranslationStrings(): array {
               return [
                   'class.widget.js' => [
                       'No data' => _('No data')
                   ]
               ];
           }
       }
  1. Obriu includes/WidgetForm.php i afegiu els nous camps Color (selector de colors), Min (camp num¨¨ric), Max (camp num¨¨ric) i Units (tria) i definiu la paleta de colors predeterminada per al selector de colors, de manera que es pugui emprar a les passes seg¨¹ents.

ui/modules/lesson_gauge_chart/includes/WidgetForm.php

<?php
       
       namespace Modules\LessonGaugeChart\Includes;
       
       use Modules\LessonGaugeChart\Widget;
       
       use Áú»¢¶Ä²©\Widgets\{
           CWidgetField,
           CWidgetForm
       };
       
       use Áú»¢¶Ä²©\Widgets\Fields\{
           CWidgetFieldColor,
           CWidgetFieldMultiSelectItem,
           CWidgetFieldNumericBox,
           CWidgetFieldSelect,
           CWidgetFieldTextBox
       };
       
       /**
         * Formulari de giny de gr¨¤fic de calibre.
         */
       class WidgetForm extends CWidgetForm {
       
           public const DEFAULT_COLOR_PALETTE = [
               'FF465C', 'B0AF07', '0EC9AC', '524BBC', 'ED1248', 'D1E754', '2AB5FF', '385CC7', 'EC1594', 'BAE37D',
               '6AC8FF', 'EE2B29', '3CA20D', '6F4BBC', '00A1FF', 'F3601B', '1CAE59', '45CFDB', '894BBC', '6D6D6D'
           ];
       
           public function addFields(): self {
               return $this
                   ->addField(
                       (new CWidgetFieldMultiSelectItem('itemid', _('Item')))
                           ->setFlags(CWidgetField::FLAG_NOT_EMPTY | CWidgetField::FLAG_LABEL_ASTERISK)
                           ->setMultiple(false)
                   )
                   ->addField(
                       (new CWidgetFieldColor('chart_color', _('Color')))->setDefault('FF0000')
                   )
                   ->addField(
                       (new CWidgetFieldNumericBox('value_min', _('Min')))
                           ->setDefault(0)
                           ->setFlags(CWidgetField::FLAG_NOT_EMPTY | CWidgetField::FLAG_LABEL_ASTERISK)
                   )
                   ->addField(
                       (new CWidgetFieldNumericBox('value_max', _('Max')))
                           ->setDefault(100)
                           ->setFlags(CWidgetField::FLAG_NOT_EMPTY | CWidgetField::FLAG_LABEL_ASTERISK)
                   )
                   ->addField(
                       (new CWidgetFieldSelect('value_units', _('Units'), [
                           Widget::UNIT_AUTO => _x('Auto', 'history source selection method'),
                           Widget::UNIT_STATIC => _x('Static', 'history source selection method')
                       ]))->setDefault(Widget::UNIT_AUTO)
                   )
                   ->addField(
                       (new CWidgetFieldTextBox('value_static_units'))
                   )
                   ->addField(
                       new CWidgetFieldTextBox('description', _('Description'))
                   );
           }
       }
  1. Obriu views/widget.edit.php i afegiu els components visuals de camp a la vista de configuraci¨®.

ui/modules/lesson_gauge_chart/views/widget.edit.php

<?php
       
       /**
         * Visualitzaci¨® del formulari del widget del gr¨¤fic de mesura.
         *
         * @var CView $this
         * @var array $data
         */
       
       $lefty_units = new CWidgetFieldSelectView($data['fields']['value_units']);
       $lefty_static_units = (new CWidgetFieldTextBoxView($data['fields']['value_static_units']))
           ->setPlaceholder(_('value'))
           ->setWidth(ZBX_TEXTAREA_TINY_WIDTH);
       
       (new CWidgetFormView($data))
           ->addField(
               (new CWidgetFieldMultiSelectItemView($data['fields']['itemid']))
                   ->setPopupParameter('numeric', true)
           )
           ->addFieldset(
               (new CWidgetFormFieldsetCollapsibleView(_('Advanced configuration')))
                   ->addField(
                       new CWidgetFieldColorView($data['fields']['chart_color'])
                   )
                   ->addField(
                       new CWidgetFieldNumericBoxView($data['fields']['value_min'])
                   )
                   ->addField(
                       new CWidgetFieldNumericBoxView($data['fields']['value_max'])
                   )
                   ->addItem([
                       $lefty_units->getLabel(),
                       (new CFormField([
                           $lefty_units->getView()->addClass(ZBX_STYLE_FORM_INPUT_MARGIN),
                           $lefty_static_units->getView()
                       ]))
                   ])
                   ->addField(
                       new CWidgetFieldTextBoxView($data['fields']['description'])
                   )
           )
           ->show();

El m¨¨tode addField() de la classe CWidgetFormView pren una cadena de classe CSS com a segon par¨¤metre.

  1. Torneu al tauler, canvieu al mode d'edici¨® i feu clic a la icona d'engranatge del giny per obrir el formulari de configuraci¨® del giny. El formulari de configuraci¨® del giny ara cont¨¦ una nova secci¨® desplegable/plegable °ä´Ç²Ô´Ú¾±²µ³Ü°ù²¹³¦¾±¨® avan?ada.

  1. Amplieu la secci¨® °ä´Ç²Ô´Ú¾±²µ³Ü°ù²¹³¦¾±¨® avan?ada per veure camps addicionals de configuraci¨® de ginys. Tingueu en compte que el camp Color encara no t¨¦ cap selector de colors. Aix¨° es deu al fet que el selector de colors s'ha d'inicialitzar amb JavaScript, que s'afegir¨¤ a la secci¨® seg¨¹ent: Afegir JavaScript al giny.

Afegir JavaScript al giny.

En aquesta secci¨®, aprendreu a afegir un gr¨¤fic de calibre -fet amb Javascript - que ensenya si el darrer valor ¨¦s normal o massa alt / massa baix.

  1. Creeu un fitxer widget.edit.js.php dins del directori views.

JavaScript ser¨¤ responsable d'inicialitzar el selector de colors a la vista de configuraci¨®.

ui/modules/lesson_gauge_chart/views/widget.edit.js.php

<?php
       
       use Modules\LessonGaugeChart\Widget;
       
       ?>
       
       window.widget_lesson_gauge_chart_form = new class {
       
           init({color_palette}) {
               this._unit_select = document.getElementById('value_units');
               this._unit_value = document.getElementById('value_static_units');
       
               this._unit_select.addEventListener('change', () => this.updateForm());
       
               colorPalette.setThemeColors(color_palette);
       
               for (const colorpicker of jQuery('.<?= ZBX_STYLE_COLOR_PICKER ?> input')) {
                   jQuery(colorpicker).colorpicker();
               }
       
               const overlay = overlays_stack.getById('widget_properties');
       
               for (const event of ['overlay.reload', 'overlay.close']) {
                   overlay.$dialogue[0].addEventListener(event, () => { jQuery.colorpicker('hide'); });
               }
           
               this.updateForm();
           }
           
           updateForm() {
               this._unit_value.disabled = this._unit_select.value == <?= Widget::UNIT_AUTO ?>;
           }
       };
  1. Obriu views/widget.edit.php i afegiu l'arxiu widget.edit.js.php amb el JavaScript a la vista de configuraci¨®.

Per fer-ho, empreu el m¨¨tode includeJsFile(). Per afegir JavaScript en l¨ªnia, empreu el m¨¨tode addJavaScript().

ui/modules/lesson_gauge_chart/views/widget.edit.php

<?php
           
       /**
        * Visualitzaci¨® del formulari del giny del gr¨¤fic de mesura.
        *
        * @var CView $this
        * @var array $data
        */
           
       use Modules\LessonGaugeChart\Includes\WidgetForm;
           
       $lefty_units = new CWidgetFieldSelectView($data['fields']['value_units']);
       $lefty_static_units = (new CWidgetFieldTextBoxView($data['fields']['value_static_units']))
           ->setPlaceholder(_('value'))
           ->setWidth(ZBX_TEXTAREA_TINY_WIDTH);
           
       (new CWidgetFormView($data))
           ->addField(
               (new CWidgetFieldMultiSelectItemView($data['fields']['itemid']))
                   ->setPopupParameter('numeric', true)
           )
           ->addFieldset(
               (new CWidgetFormFieldsetCollapsibleView(_('Advanced configuration')))
                   ->addField(
                       new CWidgetFieldColorView($data['fields']['chart_color'])
                   )
                   ->addField(
                       new CWidgetFieldNumericBoxView($data['fields']['value_min'])
                   )
                   ->addField(
                       new CWidgetFieldNumericBoxView($data['fields']['value_max'])
                   )
                   ->addItem([
                       $lefty_units->getLabel(),
                       (new CFormField([
                           $lefty_units->getView()->addClass(ZBX_STYLE_FORM_INPUT_MARGIN),
                           $lefty_static_units->getView()
                       ]))
                   ])
                   ->addField(
                       new CWidgetFieldTextBoxView($data['fields']['description'])
                    
           )
           ->includeJsFile('widget.edit.js.php')
           ->addJavaScript('widget_lesson_gauge_chart_form.init('.json_encode([
               'color_palette' => WidgetForm::DEFAULT_COLOR_PALETTE
           ], JSON_THROW_ON_ERROR).');')
           ->show();
  1. Torneu al tauler, premeu la icona d'engranatge al giny per obrir el formulari de configuraci¨® del giny. Ara, expandiu la secci¨® de °ä´Ç²Ô´Ú¾±²µ³Ü°ù²¹³¦¾±¨® avan?ada per veure el selector de color inicialitzat. Ompliu els camps amb els valors i trieu el color del gr¨¤fic.

4. Feu clic a Aplicar al formulari de configuraci¨® del giny. Tot seguit, premeu Desar canvis a la cantonada superior dreta per desar el tauler.

  1. Obriu actions/WidgetView.php i actualitzeu el controlador.

La propietat $this->fields_values ara cont¨¦ els valors de tots els camps °ä´Ç²Ô´Ú¾±²µ³Ü°ù²¹³¦¾±¨® avan?ada. Finalitzeu el controlador per permetre passar la configuraci¨® i el valor de l'element triat a la vista del giny.

ui/modules/lesson_gauge_chart/actions/WidgetView.php

<?php
           
       namespace Modules\LessonGaugeChart\Actions;
           
       use API,
           CControllerDashboardWidgetView,
           CControllerResponseData;
           
       class WidgetView extends CControllerDashboardWidgetView {
           
           protected function doAction(): void {
               $db_items = API::Item()->get([
                   'output' => ['itemid', 'value_type', 'name', 'units'],
                   'itemids' => $this->fields_values['itemid'],
                   'webitems' => true,
                   'filter' => [
                       'value_type' => [ITEM_VALUE_TYPE_UINT64, ITEM_VALUE_TYPE_FLOAT]
                   ]
               ]);
           
               $history_value = null;
           
               if ($db_items) {
                   $item = $db_items[0];
           
                   $history = API::History()->get([
                       'output' => API_OUTPUT_EXTEND,
                       'itemids' => $item['itemid'],
                       'history' => $item['value_type'],
                       'sortfield' => 'clock',
                       'sortorder' => ZBX_SORT_DOWN,
                       'limit' => 1
                   ]);
           
                   if ($history) {
                       $history_value = convertUnitsRaw([
                           'value' => $history[0]['value'],
                           'units' => $item['units']
                       ]);
                   }
               }
           
               $this->setResponse(new CControllerResponseData([
                   'name' => $this->getInput('name', $this->widget->getName()),
                   'history' => $history_value,
                   'fields_values' => $this->fields_values,
                   'user' => [
                       'debug_mode' => $this->getDebugMode()
                   ]
               ]));
           }
       }
  1. Obriu i modifiqueu views/widget.view.php

Heu de crear un contenidor per al gr¨¤fic de mesura, que dibuixareu a les passes seg¨¹ents, i un contenidor per a la descripci¨®.

Per passar valors a JavaScript com a objecte JSON, empreu el m¨¨tode setVar().

ui/modules/lesson_gauge_chart/views/widget.view.php

<?php
           
       /**
        * Visualitzaci¨® del giny del gr¨¤fic de mesura.
        *
        * @var CView $this
        * @var array $data
        */
           
       (new CWidgetView($data))
           ->addItem([
               (new CDiv())->addClass('chart'),
               $data['fields_values']['description']
                   ? (new CDiv($data['fields_values']['description']))->addClass('description')
                   : null
           ])
           ->setVar('history', $data['history'])
           ->setVar('fields_values', $data['fields_values'])
           ->show();
  1. Creeu un directori actius al lesson_gauge_chart. Aquest directori s'emprar¨¤ per emmagatzemar Javascript, CSS i, potencialment, qualsevol altre actiu, com fonts o imatges.

  2. Per a JavaScript de visualitzaci¨® de ginys, creeu un directori js dins del directori assets.

  3. Creeu un fitxer widget.js al directori assets/js.

Aquesta classe de widget de JavaScript ampliar¨¤ la classe de JavaScript base de tots els ginys del tauler - CWidget.

El tauler de control es basa en una implementaci¨® correcta d'un giny i comunica qualsevol informaci¨® rellevant al giny mitjan?ant la crida als m¨¨todes JavaScript respectius. El tauler tamb¨¦ espera que el giny generi esdeveniments quan es produeixi alguna interacci¨®. Aix¨ª, la classe CWidget cont¨¦ un conjunt de m¨¨todes amb la implementaci¨® predeterminada del comportament del giny, que es pot personalitzar ampliant la classe.

En aquest cas, cal una mica de personalitzaci¨®; per tant, s'implementar¨¤ una l¨°gica personalitzada per al comportament del giny seg¨¹ent:

-inicialitzaci¨® del giny que s'encarrega de definir l'estat inicial del giny (veieu el m¨¨tode _init()); -mostrar el contingut del giny (¨¦s a dir, dibuixar el gr¨¤fic de l'indicador) si el proc¨¦s d'actualitzaci¨® del giny ha estat satisfactori i sense errors (veieu el m¨¨tode _processUpdateResponse(response) i els m¨¨todes _resizeChart() i _updatedChart() relacionats) -canviar la mida del giny (veieu el m¨¨tode resize() i el m¨¨tode _resizeChart() relacionat)

Per a altres aspectes del giny del gr¨¤fic gauge, s'utilitzar¨¤ la implementaci¨® predeterminada del comportament del giny. Per obtenir m¨¦s informaci¨® sobre els m¨¨todes JavaScript de la classe CWidget, consulteu: JavaScript.

Com que aquest JavaScript ¨¦s necessari per a la vista del widget, s'hauria de carregar amb la p¨¤gina del tauler.

Per habilitar la c¨¤rrega de JavaScript, haureu d'actualitzar els ±è²¹°ù¨¤³¾±ð³Ù°ù±ð²õ assets/js i js_class de manifest.json tal com es veu a la passa seg¨¹ent.

ui/modules/lesson_gauge_chart/assets/js/class.widget.js

class WidgetLessonGaugeChart extends CWidget {
           
           static UNIT_AUTO = 0;
           static UNIT_STATIC = 1;
           
           onInitialize() {
               super.onInitialize();
           
               this._refresh_frame = null;
               this._chart_container = null;
               this._canvas = null;
               this._chart_color = null;
               this._min = null;
               this._max = null;
               this._value = null;
               this._last_value = null;
               this._units = '';
           }
           
           processUpdateResponse(response) {
               if (response.history === null) {
                   this._value = null;
                   this._units = '';
               }
               else {
                   this._value = Number(response.history.value);
                   this._units = response.fields_values.value_units == WidgetLessonGaugeChart.UNIT_AUTO
                       ? response.history.units
                       : response.fields_values.value_static_units;
               }
           
               this._chart_color = response.fields_values.chart_color;
               this._min = Number(response.fields_values.value_min);
               this._max = Number(response.fields_values.value_max);
       
               super.processUpdateResponse(response);
           }
       
           setContents(response) {
               if (this._canvas === null) {
                   super.setContents(response);
                   this._chart_container = this._body.querySelector('.chart');
                   this._chart_container.style.height =
                       `${this._getContentsSize().height - this._body.querySelector('.description').clientHeight}px`;
                   this._canvas = document.createElement('canvas');
       
                   this._chart_container.appendChild(this._canvas);
       
                   this._resizeChart();
               }
       
               this._updatedChart();
           }
           
           onResize() {
               super.onResize();
       
               if (this._state === WIDGET_STATE_ACTIVE) {
                   this._resizeChart();
               }
           }
           
           _resizeChart() {
               const ctx = this._canvas.getContext('2d');
               const dpr = window.devicePixelRatio;
       
               this._canvas.style.display = 'none';
               const size = Math.min(this._chart_container.offsetWidth, this._chart_container.offsetHeight);
               this._canvas.style.display = '';
       
               this._canvas.width = size * dpr;
               this._canvas.height = size * dpr;
       
               ctx.scale(dpr, dpr);
       
               this._canvas.style.width = `${size}px`;
               this._canvas.style.height = `${size}px`;
       
               this._refresh_frame = null;
       
               this._updatedChart();
           }
       
           _updatedChart() {
               if (this._last_value === null) {
                   this._last_value = this._min;
               }
       
               const start_time = Date.now();
               const end_time = start_time + 400;
       
               const animate = () => {
                   const time = Date.now();
       
                   if (time <= end_time) {
                       const progress = (time - start_time) / (end_time - start_time);
                       const smooth_progress = 0.5 + Math.sin(Math.PI * (progress - 0.5)) / 2;
                       let value = this._value !== null ? this._value : this._min;
                       value = (this._last_value + (value - this._last_value) * smooth_progress - this._min) / (this._max - this._min);
       
                       const ctx = this._canvas.getContext('2d');
                       const size = this._canvas.width;
                       const char_weight = size / 12;
                       const char_shadow = 3;
                       const char_x = size / 2;
                       const char_y = size / 2;
                       const char_radius = (size - char_weight) / 2 - char_shadow;
       
                       const font_ratio = 32 / 100;
       
                       ctx.clearRect(0, 0, size, size);
       
                       ctx.beginPath();
                       ctx.shadowBlur = char_shadow;
                       ctx.shadowColor = '#bbb';
                       ctx.strokeStyle = '#eee';
                       ctx.lineWidth = char_weight;
                       ctx.lineCap = 'round';
                       ctx.arc(char_x, char_y, char_radius, Math.PI * 0.749, Math.PI * 2.251, false);
                       ctx.stroke();
       
                       ctx.beginPath();
                       ctx.strokeStyle = `#${this._chart_color}`;
                       ctx.lineWidth = char_weight - 2;
                       ctx.lineCap = 'round';
                       ctx.arc(char_x, char_y, char_radius, Math.PI * 0.75,
                           Math.PI * (0.75 + (1.5 * Math.min(1, Math.max(0, value)))), false
                           );
                       ctx.stroke();
           
                       ctx.shadowBlur = 2;
                       ctx.fillStyle = '#1f2c33';
                       ctx.font = `${(char_radius * font_ratio)|0}px Arial`;
                       ctx.textAlign = 'center';
                       ctx.textBaseline = 'middle';
                       ctx.fillText(`${this._value !== null ? this._value : t('No data')}${this._units}`,
                           char_x, char_y, size - char_shadow * 4 - char_weight * 2
                       );
       
                       ctx.fillStyle = '#768d99';
                       ctx.font = `${(char_radius * font_ratio * .5)|0}px Arial`;
                       ctx.textBaseline = 'top';
       
                       ctx.textAlign = 'left';
                       ctx.fillText(`${this._min}${this._min != '' ? this._units : ''}`,
                           char_weight * .75, size - char_weight * 1.25, size / 2 - char_weight
                       );
       
                       ctx.textAlign = 'right';
                       ctx.fillText(`${this._max}${this._max != '' ? this._units : ''}`,
                           size - char_weight * .75, size - char_weight * 1.25, size / 2 - char_weight
                       );
       
                       requestAnimationFrame(animate);
                   }
                   else {
                       this._last_value = this._value;
                   }
               };
           
               requestAnimationFrame(animate);
           }
       }
  1. Obriu manifest.json i afegiu:
  • nom del fitxer (class.widget.js) a la matriu a la secci¨® assets/js.
  • nom de classe (WidgetLessonGaugeChart) al par¨¤metre js_class a la secci¨® widget.

La classe WidgetLessonGaugeChart ara es carregar¨¤ autom¨¤ticament amb el tauler.

ui/modules/lesson_gauge_chart/manifest.json

{
           "manifest_version": 2.0,
           "id": "lesson_gauge_chart",
           "type": "widget",
           "name": "Gauge chart",
           "namespace": "LessonGaugeChart",
           "version": "1.0",
           "author": "Áú»¢¶Ä²©",
           "actions": {
               "widget.lesson_gauge_chart.view": {
                   "class": "WidgetView"
               }
           },
           "widget": {
               "js_class": "WidgetLessonGaugeChart"
           },
           "assets": {
               "js": ["class.widget.js"]
           }
       }

Afegir estils CSS al giny.

En aquesta secci¨® aprendreu a afegir estils CSS personalitzats per fer que el giny sembli m¨¦s atractiu.

  1. Per als estils de giny, creeu un nou directori css dins del directori assets.

  2. Afegiu el fitxer widget.css a assets/css. Per estilitzar els elements del giny, empreu el selector div.dashboard-widget-{widget id}. Per configurar CSS per a tot el giny, empreu el selector form.dashboard-widget-{widget id}

ui/modules/lesson_gauge_chart/assets/css/widget.css

div.dashboard-widget-lesson_gauge_chart {
           display: grid;
           grid-template-rows: 1fr;
           padding: 0; 
       }
             
       div.dashboard-widget-lesson_gauge_chart .chart {
           display: grid;
           align-items: center;
           justify-items: center; 
       }
               
       div.dashboard-widget-lesson_gauge_chart .chart canvas {
           background: white; 
       }
             
       div.dashboard-widget-lesson_gauge_chart .description {
           padding-bottom: 8px;
           font-size: 1.750em;
           line-height: 1.2;
           text-align: center; 
       }
           
       .dashboard-grid-widget-hidden-header div.dashboard-widget-lesson_gauge_chart .chart {
           margin-top: 8px; 
       }
  1. Obriu manifest.json i afegiu el nom del fitxer (widget.css) a la matriu a la secci¨® assets/css. Aix¨° permetr¨¤ que els estils CSS definits al widget.css es carreguin amb la p¨¤gina del tauler.

ui/modules/lesson_gauge_chart/manifest.json

{
           "manifest_version": 2.0,
           "id": "lesson_gauge_chart",
           "type": "widget",
           "name": "Gauge chart",
           "namespace": "LessonGaugeChart",
           "version": "1.0",
           "author": "Áú»¢¶Ä²© SIA",
           "actions": {
               "widget.lesson_gauge_chart.view": {
                   "class": "WidgetView"
               }
           },
           "widget": {
               "js_class": "WidgetLessonGaugeChart"
           },
           "assets": {
               "css": ["widget.css"],
               "js": ["widget.js"]
           }
       }
  1. Actualitzeu la p¨¤gina del tauler per veure la versi¨® acabada del giny.