summaryrefslogtreecommitdiffstats
path: root/sd/source/ui/remotecontrol/ImagePreparer.cxx
diff options
context:
space:
mode:
Diffstat (limited to 'sd/source/ui/remotecontrol/ImagePreparer.cxx')
-rw-r--r--sd/source/ui/remotecontrol/ImagePreparer.cxx255
1 files changed, 255 insertions, 0 deletions
diff --git a/sd/source/ui/remotecontrol/ImagePreparer.cxx b/sd/source/ui/remotecontrol/ImagePreparer.cxx
new file mode 100644
index 000000000..ba8d2c1f3
--- /dev/null
+++ b/sd/source/ui/remotecontrol/ImagePreparer.cxx
@@ -0,0 +1,255 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed
+ * with this work for additional information regarding copyright
+ * ownership. The ASF licenses this file to you under the Apache
+ * License, Version 2.0 (the "License"); you may not use this file
+ * except in compliance with the License. You may obtain a copy of
+ * the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+#include "ImagePreparer.hxx"
+#include "Transmitter.hxx"
+
+#include <comphelper/base64.hxx>
+#include <comphelper/processfactory.hxx>
+#include <comphelper/propertyvalue.hxx>
+#include <osl/file.hxx>
+#include <rtl/ustrbuf.hxx>
+#include <sal/log.hxx>
+
+#include <com/sun/star/beans/PropertyValue.hpp>
+#include <com/sun/star/drawing/GraphicExportFilter.hpp>
+#include <com/sun/star/lang/XServiceName.hpp>
+#include <com/sun/star/presentation/XSlideShowController.hpp>
+#include <com/sun/star/presentation/XPresentationPage.hpp>
+#include <com/sun/star/text/XTextRange.hpp>
+
+using namespace ::sd;
+using namespace ::osl;
+using namespace ::com::sun::star;
+using namespace ::com::sun::star::uno;
+
+ImagePreparer::ImagePreparer(
+ const uno::Reference<presentation::XSlideShowController>& rxController,
+ Transmitter *aTransmitter )
+ : Timer("sd ImagePreparer"),
+ xController( rxController ),
+ pTransmitter( aTransmitter )
+{
+ SAL_INFO( "sdremote", "ImagePreparer - start" );
+ SetTimeout( 50 );
+ mnSendingSlide = 0;
+ Start();
+}
+
+ImagePreparer::~ImagePreparer()
+{
+ SAL_INFO( "sdremote", "ImagePreparer - stop" );
+ Stop();
+}
+
+void ImagePreparer::Invoke()
+{
+ sal_uInt32 aSlides = xController->getSlideCount();
+ SAL_INFO( "sdremote", "ImagePreparer " << xController->isRunning() <<
+ " sending slide " << mnSendingSlide << " of " << aSlides );
+ if ( xController->isRunning() && // not stopped/disposed of.
+ mnSendingSlide < aSlides )
+ {
+ sendPreview( mnSendingSlide );
+ sendNotes( mnSendingSlide );
+ mnSendingSlide++;
+ Start();
+ }
+ else
+ Stop();
+}
+
+void ImagePreparer::sendPreview( sal_uInt32 aSlideNumber )
+{
+ sal_uInt64 aSize;
+ uno::Sequence<sal_Int8> aImageData = preparePreview( aSlideNumber, 320, 240,
+ aSize );
+ if ( !xController->isRunning() )
+ return;
+
+ OUStringBuffer aStrBuffer;
+ ::comphelper::Base64::encode( aStrBuffer, aImageData );
+
+ OString aEncodedShortString = OUStringToOString(
+ aStrBuffer.makeStringAndClear(), RTL_TEXTENCODING_UTF8 );
+
+ // Start the writing
+ OString aBuffer = "slide_preview\n" +
+ OString::number(aSlideNumber) +
+ "\n" + aEncodedShortString + "\n\n";
+ pTransmitter->addMessage( aBuffer,
+ Transmitter::PRIORITY_LOW );
+
+}
+
+uno::Sequence<sal_Int8> ImagePreparer::preparePreview(
+ sal_uInt32 aSlideNumber, sal_uInt32 aWidth, sal_uInt32 aHeight,
+ sal_uInt64 &rSize )
+{
+ OUString aFileURL;
+ FileBase::createTempFile( nullptr, nullptr, &aFileURL );
+
+ uno::Reference< drawing::XGraphicExportFilter > xFilter =
+ drawing::GraphicExportFilter::create( ::comphelper::getProcessComponentContext() );
+
+ if ( !xController->isRunning() )
+ return uno::Sequence<sal_Int8>();
+
+ uno::Reference< lang::XComponent > xSourceDoc(
+ xController->getSlideByIndex( aSlideNumber ),
+ uno::UNO_QUERY_THROW );
+
+ xFilter->setSourceDocument( xSourceDoc );
+
+ uno::Sequence< beans::PropertyValue > aFilterData{
+ comphelper::makePropertyValue("PixelWidth", aWidth),
+ comphelper::makePropertyValue("PixelHeight", aHeight),
+ comphelper::makePropertyValue("ColorMode", sal_Int32(0)) // 0: Color, 1: B&W
+ };
+
+ uno::Sequence< beans::PropertyValue > aProps{
+ comphelper::makePropertyValue("MediaType", OUString( "image/png" )),
+ comphelper::makePropertyValue("URL", aFileURL),
+ comphelper::makePropertyValue("FilterData", aFilterData)
+ };
+
+ xFilter->filter( aProps );
+
+ File aFile(aFileURL);
+ if (aFile.open(0) != osl::File::E_None)
+ return uno::Sequence<sal_Int8>();
+
+ sal_uInt64 aRead;
+ rSize = 0;
+ aFile.getSize( rSize );
+ uno::Sequence<sal_Int8> aContents( rSize );
+
+ aFile.read( aContents.getArray(), rSize, aRead );
+ if (aRead != rSize)
+ aContents.realloc(aRead);
+
+ aFile.close();
+ File::remove( aFileURL );
+ return aContents;
+
+}
+
+void ImagePreparer::sendNotes( sal_uInt32 aSlideNumber )
+{
+
+ OString aNotes = prepareNotes( aSlideNumber );
+
+ if ( aNotes.isEmpty() )
+ return;
+
+ if ( !xController->isRunning() )
+ return;
+
+ // Start the writing
+ OString aBuffer =
+ "slide_notes\n" +
+ OString::number( static_cast<sal_Int32>(aSlideNumber) ) +
+ "\n"
+ "<html><body>" +
+ aNotes +
+ "</body></html>"
+ "\n\n";
+ pTransmitter->addMessage( aBuffer,
+ Transmitter::PRIORITY_LOW );
+}
+
+// Code copied from sdremote/source/presenter/PresenterNotesView.cxx
+OString ImagePreparer::prepareNotes( sal_uInt32 aSlideNumber )
+{
+ OUStringBuffer aRet;
+
+ if ( !xController->isRunning() )
+ return "";
+
+ uno::Reference<css::drawing::XDrawPage> aNotesPage;
+ uno::Reference< drawing::XDrawPage > xSourceDoc(
+ xController->getSlideByIndex( aSlideNumber ),
+ uno::UNO_SET_THROW );
+ uno::Reference<presentation::XPresentationPage> xPresentationPage(
+ xSourceDoc, UNO_QUERY);
+ if (xPresentationPage.is())
+ aNotesPage = xPresentationPage->getNotesPage();
+ else
+ return "";
+
+ static constexpr OUStringLiteral sNotesShapeName (
+ u"com.sun.star.presentation.NotesShape" );
+ static constexpr OUStringLiteral sTextShapeName (
+ u"com.sun.star.drawing.TextShape" );
+
+ if (aNotesPage.is())
+ {
+
+ // Iterate over all shapes and find the one that holds the text.
+ sal_Int32 nCount (aNotesPage->getCount());
+ for (sal_Int32 nIndex=0; nIndex<nCount; ++nIndex)
+ {
+
+ uno::Reference<lang::XServiceName> xServiceName (
+ aNotesPage->getByIndex(nIndex), UNO_QUERY);
+ if (xServiceName.is()
+ && xServiceName->getServiceName() == sNotesShapeName)
+ {
+ uno::Reference<text::XTextRange> xText (xServiceName, UNO_QUERY);
+ if (xText.is())
+ {
+ aRet.append(xText->getString());
+ aRet.append("<br/>");
+ }
+ }
+ else
+ {
+ uno::Reference<drawing::XShapeDescriptor> xShapeDescriptor (
+ aNotesPage->getByIndex(nIndex), UNO_QUERY);
+ if (xShapeDescriptor.is())
+ {
+ OUString sType (xShapeDescriptor->getShapeType());
+ if (sType == sNotesShapeName || sType == sTextShapeName)
+ {
+ uno::Reference<text::XTextRange> xText (
+ aNotesPage->getByIndex(nIndex), UNO_QUERY);
+ if (xText.is())
+ {
+ aRet.append(xText->getString());
+ aRet.append("<br/>");
+ }
+ }
+ }
+ }
+ }
+ }
+ // Replace all newlines with <br\> tags
+ for ( sal_Int32 i = 0; i < aRet.getLength(); i++ )
+ {
+ if ( aRet[i] == '\n' )
+ {
+ aRet[i]= '<';
+ aRet.insert( i+1, "br/>" );
+ }
+ }
+ return OUStringToOString(
+ aRet.makeStringAndClear(), RTL_TEXTENCODING_UTF8 );
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */