feat: add duration and title options to clip command (#6669)
Reviewed-by: pajlada <rasmus.karlsson@pajlada.com>
This commit is contained in:
@@ -20,6 +20,7 @@
|
|||||||
- Minor: Added broadcaster-only `/poll`, `/cancelpoll`, and `/endpoll` commands. (#6583, #6605)
|
- Minor: Added broadcaster-only `/poll`, `/cancelpoll`, and `/endpoll` commands. (#6583, #6605)
|
||||||
- Minor: Added broadcaster-only `/prediction`, `/cancelprediction`, `/lockprediction`, and `/completeprediction` commands. (#6583, #6612, #6632)
|
- Minor: Added broadcaster-only `/prediction`, `/cancelprediction`, `/lockprediction`, and `/completeprediction` commands. (#6583, #6612, #6632)
|
||||||
- Minor: Added support for BetterTTV Pro subscriber badges. (#6625)
|
- Minor: Added support for BetterTTV Pro subscriber badges. (#6625)
|
||||||
|
- Minor: Added title and duration options for `/clip` command. (#6669)
|
||||||
- Minor: Added Markdown support to user notes. (#6490)
|
- Minor: Added Markdown support to user notes. (#6490)
|
||||||
- Bugfix: Moderation checks now include the lead moderator badge. (#6642)
|
- Bugfix: Moderation checks now include the lead moderator badge. (#6642)
|
||||||
- Bugfix: Fixed lead moderator badges not being filtered by the `Channel` badge setting. (#6665)
|
- Bugfix: Fixed lead moderator badges not being filtered by the `Channel` badge setting. (#6665)
|
||||||
|
|||||||
@@ -79,7 +79,8 @@ public:
|
|||||||
(override));
|
(override));
|
||||||
|
|
||||||
MOCK_METHOD(void, createClip,
|
MOCK_METHOD(void, createClip,
|
||||||
(QString channelId, ResultCallback<HelixClip> successCallback,
|
(QString channelId, QString title, std::optional<int> duration,
|
||||||
|
ResultCallback<HelixClip> successCallback,
|
||||||
std::function<void(HelixClipError, QString)> failureCallback,
|
std::function<void(HelixClipError, QString)> failureCallback,
|
||||||
std::function<void()> finallyCallback),
|
std::function<void()> finallyCallback),
|
||||||
(override));
|
(override));
|
||||||
|
|||||||
@@ -200,7 +200,41 @@ QString clip(const CommandContext &ctx)
|
|||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx.twitchChannel->createClip();
|
QString title = "";
|
||||||
|
std::optional<int> duration = std::nullopt;
|
||||||
|
if (!ctx.words.empty())
|
||||||
|
{
|
||||||
|
QCommandLineParser parser;
|
||||||
|
parser.setSingleDashWordOptionMode(
|
||||||
|
QCommandLineParser::ParseAsLongOptions);
|
||||||
|
parser.setOptionsAfterPositionalArgumentsMode(
|
||||||
|
QCommandLineParser::ParseAsPositionalArguments);
|
||||||
|
parser.addPositionalArgument("title", "The title of the clip");
|
||||||
|
|
||||||
|
QCommandLineOption durationOption(
|
||||||
|
{"d", "duration"}, "The duration of the clip", "duration");
|
||||||
|
parser.addOptions({
|
||||||
|
durationOption,
|
||||||
|
});
|
||||||
|
parser.parse(ctx.words);
|
||||||
|
|
||||||
|
title = parser.positionalArguments().join(' ');
|
||||||
|
|
||||||
|
if (parser.isSet(durationOption))
|
||||||
|
{
|
||||||
|
bool ok = false;
|
||||||
|
duration = parser.value(durationOption).toInt(&ok);
|
||||||
|
|
||||||
|
if (!ok)
|
||||||
|
{
|
||||||
|
ctx.channel->addSystemMessage(
|
||||||
|
"Could not parse clip duration to an integer.");
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx.twitchChannel->createClip(title, duration);
|
||||||
|
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1956,7 +1956,8 @@ void TwitchChannel::setCheerEmoteSets(
|
|||||||
*this->cheerEmoteSets_.access() = std::move(emoteSets);
|
*this->cheerEmoteSets_.access() = std::move(emoteSets);
|
||||||
}
|
}
|
||||||
|
|
||||||
void TwitchChannel::createClip()
|
void TwitchChannel::createClip(const QString &title,
|
||||||
|
const std::optional<int> duration)
|
||||||
{
|
{
|
||||||
if (!this->isLive())
|
if (!this->isLive())
|
||||||
{
|
{
|
||||||
@@ -1980,7 +1981,7 @@ void TwitchChannel::createClip()
|
|||||||
this->isClipCreationInProgress = true;
|
this->isClipCreationInProgress = true;
|
||||||
|
|
||||||
getHelix()->createClip(
|
getHelix()->createClip(
|
||||||
this->roomId(),
|
this->roomId(), title, duration,
|
||||||
// successCallback
|
// successCallback
|
||||||
[this](const HelixClip &clip) {
|
[this](const HelixClip &clip) {
|
||||||
MessageBuilder builder;
|
MessageBuilder builder;
|
||||||
|
|||||||
@@ -182,7 +182,7 @@ public:
|
|||||||
bool canReconnect() const override;
|
bool canReconnect() const override;
|
||||||
void reconnect() override;
|
void reconnect() override;
|
||||||
QString getCurrentStreamID() const override;
|
QString getCurrentStreamID() const override;
|
||||||
void createClip();
|
void createClip(const QString &title, std::optional<int> duration);
|
||||||
|
|
||||||
/// Delete the message with the specified ID as a moderator.
|
/// Delete the message with the specified ID as a moderator.
|
||||||
///
|
///
|
||||||
|
|||||||
@@ -354,13 +354,24 @@ void Helix::getGameById(QString gameId,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Helix::createClip(
|
void Helix::createClip(
|
||||||
QString channelId, ResultCallback<HelixClip> successCallback,
|
QString channelId, QString title, std::optional<int> duration,
|
||||||
|
ResultCallback<HelixClip> successCallback,
|
||||||
std::function<void(HelixClipError, QString)> failureCallback,
|
std::function<void(HelixClipError, QString)> failureCallback,
|
||||||
std::function<void()> finallyCallback)
|
std::function<void()> finallyCallback)
|
||||||
{
|
{
|
||||||
QUrlQuery urlQuery;
|
QUrlQuery urlQuery;
|
||||||
urlQuery.addQueryItem("broadcaster_id", channelId);
|
urlQuery.addQueryItem("broadcaster_id", channelId);
|
||||||
|
|
||||||
|
if (!title.isEmpty())
|
||||||
|
{
|
||||||
|
urlQuery.addQueryItem("title", title);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (duration.has_value())
|
||||||
|
{
|
||||||
|
urlQuery.addQueryItem("duration", QString::number(*duration));
|
||||||
|
}
|
||||||
|
|
||||||
this->makePost("clips", urlQuery)
|
this->makePost("clips", urlQuery)
|
||||||
.header("Content-Type", "application/json")
|
.header("Content-Type", "application/json")
|
||||||
.onSuccess([successCallback, failureCallback](auto result) {
|
.onSuccess([successCallback, failureCallback](auto result) {
|
||||||
|
|||||||
@@ -1036,7 +1036,8 @@ public:
|
|||||||
|
|
||||||
// https://dev.twitch.tv/docs/api/reference#create-clip
|
// https://dev.twitch.tv/docs/api/reference#create-clip
|
||||||
virtual void createClip(
|
virtual void createClip(
|
||||||
QString channelId, ResultCallback<HelixClip> successCallback,
|
QString channelId, QString title, std::optional<int> duration,
|
||||||
|
ResultCallback<HelixClip> successCallback,
|
||||||
std::function<void(HelixClipError, QString)> failureCallback,
|
std::function<void(HelixClipError, QString)> failureCallback,
|
||||||
std::function<void()> finallyCallback) = 0;
|
std::function<void()> finallyCallback) = 0;
|
||||||
|
|
||||||
@@ -1428,7 +1429,8 @@ public:
|
|||||||
|
|
||||||
// https://dev.twitch.tv/docs/api/reference#create-clip
|
// https://dev.twitch.tv/docs/api/reference#create-clip
|
||||||
void createClip(
|
void createClip(
|
||||||
QString channelId, ResultCallback<HelixClip> successCallback,
|
QString channelId, QString title, std::optional<int> duration,
|
||||||
|
ResultCallback<HelixClip> successCallback,
|
||||||
std::function<void(HelixClipError, QString)> failureCallback,
|
std::function<void(HelixClipError, QString)> failureCallback,
|
||||||
std::function<void()> finallyCallback) final;
|
std::function<void()> finallyCallback) final;
|
||||||
|
|
||||||
|
|||||||
@@ -483,7 +483,7 @@ void Split::addShortcuts()
|
|||||||
auto *twitchChannel =
|
auto *twitchChannel =
|
||||||
dynamic_cast<TwitchChannel *>(this->getChannel().get());
|
dynamic_cast<TwitchChannel *>(this->getChannel().get());
|
||||||
|
|
||||||
twitchChannel->createClip();
|
twitchChannel->createClip({}, {});
|
||||||
return "";
|
return "";
|
||||||
}},
|
}},
|
||||||
{"reloadEmotes",
|
{"reloadEmotes",
|
||||||
|
|||||||
@@ -478,7 +478,7 @@ std::unique_ptr<QMenu> SplitHeader::createMainMenu()
|
|||||||
h->getDisplaySequence(HotkeyCategory::Split, "createClip"),
|
h->getDisplaySequence(HotkeyCategory::Split, "createClip"),
|
||||||
this->split_,
|
this->split_,
|
||||||
[twitchChannel] {
|
[twitchChannel] {
|
||||||
twitchChannel->createClip();
|
twitchChannel->createClip({}, {});
|
||||||
})
|
})
|
||||||
->setVisible(twitchChannel->isLive());
|
->setVisible(twitchChannel->isLive());
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user