summaryrefslogtreecommitdiffstats
path: root/kate/kjswrapper/plugin_katekjswrapper.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'kate/kjswrapper/plugin_katekjswrapper.cpp')
-rw-r--r--kate/kjswrapper/plugin_katekjswrapper.cpp437
1 files changed, 437 insertions, 0 deletions
diff --git a/kate/kjswrapper/plugin_katekjswrapper.cpp b/kate/kjswrapper/plugin_katekjswrapper.cpp
new file mode 100644
index 0000000..c3e54b7
--- /dev/null
+++ b/kate/kjswrapper/plugin_katekjswrapper.cpp
@@ -0,0 +1,437 @@
+/* This file is part of the KDE project
+ Copyright (C) 2004 Joseph Wenninger <jowenn@kde.org>
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Library General Public
+ License version 2 as published by the Free Software Foundation.
+
+ This library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Library General Public License for more details.
+
+ You should have received a copy of the GNU Library General Public License
+ along with this library; see the file COPYING.LIB. If not, write to
+ the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ Boston, MA 02110-1301, USA.
+*/
+//BEGIN includes
+#include "plugin_katekjswrapper.h"
+#include "plugin_katekjswrapper.moc"
+#include "bindings.h"
+
+#include <kjsembed/kjsembedpart.h>
+#include <kjsembed/jssecuritypolicy.h>
+#include <kjsembed/jsfactory.h>
+#include <kjsembed/jsconsolewidget.h>
+#include <kjs/interpreter.h>
+#include <kjs/value.h>
+#include <kjs/object.h>
+#include <kgenericfactory.h>
+#include <kdebug.h>
+#include <qlayout.h>
+#include <kstandarddirs.h>
+#include <kate/mainwindow.h>
+#include <kate/toolviewmanager.h>
+#include <kdockwidget.h>
+#include <qvbox.h>
+//END includes
+
+K_EXPORT_COMPONENT_FACTORY( katekjswrapperplugin, KGenericFactory<PluginKateKJSWrapper>( "katekjswrapper" ) )
+
+PluginKateKJSWrapperView::~PluginKateKJSWrapperView() {
+}
+
+void PluginKateKJSWrapperView::removeFromWindow() {
+ kdDebug()<<"PluginKateKJSWrapperView::removeFromWindow"<<endl;
+ for (QValueList<QGuardedPtr<KMDI::ToolViewAccessor> >::iterator it=toolviews.begin();it!=toolviews.end();it=toolviews.begin()) {
+ kdDebug()<<"removeFromWindow: removing a toolview"<<endl;
+ KMDI::ToolViewAccessor* tva=(*it);
+ toolviews.remove(it);
+ win->toolViewManager()->removeToolView (tva);
+ }
+ win->guiFactory()->removeClient (this);
+ }
+
+PluginKateKJSWrapper::PluginKateKJSWrapper( QObject* parent, const char* name, const QStringList& list)
+ : Kate::Plugin ( (Kate::Application *)parent, name ) {
+ m_views.setAutoDelete(true);
+ m_scriptname=list[0];
+ m_kateAppBindings=new Kate::JS::Bindings(this);
+ KJSEmbed::JSSecurityPolicy::setDefaultPolicy( KJSEmbed::JSSecurityPolicy::CapabilityAll );
+ m_part = new KJSEmbed::KJSEmbedPart(this);
+ KJS::Interpreter *js = m_part->interpreter();
+
+ KJSEmbed::JSFactory *factory=m_part->factory();
+
+/* factories for kate app classes */
+ factory->addQObjectPlugin("Kate::Application",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::DocumentManager",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::MainWindow",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::PluginManager",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::InitPluginManager",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::ProjectManager",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::Project",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::ViewManager",m_kateAppBindings);
+ factory->addQObjectPlugin("Kate::View",m_kateAppBindings);
+/* toplevel objects*/
+ KJS::Object appobj=m_part->addObject(Kate::application(),"KATE");
+ js->globalObject().put( js->globalExec(), "addConfigPage", KJS::Object(new Kate::JS::Management(js->globalExec(),Kate::JS::Management::AddConfigPage,this )));
+ js->globalObject().put( js->globalExec(), "setConfigPages", KJS::Object(new Kate::JS::Management(js->globalExec(),Kate::JS::Management::SetConfigPages,this )));
+ js->globalObject().put( js->globalExec(), "removeConfigPage", KJS::Object(new Kate::JS::Management(js->globalExec(),Kate::JS::Management::RemoveConfigPage,this )));
+ js->globalObject().put( js->globalExec(), "setWindowConfiguration", KJS::Object(new Kate::JS::Management(js->globalExec(),Kate::JS::Management::SetWindowConfiguration,this )));
+ js->globalObject().put( js->globalExec(), "KJSConsole", KJS::Object(new Kate::JS::Management(js->globalExec(),Kate::JS::Management::KJSConsole,this )));
+
+/* KJSEmbed::JSConsoleWidget *w=m_part->view();
+ w->show();
+ //w->show();*/
+ kdDebug()<<"m_scriptname="<<m_scriptname<<endl;
+ m_part->runFile(locate("appdata",QString("plugins/%1/%2.js").arg(m_scriptname).arg(m_scriptname)));
+//"/home/jowenn/development/kde/cvs/kdeaddons/kate/kjswrapper/samples/test1.js");
+}
+
+PluginKateKJSWrapper::~PluginKateKJSWrapper()
+{
+ delete m_part;
+ m_part=0;
+}
+
+
+uint PluginKateKJSWrapper::configPages () const {
+ KJS::Interpreter *js = m_part->interpreter();
+ KJS::ExecState *exec=js->globalExec();
+
+ if (! (m_configPageFactories.isNull() || (m_configPageFactories.type()==KJS::NullType))) {
+ KJS::Object constrs=m_configPageFactories.toObject(exec);
+ if (!exec->hadException()) {
+ if (QString(constrs.classInfo()->className)=="Array") {
+ kdDebug()<<"config page constructor array detected"<<endl;
+ uint size=constrs.get(exec,KJS::Identifier("length")).toInteger(exec);
+ if (exec->hadException()) {
+ exec->clearException();
+ kdDebug()<<"Error while retrieving array length"<<endl;
+ }
+ else return size;
+ } else return 1;
+ }
+ }
+ exec->clearException();
+ return 0;
+}
+
+
+static KJS::Object getObj(KJS::Interpreter *js, KJS::Value mightBeArray, int id) {
+ KJS::ExecState *exec=js->globalExec();
+ KJS::Object constrs=mightBeArray.toObject(exec);
+ KJS::Value constr;
+ if (!exec->hadException()) {
+ if (QString(constrs.classInfo()->className)=="Array") {
+ kdDebug()<<"config page constructor array detected"<<endl;
+ constr=constrs.get(exec,id);
+ } else constr=mightBeArray;
+
+ }
+ return constr.toObject(js->globalExec());
+}
+
+QString PluginKateKJSWrapper::configPageName(uint id) const {
+ if (id>=configPages()) return "";
+ KJS::Interpreter *js = m_part->interpreter();
+
+ KJS::Object constr=getObj(js,m_configPageFactories,id);
+
+ KJS::Value o=constr.get(js->globalExec(),KJS::Identifier("name"));
+ QString retVal( o.toString(js->globalExec()).qstring() );
+
+ kdDebug()<<"=============================================================================================="<<endl;
+ kdDebug()<<"PluginKateKJSWrapper::configPageName: "<<retVal<<endl;
+ kdDebug()<<"=============================================================================================="<<endl;
+ js->globalExec()->clearException();
+ return retVal;
+}
+
+QString PluginKateKJSWrapper::configPageFullName(uint id) const {
+ if (id>=configPages()) return "";
+ KJS::Interpreter *js = m_part->interpreter();
+
+ KJS::Object constr=getObj(js,m_configPageFactories,id);
+
+ KJS::Value o=constr.get(js->globalExec(),KJS::Identifier("fullName"));
+ QString retVal( o.toString(js->globalExec()).qstring() );
+
+ kdDebug()<<"=============================================================================================="<<endl;
+ kdDebug()<<"PluginKateKJSWrapper::configPageFullName: "<<retVal<<endl;
+ kdDebug()<<"=============================================================================================="<<endl;
+ js->globalExec()->clearException();
+ return retVal;
+}
+
+QPixmap PluginKateKJSWrapper::configPagePixmap (uint /*number = 0*/,
+ int /*size = KIcon::SizeSmall*/) const {
+ return 0;
+}
+
+
+Kate::PluginConfigPage* PluginKateKJSWrapper::configPage (uint id,
+ QWidget *w, const char */*name*/) {
+ kdDebug()<<"PluginKateKJSWrapper::configPage"<<endl;
+
+ if (id>=configPages()) return 0;
+ KJS::Interpreter *js = m_part->interpreter();
+
+ KJS::Object constr=getObj(js,m_configPageFactories,id);
+
+ if (js->globalExec()->hadException()) {
+ kdDebug()<<"PluginKateKJSWrapper::configPage: exit 1"<<endl;
+ js->globalExec()->clearException();
+ return 0;
+ }
+
+ if (!constr.implementsConstruct()) {
+ kdWarning()<<"config page factory has to be an object constructor"<<endl;
+ return 0;
+ }
+
+ KateKJSWrapperConfigPage *p=new KateKJSWrapperConfigPage(constr,this,w);
+ return (Kate::PluginConfigPage*)p;
+/*
+ KateKJSWrapperConfigPage* p = new KateKJSWrapperConfigPage(this, w);
+ //init
+ connect( p, SIGNAL(configPageApplyRequest(KateKJSWrapperConfigPage*)),
+ this, SLOT(applyConfig(KateKJSWrapperConfigPage*)) );
+ return (Kate::PluginConfigPage*);*/
+}
+
+
+
+
+static KMDI::ToolViewAccessor *createToolView(KJSEmbed::JSFactory *factory,KJS::Interpreter *js, Kate::MainWindow *winN,KJS::Object win,KJS::Object viewConstructor) {
+ KJS::List params;
+ KJS::ExecState *exec = js->globalExec();
+ params.append(win);
+ exec->clearException();
+ int dockPos;
+ if (!viewConstructor.implementsConstruct()) return 0;
+ KJS::Value dockPosV=viewConstructor.get(exec,KJS::Identifier("startPosition"));
+ if (exec->hadException()) {
+ dockPos=KDockWidget::DockLeft;
+ exec->clearException();
+ } else {
+ dockPos=dockPosV.toInteger(exec);
+ if (exec->hadException()) {
+ dockPos=KDockWidget::DockLeft;
+ exec->clearException();
+ }
+ }
+ QString viewName;
+ KJS::Value viewNameV=viewConstructor.get(exec,KJS::Identifier("name"));
+ if (exec->hadException()) {
+ viewName="kjs_unknown";
+ exec->clearException();
+ } else {
+ viewName=QString( viewNameV.toString(exec).qstring() );
+ if (exec->hadException()) {
+ viewName="kjs_unknown";
+ exec->clearException();
+ }
+ }
+
+ Kate::JS::ToolView *tv=new Kate::JS::ToolView(viewConstructor,exec,factory,params,viewName.utf8());
+ //params.append(factory->createProxy(exec,tv));
+ //KJS::Object otv=viewConstructor.construct(exec,params);
+ if (exec->hadException()) {
+ kdDebug()<<"Error while calling constructor"<<endl;
+ delete tv;
+ kdDebug()<<exec->exception().toString(exec).qstring()<<endl;
+ exec->clearException();
+ return 0;
+ }
+ KMDI::ToolViewAccessor *tva=winN->toolViewManager()->addToolView((KDockWidget::DockPosition)dockPos,tv,
+ tv->icon()?(*(tv->icon())):QPixmap(),tv->caption());
+ kdDebug()<<"****************************************************************************************"<<endl;
+ kdDebug()<<"PluginKateKJSWrapper: Toolview has been added"<<endl;
+ kdDebug()<<"****************************************************************************************"<<endl;
+ return tva;
+
+}
+
+PluginKateKJSWrapperView *PluginKateKJSWrapper::getViewObject(Kate::MainWindow *win) {
+ PluginKateKJSWrapperView * view=m_views[win];
+ if (!view) {
+ view=new PluginKateKJSWrapperView();
+ view->win=win;
+ connect(win,SIGNAL(destroyed()),this,SLOT(slotWindowDestroyed()));
+ m_views.insert(win,view);
+ KJS::Interpreter *js = m_part->interpreter();
+ KJS::ExecState *exec = js->globalExec();
+ view->actionCollectionObj=m_part->factory()->createProxy(exec,view->actionCollection());
+ view->winObj=m_part->factory()->createProxy(exec,win);
+ } else kdDebug()<<"returning cached View/Window Object"<<endl;
+ return view;
+}
+
+void PluginKateKJSWrapper::addView(Kate::MainWindow *win)
+{
+ PluginKateKJSWrapperView * view=getViewObject(win); // this is needed to ensure correct caching the javascript object
+ KJS::Interpreter *js = m_part->interpreter();
+ KJS::ExecState *exec = js->globalExec();
+ exec->clearException();
+ kdDebug()<<"****************************************************************************************"<<endl;
+ kdDebug()<<"PluginKateKJSWrapper::addView"<<endl;
+ kdDebug()<<"****************************************************************************************"<<endl;
+ kdDebug()<<"checking for newWindowHandler"<<endl;
+ if (!m_newWindowHandler.isNull()) {
+ KJS::List param;
+ param.append(view->winObj);
+ KJS::Object newWinFunc=m_newWindowHandler.toObject(exec);
+ if (exec->hadException()) {
+ exec->clearException();
+ } else {
+ if (newWinFunc.implementsCall()) {
+ newWinFunc.call(exec,js->globalObject(),param);
+ if (exec->hadException()) {
+ kdDebug()<<"Error while calling newWindowHandler"<<endl;
+ exec->clearException();
+ }
+ }
+ }
+ }
+ if (exec->hadException()) kdDebug()<<"void PluginKateKJSWrapper::addView(Kate::MainWindow *win): exec had an exception - 1"<<endl;
+
+ kdDebug()<<"checking for toolview constructors"<<endl;
+ if (! (m_toolViewConstructors.isNull() || (m_toolViewConstructors.type()==KJS::NullType))) {
+ KJS::Object constrs=m_toolViewConstructors.toObject(exec);
+ if (!exec->hadException()) {
+ if (QString(constrs.classInfo()->className)=="Array") {
+ kdDebug()<<"Toolview constructor array detected"<<endl;
+ int size=constrs.get(exec,KJS::Identifier("length")).toInteger(exec);
+ if (exec->hadException()) {
+ exec->clearException();
+ kdDebug()<<"Error while retrieving array length"<<endl;
+ }
+ else {
+ for (int i=0;i<size;i++) {
+ KJS::Object constrO=constrs.get(exec,i).toObject(exec);
+ if (exec->hadException()) {
+ exec->clearException();
+ } else {
+ KMDI::ToolViewAccessor *w=createToolView(m_part->factory(),js,win,view->winObj,constrO);
+ if (w) {
+ view->toolviews.append(QGuardedPtr<KMDI::ToolViewAccessor>(w));
+ }
+ exec->clearException();
+ }
+ }
+ }
+ } else {
+ kdDebug()<<"Single toolview constructor detected"<<endl;
+ if (!constrs.implementsConstruct()) {
+ kdWarning()<<"wrong object type"<<endl;
+ } else {
+ KMDI::ToolViewAccessor *w=createToolView(m_part->factory(),js,win,view->winObj,constrs);
+ if (w) {
+ view->toolviews.append(QGuardedPtr<KMDI::ToolViewAccessor>(w));
+ }
+ exec->clearException();
+ }
+ }
+
+ }
+ } else kdDebug()<<"void PluginKateKJSWrapper::addView(Kate::MainWindow *win): no toolview constructors"<<endl;
+
+
+ if (exec->hadException()) kdDebug()<<"void PluginKateKJSWrapper::addView(Kate::MainWindow *win): exec had an exception - 2"<<endl;
+
+ view->setInstance (new KInstance("kate"));
+ view->setXMLFile(QString("plugins/%1/%2.rc").arg(m_scriptname).arg(m_scriptname));
+ win->guiFactory()->addClient (view);
+}
+
+
+void PluginKateKJSWrapper::slotWindowDestroyed() {
+ m_views.remove((void*)sender());
+}
+
+void PluginKateKJSWrapper::removeView(Kate::MainWindow *win)
+{
+//here toolviews must not be destroyed. Only cleanup functions called the view should be removed in the slot connected to the windows destroy signal only
+ m_views[win]->removeFromWindow();
+}
+
+
+
+void PluginKateKJSWrapper::applyConfig( KateKJSWrapperConfigPage *p )
+{
+#if 0
+ config->writeEntry( "Command History Length", p->sb_cmdhistlen->value() );
+ // truncate the cmd hist if nessecary?
+ config->writeEntry( "Start In", p->rg_startin->id(p->rg_startin->selected()) );
+ config->sync();
+#endif
+}
+
+KateKJSWrapperConfigPage::KateKJSWrapperConfigPage(KJS::Object pageConstructor,PluginKateKJSWrapper* parent,
+ QWidget *parentWidget)
+ : Kate::PluginConfigPage( parentWidget ),m_plugin(parent)
+{
+ QVBoxLayout *l=new QVBoxLayout(this);
+ l->setAutoAdd(true);
+ l->activate();
+ KJS::Interpreter *js = parent->m_part->interpreter();
+ KJS::ExecState *exec = js->globalExec();
+ exec->clearException();
+ KJS::List param;
+ param.append(parent->m_part->factory()->createProxy(exec,this,0));
+ m_pageObject=pageConstructor.construct(exec,param);
+}
+
+
+static void callJS(KJSEmbed::KJSEmbedPart *p,KJS::Object o,const QString& funcName){
+ KJS::Interpreter *js = p->interpreter();
+ KJS::ExecState *exec = js->globalExec();
+ KJS::List param;
+ exec->clearException();
+ KJS::Value funcV=o.get(exec,KJS::Identifier(funcName));
+ if (exec->hadException()) {
+#warning clear exception ?
+ return;
+ }
+ KJS::Object func=funcV.toObject(exec);
+ if (exec->hadException()) {
+#warning clear exception ?
+ return;
+ }
+ if (func.implementsCall()) {
+ func.call(exec,o,param);
+ if (js->globalExec()->hadException()) {
+#warning clear exception ?
+ return;
+ }
+ }
+}
+
+void KateKJSWrapperConfigPage::apply()
+{
+ callJS(m_plugin->m_part,m_pageObject,"apply");
+}
+
+void KateKJSWrapperConfigPage::reset()
+{
+ callJS(m_plugin->m_part,m_pageObject,"reset");
+}
+
+void KateKJSWrapperConfigPage::defaults()
+{
+ callJS(m_plugin->m_part,m_pageObject,"defaults");
+}
+
+
+Kate::JS::ToolView::ToolView(KJS::Object constr, KJS::ExecState *exec, KJSEmbed::JSFactory *factory, KJS::List parameters, const char *name):QVBox(0,name) {
+ parameters.append(factory->createProxy(exec,this));
+ handler=constr.construct(exec,parameters);
+
+}
+
+Kate::JS::ToolView::~ToolView() {
+}
+