32#include "moc_qgsimagedroptextedit.cpp" 
   38#include <QImageReader> 
   40#include <QApplication> 
   41#include <QDesktopServices> 
   44QgsImageDropTextEdit::QgsImageDropTextEdit( QWidget *parent )
 
   47  setTextInteractionFlags( Qt::TextEditorInteraction | Qt::LinksAccessibleByMouse );
 
   50QgsImageDropTextEdit::~QgsImageDropTextEdit() = 
default;
 
   52bool QgsImageDropTextEdit::canInsertFromMimeData( 
const QMimeData *source )
 const 
   54  if ( source->hasImage() || QTextEdit::canInsertFromMimeData( source ) )
 
   57  const QList<QUrl> urls = source->urls();
 
   59  files.reserve( urls.size() );
 
   60  for ( 
const QUrl &url : urls )
 
   62    QString fileName = url.toLocalFile();
 
   65    if ( !fileName.isEmpty() )
 
   72  for ( 
const QString &file : std::as_const( files ) )
 
   75    const QList<QByteArray> formats = QImageReader::supportedImageFormats();
 
   76    for ( 
const QByteArray &format : formats )
 
   78      if ( fi.suffix().compare( format, Qt::CaseInsensitive ) == 0 )
 
   89void QgsImageDropTextEdit::insertFromMimeData( 
const QMimeData *source )
 
   91  if ( source->hasImage() )
 
   93    const QStringList formats = source->formats();
 
   95    for ( 
const QString &
string : formats )
 
   97      if ( 
string == QLatin1String( 
"image/bmp" ) )
 
   99        format = QStringLiteral( 
"BMP" );
 
  102      if ( 
string == QLatin1String( 
"image/jpeg" ) )
 
  104        format = QStringLiteral( 
"JPG" );
 
  107      if ( 
string == QLatin1String( 
"image/jpg" ) )
 
  109        format = QStringLiteral( 
"JPG" );
 
  112      if ( 
string == QLatin1String( 
"image/gif" ) )
 
  114        format = QStringLiteral( 
"GIF" );
 
  117      if ( 
string == QLatin1String( 
"image/png" ) )
 
  119        format = QStringLiteral( 
"PNG" );
 
  122      if ( 
string == QLatin1String( 
"image/pbm" ) )
 
  124        format = QStringLiteral( 
"PBM" );
 
  127      if ( 
string == QLatin1String( 
"image/pgm" ) )
 
  129        format = QStringLiteral( 
"PGM" );
 
  132      if ( 
string == QLatin1String( 
"image/ppm" ) )
 
  134        format = QStringLiteral( 
"PPM" );
 
  137      if ( 
string == QLatin1String( 
"image/tiff" ) )
 
  139        format = QStringLiteral( 
"TIFF" );
 
  142      if ( 
string == QLatin1String( 
"image/xbm" ) )
 
  144        format = QStringLiteral( 
"XBM" );
 
  147      if ( 
string == QLatin1String( 
"image/xpm" ) )
 
  149        format = QStringLiteral( 
"XPM" );
 
  153    if ( !format.isEmpty() )
 
  155      dropImage( qvariant_cast<QImage>( source->imageData() ), format );
 
  161    const QList<QUrl> urls = source->urls();
 
  163    files.reserve( urls.size() );
 
  164    for ( 
const QUrl &url : urls )
 
  166      if ( url.isLocalFile() )
 
  168        QString fileName = url.toLocalFile();
 
  171        if ( !fileName.isEmpty() )
 
  182    for ( 
const QString &file : std::as_const( files ) )
 
  184      const QFileInfo fi( file );
 
  185      const QList<QByteArray> formats = QImageReader::supportedImageFormats();
 
  186      bool isImage = 
false;
 
  187      for ( 
const QByteArray &format : formats )
 
  189        if ( fi.suffix().compare( format, Qt::CaseInsensitive ) == 0 )
 
  191          const QImage image( file );
 
  192          dropImage( image, format );
 
  199        dropLink( QUrl::fromLocalFile( file ) );
 
  202    if ( !files.empty() )
 
  206  QTextEdit::insertFromMimeData( source );
 
  209void QgsImageDropTextEdit::mouseMoveEvent( QMouseEvent *e )
 
  211  QTextEdit::mouseMoveEvent( e );
 
  212  mActiveAnchor = anchorAt( e->pos() );
 
  213  if ( !mActiveAnchor.isEmpty() && !mCursorOverride )
 
  214    mCursorOverride = std::make_unique<QgsTemporaryCursorOverride>( Qt::PointingHandCursor );
 
  215  else if ( mActiveAnchor.isEmpty() && mCursorOverride )
 
  216    mCursorOverride.reset();
 
  219void QgsImageDropTextEdit::mouseReleaseEvent( QMouseEvent *e )
 
  221  if ( e->button() == Qt::LeftButton && !mActiveAnchor.isEmpty() )
 
  223    QDesktopServices::openUrl( QUrl( mActiveAnchor ) );
 
  224    if ( mCursorOverride )
 
  225      mCursorOverride.reset();
 
  226    mActiveAnchor.clear();
 
  230    QTextEdit::mouseReleaseEvent( e );
 
  234void QgsImageDropTextEdit::dropImage( 
const QImage &image, 
const QString &format )
 
  237  QBuffer buffer( &bytes );
 
  238  buffer.open( QIODevice::WriteOnly );
 
  239  image.save( &buffer, format.toLocal8Bit().data() );
 
  241  QByteArray base64 = bytes.toBase64();
 
  243  for ( 
int i = 0; i < base64.size(); i++ )
 
  245    base64l.append( base64[i] );
 
  248      base64l.append( 
"\n" );
 
  252  QTextCursor cursor = textCursor();
 
  253  QTextImageFormat imageFormat;
 
  254  imageFormat.setWidth( image.width() );
 
  255  imageFormat.setHeight( image.height() );
 
  256  imageFormat.setName( QStringLiteral( 
"data:image/%1;base64,%2" )
 
  257                         .arg( QStringLiteral( 
"%1.%2" ).arg( rand() ).arg( format ), base64l.data() )
 
  259  cursor.insertImage( imageFormat );
 
  262void QgsImageDropTextEdit::dropLink( 
const QUrl &url )
 
  264  QTextCursor cursor = textCursor();
 
  265  cursor.insertHtml( QStringLiteral( 
"<a href=\"%1\">%1</a>" ).arg( url.toString() ) );