void QgsSymbolLegendNode::exportSymbolToJson( const QgsLegendSettings &settings, const QgsRenderContext &context, QJsonObject &json ) const
{
  const QgsSymbol *s = mItem.symbol();
  if ( !s )
  {
    return;
  }

  QgsRenderContext ctx;
  ctx.setScaleFactor( settings.dpi() / 25.4 );
  ctx.setRendererScale( settings.mapScale() );
  ctx.setMapToPixel( QgsMapToPixel( 1 / ( settings.mmPerMapUnit() * ctx.scaleFactor() ) ) );
  ctx.setForceVectorOutput( true );

  // ensure that a minimal expression context is available
  QgsExpressionContext expContext = context.expressionContext();
  expContext.appendScopes( QgsExpressionContextUtils::globalProjectLayerScopes( nullptr ) );
  ctx.setExpressionContext( expContext );

  const QPixmap pix = QgsSymbolLayerUtils::symbolPreviewPixmap( mItem.symbol(), minimumIconSize(), 0, &ctx );
  QImage img( pix.toImage().convertToFormat( QImage::Format_ARGB32_Premultiplied ) );

  int opacity = 255;
  if ( QgsVectorLayer *vectorLayer = qobject_cast<QgsVectorLayer *>( layerNode()->layer() ) )
    opacity = ( 255 * vectorLayer->opacity() );

  if ( opacity != 255 )
  {
    QPainter painter;
    painter.begin( &img );
    painter.setCompositionMode( QPainter::CompositionMode_DestinationIn );
    painter.fillRect( pix.rect(), QColor( 0, 0, 0, opacity ) );
    painter.end();
  }

  QByteArray byteArray;
  QBuffer buffer( &byteArray );
  img.save( &buffer, "PNG" );
  const QString base64 = QString::fromLatin1( byteArray.toBase64().data() );
  json[ "icon" ] = base64;
}
QSize QgsSymbolLegendNode::minimumIconSize() const
{
  std::unique_ptr<QgsRenderContext> context( createTemporaryRenderContext() );
  return minimumIconSize( context.get() );
}
QSize QgsSymbolLegendNode::minimumIconSize() const
{
  QScopedPointer<QgsRenderContext> context( createTemporaryRenderContext() );
  return minimumIconSize( context.data() );
}