diff --git a/database.sql b/database.sql
index 2d53b194ac..9abd088383 100644
--- a/database.sql
+++ b/database.sql
@@ -1,6 +1,6 @@
-- ------------------------------------------
-- Friendica 2025.07-rc (Interrupted Fern)
--- DB_UPDATE_VERSION 1580
+-- DB_UPDATE_VERSION 1581
-- ------------------------------------------
@@ -1441,6 +1441,9 @@ CREATE TABLE IF NOT EXISTS `post-media` (
`publisher-url` varbinary(383) COMMENT 'URL of the publisher of the media',
`publisher-name` varchar(255) COMMENT 'Name of the publisher of the media',
`publisher-image` varbinary(383) COMMENT 'Image of the publisher of the media',
+ `player-url` varbinary(383) COMMENT 'URL of the embedded player for this media',
+ `player-height` smallint unsigned COMMENT 'Height of the embedded player',
+ `player-width` smallint unsigned COMMENT 'Width of the embedded player',
`language` char(3) COMMENT 'Language information about this media in the ISO 639 format',
`published` datetime COMMENT 'Publification date of this media',
`modified` datetime COMMENT 'Modification date of this media',
diff --git a/doc/database/db_post-media.md b/doc/database/db_post-media.md
index acbd1f75cb..66abde57f3 100644
--- a/doc/database/db_post-media.md
+++ b/doc/database/db_post-media.md
@@ -30,6 +30,9 @@ Fields
| publisher-url | URL of the publisher of the media | varbinary(383) | YES | | NULL | |
| publisher-name | Name of the publisher of the media | varchar(255) | YES | | NULL | |
| publisher-image | Image of the publisher of the media | varbinary(383) | YES | | NULL | |
+| player-url | URL of the embedded player for this media | varbinary(383) | YES | | NULL | |
+| player-height | Height of the embedded player | smallint unsigned | YES | | NULL | |
+| player-width | Width of the embedded player | smallint unsigned | YES | | NULL | |
| language | Language information about this media in the ISO 639 format | char(3) | YES | | NULL | |
| published | Publification date of this media | datetime | YES | | NULL | |
| modified | Modification date of this media | datetime | YES | | NULL | |
diff --git a/src/Content/Item.php b/src/Content/Item.php
index 4b0791fe3a..9d3dc4878f 100644
--- a/src/Content/Item.php
+++ b/src/Content/Item.php
@@ -8,17 +8,16 @@
namespace Friendica\Content;
use Friendica\App\BaseURL;
-use Friendica\AppHelper;
use Friendica\Content\Text\BBCode;
use Friendica\Content\Text\BBCode\Video;
use Friendica\Content\Text\HTML;
+use Friendica\Core\Config\Capability\IManageConfigValues;
use Friendica\Core\L10n;
use Friendica\Core\PConfig\Capability\IManagePersonalConfigValues;
use Friendica\Core\Protocol;
use Friendica\Core\Session\Capability\IHandleUserSessions;
use Friendica\Core\System;
use Friendica\Database\DBA;
-use Friendica\DI;
use Friendica\Event\ArrayFilterEvent;
use Friendica\Model\Attach;
use Friendica\Model\Circle;
@@ -66,17 +65,17 @@ class Item
private $aclFormatter;
/** @var IManagePersonalConfigValues */
private $pConfig;
+ /** @var IManageConfigValues */
+ private $config;
/** @var BaseURL */
private $baseURL;
/** @var Emailer */
private $emailer;
- /** @var AppHelper */
- private $appHelper;
private EventDispatcherInterface $eventDispatcher;
/** @var LoggerInterface */
protected $logger;
- public function __construct(LoggerInterface $logger, Profiler $profiler, Activity $activity, L10n $l10n, IHandleUserSessions $userSession, Video $bbCodeVideo, ACLFormatter $aclFormatter, IManagePersonalConfigValues $pConfig, BaseURL $baseURL, Emailer $emailer, AppHelper $appHelper, EventDispatcherInterface $eventDispatcher)
+ public function __construct(LoggerInterface $logger, Profiler $profiler, Activity $activity, L10n $l10n, IHandleUserSessions $userSession, Video $bbCodeVideo, ACLFormatter $aclFormatter, IManagePersonalConfigValues $pConfig, IManageConfigValues $config, BaseURL $baseURL, Emailer $emailer, EventDispatcherInterface $eventDispatcher)
{
$this->profiler = $profiler;
$this->activity = $activity;
@@ -86,8 +85,8 @@ class Item
$this->aclFormatter = $aclFormatter;
$this->baseURL = $baseURL;
$this->pConfig = $pConfig;
+ $this->config = $config;
$this->emailer = $emailer;
- $this->appHelper = $appHelper;
$this->eventDispatcher = $eventDispatcher;
$this->logger = $logger;
}
@@ -1091,7 +1090,7 @@ class Item
public function isTooOld(string $created, int $uid = 0): bool
{
// check for create date and expire time
- $expire_interval = DI::config()->get('system', 'dbclean-expire-days', 0);
+ $expire_interval = $this->config->get('system', 'dbclean-expire-days', 0);
if ($uid) {
$user = DBA::selectFirst('user', ['expire'], ['uid' => $uid]);
@@ -1205,8 +1204,6 @@ class Item
$result = [];
- $eventDispatcher = DI::eventDispatcher();
-
foreach ($this->splitByBlocks($searchtext) as $block) {
$languages = $ld->detect($block)->close() ?: [];
@@ -1217,7 +1214,7 @@ class Item
'author-id' => $author_id,
];
- $hook_data = $eventDispatcher->dispatch(
+ $hook_data = $this->eventDispatcher->dispatch(
new ArrayFilterEvent(ArrayFilterEvent::DETECT_LANGUAGES, $hook_data),
)->getArray();
@@ -1355,4 +1352,38 @@ class Item
$used_languages = $this->l10n->t("Detected languages in this post:\n%s", $used_languages);
return $used_languages;
}
+
+ /**
+ * Returns the HTML code for an iframe player for embedded content like videos.
+ * The iframe will automatically adjust its height based on the aspect ratio.
+ *
+ * @param string $player_url URL of the embedded player
+ * @param int|null $width Player width
+ * @param int|null $height Player height
+ * @return string
+ */
+ public function getPlayerIframe(string $player_url, ?int $width, ?int $height): string
+ {
+ $attributes = ' src="' . $player_url . '"';
+ $max_height = $this->config->get('system', 'max_video_height') ?: $height;
+
+ if ($width != 0 && $height != 0) {
+ if ($height > $width && $height > $max_height) {
+ $factor = 100;
+ $height_attr = $max_height;
+ } else {
+ $factor = round($height / $width, 2) * 100;
+ $height_attr = '100%';
+ }
+ $attributes .= ' height="' . $height_attr. '" style="position:absolute;left:0px;top:0px"';
+ $return = '
';
+ } else {
+ $height = min($max_height, $height);
+ $attributes .= ' height="' . $height . '"';
+ $return = '
';
+ }
+
+ $return .= '
';
+ return $return;
+ }
}
diff --git a/src/Content/Post/Entity/PostMedia.php b/src/Content/Post/Entity/PostMedia.php
index b06e258710..1c8ed55927 100644
--- a/src/Content/Post/Entity/PostMedia.php
+++ b/src/Content/Post/Entity/PostMedia.php
@@ -35,6 +35,9 @@ use Psr\Http\Message\UriInterface;
* @property-read ?string $publisherName
* @property-read ?UriInterface $publisherImage
* @property-read ?string $blurhash
+ * @property-read ?UriInterface $playerUrl
+ * @property-read ?int $playerWidth
+ * @property-read ?int $playerHeight
*/
class PostMedia extends BaseEntity
{
@@ -98,6 +101,12 @@ class PostMedia extends BaseEntity
* @see https://blurha.sh/
*/
protected $blurhash;
+ /** @var ?UriInterface Player URL */
+ protected $playerUrl;
+ /** @var ?int In pixels */
+ protected $playerWidth;
+ /** @var ?int In pixels */
+ protected $playerHeight;
public function __construct(
int $uriId,
@@ -120,7 +129,10 @@ class PostMedia extends BaseEntity
?string $publisherName = null,
?UriInterface $publisherImage = null,
?string $blurhash = null,
- int $id = null
+ ?UriInterface $playerUrl = null,
+ ?int $playerWidth = null,
+ ?int $playerHeight = null,
+ ?int $id = null
) {
$this->uriId = $uriId;
$this->url = $url;
@@ -142,6 +154,9 @@ class PostMedia extends BaseEntity
$this->publisherName = $publisherName;
$this->publisherImage = $publisherImage;
$this->blurhash = $blurhash;
+ $this->playerUrl = $playerUrl;
+ $this->playerWidth = $playerWidth;
+ $this->playerHeight = $playerHeight;
$this->id = $id;
}
@@ -247,6 +262,9 @@ class PostMedia extends BaseEntity
$this->publisherName,
$this->publisherImage,
$this->blurhash,
+ $this->playerUrl,
+ $this->playerWidth,
+ $this->playerHeight,
$this->id,
);
}
@@ -274,6 +292,9 @@ class PostMedia extends BaseEntity
$this->publisherName,
$this->publisherImage,
$this->blurhash,
+ $this->playerUrl,
+ $this->playerWidth,
+ $this->playerHeight,
$this->id,
);
}
diff --git a/src/Content/Post/Factory/PostMedia.php b/src/Content/Post/Factory/PostMedia.php
index 1ebedda72e..e1e1a58dd1 100644
--- a/src/Content/Post/Factory/PostMedia.php
+++ b/src/Content/Post/Factory/PostMedia.php
@@ -55,6 +55,9 @@ class PostMedia extends BaseFactory implements ICanCreateFromTableRow
$row['publisher-name'],
UtilNetwork::createUriFromString($row['publisher-image']),
$row['blurhash'],
+ UtilNetwork::createUriFromString($row['player-url']),
+ $row['player-width'],
+ $row['player-height'],
$row['id']
);
}
diff --git a/src/Content/Post/Repository/PostMedia.php b/src/Content/Post/Repository/PostMedia.php
index 72e337b211..d0c847858a 100644
--- a/src/Content/Post/Repository/PostMedia.php
+++ b/src/Content/Post/Repository/PostMedia.php
@@ -79,6 +79,9 @@ class PostMedia extends BaseRepository
'publisher-image' => $PostMedia->publisherImage ? $PostMedia->publisherImage->__toString() : null,
'media-uri-id' => $PostMedia->activityUriId,
'blurhash' => $PostMedia->blurhash,
+ 'player-url' => $PostMedia->playerUrl,
+ 'player-height' => $PostMedia->playerHeight,
+ 'player-width' => $PostMedia->playerWidth,
];
if ($PostMedia->id) {
diff --git a/src/Content/Text/BBCode.php b/src/Content/Text/BBCode.php
index f4eeb8a764..c42964901b 100644
--- a/src/Content/Text/BBCode.php
+++ b/src/Content/Text/BBCode.php
@@ -414,7 +414,7 @@ class BBCode
* @return string
* @throws \Friendica\Network\HTTPException\InternalServerErrorException
*/
- public static function convertAttachment(string $text, int $simplehtml = self::INTERNAL, bool $tryoembed = true, array $data = [], int $uriid = 0, int $preview_mode = self::PREVIEW_LARGE): string
+ public static function convertAttachment(string $text, int $simplehtml = self::INTERNAL, bool $tryoembed = true, array $data = [], int $uriid = 0, int $preview_mode = self::PREVIEW_LARGE, bool $embed = false): string
{
DI::profiler()->startRecording('rendering');
$data = $data ?: self::getAttachmentData($text);
@@ -451,6 +451,11 @@ class BBCode
$return = sprintf('
', $data['type']);
}
+ if ($embed && $data['player_url'] != '' && $data['player_height'] != 0) {
+ $return .= DI::contentItem()->getPlayerIframe($data['player_url'], $data['player_width'], $data['player_height']);
+ $preview_mode = self::PREVIEW_NO_IMAGE;
+ }
+
if ($preview_mode == self::PREVIEW_NO_IMAGE) {
unset($data['image']);
unset($data['preview']);
diff --git a/src/Model/Item.php b/src/Model/Item.php
index 47f96c5cb6..a288d9f3f4 100644
--- a/src/Model/Item.php
+++ b/src/Model/Item.php
@@ -610,7 +610,7 @@ class Item
/**
* Inserts item record
*
- * @param array
$item Item array to be inserted
+ * @param array $item Item array to be inserted
* @param int $notify Notification (type?)
* @param bool $post_local (???)
* @return int Zero means error, otherwise primary key (id) is being returned
@@ -3033,8 +3033,8 @@ class Item
if (!empty($sharedSplitAttachments)) {
$s = self::addGallery($s, $sharedSplitAttachments['visual']);
- $s = self::addVisualAttachments($sharedSplitAttachments['visual'], $shared_item, $s, true);
- $s = self::addLinkAttachment($shared_uri_id ?: $item['uri-id'], $sharedSplitAttachments, $body, $s, true, $quote_shared_links);
+ $s = self::addVisualAttachments($sharedSplitAttachments['visual'], $shared_item, $s, true, $uid);
+ $s = self::addLinkAttachment($shared_uri_id ?: $item['uri-id'], $sharedSplitAttachments, $body, $s, true, $quote_shared_links, $uid);
$s = self::addNonVisualAttachments($sharedSplitAttachments['additional'], $item, $s);
$body = BBCode::removeSharedData($body);
}
@@ -3046,8 +3046,8 @@ class Item
}
$s = self::addGallery($s, $itemSplitAttachments['visual']);
- $s = self::addVisualAttachments($itemSplitAttachments['visual'], $item, $s, false);
- $s = self::addLinkAttachment($item['uri-id'], $itemSplitAttachments, $body, $s, false, $shared_links);
+ $s = self::addVisualAttachments($itemSplitAttachments['visual'], $item, $s, false, $uid);
+ $s = self::addLinkAttachment($item['uri-id'], $itemSplitAttachments, $body, $s, false, $shared_links, $uid);
$s = self::addNonVisualAttachments($itemSplitAttachments['additional'], $item, $s);
$s = self::addQuestions($item, $s);
@@ -3246,10 +3246,11 @@ class Item
* @param array $item
* @param string $content
* @param bool $shared
+ * @param int $uid
* @return string modified content
* @throws ServiceUnavailableException
*/
- private static function addVisualAttachments(PostMedias $PostMedias, array $item, string $content, bool $shared): string
+ private static function addVisualAttachments(PostMedias $PostMedias, array $item, string $content, bool $shared, int $uid): string
{
DI::profiler()->startRecording('rendering');
$leading = '';
@@ -3282,19 +3283,25 @@ class Item
$height = 'auto';
$width = '100%';
}
- /// @todo Move the template to /content as well
- $media = Renderer::replaceMacros(Renderer::getMarkupTemplate($PostMedia->type == Post\Media::HLS ? 'hls_top.tpl' : 'video_top.tpl'), [
- '$video' => [
- 'id' => $PostMedia->id,
- 'src' => (string)$PostMedia->url,
- 'name' => $PostMedia->name ?: $PostMedia->url,
- 'preview' => $preview_url,
- 'mime' => (string)$PostMedia->mimetype,
- 'height' => $height,
- 'width' => $width,
- 'description' => $PostMedia->description,
- ],
- ]);
+
+ if (DI::pConfig()->get($uid, 'system', 'embed_media', false) && ($PostMedia->playerUrl != '') && ($PostMedia->playerHeight > 0)) {
+ $media = DI::contentItem()->getPlayerIframe($PostMedia->playerUrl, $PostMedia->playerWidth, $PostMedia->playerHeight);
+ } else {
+ /// @todo Move the template to /content as well
+ $media = Renderer::replaceMacros(Renderer::getMarkupTemplate($PostMedia->type == Post\Media::HLS ? 'hls_top.tpl' : 'video_top.tpl'), [
+ '$video' => [
+ 'id' => $PostMedia->id,
+ 'src' => (string)$PostMedia->url,
+ 'name' => $PostMedia->name ?: $PostMedia->url,
+ 'preview' => $preview_url,
+ 'mime' => (string)$PostMedia->mimetype,
+ 'height' => $height,
+ 'width' => $width,
+ 'description' => $PostMedia->description,
+ ],
+ ]);
+ }
+
if (($item['post-type'] ?? null) == Item::PT_VIDEO) {
$leading .= $media;
} else {
@@ -3320,7 +3327,7 @@ class Item
continue;
}
- if (empty($PostMedia->description) && DI::pConfig()->get(DI::userSession()->getLocalUserId(), 'accessibility', 'hide_empty_descriptions')) {
+ if (empty($PostMedia->description) && DI::pConfig()->get($uid, 'accessibility', 'hide_empty_descriptions')) {
continue;
}
$images[] = $PostMedia->withUrl(new Uri($src_url))->withPreview(new Uri($preview_url), $preview_size);
@@ -3362,11 +3369,12 @@ class Item
* @param string $content
* @param bool $shared
* @param array $ignore_links A list of URLs to ignore
+ * @param int $uid
* @return string modified content
* @throws InternalServerErrorException
* @throws ServiceUnavailableException
*/
- private static function addLinkAttachment(int $uriid, array $attachments, string $body, string $content, bool $shared, array $ignore_links): string
+ private static function addLinkAttachment(int $uriid, array $attachments, string $body, string $content, bool $shared, array $ignore_links, int $uid): string
{
DI::profiler()->startRecording('rendering');
// Don't show a preview when there is a visual attachment (audio or video)
@@ -3405,6 +3413,10 @@ class Item
'title' => $attachment->name ?? '',
'type' => 'link',
'url' => (string)$attachment->url,
+ 'player_url' => (string)$attachment->playerUrl,
+ 'player_width' => $attachment->playerWidth,
+ 'player_height' => $attachment->playerHeight,
+
];
if ($preview && $attachment->preview) {
@@ -3455,9 +3467,9 @@ class Item
}
// @todo Use a template
- $preview_mode = DI::pConfig()->get(DI::userSession()->getLocalUserId(), 'system', 'preview_mode', BBCode::PREVIEW_LARGE);
+ $preview_mode = DI::pConfig()->get($uid, 'system', 'preview_mode', BBCode::PREVIEW_LARGE);
if ($preview_mode != BBCode::PREVIEW_NONE) {
- $rendered = BBCode::convertAttachment('', BBCode::INTERNAL, false, $data, $uriid, $preview_mode);
+ $rendered = BBCode::convertAttachment('', BBCode::INTERNAL, false, $data, $uriid, $preview_mode, DI::pConfig()->get($uid, 'system', 'embed_remote_media', false));
} elseif (!self::containsLink($content, $data['url'], Post\Media::HTML)) {
$rendered = Renderer::replaceMacros(Renderer::getMarkupTemplate('content/link.tpl'), [
'$url' => $data['url'],
diff --git a/src/Model/Post/Media.php b/src/Model/Post/Media.php
index d069ef15cc..7400505d47 100644
--- a/src/Model/Post/Media.php
+++ b/src/Model/Post/Media.php
@@ -459,16 +459,19 @@ class Media
}
$media['type'] = self::HTML;
- $media['size'] = $data['size'] ?? null;
- $media['author-url'] = $data['author_url'] ?? null;
- $media['author-name'] = $data['author_name'] ?? null;
- $media['author-image'] = $data['author_img'] ?? null;
- $media['publisher-url'] = $data['publisher_url'] ?? null;
- $media['publisher-name'] = $data['publisher_name'] ?? null;
- $media['publisher-image'] = $data['publisher_img'] ?? null;
- $media['language'] = $data['language'] ?? null;
- $media['published'] = $data['published'] ?? null;
- $media['modified'] = $data['modified'] ?? null;
+ $media['size'] = $data['size'] ?? null;
+ $media['author-url'] = $data['author_url'] ?? null;
+ $media['author-name'] = $data['author_name'] ?? null;
+ $media['author-image'] = $data['author_img'] ?? null;
+ $media['publisher-url'] = $data['publisher_url'] ?? null;
+ $media['publisher-name'] = $data['publisher_name'] ?? null;
+ $media['publisher-image'] = $data['publisher_img'] ?? null;
+ $media['player-url'] = $data['player']['embed'] ?? null;
+ $media['player-height'] = $data['player']['height'] ?? null;
+ $media['player-width'] = $data['player']['width'] ?? null;
+ $media['language'] = $data['language'] ?? null;
+ $media['published'] = $data['published'] ?? null;
+ $media['modified'] = $data['modified'] ?? null;
if (DI::config()->get('system', 'add_page_media')) {
if (!empty($data['audio'])) {
@@ -624,7 +627,8 @@ class Media
/**
* Fetch video dimensions using getID3
*
- * @param array $media
+ * @param array $media Media array
+ * @param bool $full_file If true, the whole video will be fetched
* @return array media with added dimensions
*/
private static function getVideoDimensions(array $media, bool $full_file): array
diff --git a/src/Module/Settings/Display.php b/src/Module/Settings/Display.php
index 95a6cbc8c2..12da8f79eb 100644
--- a/src/Module/Settings/Display.php
+++ b/src/Module/Settings/Display.php
@@ -104,6 +104,8 @@ class Display extends BaseSettings
$display_eventlist = (bool)$request['display_eventlist'];
$preview_mode = (int)$request['preview_mode'];
$update_content = (int)$request['update_content'];
+ $embed_remote_media = (bool)$request['embed_remote_media'];
+ $embed_media = (bool)$request['embed_media'];
$enabled_timelines = [];
foreach ($enable as $code => $enabled) {
@@ -148,6 +150,8 @@ class Display extends BaseSettings
$this->pConfig->set($uid, 'system', 'show_page_drop', $show_page_drop);
$this->pConfig->set($uid, 'system', 'display_eventlist', $display_eventlist);
$this->pConfig->set($uid, 'system', 'preview_mode', $preview_mode);
+ $this->pConfig->set($uid, 'system', 'embed_remote_media', $embed_remote_media);
+ $this->pConfig->set($uid, 'system', 'embed_media', $embed_media);
$this->pConfig->set($uid, 'system', 'network_timelines', $network_timelines);
$this->pConfig->set($uid, 'system', 'enabled_timelines', $enabled_timelines);
@@ -241,6 +245,8 @@ class Display extends BaseSettings
$stay_local = $this->pConfig->get($uid, 'system', 'stay_local', true);
$show_page_drop = $this->pConfig->get($uid, 'system', 'show_page_drop', true);
$display_eventlist = $this->pConfig->get($uid, 'system', 'display_eventlist', true);
+ $embed_remote_media = $this->pConfig->get($uid, 'system', 'embed_remote_media', false);
+ $embed_media = $this->pConfig->get($uid, 'system', 'embed_media', false);
$hide_empty_descriptions = $this->pConfig->get($uid, 'accessibility', 'hide_empty_descriptions', false);
$hide_custom_emojis = $this->pConfig->get($uid, 'accessibility', 'hide_custom_emojis', false);
@@ -335,6 +341,8 @@ class Display extends BaseSettings
'$hide_empty_descriptions' => ['hide_empty_descriptions', $this->t('Hide pictures with empty alternative text'), $hide_empty_descriptions, $this->t("Don't display pictures that are missing the alternative text.")],
'$hide_custom_emojis' => ['hide_custom_emojis', $this->t('Hide custom emojis'), $hide_custom_emojis, $this->t("Don't display custom emojis.")],
'$platform_icon_style' => ['platform_icon_style', $this->t('Platform icons style'), $platform_icon_style, $this->t('Style of the platform icons'), $platform_icon_styles, false],
+ '$embed_remote_media' => ['embed_remote_media', $this->t('Embed remote media'), $embed_remote_media, $this->t('When enabled, remote media will be embedded in the post, like for example YouTube videos.')],
+ '$embed_media' => ['embed_media', $this->t('Embed supported media'), $embed_media, $this->t('When enabled, remote media will be embedded in the post instead of using the local player if this is supported by the remote system. This is useful for media where the remote player is better than the local one, like for example Peertube videos.')],
'$timeline_label' => $this->t('Label'),
'$timeline_descriptiom' => $this->t('Description'),
diff --git a/src/Protocol/ActivityPub/Processor.php b/src/Protocol/ActivityPub/Processor.php
index 9d3ab19b1b..f21ca48d1a 100644
--- a/src/Protocol/ActivityPub/Processor.php
+++ b/src/Protocol/ActivityPub/Processor.php
@@ -145,15 +145,18 @@ class Processor
return;
}
- $data = ['uri-id' => $uriid];
- $data['type'] = Post\Media::UNKNOWN;
- $data['url'] = $attachment['url'];
- $data['mimetype'] = $attachment['mediaType'] ?? null;
- $data['height'] = $attachment['height'] ?? null;
- $data['width'] = $attachment['width'] ?? null;
- $data['size'] = $attachment['size'] ?? null;
- $data['preview'] = $attachment['image'] ?? null;
- $data['description'] = $attachment['name'] ?? null;
+ $data = ['uri-id' => $uriid];
+ $data['type'] = Post\Media::UNKNOWN;
+ $data['url'] = $attachment['url'];
+ $data['mimetype'] = $attachment['mediaType'] ?? null;
+ $data['height'] = $attachment['height'] ?? null;
+ $data['width'] = $attachment['width'] ?? null;
+ $data['size'] = $attachment['size'] ?? null;
+ $data['preview'] = $attachment['image'] ?? null;
+ $data['description'] = $attachment['name'] ?? null;
+ $data['player-url'] = $attachment['player-url'] ?? null;
+ $data['player-height'] = $attachment['player-height'] ?? null;
+ $data['player-width'] = $attachment['player-width'] ?? null;
Post\Media::insert($data);
}
diff --git a/src/Protocol/ActivityPub/Receiver.php b/src/Protocol/ActivityPub/Receiver.php
index f5d11d5cca..1392ec7869 100644
--- a/src/Protocol/ActivityPub/Receiver.php
+++ b/src/Protocol/ActivityPub/Receiver.php
@@ -28,6 +28,7 @@ use Friendica\Util\HTTPSignature;
use Friendica\Util\JsonLD;
use Friendica\Util\LDSignature;
use Friendica\Util\Network;
+use Friendica\Util\ParseUrl;
use Friendica\Util\Strings;
/**
@@ -1861,11 +1862,12 @@ class Receiver
* This is the case with audio and video posts.
* Then the links are added as attachments
*
- * @param array $urls The object URL list
- * @param string|null $icon The icon URL to use for the attachments
+ * @param array $urls The object URL list
+ * @param string|null $icon The icon URL to use for the attachments
+ * @param array $player Embedded player data (url, width, height)
* @return array an array of attachments
*/
- private static function processAttachmentUrls(array $urls, ?string $icon): array
+ private static function processAttachmentUrls(array $urls, ?string $icon, array $player): array
{
$attachments = [];
foreach ($urls as $key => $url) {
@@ -1890,32 +1892,53 @@ class Receiver
$filetype = strtolower(substr($mediatype, 0, strpos($mediatype, '/')));
+ $height = JsonLD::fetchElement($url, 'as:height', '@value');
+ $width = JsonLD::fetchElement($url, 'as:width', '@value');
+
if ($filetype == 'audio') {
- $attachments[] = ['type' => $filetype, 'mediaType' => $mediatype, 'url' => $href, 'height' => null, 'size' => null, 'name' => '', 'image' => $icon];
+ $attachments[] = ['type' => $filetype, 'mediaType' => $mediatype, 'url' => $href, 'height' => $height, 'width' => $width, 'size' => null, 'name' => '', 'image' => $icon];
} elseif ($filetype == 'video') {
- $height = (int)JsonLD::fetchElement($url, 'as:height', '@value');
// PeerTube audio-only track
- if ($height === 0) {
+ if (!$height) {
continue;
}
$size = (int)JsonLD::fetchElement($url, 'pt:size', '@value');
- $attachments[] = ['type' => $filetype, 'mediaType' => $mediatype, 'url' => $href, 'height' => $height, 'size' => $size, 'name' => '', 'image' => $icon];
+ $attachments[] = ['type' => $filetype, 'mediaType' => $mediatype, 'url' => $href, 'height' => $height, 'width' => $width, 'size' => $size, 'name' => '', 'image' => $icon];
} elseif (in_array($mediatype, ['application/x-bittorrent', 'application/x-bittorrent;x-scheme-handler/magnet'])) {
- $height = (int)JsonLD::fetchElement($url, 'as:height', '@value');
-
// For Torrent links we always store the highest resolution
if (!empty($attachments[$mediatype]['height']) && ($height < $attachments[$mediatype]['height'])) {
continue;
}
- $attachments[$mediatype] = ['type' => $mediatype, 'mediaType' => $mediatype, 'url' => $href, 'height' => $height, 'size' => null, 'name' => ''];
+ $attachments[$mediatype] = ['type' => $mediatype, 'mediaType' => $mediatype, 'url' => $href, 'height' => $height, 'width' => $width, 'size' => null, 'name' => ''];
} elseif ($mediatype == 'application/x-mpegURL') {
// PeerTube uses HLS streams for video. We prefer HLS streams over the video file itself.
// But we still store the video file as an attachment to be used by the API which currently does not support HLS streams.
- $attachments = array_merge($attachments, self::processAttachmentUrls($url['as:tag'], $icon));
- $attachments[] = ['type' => $filetype, 'mediaType' => $mediatype, 'url' => $href, 'height' => null, 'size' => null, 'name' => '', 'image' => $icon];
+ $attachments = array_merge($attachments, self::processAttachmentUrls($url['as:tag'], $icon, []));
+
+ $attachment = ['type' => $filetype, 'mediaType' => $mediatype, 'url' => $href, 'height' => $height, 'width' => $width, 'size' => null, 'name' => '', 'image' => $icon];
+ if (!empty($player)) {
+ $attachment['player-url'] = $player['embed'] ?? null;
+ $attachment['player-height'] = $player['height'] ?? null;
+ $attachment['player-width'] = $player['width'] ?? null;
+
+ foreach ($attachments as $media) {
+ if (isset($media['height']) && isset($media['width'])) {
+ if ($media['height'] > $attachment['player-height'] || $media['width'] > $attachment['player-width']) {
+ $attachment['player-height'] = $media['height'];
+ $attachment['player-width'] = $media['width'];
+ }
+ }
+ }
+ if (!$height && !$width) {
+ $attachment['height'] = $attachment['player-height'];
+ $attachment['width'] = $attachment['player-width'];
+ }
+ }
+ DI::logger()->info('Adding video attachment', ['attachment' => $attachment]);
+ $attachments[] = $attachment;
}
}
@@ -2095,7 +2118,15 @@ class Receiver
if (in_array($object_data['object_type'], ['as:Audio', 'as:Video'])) {
$object_data['alternate-url'] = self::extractAlternateUrl($object['as:url'] ?? []) ?: $object_data['alternate-url'];
- $object_data['attachments'] = array_merge($object_data['attachments'], self::processAttachmentUrls($object['as:url'] ?? [], self::processIcon($object)));
+
+ $siteinfo = ParseUrl::getSiteinfoCached($object_data['alternate-url']);
+ if (isset($siteinfo['player'])) {
+ $player = $siteinfo['player'];
+ } else {
+ $player = [];
+ }
+
+ $object_data['attachments'] = array_merge($object_data['attachments'], self::processAttachmentUrls($object['as:url'] ?? [], self::processIcon($object), $player));
}
$object_data['can-comment'] = JsonLD::fetchElement($object, 'pt:commentsEnabled', '@value');
diff --git a/static/dbstructure.config.php b/static/dbstructure.config.php
index 183b2281d3..031cef6174 100644
--- a/static/dbstructure.config.php
+++ b/static/dbstructure.config.php
@@ -44,7 +44,7 @@ use Friendica\Database\DBA;
// This file is required several times during the test in DbaDefinition which justifies this condition
if (!defined('DB_UPDATE_VERSION')) {
- define('DB_UPDATE_VERSION', 1580);
+ define('DB_UPDATE_VERSION', 1581);
}
return [
@@ -1447,6 +1447,9 @@ return [
"publisher-url" => ["type" => "varbinary(383)", "comment" => "URL of the publisher of the media"],
"publisher-name" => ["type" => "varchar(255)", "comment" => "Name of the publisher of the media"],
"publisher-image" => ["type" => "varbinary(383)", "comment" => "Image of the publisher of the media"],
+ "player-url" => ["type" => "varbinary(383)", "comment" => "URL of the embedded player for this media"],
+ "player-height" => ["type" => "smallint unsigned", "comment" => "Height of the embedded player"],
+ "player-width" => ["type" => "smallint unsigned", "comment" => "Width of the embedded player"],
"language" => ["type" => "char(3)", "comment" => "Language information about this media in the ISO 639 format"],
"published" => ["type" => "datetime", "comment" => "Publification date of this media"],
"modified" => ["type" => "datetime", "comment" => "Modification date of this media"],
diff --git a/tests/src/Content/Text/BBCodeTest.php b/tests/src/Content/Text/BBCodeTest.php
index 1717ae5aa1..46fe865212 100644
--- a/tests/src/Content/Text/BBCodeTest.php
+++ b/tests/src/Content/Text/BBCodeTest.php
@@ -722,4 +722,42 @@ Lucas: For the right price, yes.[/share]',
self::assertEquals($expected, $actual);
}
+
+ public function dataConvertAttachment(): array
+ {
+ return [
+ 'player' => [
+ 'expected' => 'text ',
+ 'data' => [
+ 'author_name' => 'author_name',
+ 'author_url' => 'http://domain.tld/author_url',
+ 'description' => 'description',
+ 'image' => 'http://domain.tld/image',
+ 'preview' => 'http://domain.tld/preview',
+ 'provider_name' => 'provider_name',
+ 'provider_url' => 'http://domain.tld/provider_url',
+ 'text' => 'text',
+ 'title' => 'title',
+ 'type' => 'link',
+ 'url' => 'http://domain.tld/page',
+ 'player_url' => 'http://domain.tld/player',
+ 'player_width' => 640,
+ 'player_height' => 480,
+ ],
+ ],
+ ];
+ }
+
+ /**
+ * @dataProvider dataConvertAttachment
+ *
+ * @param string $expected Expected BBCode output
+ * @param string $text Input text
+ */
+ public function testConvertAttachment(string $expected, array $data)
+ {
+ $actual = BBCode::convertAttachment('', BBCode::INTERNAL, true, $data, 0, BBCode::PREVIEW_LARGE, true);
+
+ self::assertEquals($expected, $actual);
+ }
}
diff --git a/view/lang/C/messages.po b/view/lang/C/messages.po
index 9709f96044..5d72c3cde6 100644
--- a/view/lang/C/messages.po
+++ b/view/lang/C/messages.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: 2025.07-rc\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2025-09-03 21:32+0200\n"
+"POT-Creation-Date: 2025-09-05 02:58+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME \n"
"Language-Team: LANGUAGE \n"
@@ -70,7 +70,7 @@ msgstr ""
#: src/Module/Settings/ContactImport.php:49
#: src/Module/Settings/ContactImport.php:96
#: src/Module/Settings/Delegation.php:76 src/Module/Settings/Display.php:80
-#: src/Module/Settings/Display.php:188
+#: src/Module/Settings/Display.php:192
#: src/Module/Settings/Profile/Photo/Crop.php:148
#: src/Module/Settings/Profile/Photo/Index.php:96
#: src/Module/Settings/RemoveMe.php:103 src/Module/Settings/UserExport.php:64
@@ -1756,7 +1756,7 @@ msgstr ""
#: src/Content/Feature.php:131 src/Content/Widget.php:613
#: src/Module/Admin/Site.php:463 src/Module/BaseSettings.php:113
-#: src/Module/Settings/Channels.php:216 src/Module/Settings/Display.php:313
+#: src/Module/Settings/Channels.php:216 src/Module/Settings/Display.php:319
msgid "Channels"
msgstr ""
@@ -1845,57 +1845,57 @@ msgstr ""
msgid "Create new group"
msgstr ""
-#: src/Content/Item.php:329 src/Model/Item.php:2780
+#: src/Content/Item.php:328 src/Model/Item.php:2780
msgid "event"
msgstr ""
-#: src/Content/Item.php:332 src/Content/Item.php:342
+#: src/Content/Item.php:331 src/Content/Item.php:341
msgid "status"
msgstr ""
-#: src/Content/Item.php:338 src/Model/Item.php:2782
+#: src/Content/Item.php:337 src/Model/Item.php:2782
#: src/Module/Post/Tag/Add.php:112
msgid "photo"
msgstr ""
-#: src/Content/Item.php:352 src/Module/Post/Tag/Add.php:130
+#: src/Content/Item.php:351 src/Module/Post/Tag/Add.php:130
#, php-format
msgid "%1$s tagged %2$s's %3$s with %4$s"
msgstr ""
-#: src/Content/Item.php:426 view/theme/frio/theme.php:251
+#: src/Content/Item.php:425 view/theme/frio/theme.php:251
msgid "Follow Thread"
msgstr ""
-#: src/Content/Item.php:427 src/Model/Contact.php:1299
+#: src/Content/Item.php:426 src/Model/Contact.php:1299
msgid "View Status"
msgstr ""
-#: src/Content/Item.php:428 src/Content/Item.php:451 src/Model/Contact.php:1234
+#: src/Content/Item.php:427 src/Content/Item.php:450 src/Model/Contact.php:1234
#: src/Model/Contact.php:1290 src/Model/Contact.php:1300
#: src/Module/Directory.php:143 src/Module/Settings/Profile/Index.php:275
msgid "View Profile"
msgstr ""
-#: src/Content/Item.php:429 src/Model/Contact.php:1301
+#: src/Content/Item.php:428 src/Model/Contact.php:1301
msgid "View Photos"
msgstr ""
-#: src/Content/Item.php:430 src/Model/Contact.php:1268
+#: src/Content/Item.php:429 src/Model/Contact.php:1268
#: src/Model/Profile.php:443
msgid "Network Posts"
msgstr ""
-#: src/Content/Item.php:431 src/Model/Contact.php:1292
+#: src/Content/Item.php:430 src/Model/Contact.php:1292
#: src/Model/Contact.php:1303
msgid "View Contact"
msgstr ""
-#: src/Content/Item.php:432 src/Model/Contact.php:1304
+#: src/Content/Item.php:431 src/Model/Contact.php:1304
msgid "Send PM"
msgstr ""
-#: src/Content/Item.php:433 src/Module/Contact.php:453
+#: src/Content/Item.php:432 src/Module/Contact.php:453
#: src/Module/Contact/Profile.php:562
#: src/Module/Moderation/Blocklist/Contact.php:104
#: src/Module/Moderation/Users/Active.php:93
@@ -1903,7 +1903,7 @@ msgstr ""
msgid "Block"
msgstr ""
-#: src/Content/Item.php:434 src/Module/Contact.php:454
+#: src/Content/Item.php:433 src/Module/Contact.php:454
#: src/Module/Contact/Profile.php:570
#: src/Module/Notifications/Introductions.php:126
#: src/Module/Notifications/Introductions.php:199
@@ -1911,50 +1911,50 @@ msgstr ""
msgid "Ignore"
msgstr ""
-#: src/Content/Item.php:435 src/Module/Contact.php:455
+#: src/Content/Item.php:434 src/Module/Contact.php:455
#: src/Module/Contact/Profile.php:578
msgid "Collapse"
msgstr ""
-#: src/Content/Item.php:436 src/Object/Post.php:287
+#: src/Content/Item.php:435 src/Object/Post.php:287
#, php-format
msgid "Ignore %s server"
msgstr ""
-#: src/Content/Item.php:440 src/Module/Settings/Channels.php:188
+#: src/Content/Item.php:439 src/Module/Settings/Channels.php:188
#: src/Module/Settings/Channels.php:214 src/Object/Post.php:508
msgid "Languages"
msgstr ""
-#: src/Content/Item.php:443 src/Object/Post.php:591
+#: src/Content/Item.php:442 src/Object/Post.php:591
msgid "Search Text"
msgstr ""
-#: src/Content/Item.php:448 src/Content/Widget.php:65
+#: src/Content/Item.php:447 src/Content/Widget.php:65
#: src/Model/Contact.php:1293 src/Model/Contact.php:1305
#: src/Module/Contact/Follow.php:152 view/theme/vier/theme.php:182
msgid "Connect/Follow"
msgstr ""
-#: src/Content/Item.php:879
+#: src/Content/Item.php:878
msgid "Unable to fetch user."
msgstr ""
-#: src/Content/Item.php:1343 src/Core/L10n.php:453
+#: src/Content/Item.php:1340 src/Core/L10n.php:453
msgid "Undetermined"
msgstr ""
-#: src/Content/Item.php:1350
+#: src/Content/Item.php:1347
#, php-format
msgid "%s (%s - %s): %s"
msgstr ""
-#: src/Content/Item.php:1352
+#: src/Content/Item.php:1349
#, php-format
msgid "%s (%s): %s"
msgstr ""
-#: src/Content/Item.php:1355
+#: src/Content/Item.php:1352
#, php-format
msgid ""
"Detected languages in this post:\n"
@@ -2041,7 +2041,7 @@ msgstr ""
#: src/Content/Nav.php:230 src/Content/Nav.php:290
#: src/Module/BaseProfile.php:70 src/Module/BaseProfile.php:73
#: src/Module/BaseProfile.php:81 src/Module/BaseProfile.php:84
-#: src/Module/Settings/Display.php:314 view/theme/frio/theme.php:225
+#: src/Module/Settings/Display.php:320 view/theme/frio/theme.php:225
#: view/theme/frio/theme.php:229
msgid "Calendar"
msgstr ""
@@ -2273,33 +2273,33 @@ msgstr ""
msgid "last"
msgstr ""
-#: src/Content/Text/BBCode.php:903
+#: src/Content/Text/BBCode.php:908
#, php-format
msgid "%2$s %3$s"
msgstr ""
-#: src/Content/Text/BBCode.php:931 src/Model/Item.php:3618
-#: src/Model/Item.php:3624 src/Model/Item.php:3625
+#: src/Content/Text/BBCode.php:936 src/Model/Item.php:3630
+#: src/Model/Item.php:3636 src/Model/Item.php:3637
msgid "Link to source"
msgstr ""
-#: src/Content/Text/BBCode.php:1753 src/Content/Text/HTML.php:900
+#: src/Content/Text/BBCode.php:1758 src/Content/Text/HTML.php:900
msgid "Click to open/close"
msgstr ""
-#: src/Content/Text/BBCode.php:1808
+#: src/Content/Text/BBCode.php:1813
msgid "$1 wrote:"
msgstr ""
-#: src/Content/Text/BBCode.php:1882 src/Content/Text/BBCode.php:1883
+#: src/Content/Text/BBCode.php:1887 src/Content/Text/BBCode.php:1888
msgid "Encrypted content"
msgstr ""
-#: src/Content/Text/BBCode.php:2229
+#: src/Content/Text/BBCode.php:2234
msgid "Invalid source protocol"
msgstr ""
-#: src/Content/Text/BBCode.php:2248
+#: src/Content/Text/BBCode.php:2253
msgid "Invalid link protocol"
msgstr ""
@@ -2885,37 +2885,37 @@ msgid "%s (%s)"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:421
-#: src/Module/Settings/Display.php:282
+#: src/Module/Settings/Display.php:288
msgid "Monday"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:422
-#: src/Module/Settings/Display.php:283
+#: src/Module/Settings/Display.php:289
msgid "Tuesday"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:423
-#: src/Module/Settings/Display.php:284
+#: src/Module/Settings/Display.php:290
msgid "Wednesday"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:424
-#: src/Module/Settings/Display.php:285
+#: src/Module/Settings/Display.php:291
msgid "Thursday"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:425
-#: src/Module/Settings/Display.php:286
+#: src/Module/Settings/Display.php:292
msgid "Friday"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:426
-#: src/Module/Settings/Display.php:287
+#: src/Module/Settings/Display.php:293
msgid "Saturday"
msgstr ""
#: src/Core/L10n.php:512 src/Model/Event.php:420
-#: src/Module/Settings/Display.php:281
+#: src/Module/Settings/Display.php:287
msgid "Sunday"
msgstr ""
@@ -3344,17 +3344,17 @@ msgid "today"
msgstr ""
#: src/Model/Event.php:454 src/Module/Calendar/Show.php:118
-#: src/Module/Settings/Display.php:292 src/Util/Temporal.php:343
+#: src/Module/Settings/Display.php:298 src/Util/Temporal.php:343
msgid "month"
msgstr ""
#: src/Model/Event.php:455 src/Module/Calendar/Show.php:119
-#: src/Module/Settings/Display.php:293 src/Util/Temporal.php:344
+#: src/Module/Settings/Display.php:299 src/Util/Temporal.php:344
msgid "week"
msgstr ""
#: src/Model/Event.php:456 src/Module/Calendar/Show.php:120
-#: src/Module/Settings/Display.php:294 src/Util/Temporal.php:345
+#: src/Module/Settings/Display.php:300 src/Util/Temporal.php:345
msgid "day"
msgstr ""
@@ -3448,44 +3448,44 @@ msgstr ""
msgid "Sensitive content"
msgstr ""
-#: src/Model/Item.php:3518
+#: src/Model/Item.php:3530
msgid "bytes"
msgstr ""
-#: src/Model/Item.php:3549
+#: src/Model/Item.php:3561
#, php-format
msgid "%2$s (%3$d%%, %1$d vote)"
msgid_plural "%2$s (%3$d%%, %1$d votes)"
msgstr[0] ""
msgstr[1] ""
-#: src/Model/Item.php:3551
+#: src/Model/Item.php:3563
#, php-format
msgid "%2$s (%1$d vote)"
msgid_plural "%2$s (%1$d votes)"
msgstr[0] ""
msgstr[1] ""
-#: src/Model/Item.php:3556
+#: src/Model/Item.php:3568
#, php-format
msgid "%d voter. Poll end: %s"
msgid_plural "%d voters. Poll end: %s"
msgstr[0] ""
msgstr[1] ""
-#: src/Model/Item.php:3558
+#: src/Model/Item.php:3570
#, php-format
msgid "%d voter."
msgid_plural "%d voters."
msgstr[0] ""
msgstr[1] ""
-#: src/Model/Item.php:3560
+#: src/Model/Item.php:3572
#, php-format
msgid "Poll end: %s"
msgstr ""
-#: src/Model/Item.php:3601 src/Model/Item.php:3602
+#: src/Model/Item.php:3613 src/Model/Item.php:3614
msgid "View on separate page"
msgstr ""
@@ -3897,7 +3897,7 @@ msgid "Disable"
msgstr ""
#: src/Module/Admin/Addons/Details.php:78
-#: src/Module/Admin/Themes/Details.php:41 src/Module/Settings/Display.php:341
+#: src/Module/Admin/Themes/Details.php:41 src/Module/Settings/Display.php:349
msgid "Enable"
msgstr ""
@@ -3952,7 +3952,7 @@ msgstr ""
#: src/Module/Settings/Connectors.php:143
#: src/Module/Settings/Connectors.php:228
#: src/Module/Settings/ContactImport.php:110
-#: src/Module/Settings/Delegation.php:179 src/Module/Settings/Display.php:307
+#: src/Module/Settings/Delegation.php:179 src/Module/Settings/Display.php:313
#: src/Module/Settings/Features.php:61
#: src/Module/Settings/Profile/Index.php:272
msgid "Save Settings"
@@ -4304,11 +4304,11 @@ msgstr ""
msgid "%s is no valid input for maximum image size"
msgstr ""
-#: src/Module/Admin/Site.php:361 src/Module/Settings/Display.php:206
+#: src/Module/Admin/Site.php:361 src/Module/Settings/Display.php:210
msgid "No special theme for mobile devices"
msgstr ""
-#: src/Module/Admin/Site.php:378 src/Module/Settings/Display.php:216
+#: src/Module/Admin/Site.php:378 src/Module/Settings/Display.php:220
#, php-format
msgid "%s - (Experimental)"
msgstr ""
@@ -5211,7 +5211,7 @@ msgid "Can be \"all\" or \"tags\". \"all\" means that every public post should b
msgstr ""
#: src/Module/Admin/Site.php:584 src/Module/Contact/Profile.php:348
-#: src/Module/Settings/Display.php:249
+#: src/Module/Settings/Display.php:255
#: src/Module/Settings/TwoFactor/Index.php:132
msgid "Disabled"
msgstr ""
@@ -5950,7 +5950,7 @@ msgstr ""
msgid "New Event"
msgstr ""
-#: src/Module/Calendar/Show.php:121 src/Module/Settings/Display.php:295
+#: src/Module/Calendar/Show.php:121 src/Module/Settings/Display.php:301
msgid "list"
msgstr ""
@@ -9592,12 +9592,12 @@ msgid "When selected, the channel results are reshared. This only works for publ
msgstr ""
#: src/Module/Settings/Channels.php:176 src/Module/Settings/Channels.php:202
-#: src/Module/Settings/Display.php:339
+#: src/Module/Settings/Display.php:347
msgid "Label"
msgstr ""
#: src/Module/Settings/Channels.php:177 src/Module/Settings/Channels.php:203
-#: src/Module/Settings/Display.php:340
+#: src/Module/Settings/Display.php:348
#: src/Module/Settings/TwoFactor/AppSpecific.php:123
msgid "Description"
msgstr ""
@@ -9980,218 +9980,234 @@ msgstr ""
msgid "No entries."
msgstr ""
-#: src/Module/Settings/Display.php:174
+#: src/Module/Settings/Display.php:178
msgid "The theme you chose isn't available."
msgstr ""
-#: src/Module/Settings/Display.php:214
+#: src/Module/Settings/Display.php:218
#, php-format
msgid "%s - (Unsupported)"
msgstr ""
-#: src/Module/Settings/Display.php:250
+#: src/Module/Settings/Display.php:256
msgid "Color/Black"
msgstr ""
-#: src/Module/Settings/Display.php:251 view/theme/frio/php/scheme.php:95
+#: src/Module/Settings/Display.php:257 view/theme/frio/php/scheme.php:95
msgid "Black"
msgstr ""
-#: src/Module/Settings/Display.php:252
+#: src/Module/Settings/Display.php:258
msgid "Color/White"
msgstr ""
-#: src/Module/Settings/Display.php:253
+#: src/Module/Settings/Display.php:259
msgid "White"
msgstr ""
-#: src/Module/Settings/Display.php:258
+#: src/Module/Settings/Display.php:264
msgid "No preview"
msgstr ""
-#: src/Module/Settings/Display.php:259
+#: src/Module/Settings/Display.php:265
msgid "No image"
msgstr ""
-#: src/Module/Settings/Display.php:260
+#: src/Module/Settings/Display.php:266
msgid "Small Image"
msgstr ""
-#: src/Module/Settings/Display.php:261
+#: src/Module/Settings/Display.php:267
msgid "Large Image"
msgstr ""
-#: src/Module/Settings/Display.php:306
+#: src/Module/Settings/Display.php:312
msgid "Display Settings"
msgstr ""
-#: src/Module/Settings/Display.php:308
+#: src/Module/Settings/Display.php:314
msgid "General Theme Settings"
msgstr ""
-#: src/Module/Settings/Display.php:309
+#: src/Module/Settings/Display.php:315
msgid "Custom Theme Settings"
msgstr ""
-#: src/Module/Settings/Display.php:310
+#: src/Module/Settings/Display.php:316
msgid "Content Settings"
msgstr ""
-#: src/Module/Settings/Display.php:311 view/theme/duepuntozero/config.php:74
+#: src/Module/Settings/Display.php:317 view/theme/duepuntozero/config.php:74
#: view/theme/frio/config.php:156 view/theme/quattro/config.php:76
#: view/theme/vier/config.php:124
msgid "Theme settings"
msgstr ""
-#: src/Module/Settings/Display.php:312
+#: src/Module/Settings/Display.php:318
msgid "Timelines"
msgstr ""
-#: src/Module/Settings/Display.php:319
+#: src/Module/Settings/Display.php:325
msgid "Display Theme:"
msgstr ""
-#: src/Module/Settings/Display.php:320
+#: src/Module/Settings/Display.php:326
msgid "Mobile Theme:"
msgstr ""
-#: src/Module/Settings/Display.php:323
+#: src/Module/Settings/Display.php:329
msgid "Number of items to display per page:"
msgstr ""
-#: src/Module/Settings/Display.php:323 src/Module/Settings/Display.php:324
+#: src/Module/Settings/Display.php:329 src/Module/Settings/Display.php:330
msgid "Maximum of 100 items"
msgstr ""
-#: src/Module/Settings/Display.php:324
+#: src/Module/Settings/Display.php:330
msgid "Number of items to display per page when viewed from mobile device:"
msgstr ""
-#: src/Module/Settings/Display.php:325
+#: src/Module/Settings/Display.php:331
msgid "Regularly update the page content"
msgstr ""
-#: src/Module/Settings/Display.php:325
+#: src/Module/Settings/Display.php:331
msgid "When enabled, new content on network, community and channels are added on top."
msgstr ""
-#: src/Module/Settings/Display.php:326
+#: src/Module/Settings/Display.php:332
msgid "Display emoticons"
msgstr ""
-#: src/Module/Settings/Display.php:326
+#: src/Module/Settings/Display.php:332
msgid "When enabled, emoticons are replaced with matching symbols."
msgstr ""
-#: src/Module/Settings/Display.php:327
+#: src/Module/Settings/Display.php:333
msgid "Infinite scroll"
msgstr ""
-#: src/Module/Settings/Display.php:327
+#: src/Module/Settings/Display.php:333
msgid "Automatic fetch new items when reaching the page end."
msgstr ""
-#: src/Module/Settings/Display.php:328
+#: src/Module/Settings/Display.php:334
msgid "Enable Smart Threading"
msgstr ""
-#: src/Module/Settings/Display.php:328
+#: src/Module/Settings/Display.php:334
msgid "Enable the automatic suppression of extraneous thread indentation."
msgstr ""
-#: src/Module/Settings/Display.php:329
+#: src/Module/Settings/Display.php:335
msgid "Display the Dislike feature"
msgstr ""
-#: src/Module/Settings/Display.php:329
+#: src/Module/Settings/Display.php:335
msgid "Display the Dislike button and dislike reactions on posts and comments."
msgstr ""
-#: src/Module/Settings/Display.php:330
+#: src/Module/Settings/Display.php:336
msgid "Display the resharer"
msgstr ""
-#: src/Module/Settings/Display.php:330
+#: src/Module/Settings/Display.php:336
msgid "Display the first resharer as icon and text on a reshared item."
msgstr ""
-#: src/Module/Settings/Display.php:331
+#: src/Module/Settings/Display.php:337
msgid "Stay local"
msgstr ""
-#: src/Module/Settings/Display.php:331
+#: src/Module/Settings/Display.php:337
msgid "Don't go to a remote system when following a contact link."
msgstr ""
-#: src/Module/Settings/Display.php:332
+#: src/Module/Settings/Display.php:338
msgid "Show the post deletion checkbox"
msgstr ""
-#: src/Module/Settings/Display.php:332
+#: src/Module/Settings/Display.php:338
msgid "Display the checkbox for the post deletion on the network page."
msgstr ""
-#: src/Module/Settings/Display.php:333
+#: src/Module/Settings/Display.php:339
msgid "DIsplay the event list"
msgstr ""
-#: src/Module/Settings/Display.php:333
+#: src/Module/Settings/Display.php:339
msgid "Display the birthday reminder and event list on the network page."
msgstr ""
-#: src/Module/Settings/Display.php:334
+#: src/Module/Settings/Display.php:340
msgid "Link preview mode"
msgstr ""
-#: src/Module/Settings/Display.php:334
+#: src/Module/Settings/Display.php:340
msgid "Appearance of the link preview that is added to each post with a link."
msgstr ""
-#: src/Module/Settings/Display.php:335
+#: src/Module/Settings/Display.php:341
msgid "Hide pictures with empty alternative text"
msgstr ""
-#: src/Module/Settings/Display.php:335
+#: src/Module/Settings/Display.php:341
msgid "Don't display pictures that are missing the alternative text."
msgstr ""
-#: src/Module/Settings/Display.php:336
+#: src/Module/Settings/Display.php:342
msgid "Hide custom emojis"
msgstr ""
-#: src/Module/Settings/Display.php:336
+#: src/Module/Settings/Display.php:342
msgid "Don't display custom emojis."
msgstr ""
-#: src/Module/Settings/Display.php:337
+#: src/Module/Settings/Display.php:343
msgid "Platform icons style"
msgstr ""
-#: src/Module/Settings/Display.php:337
+#: src/Module/Settings/Display.php:343
msgid "Style of the platform icons"
msgstr ""
-#: src/Module/Settings/Display.php:342
-msgid "Bookmark"
+#: src/Module/Settings/Display.php:344
+msgid "Embed remote media"
msgstr ""
#: src/Module/Settings/Display.php:344
+msgid "When enabled, remote media will be embedded in the post, like for example YouTube videos."
+msgstr ""
+
+#: src/Module/Settings/Display.php:345
+msgid "Embed supported media"
+msgstr ""
+
+#: src/Module/Settings/Display.php:345
+msgid "When enabled, remote media will be embedded in the post instead of using the local player if this is supported by the remote system. This is useful for media where the remote player is better than the local one, like for example Peertube videos."
+msgstr ""
+
+#: src/Module/Settings/Display.php:350
+msgid "Bookmark"
+msgstr ""
+
+#: src/Module/Settings/Display.php:352
msgid "Enable timelines that you want to see in the channels widget. Bookmark timelines that you want to see in the top menu."
msgstr ""
-#: src/Module/Settings/Display.php:346
+#: src/Module/Settings/Display.php:354
msgid "Channel languages:"
msgstr ""
-#: src/Module/Settings/Display.php:346
+#: src/Module/Settings/Display.php:354
msgid "Select all the languages you want to see in your channels. \"Unspecified\" describes all posts for which no language information was detected (e.g. posts with just an image or too little text to be sure of the language). If you want to see all languages, you will need to select all items in the list."
msgstr ""
-#: src/Module/Settings/Display.php:348
+#: src/Module/Settings/Display.php:356
msgid "Beginning of week:"
msgstr ""
-#: src/Module/Settings/Display.php:349
+#: src/Module/Settings/Display.php:357
msgid "Default calendar view:"
msgstr ""
@@ -11798,7 +11814,7 @@ msgstr ""
msgid "Quote shared by: %s"
msgstr ""
-#: src/Protocol/ActivityPub/Receiver.php:568
+#: src/Protocol/ActivityPub/Receiver.php:569
msgid "Chat"
msgstr ""
diff --git a/view/templates/settings/display.tpl b/view/templates/settings/display.tpl
index 500300dde0..289ace6dcd 100644
--- a/view/templates/settings/display.tpl
+++ b/view/templates/settings/display.tpl
@@ -31,6 +31,8 @@
{{include file="field_checkbox.tpl" field=$hide_empty_descriptions}}
{{include file="field_checkbox.tpl" field=$hide_custom_emojis}}
{{include file="field_select.tpl" field=$platform_icon_style}}
+ {{include file="field_checkbox.tpl" field=$embed_remote_media}}
+ {{include file="field_checkbox.tpl" field=$embed_media}}
{{$timeline_title}}
{{$timeline_explanation}}
diff --git a/view/theme/frio/templates/settings/display.tpl b/view/theme/frio/templates/settings/display.tpl
index 7fdbd89260..f3e19c3c9c 100644
--- a/view/theme/frio/templates/settings/display.tpl
+++ b/view/theme/frio/templates/settings/display.tpl
@@ -78,6 +78,8 @@
{{include file="field_checkbox.tpl" field=$hide_empty_descriptions}}
{{include file="field_checkbox.tpl" field=$hide_custom_emojis}}
{{include file="field_select.tpl" field=$platform_icon_style}}
+ {{include file="field_checkbox.tpl" field=$embed_remote_media}}
+ {{include file="field_checkbox.tpl" field=$embed_media}}