From 42eb6a19a9a8ad8b37d3964e71fd33b70e70ad5b Mon Sep 17 00:00:00 2001 From: Dan Garner Date: Thu, 31 Aug 2023 10:15:21 +0100 Subject: [PATCH 1/2] Toolbar: fix missing thumbnails xibosignageltd/xibo-private#403 --- ui/src/editor-core/toolbar.js | 34 ++++++++++++++++++++-------------- ui/src/style/common.scss | 25 ------------------------- 2 files changed, 20 insertions(+), 39 deletions(-) diff --git a/ui/src/editor-core/toolbar.js b/ui/src/editor-core/toolbar.js index 2186eeb3e7..dfb44651ca 100644 --- a/ui/src/editor-core/toolbar.js +++ b/ui/src/editor-core/toolbar.js @@ -165,6 +165,7 @@ Toolbar.prototype.init = function({isPlaylist = false} = {}) { moduleId: 'playlist', name: toolbarTrans.playlist, type: 'playlist', + icon: 'fa fa-list-ol', dataType: '', regionSpecific: 1, group: [], @@ -181,6 +182,7 @@ Toolbar.prototype.init = function({isPlaylist = false} = {}) { moduleId: 'zone', name: toolbarTrans.zone, type: 'zone', + icon: 'fas fa-border-none', dataType: '', target: 'layout', }); @@ -233,43 +235,43 @@ Toolbar.prototype.init = function({isPlaylist = false} = {}) { this.interactiveList = [ { name: toolbarTrans.interactive.actions.navWidget, - icon: 'fa fa-arrows-alt', + icon: 'fa fa-square-o', type: 'navWidget', target: '["frame"]', dataType: '', }, { name: toolbarTrans.interactive.actions.navLayout, - icon: 'fa fa-arrows-alt', + icon: 'fa fa-desktop', type: 'navLayout', target: '["layout"]', dataType: '', }, { - name: toolbarTrans.interactive.actions.nextWidget, - icon: 'fa-arrow-right-alt', - type: 'nextWidget', + name: toolbarTrans.interactive.actions.previousWidget, + icon: 'fa fa-caret-square-o-left', + type: 'previousWidget', target: '["playlist"]', dataType: '', }, { - name: toolbarTrans.interactive.actions.previousWidget, - icon: 'fa-arrow-left-alt', - type: 'previousWidget', + name: toolbarTrans.interactive.actions.nextWidget, + icon: 'fa fa-caret-square-o-right', + type: 'nextWidget', target: '["playlist"]', dataType: '', }, { - name: toolbarTrans.interactive.actions.nextLayout, - icon: 'fa-arrow-right', - type: 'nextLayout', + name: toolbarTrans.interactive.actions.previousLayout, + icon: 'fa fa-arrow-circle-left', + type: 'previousLayout', target: '["layout"]', dataType: '', }, { - name: toolbarTrans.interactive.actions.previousLayout, - icon: 'fa-arrow-left', - type: 'previousLayout', + name: toolbarTrans.interactive.actions.nextLayout, + icon: 'fa fa-arrow-circle-right', + type: 'nextLayout', target: '["layout"]', dataType: '', }, @@ -1540,6 +1542,10 @@ Toolbar.prototype.mediaContentPopulate = function(menu) { element.videoThumbnail = element.thumbnail; } + // Resolve the icon + element.icon = modulesList.filter((el) => + el.type === element.type)[0]?.icon || null; + // Use template const $card = $(ToolbarCardMediaTemplate(element)); diff --git a/ui/src/style/common.scss b/ui/src/style/common.scss index 1e50be12e6..e32733e073 100644 --- a/ui/src/style/common.scss +++ b/ui/src/style/common.scss @@ -271,31 +271,6 @@ $fa-font-path: "~font-awesome/fonts"; @extend .fa, .fa-user-secret; } -/* Actions icons */ -.actions-icon-navLayout { - @extend .fa, .fa-desktop; -} - -.actions-icon-navWidget { - @extend .fa, .fa-square-o; -} - -.actions-icon-nextWidget { - @extend .fa, .fa-caret-square-o-right; -} - -.actions-icon-previousWidget { - @extend .fa, .fa-caret-square-o-left; -} - -.actions-icon-nextLayout { - @extend .fa, .fa-arrow-circle-right; -} - -.actions-icon-previousLayout { - @extend .fa, .fa-arrow-circle-left; -} - /* Form icons */ .bg_not_found_icon { @extend .fa, .fa-exclamation-triangle; From 630ed86cb9c92497c5db43cddf57e3404eb634f8 Mon Sep 17 00:00:00 2001 From: Dan Garner Date: Thu, 31 Aug 2023 11:05:06 +0100 Subject: [PATCH 2/2] Interactive: fix action form. --- lib/Controller/Action.php | 151 ------------------------- lib/routes-web.php | 7 -- ui/src/editor-core/properties-panel.js | 23 +++- ui/src/layout-editor/main.js | 9 +- views/common.twig | 14 +-- 5 files changed, 29 insertions(+), 175 deletions(-) diff --git a/lib/Controller/Action.php b/lib/Controller/Action.php index f127241df7..70e8332886 100644 --- a/lib/Controller/Action.php +++ b/lib/Controller/Action.php @@ -24,7 +24,6 @@ use Slim\Http\Response as Response; use Slim\Http\ServerRequest as Request; -use Xibo\Entity\Widget; use Xibo\Factory\ActionFactory; use Xibo\Factory\LayoutFactory; use Xibo\Factory\ModuleFactory; @@ -219,25 +218,6 @@ public function grid(Request $request, Response $response) : Response // dynamic field to display in the grid instead of regionId $action->setUnmatchedProperty('regionName', $region->name); } - - if ($this->isApi($request)) { - continue; - } - - $action->includeProperty('buttons'); - $action->buttons = []; - - $action->buttons[] = [ - 'id' => 'action_edit_button', - 'url' => $this->urlFor($request, 'action.edit.form', ['id' => $action->actionId]), - 'text' => __('Edit') - ]; - - $action->buttons[] = [ - 'id' => 'action_delete_button', - 'url' => $this->urlFor($request, 'action.delete.form', ['id' => $action->actionId]), - 'text' => __('Delete') - ]; } $this->getState()->template = 'grid'; @@ -247,64 +227,6 @@ public function grid(Request $request, Response $response) : Response return $this->render($request, $response); } - /** - * Action Add Form - * @param Request $request - * @param Response $response - * @param string $source - * @param int $id - * @return \Psr\Http\Message\ResponseInterface|Response - * @throws GeneralException - */ - public function addForm(Request $request, Response $response, string $source, int $id) : Response - { - $sourceObject = $this->checkIfSourceExists($source, $id); - - if ($source === 'layout') { - /** @var \Xibo\Entity\Layout $layout */ - $layout = $sourceObject; - } elseif ($source === 'region') { - /** @var \Xibo\Entity\Region $region */ - $region = $sourceObject; - $layout = $this->layoutFactory->getById($region->layoutId); - } else { - /** @var Widget $widget */ - $widget = $sourceObject; - $region = $this->regionFactory->getByPlaylistId($widget->playlistId)[0]; - $layout = $this->layoutFactory->getById($region->layoutId); - } - - // Make sure the Layout is checked out to begin with - if (!$layout->isEditable()) { - throw new InvalidArgumentException(__('Layout is not checked out'), 'publishedStatusId'); - } - - $layout->load(); - - // all widgets - $widgets = $layout->getDrawerWidgets(); - - foreach ($widgets as $widget) { - $module = $this->moduleFactory->getByType($widget->type); - // if we don't have a name set in the Widget - $widget->setUnmatchedProperty( - 'name', - sprintf('%s [%s]', $widget->getOptionValue('name', $module->name), $module->type) - ); - } - - $this->getState()->template = 'action-form-add'; - $this->getState()->setData([ - 'sourceObject' => $sourceObject, - 'source' => $source, - 'id' => $id, - 'regions' => $layout->regions, - 'widgets' => $widgets, - ]); - - return $this->render($request, $response); - } - /** * Add a new Action * @@ -460,52 +382,6 @@ public function add(Request $request, Response $response) : Response return $this->render($request, $response); } - /** - * Action Edit Form - * @param Request $request - * @param Response $response - * @param int $id - * @return \Psr\Http\Message\ResponseInterface|Response - * @throws GeneralException - */ - public function editForm(Request $request, Response $response, int $id) : Response - { - $action = $this->actionFactory->getById($id); - $layout = $this->layoutFactory->getById($action->layoutId); - - $layout->load(); - - // all widgets, assigned to this layout or drawer - $widgets = $layout->getDrawerWidgets(); - - foreach ($widgets as $widget) { - $module = $this->moduleFactory->getByType($widget->type); - $widget->name = $widget->getOptionValue('name', $module->name); - } - - // Make sure the Layout is checked out to begin with - if (!$layout->isEditable()) { - throw new InvalidArgumentException(__('Layout is not checked out'), 'statusId'); - } - - try { - $code = (($action->layoutCode != null) ? [$this->layoutFactory->getByCode($action->layoutCode)] : []); - } catch (NotFoundException $notFoundException) { - $code = []; - } - - $this->getState()->template = 'action-form-edit'; - $this->getState()->setData([ - 'action' => $action, - 'source' => $action->source, - 'regions' => $layout->regions, - 'widgets' => $widgets, - 'layout' => $code - ]); - - return $this->render($request, $response); - } - /** * Edit Action * @@ -649,33 +525,6 @@ public function edit(Request $request, Response $response, int $id) : Response return $this->render($request, $response); } - /** - * Shows the Delete Group Form - * @param Request $request - * @param Response $response - * @param int $id - * @return \Psr\Http\Message\ResponseInterface|Response - * @throws GeneralException - */ - function deleteForm(Request $request, Response $response, int $id) : Response - { - $action = $this->actionFactory->getById($id); - $layout = $this->layoutFactory->getById($action->layoutId); - - // Make sure the Layout is checked out to begin with - if (!$layout->isEditable()) { - throw new InvalidArgumentException(__('Layout is not checked out'), 'publishedStatusId'); - } - - $this->getState()->template = 'action-form-delete'; - $this->getState()->setData([ - 'action' => $action, - 'source' => $action->source, - ]); - - return $this->render($request, $response); - } - /** * Delete Action * @param Request $request diff --git a/lib/routes-web.php b/lib/routes-web.php index 6e5e0e69cf..3cb33b770e 100644 --- a/lib/routes-web.php +++ b/lib/routes-web.php @@ -706,13 +706,6 @@ $group->get('/tag/form/usage/{id}', ['\Xibo\Controller\Tag', 'usageForm'])->setName('tag.usage.form'); })->addMiddleware(new FeatureAuth($app->getContainer(), ['tag.view'])); -// Actions -$app->group('', function(\Slim\Routing\RouteCollectorProxy $group) { - $group->get('/action/form/add/{source}/{id}', ['\Xibo\Controller\Action', 'addForm'])->setName('action.add.form'); - $group->get('/action/form/edit/{id}', ['\Xibo\Controller\Action', 'editForm'])->setName('action.edit.form'); - $group->get('/action/form/delete/{id}', ['\Xibo\Controller\Action', 'deleteForm'])->setName('action.delete.form'); -})->addMiddleware(new FeatureAuth($app->getContainer(), ['layout.modify', 'playlist.modify'])); - // Menu Boards $app->group('', function (\Slim\Routing\RouteCollectorProxy $group) { $group->get('/menuboard/view', ['\Xibo\Controller\MenuBoard','displayPage'])->setName('menuBoard.view'); diff --git a/ui/src/editor-core/properties-panel.js b/ui/src/editor-core/properties-panel.js index 66d4b5f02a..7d1d0831da 100644 --- a/ui/src/editor-core/properties-panel.js +++ b/ui/src/editor-core/properties-panel.js @@ -1,3 +1,24 @@ +/* + * Copyright (C) 2023 Xibo Signage Ltd + * + * Xibo - Digital Signage - https://xibosignage.com + * + * This file is part of Xibo. + * + * Xibo is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * any later version. + * + * Xibo is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with Xibo. If not, see . + */ + /* eslint-disable new-cap */ // PROPERTIES PANEL Module @@ -1899,7 +1920,7 @@ PropertiesPanel.prototype.openEditAction = function(action) { $newActionContainer.data(actionData); // Form conditions - forms.setConditions($newActionContainer); + forms.setConditions($newActionContainer, null, 'actions'); // Initialise tooltips app.common.reloadTooltips( diff --git a/ui/src/layout-editor/main.js b/ui/src/layout-editor/main.js index 6ce7b6e628..b49b4781fb 100644 --- a/ui/src/layout-editor/main.js +++ b/ui/src/layout-editor/main.js @@ -3944,8 +3944,9 @@ lD.populateDropdownWithLayoutElements = function( let typeInputValue = $dropdown.find(':selected').data('type'); // Update targetId and target + // Input fields are prepended with input_ if ( - $typeInput.attr('id') === 'target' + $typeInput.attr('id') === 'input_target' ) { // Update targetId and target actionData.targetId = $dropdown.val(); @@ -3954,7 +3955,7 @@ lD.populateDropdownWithLayoutElements = function( // Update sourceId and source if ( - $typeInput.attr('id') === 'source' + $typeInput.attr('id') === 'input_source' ) { // Update sourceId and source actionData.sourceId = $dropdown.val(); @@ -3971,7 +3972,9 @@ lD.populateDropdownWithLayoutElements = function( } // For target, if target is layout, change it to screen - if ($typeInput.attr('id') === 'target' && typeInputValue === 'layout') { + if ($typeInput.attr('id') === 'input_target' && + typeInputValue === 'layout' + ) { typeInputValue = 'screen'; } diff --git a/views/common.twig b/views/common.twig index 79e3321bde..a290f0963a 100644 --- a/views/common.twig +++ b/views/common.twig @@ -127,10 +127,6 @@ url: "{{ url_for("layout.delete.form", {id: ':id'}) }}", type: 'GET' }, - addActionForm: { - url: "{{ url_for("action.add.form", {source: 'layout', id:':id'}) }}", - type: 'GET' - }, addDrawer: { url: "{{ url_for("region.add.drawer", {id: ':id'}) }}", type: 'POST' @@ -183,10 +179,6 @@ getPermissions: { url: "{{ url_for("user.permissions.form", {entity: 'Region', id: ':id'}) }}", type: 'GET' - }, - addActionForm: { - url: "{{ url_for("action.add.form", {source: 'region', id:':id'}) }}", - type: 'GET' } }, widget: { @@ -234,10 +226,6 @@ url: "{{ url_for("user.permissions.form", {entity: 'Widget', id: ':id'}) }}", type: 'GET' }, - addActionForm: { - url: "{{ url_for("action.add.form", {source: 'widget', id:':id'}) }}", - type: 'GET' - }, setRegion: { url: "{{ url_for("module.widget.set.region", {id: ':id'}) }}", type: 'PUT' @@ -679,7 +667,7 @@ size: "{{ "Size" |trans }}", }, playlist: "{{ "Playlist"|trans }}", - zone: "{{ "Zone"|trans }}", + zone: "{{ "Zone"|trans }}", element: "{{ "Element"|trans }}", elementGroup: "{{ "Element Group"|trans }}", layout: "{{ "Layout"|trans }}",