Add basic video content element and first video

Allow to render videos with native HTML5 support in browser.
A first example video is also added to fileadmin.
This commit is contained in:
Daniel Siepmann 2020-08-19 23:01:35 +02:00
parent 840efdaa09
commit 746aaf3285
15 changed files with 215 additions and 4 deletions

View file

@ -0,0 +1,55 @@
<?php
namespace DanielSiepmann\DsSite\Backend\PreviewRenderer;
/*
* Copyright (C) 2020 Daniel Siepmann <coding@daniel-siepmann.de>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
use TYPO3\CMS\Backend\Preview\StandardContentPreviewRenderer;
use TYPO3\CMS\Backend\View\BackendLayout\Grid\GridColumnItem;
use TYPO3\CMS\Frontend\ContentObject\ContentDataProcessor;
use TYPO3\CMS\Frontend\ContentObject\ContentObjectRenderer;
use TYPO3\CMS\Frontend\DataProcessing\FilesProcessor;
class Video extends StandardContentPreviewRenderer
{
public function renderPageModulePreviewContent(GridColumnItem $item): string
{
$record = $item->getRecord();
$contentObjectRenderer = new ContentObjectRenderer();
$contentObjectRenderer->start($record, 'tt_content');
$record = (new ContentDataProcessor())->process($contentObjectRenderer, [
'dataProcessing.' => [
'10' => FilesProcessor::class,
'10.' => [
'references.' => [
'fieldName' => 'media',
],
'as' => 'videos',
],
],
], $record);
$item->setRecord($record);
return parent::renderPageModulePreviewContent($item);
}
}

View file

@ -1,6 +1,6 @@
mod.wizards.newContentElement.wizardItems { mod.wizards.newContentElement.wizardItems {
common { common {
show = text, image show = text, image, video
elements { elements {
image { image {
@ -26,6 +26,6 @@ mod.wizards.newContentElement.wizardItems {
} }
TCEFORM.tt_content { TCEFORM.tt_content {
CType { CType {
keepItems := addToList(text, image, menu_abstract, menu_subpages) keepItems := addToList(text, image, video, menu_abstract, menu_subpages)
} }
} }

View file

@ -0,0 +1,19 @@
mod {
wizards.newContentElement.wizardItems.common {
elements {
video {
iconIdentifier = content-media
title = Video
description = Displays a Video
tt_content_defValues {
CType = video
}
}
}
show := addToList(video)
}
web_layout.tt_content.preview.video = EXT:ds_site/Resources/Private/Templates/Backend/ContentElements/Video.html
}
TCEFORM.tt_content {
CType.keepItems := addToList(video)
}

View file

@ -0,0 +1,52 @@
<?php
use DanielSiepmann\DsSite\Backend\PreviewRenderer\Video;
(function (string $extensionKey, string $tableName, string $contentType) {
$languagePath = 'LLL:EXT:' . $extensionKey . '/Resources/Private/Language/locallang_tca.xlf:' . $tableName . '.';
\TYPO3\CMS\Core\Utility\ArrayUtility::mergeRecursiveWithOverrule($GLOBALS['TCA'][$tableName], [
'ctrl' => [
'typeicon_classes' => [
$contentType => 'content-media',
],
],
'types' => [
$contentType => [
'showitem' => implode(',', [
'--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:general',
'--palette--;;general',
' --palette--;;headers',
'media',
'--div--;LLL:EXT:frontend/Resources/Private/Language/locallang_ttc.xlf:tabs.appearance',
'--palette--;;frames',
'--palette--;;appearanceLinks',
'--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:language',
'--palette--;;language',
'--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:access',
'--palette--;;hidden',
'--palette--;;access',
'--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:categories',
'categories',
'--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:notes',
'rowDescription',
'--div--;LLL:EXT:core/Resources/Private/Language/Form/locallang_tabs.xlf:extended',
]),
'previewRenderer' => Video::class,
],
],
]);
\TYPO3\CMS\Core\Utility\ExtensionManagementUtility::addTcaSelectItem(
$tableName,
'CType',
[
$languagePath . $contentType,
$contentType,
'content-media',
'default'
],
'image',
'after'
);
})('ds_site', 'tt_content', 'video');

View file

@ -0,0 +1,16 @@
tt_content.video =< lib.contentElement
tt_content.video {
templateName = Video
dataProcessing {
10 = TYPO3\CMS\Frontend\DataProcessing\FilesProcessor
10 {
references.fieldName = media
as = videos
}
}
stdWrap {
editIcons := appendString(media)
}
}

View file

@ -9,6 +9,9 @@
<trans-unit id="tt_content.admonition"> <trans-unit id="tt_content.admonition">
<source>Admonition</source> <source>Admonition</source>
</trans-unit> </trans-unit>
<trans-unit id="tt_content.video">
<source>Video</source>
</trans-unit>
</body> </body>
</file> </file>
</xliff> </xliff>

View file

@ -1,6 +1,5 @@
<html xmlns:f="http://typo3.org/ns/TYPO3/Fluid/ViewHelpers" <html xmlns:f="http://typo3.org/ns/TYPO3/Fluid/ViewHelpers"
data-namespace-typo3-fluid="true"> data-namespace-typo3-fluid="true">
<figure> <figure>
<a href="{f:uri.image(image: image)}" target="_blank"><f:image image="{image}" maxWidth="1015" /></a> <a href="{f:uri.image(image: image)}" target="_blank"><f:image image="{image}" maxWidth="1015" /></a>
<figcaption>Figure i{image.originalFile.uid}: {image.description}</figcaption> <figcaption>Figure i{image.originalFile.uid}: {image.description}</figcaption>

View file

@ -0,0 +1,16 @@
<html xmlns:f="http://typo3.org/ns/TYPO3/Fluid/ViewHelpers"
data-namespace-typo3-fluid="true">
<figure>
<video controls>
<source src="{video.publicUrl}" type="video/mp4">
<p>
Sorry, your browser doesn't support embedded videos.<br>
You can find the raw video file here: <a href="{video.publicUrl}">{video.publicUrl}</a>
</p>
</video>
<figcaption>
<p>Video v{video.originalFile.uid}: {video.title}</p>
<p>{video.description -> f:format.nl2br()}</p>
</figcaption>
</figure>
</html>

View file

@ -16,3 +16,10 @@
color: #fff; color: #fff;
} }
} }
.exampleContent {
video {
width: 40rem;
max-width: 100%;
}
}

View file

@ -0,0 +1,3 @@
video {
max-width: 100%;
}

View file

@ -30,3 +30,4 @@
@import "components/feedit"; @import "components/feedit";
@import "components/ckeditor"; @import "components/ckeditor";
@import "components/admonition"; @import "components/admonition";
@import "components/video";

View file

@ -0,0 +1,22 @@
<html xmlns:f="http://typo3.org/ns/TYPO3/CMS/Fluid/ViewHelpers"
xmlns:be="http://typo3.org/ns/TYPO3/CMS/Backend/ViewHelpers"
data-namespace-typo3-fluid="true">
<a href="{be:uri.editRecord(
uid: uid,
table: 'tt_content'
)}">
<f:for each="{videos}" as="video">
<figure>
<video controls preload="metadata">
<source src="/{video.publicUrl}" type="video/mp4">
</video>
<figcaption>
<p>
Video v{video.originalFile.uid}: {video.title}<br>
{video.description -> f:format.nl2br()}
</p>
</figcaption>
</figure>
</f:for>
</a>
</html>

View file

@ -0,0 +1,11 @@
<html xmlns:f="http://typo3.org/ns/TYPO3/Fluid/ViewHelpers"
data-namespace-typo3-fluid="true">
{f:layout(name: 'Default')}
<f:section name="Content">
<f:for each="{videos}" as="video">
{f:render(partial: 'Video', arguments: {video: video})}
</f:for>
</f:section>
</html>

View file

@ -1 +1 @@
.typo3-login .panel,.typo3-login .panel-footer{background-color:rgba(0,0,0,.2)}.typo3-login input{color:#9cd9f0;border-color:#9cd9f0;background-color:#2e3436}.typo3-login .form-control:focus{border-color:#77dfd8}.typo3-login a{color:#fff} .typo3-login .panel,.typo3-login .panel-footer{background-color:rgba(0,0,0,.2)}.typo3-login input{color:#9cd9f0;border-color:#9cd9f0;background-color:#2e3436}.typo3-login .form-control:focus{border-color:#77dfd8}.typo3-login a{color:#fff}.exampleContent video{width:40rem;max-width:100%}

View file

@ -0,0 +1,7 @@
window.TYPO3.Feedit = {
openBackendHandler: function (event) {
event.preventDefault();
console.log(event);
},
};