Fix the stupid things.

This includes:
 - NuulsUploader.cpp
   - changing upload delay to a #define
   - moving png conversion code to `boost::optional<QByteArray> convertToPng(QImage image)`
   - in uploadImageToNuuls: moving content type definition to a variable, move things around a bit to eliminate an if
   - in upload: adding a comment about `source->hasUrls()` and `source->urls()`, change `uploadQueue.size()` to `!uploadQueue.empty()`
 - ResizingTextEdit.cpp
   - changing #include order
This commit is contained in:
Mm2PL 2019-10-11 15:41:33 +02:00
parent 970503b755
commit bf434f3ac5
No known key found for this signature in database
GPG key ID: 1C400DA5602DE62E
3 changed files with 78 additions and 46 deletions

View file

@ -6,6 +6,41 @@
#include <QHttpMultiPart> #include <QHttpMultiPart>
#define UPLOAD_DELAY 2000
// Delay between uploads in milliseconds
namespace {
QString getImageFileFormat(QString path)
{
static QStringList listOfImageFormats = {".png", ".jpg", ".jpeg"};
for (const QString &format : listOfImageFormats)
{
if (path.endsWith(format))
{
return format.mid(1);
}
}
return QString();
}
boost::optional<QByteArray> convertToPng(QImage image)
{
QByteArray imageData;
QBuffer buf(&imageData);
buf.open(QIODevice::WriteOnly);
bool success = image.save(&buf, "png");
if (success)
{
return boost::optional<QByteArray>(imageData);
}
else
{
return boost::optional<QByteArray>(boost::none);
}
}
} // namespace
namespace chatterino { namespace chatterino {
bool isUploading = false; bool isUploading = false;
@ -15,6 +50,8 @@ void uploadImageToNuuls(TypedBytes imageData, ChannelPtr channel,
ResizingTextEdit &textEdit) ResizingTextEdit &textEdit)
{ {
const char *boundary = "thisistheboudaryasd"; const char *boundary = "thisistheboudaryasd";
QString contentType =
QString("multipart/form-data; boundary=%1").arg(boundary);
static QUrl url(Env::get().imageUploaderUrl); static QUrl url(Env::get().imageUploaderUrl);
QHttpMultiPart *payload = new QHttpMultiPart(QHttpMultiPart::FormDataType); QHttpMultiPart *payload = new QHttpMultiPart(QHttpMultiPart::FormDataType);
@ -26,17 +63,17 @@ void uploadImageToNuuls(TypedBytes imageData, ChannelPtr channel,
QVariant(imageData.data.length())); QVariant(imageData.data.length()));
part.setHeader( part.setHeader(
QNetworkRequest::ContentDispositionHeader, QNetworkRequest::ContentDispositionHeader,
QString("form-data; name=\"attachment\"; filename=\"control_v.%1\"")); QString("form-data; name=\"attachment\"; filename=\"control_v.%1\"")
.arg(imageData.type));
payload->setBoundary(boundary); payload->setBoundary(boundary);
payload->append(part); payload->append(part);
NetworkRequest(url, NetworkRequestType::Post) NetworkRequest(url, NetworkRequestType::Post)
.header("Content-Type", (std::string("multipart/form-data; boundary=") + .header("Content-Type", contentType)
std::string(boundary))
.c_str())
.multiPart(payload) .multiPart(payload)
.onSuccess([&textEdit, channel](NetworkResult result) -> Outcome { .onSuccess([&textEdit, channel](NetworkResult result) -> Outcome {
textEdit.insertPlainText(result.getData() + QString(" ")); textEdit.insertPlainText(result.getData() + QString(" "));
isUploading = false;
if (uploadQueue.empty()) if (uploadQueue.empty())
{ {
channel->addMessage(makeSystemMessage( channel->addMessage(makeSystemMessage(
@ -48,16 +85,16 @@ void uploadImageToNuuls(TypedBytes imageData, ChannelPtr channel,
QString("Your image has been uploaded. %1 left. Please " QString("Your image has been uploaded. %1 left. Please "
"wait until all of them are uploaded. About %2 " "wait until all of them are uploaded. About %2 "
"seconds left.") "seconds left.")
.arg(uploadQueue.size()) .arg(uploadQueue.size(),
.arg(uploadQueue.size() * 3))); uploadQueue.size() *
(UPLOAD_DELAY / 1000 +
1) // convert UPLOAD_DELAY to seconds
)));
// Argument number 2 is the ETA. // Argument number 2 is the ETA.
// 2 seconds for the timer that's there not to spam Nuuls' server // 2 seconds for the timer that's there not to spam Nuuls' server
// and 1 second of actual uploading. // and 1 second of actual uploading.
}
isUploading = false; QTimer::singleShot(UPLOAD_DELAY, [channel, &textEdit]() {
if (uploadQueue.size())
{
QTimer::singleShot(2000, [channel, &textEdit]() {
uploadImageToNuuls(uploadQueue.front(), channel, textEdit); uploadImageToNuuls(uploadQueue.front(), channel, textEdit);
uploadQueue.pop(); uploadQueue.pop();
}); });
@ -104,6 +141,8 @@ void upload(const QMimeData *source, ChannelPtr channel,
} }
else if (source->hasUrls()) else if (source->hasUrls())
{ {
// This path gets chosen when files are copied from a file manager, like explorer.exe, caja.
// Each entry in source->urls() is a QUrl pointng to a file that was copied.
for (const QUrl &path : source->urls()) for (const QUrl &path : source->urls())
{ {
if (!getImageFileFormat(path.toLocalFile()).isEmpty()) if (!getImageFileFormat(path.toLocalFile()).isEmpty())
@ -117,14 +156,21 @@ void upload(const QMimeData *source, ChannelPtr channel,
makeSystemMessage(QString("Couldn't load image :("))); makeSystemMessage(QString("Couldn't load image :(")));
return; return;
} }
QByteArray imageData;
QBuffer buf(&imageData);
buf.open(QIODevice::WriteOnly);
img.save(&buf, "png");
TypedBytes data = {imageData, "png"}; boost::optional<QByteArray> imageData = convertToPng(img);
if (imageData)
{
TypedBytes data = {imageData.get(), "png"};
uploadQueue.push(data); uploadQueue.push(data);
} }
else
{
channel->addMessage(makeSystemMessage(
QString("Cannot upload file: %1, Couldn't convert "
"image to png.")
.arg(path.toLocalFile())));
}
}
else if (path.toLocalFile().endsWith(".gif")) else if (path.toLocalFile().endsWith(".gif"))
{ {
channel->addMessage(makeSystemMessage( channel->addMessage(makeSystemMessage(
@ -150,7 +196,7 @@ void upload(const QMimeData *source, ChannelPtr channel,
isUploading = false; isUploading = false;
} }
} }
if (uploadQueue.size()) if (!uploadQueue.empty())
{ {
uploadImageToNuuls(uploadQueue.front(), channel, outputTextEdit); uploadImageToNuuls(uploadQueue.front(), channel, outputTextEdit);
uploadQueue.pop(); uploadQueue.pop();
@ -159,28 +205,17 @@ void upload(const QMimeData *source, ChannelPtr channel,
else else
{ // not PNG, try loading it into QImage and save it to a PNG. { // not PNG, try loading it into QImage and save it to a PNG.
QImage image = qvariant_cast<QImage>(source->imageData()); QImage image = qvariant_cast<QImage>(source->imageData());
QByteArray imageData; boost::optional<QByteArray> imageData = convertToPng(image);
QBuffer buf(&imageData); if (imageData)
buf.open(QIODevice::WriteOnly); {
image.save(&buf, "png"); uploadImageToNuuls({imageData.get(), "png"}, channel,
outputTextEdit);
uploadImageToNuuls({imageData, "png"}, channel, outputTextEdit); }
else
{
channel->addMessage(makeSystemMessage(
QString("Cannot upload file, failed to convert to png.")));
}
} }
} }
} // namespace chatterino } // namespace chatterino
namespace {
QString getImageFileFormat(QString path)
{
static QStringList listOfImageFormats = {".png", ".jpg", ".jpeg"};
for (const QString &format : listOfImageFormats)
{
if (path.endsWith(format))
{
return format.mid(1);
}
}
return QString();
}
} // namespace

View file

@ -16,7 +16,3 @@ void upload(TypedBytes imageData, ChannelPtr channel,
void upload(const QMimeData *source, ChannelPtr channel, void upload(const QMimeData *source, ChannelPtr channel,
ResizingTextEdit &outputTextEdit); ResizingTextEdit &outputTextEdit);
} // namespace chatterino } // namespace chatterino
namespace {
QString getImageFileFormat(QString path);
}

View file

@ -1,9 +1,10 @@
#include <QMimeData> #include "widgets/helper/ResizingTextEdit.hpp"
#include "common/Common.hpp" #include "common/Common.hpp"
#include "common/CompletionModel.hpp" #include "common/CompletionModel.hpp"
#include "singletons/Settings.hpp" #include "singletons/Settings.hpp"
#include "widgets/helper/ResizingTextEdit.hpp"
#include <QMimeData>
namespace chatterino { namespace chatterino {