1 /***************************************************************************
2 Copyright (C) 2002 by George Russell <george.russell@clara.net>
3 Copyright (C) 2003-2004 by Olaf Schmidt <ojschmidt@kde.org>
4 ***************************************************************************/
6 /***************************************************************************
8 * This program is free software; you can redistribute it and/or modify *
9 * it under the terms of the GNU General Public License as published by *
10 * the Free Software Foundation; either version 2 of the License, or *
11 * (at your option) any later version. *
13 ***************************************************************************/
16 #include "khtmlkttsd.h"
19 #include <dom/dom_string.h>
20 #include <dom/html_document.h>
21 #include <dom/html_element.h>
23 #include <kactioncollection.h>
25 #include <khtml_part.h> // this plugin applies to a khtml part
26 #include <config-kttsplugin.h>
28 #include <webkitpart.h>
32 #include <webkitview.h>
38 #include <kmessagebox.h>
39 #include <kpluginfactory.h>
40 #include <kservicetypetrader.h>
42 #include <ktoolinvocation.h>
45 #include "kspeechinterface.h"
47 KHTMLPluginKTTSD::KHTMLPluginKTTSD( QObject
* parent
, const QVariantList
& )
50 if (qobject_cast
<KHTMLPart
*>(parent
)) { // should always be true, but let's make sure
51 QAction
*action
= actionCollection()->addAction( "tools_kttsd" );
52 action
->setIcon( KIcon("text-speak") );
53 action
->setText( i18n("&Speak Text") );
54 connect(action
, SIGNAL(triggered(bool) ), SLOT(slotReadOut()));
58 KHTMLPluginKTTSD::~KHTMLPluginKTTSD()
62 void KHTMLPluginKTTSD::slotReadOut()
64 // The parent is assumed to be a KHTMLPart (checked in constructor)
65 KParts::ReadOnlyPart
* part
= static_cast<KParts::ReadOnlyPart
*>(parent());
67 if (!QDBusConnection::sessionBus().interface()->isServiceRegistered("org.kde.kttsd"))
70 if (KToolInvocation::startServiceByDesktopName("kttsd", QStringList(), &error
)) {
71 KMessageBox::error(part
->widget(), error
, i18n("Starting KTTSD Failed") );
74 // Find out if KTTSD supports xhtml (rich speak).
75 bool supportsXhtml
= false;
76 org::kde::KSpeech
kttsd( "org.kde.kttsd", "/KSpeech", QDBusConnection::sessionBus() );
77 QString talker
= kttsd
.defaultTalker();
78 QDBusReply
<int> reply
= kttsd
.getTalkerCapabilities2(talker
);
79 if ( !reply
.isValid())
80 kDebug() << "D-Bus call getTalkerCapabilities2() failed, assuming non-XHTML support.";
83 supportsXhtml
= reply
.value() & KSpeech::tcCanParseHtml
;
87 bool hasSelection
= false;
88 KHTMLPart
*compPart
= dynamic_cast<KHTMLPart
*>(part
);
93 kDebug() << "KTTS claims to support rich speak (XHTML to SSML).";
95 query
= compPart
->selectedTextAsHTML();
98 // TODO: Fooling around with the selection probably has unwanted
99 // side effects, but until a method is supplied to get valid xhtml
100 // from entire document..
101 // query = part->document().toString().string();
102 compPart
->selectAll();
103 query
= compPart
->selectedTextAsHTML();
104 // Restore no selection.
105 compPart
->setSelection(compPart
->document().createRange());
109 query
= compPart
->selectedText();
111 query
= compPart
->htmlDocument().body().innerText().string();
114 #ifdef HAVE_WEBKITKDE
117 WebKitPart
*webkitPart
= dynamic_cast<WebKitPart
*>(part
);
122 kDebug() << "KTTS claims to support rich speak (XHTML to SSML).";
124 query
= webkitPart
->view()->page()->currentFrame()->toHtml();
127 // TODO: Fooling around with the selection probably has unwanted
128 // side effects, but until a method is supplied to get valid xhtml
129 // from entire document..
130 // query = part->document().toString().string();
132 webkitPart
->selectAll();
133 query
= webkitPart
->view()->page()->currentFrame()->toHtml();
134 // Restore no selection.
135 webkitPart
->setSelection(webkitPart
->document().createRange());
140 query
= webkitPart
->view()->selectedText();
142 query
= webkitPart
->view()->page()->currentFrame()->toHtml();
148 // kDebug() << "query =" << query;
150 reply
= kttsd
.say(query
, KSpeech::soNone
);
151 if ( !reply
.isValid()) {
152 KMessageBox::sorry(part
->widget(), i18n("The D-Bus call say() failed."),
153 i18n("D-Bus Call Failed"));
157 K_PLUGIN_FACTORY(KHTMLPluginKTTSDFactory
,
158 const KService::List offers
= KServiceTypeTrader::self()->query("DBUS/Text-to-Speech", "Name == 'KTTSD'");
159 // If KTTSD is not installed, don't create the plugin at all.
160 if (!offers
.isEmpty()) {
161 registerPlugin
<KHTMLPluginKTTSD
>();
164 K_EXPORT_PLUGIN( KHTMLPluginKTTSDFactory( "khtmlkttsd" ) )
166 #include "khtmlkttsd.moc"