00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "config.h"
00023
00024 #include "khtmlview.h"
00025 #include "khtml_part.h"
00026 #include "khtmlpart_p.h"
00027 #include "khtml_settings.h"
00028 #include "xml/dom2_eventsimpl.h"
00029 #include "xml/dom_docimpl.h"
00030 #include "misc/htmltags.h"
00031 #include "html/html_documentimpl.h"
00032 #include "rendering/render_frames.h"
00033
00034 #include <qstylesheet.h>
00035 #include <qtimer.h>
00036 #include <qpaintdevicemetrics.h>
00037 #include <qapplication.h>
00038 #include <kdebug.h>
00039 #include <kmessagebox.h>
00040 #include <kinputdialog.h>
00041 #include <klocale.h>
00042 #include <kmdcodec.h>
00043 #include <kparts/browserinterface.h>
00044 #include <kwin.h>
00045
00046 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00047 #include <kwinmodule.h>
00048 #endif
00049
00050 #ifndef KONQ_EMBEDDED
00051 #include <kbookmarkmanager.h>
00052 #endif
00053 #include <kglobalsettings.h>
00054 #include <assert.h>
00055 #include <qstyle.h>
00056 #include <qobjectlist.h>
00057 #include <kstringhandler.h>
00058
00059 #include "kjs_proxy.h"
00060 #include "kjs_window.h"
00061 #include "kjs_navigator.h"
00062 #include "kjs_mozilla.h"
00063 #include "kjs_html.h"
00064 #include "kjs_range.h"
00065 #include "kjs_traversal.h"
00066 #include "kjs_css.h"
00067 #include "kjs_events.h"
00068 #include "kjs_views.h"
00069 #include "xmlhttprequest.h"
00070 #include "xmlserializer.h"
00071 #include "domparser.h"
00072
00073 using namespace KJS;
00074
00075 namespace KJS {
00076
00077 class History : public ObjectImp {
00078 friend class HistoryFunc;
00079 public:
00080 History(ExecState *exec, KHTMLPart *p)
00081 : ObjectImp(exec->interpreter()->builtinObjectPrototype()), part(p) { }
00082 virtual Value get(ExecState *exec, const Identifier &propertyName) const;
00083 Value getValueProperty(ExecState *exec, int token) const;
00084 virtual const ClassInfo* classInfo() const { return &info; }
00085 static const ClassInfo info;
00086 enum { Back, Forward, Go, Length };
00087 private:
00088 QGuardedPtr<KHTMLPart> part;
00089 };
00090
00091 class External : public ObjectImp {
00092 friend class ExternalFunc;
00093 public:
00094 External(ExecState *exec, KHTMLPart *p)
00095 : ObjectImp(exec->interpreter()->builtinObjectPrototype()), part(p) { }
00096 virtual Value get(ExecState *exec, const Identifier &propertyName) const;
00097 virtual const ClassInfo* classInfo() const { return &info; }
00098 static const ClassInfo info;
00099 enum { AddFavorite };
00100 private:
00101 QGuardedPtr<KHTMLPart> part;
00102 };
00103
00104 class FrameArray : public ObjectImp {
00105 public:
00106 FrameArray(ExecState *exec, KHTMLPart *p)
00107 : ObjectImp(exec->interpreter()->builtinObjectPrototype()), part(p) { }
00108 virtual Value get(ExecState *exec, const Identifier &propertyName) const;
00109 private:
00110 QGuardedPtr<KHTMLPart> part;
00111 };
00112
00113 #ifdef Q_WS_QWS
00114 class KonquerorFunc : public DOMFunction {
00115 public:
00116 KonquerorFunc(ExecState *exec, const Konqueror* k, const char* name)
00117 : DOMFunction(exec), konqueror(k), m_name(name) { }
00118 virtual Value tryCall(ExecState *exec, Object &thisObj, const List &args);
00119
00120 private:
00121 const Konqueror* konqueror;
00122 QCString m_name;
00123 };
00124 #endif
00125 }
00126
00127 #include "kjs_window.lut.h"
00128 #include "rendering/render_replaced.h"
00129
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146 const ClassInfo Screen::info = { "Screen", 0, &ScreenTable, 0 };
00147
00148
00149 Screen::Screen(ExecState *exec)
00150 : ObjectImp(exec->interpreter()->builtinObjectPrototype()) {}
00151
00152 Value Screen::get(ExecState *exec, const Identifier &p) const
00153 {
00154 #ifdef KJS_VERBOSE
00155 kdDebug(6070) << "Screen::get " << p.qstring() << endl;
00156 #endif
00157 return lookupGetValue<Screen,ObjectImp>(exec,p,&ScreenTable,this);
00158 }
00159
00160 Value Screen::getValueProperty(ExecState *exec, int token) const
00161 {
00162 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00163 KWinModule info(0, KWinModule::INFO_DESKTOP);
00164 #endif
00165 QWidget *thisWidget = Window::retrieveActive(exec)->part()->widget();
00166 QRect sg = KGlobalSettings::desktopGeometry(thisWidget);
00167
00168 switch( token ) {
00169 case Height:
00170 return Number(sg.height());
00171 case Width:
00172 return Number(sg.width());
00173 case ColorDepth:
00174 case PixelDepth: {
00175 QPaintDeviceMetrics m(QApplication::desktop());
00176 return Number(m.depth());
00177 }
00178 case AvailLeft: {
00179 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00180 QRect clipped = info.workArea().intersect(sg);
00181 return Number(clipped.x()-sg.x());
00182 #else
00183 return Number(10);
00184 #endif
00185 }
00186 case AvailTop: {
00187 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00188 QRect clipped = info.workArea().intersect(sg);
00189 return Number(clipped.y()-sg.y());
00190 #else
00191 return Number(10);
00192 #endif
00193 }
00194 case AvailHeight: {
00195 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00196 QRect clipped = info.workArea().intersect(sg);
00197 return Number(clipped.height());
00198 #else
00199 return Number(100);
00200 #endif
00201 }
00202 case AvailWidth: {
00203 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00204 QRect clipped = info.workArea().intersect(sg);
00205 return Number(clipped.width());
00206 #else
00207 return Number(100);
00208 #endif
00209 }
00210 default:
00211 kdDebug(6070) << "WARNING: Screen::getValueProperty unhandled token " << token << endl;
00212 return Undefined();
00213 }
00214 }
00215
00217
00218 const ClassInfo Window::info = { "Window", &DOMAbstractView::info, &WindowTable, 0 };
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
00289
00290
00291
00292
00293
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313
00314
00315
00316
00317
00318
00319
00320
00321
00322
00323
00324
00325
00326
00327
00328
00329
00330
00331
00332
00333
00334
00335
00336 IMPLEMENT_PROTOFUNC_DOM(WindowFunc)
00337
00338 Window::Window(khtml::ChildFrame *p)
00339 : ObjectImp(), m_frame(p), screen(0), history(0), external(0), m_frames(0), loc(0), m_evt(0)
00340 {
00341 winq = new WindowQObject(this);
00342
00343 }
00344
00345 Window::~Window()
00346 {
00347 delete winq;
00348 }
00349
00350 Window *Window::retrieveWindow(KParts::ReadOnlyPart *p)
00351 {
00352 Object obj = Object::dynamicCast( retrieve( p ) );
00353 #ifndef NDEBUG
00354
00355 KHTMLPart *part = ::qt_cast<KHTMLPart *>(p);
00356 if ( part && part->jScriptEnabled() )
00357 {
00358 assert( obj.isValid() );
00359 #ifndef QWS
00360 assert( dynamic_cast<KJS::Window*>(obj.imp()) );
00361 #endif
00362 }
00363 #endif
00364 if ( !obj.isValid() )
00365 return 0;
00366 return static_cast<KJS::Window*>(obj.imp());
00367 }
00368
00369 Window *Window::retrieveActive(ExecState *exec)
00370 {
00371 ValueImp *imp = exec->interpreter()->globalObject().imp();
00372 assert( imp );
00373 #ifndef QWS
00374 assert( dynamic_cast<KJS::Window*>(imp) );
00375 #endif
00376 return static_cast<KJS::Window*>(imp);
00377 }
00378
00379 Value Window::retrieve(KParts::ReadOnlyPart *p)
00380 {
00381 assert(p);
00382 KHTMLPart * part = ::qt_cast<KHTMLPart *>(p);
00383 KJSProxy *proxy = 0L;
00384 if (!part) {
00385 part = ::qt_cast<KHTMLPart *>(p->parent());
00386 if (part)
00387 proxy = part->framejScript(p);
00388 } else
00389 proxy = part->jScript();
00390 if (proxy) {
00391 #ifdef KJS_VERBOSE
00392 kdDebug(6070) << "Window::retrieve part=" << part << " '" << part->name() << "' interpreter=" << proxy->interpreter() << " window=" << proxy->interpreter()->globalObject().imp() << endl;
00393 #endif
00394 return proxy->interpreter()->globalObject();
00395 } else {
00396 #ifdef KJS_VERBOSE
00397 kdDebug(6070) << "Window::retrieve part=" << p << " '" << p->name() << "' no jsproxy." << endl;
00398 #endif
00399 return Undefined();
00400 }
00401 }
00402
00403 Location *Window::location() const
00404 {
00405 if (!loc)
00406 const_cast<Window*>(this)->loc = new Location(m_frame);
00407 return loc;
00408 }
00409
00410 ObjectImp* Window::frames( ExecState* exec ) const
00411 {
00412 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
00413 if (part)
00414 return m_frames ? m_frames :
00415 (const_cast<Window*>(this)->m_frames = new FrameArray(exec, part));
00416 return 0L;
00417 }
00418
00419
00420 void Window::mark()
00421 {
00422 ObjectImp::mark();
00423 if (screen && !screen->marked())
00424 screen->mark();
00425 if (history && !history->marked())
00426 history->mark();
00427 if (external && !external->marked())
00428 external->mark();
00429 if (m_frames && !m_frames->marked())
00430 m_frames->mark();
00431
00432 if (loc && !loc->marked())
00433 loc->mark();
00434 if (winq)
00435 winq->mark();
00436 }
00437
00438 bool Window::hasProperty(ExecState *exec, const Identifier &p) const
00439 {
00440
00441 if (m_frame.isNull() || m_frame->m_part.isNull())
00442 return ( p == "closed" );
00443
00444 if (ObjectImp::hasProperty(exec, p))
00445 return true;
00446
00447 if (Lookup::findEntry(&WindowTable, p))
00448 return true;
00449
00450 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
00451 if (!part)
00452 return false;
00453
00454 QString q = p.qstring();
00455 if (part->findFramePart(p.qstring()))
00456 return true;
00457
00458 bool ok;
00459 unsigned int i = p.toArrayIndex(&ok);
00460 if (ok) {
00461 QPtrList<KParts::ReadOnlyPart> frames = part->frames();
00462 unsigned int len = frames.count();
00463 if (i < len)
00464 return true;
00465 }
00466
00467
00468 if (part->document().isHTMLDocument()) {
00469 DOM::HTMLDocument doc = part->htmlDocument();
00470
00471
00472 if (static_cast<DOM::DocumentImpl*>(doc.handle())->underDocNamedCache().get(p.qstring()))
00473 return true;
00474
00475 return !doc.getElementById(p.string()).isNull();
00476 }
00477
00478 return false;
00479 }
00480
00481 UString Window::toString(ExecState *) const
00482 {
00483 return "[object Window]";
00484 }
00485
00486 Value Window::get(ExecState *exec, const Identifier &p) const
00487 {
00488 #ifdef KJS_VERBOSE
00489 kdDebug(6070) << "Window("<<this<<")::get " << p.qstring() << endl;
00490 #endif
00491
00492 if (m_frame.isNull() || m_frame->m_part.isNull()) {
00493 if ( p == "closed" )
00494 return Boolean( true );
00495 return Undefined();
00496 }
00497
00498
00499 ValueImp *val = getDirect(p);
00500 if (val) {
00501
00502 return isSafeScript(exec) ? Value(val) : Undefined();
00503 }
00504
00505 const HashEntry* entry = Lookup::findEntry(&WindowTable, p);
00506 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
00507
00508
00509 if (entry) {
00510
00511 switch(entry->value) {
00512 case Closed:
00513 return Boolean( false );
00514 case _Location:
00515
00516 return Value(location());
00517 case _Window:
00518 case Self:
00519 return retrieve(m_frame->m_part);
00520 default:
00521 break;
00522 }
00523 if (!part)
00524 return Undefined();
00525
00526 switch(entry->value) {
00527 case Frames:
00528 return Value(frames(exec));
00529 case Opener:
00530 if (!part->opener())
00531 return Null();
00532 else
00533 return retrieve(part->opener());
00534 case Parent:
00535 return retrieve(part->parentPart() ? part->parentPart() : (KHTMLPart*)part);
00536 case Top: {
00537 KHTMLPart *p = part;
00538 while (p->parentPart())
00539 p = p->parentPart();
00540 return retrieve(p);
00541 }
00542 case Alert:
00543 case Confirm:
00544 case Prompt:
00545 case Open:
00546 case Close:
00547 case Focus:
00548 case Blur:
00549 case AToB:
00550 case BToA:
00551 case GetComputedStyle:
00552 return lookupOrCreateFunction<WindowFunc>(exec,p,this,entry->value,entry->params,entry->attr);
00553 default:
00554 break;
00555 }
00556 } else if (!part) {
00557
00558 QString rvalue;
00559 KParts::LiveConnectExtension::Type rtype;
00560 unsigned long robjid;
00561 if (m_frame->m_liveconnect &&
00562 isSafeScript(exec) &&
00563 m_frame->m_liveconnect->get(0, p.qstring(), rtype, robjid, rvalue))
00564 return getLiveConnectValue(m_frame->m_liveconnect, p.qstring(), rtype, rvalue, robjid);
00565 return Undefined();
00566 }
00567
00568 if (isSafeScript(exec) && entry)
00569 {
00570
00571 switch( entry->value ) {
00572 case Crypto:
00573 return Undefined();
00574 case DefaultStatus:
00575 return String(UString(part->jsDefaultStatusBarText()));
00576 case Status:
00577 return String(UString(part->jsStatusBarText()));
00578 case Document:
00579 if (part->document().isNull()) {
00580 kdDebug(6070) << "Document.write: adding <HTML><BODY> to create document" << endl;
00581 part->begin();
00582 part->write("<HTML><BODY>");
00583 part->end();
00584 }
00585 return getDOMNode(exec,part->document());
00586 case FrameElement:
00587 if (m_frame->m_frame)
00588 return getDOMNode(exec,m_frame->m_frame->element());
00589 else
00590 return Undefined();
00591 case Node:
00592 return getNodeConstructor(exec);
00593 case Range:
00594 return getRangeConstructor(exec);
00595 case NodeFilter:
00596 return getNodeFilterConstructor(exec);
00597 case DOMException:
00598 return getDOMExceptionConstructor(exec);
00599 case CSSRule:
00600 return getCSSRuleConstructor(exec);
00601 case EventCtor:
00602 return getEventConstructor(exec);
00603 case MutationEventCtor:
00604 return getMutationEventConstructor(exec);
00605 case KeyboardEventCtor:
00606 return getKeyboardEventConstructor(exec);
00607 case EventExceptionCtor:
00608 return getEventExceptionConstructor(exec);
00609 case _History:
00610 return Value(history ? history :
00611 (const_cast<Window*>(this)->history = new History(exec,part)));
00612
00613 case _External:
00614 return Value(external ? external :
00615 (const_cast<Window*>(this)->external = new External(exec,part)));
00616
00617 case Event:
00618 if (m_evt)
00619 return getDOMEvent(exec,*m_evt);
00620 else {
00621 #ifdef KJS_VERBOSE
00622 kdDebug(6070) << "WARNING: window(" << this << "," << part->name() << ").event, no event!" << endl;
00623 #endif
00624 return Undefined();
00625 }
00626 case InnerHeight:
00627 if (!part->view())
00628 return Undefined();
00629 khtml::RenderWidget::flushWidgetResizes();
00630 return Number(part->view()->visibleHeight());
00631 case InnerWidth:
00632 if (!part->view())
00633 return Undefined();
00634 khtml::RenderWidget::flushWidgetResizes();
00635 return Number(part->view()->visibleWidth());
00636 case Length:
00637 return Number(part->frames().count());
00638 case Name:
00639 return String(part->name());
00640 case SideBar:
00641 return Value(new MozillaSidebarExtension(exec, part));
00642 case _Navigator:
00643 case ClientInformation: {
00644
00645 Value nav( new Navigator(exec, part) );
00646 const_cast<Window *>(this)->put(exec, "navigator", nav, DontDelete|ReadOnly|Internal);
00647 const_cast<Window *>(this)->put(exec, "clientInformation", nav, DontDelete|ReadOnly|Internal);
00648 return nav;
00649 }
00650 #ifdef Q_WS_QWS
00651 case _Konqueror: {
00652 Value k( new Konqueror(part) );
00653 const_cast<Window *>(this)->put(exec, "konqueror", k, DontDelete|ReadOnly|Internal);
00654 return k;
00655 }
00656 #endif
00657 case OffscreenBuffering:
00658 return Boolean(true);
00659 case OuterHeight:
00660 case OuterWidth:
00661 {
00662 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00663 if (!part->widget())
00664 return Number(0);
00665 KWin::WindowInfo inf = KWin::windowInfo(part->widget()->topLevelWidget()->winId());
00666 return Number(entry->value == OuterHeight ?
00667 inf.geometry().height() : inf.geometry().width());
00668 #else
00669 return Number(entry->value == OuterHeight ?
00670 part->view()->height() : part->view()->width());
00671 #endif
00672 }
00673 case PageXOffset:
00674 return Number(part->view()->contentsX());
00675 case PageYOffset:
00676 return Number(part->view()->contentsY());
00677 case Personalbar:
00678 return Undefined();
00679 case ScreenLeft:
00680 case ScreenX: {
00681 if (!part->view())
00682 return Undefined();
00683 QRect sg = KGlobalSettings::desktopGeometry(part->view());
00684 return Number(part->view()->mapToGlobal(QPoint(0,0)).x() + sg.x());
00685 }
00686 case ScreenTop:
00687 case ScreenY: {
00688 if (!part->view())
00689 return Undefined();
00690 QRect sg = KGlobalSettings::desktopGeometry(part->view());
00691 return Number(part->view()->mapToGlobal(QPoint(0,0)).y() + sg.y());
00692 }
00693 case ScrollX: {
00694 if (!part->view())
00695 return Undefined();
00696 return Number(part->view()->contentsX());
00697 }
00698 case ScrollY: {
00699 if (!part->view())
00700 return Undefined();
00701 return Number(part->view()->contentsY());
00702 }
00703 case Scrollbars:
00704 return Undefined();
00705 case _Screen:
00706 return Value(screen ? screen :
00707 (const_cast<Window*>(this)->screen = new Screen(exec)));
00708 case Image:
00709 return Value(new ImageConstructorImp(exec, part->document()));
00710 case Option:
00711 return Value(new OptionConstructorImp(exec, part->document()));
00712 case XMLHttpRequest:
00713 return Value(new XMLHttpRequestConstructorImp(exec, part->document()));
00714 case XMLSerializer:
00715 return Value(new XMLSerializerConstructorImp(exec));
00716 case DOMParser:
00717 return Value(new DOMParserConstructorImp(exec, part->xmlDocImpl()));
00718 case Scroll:
00719 case ScrollBy:
00720 case ScrollTo:
00721 case MoveBy:
00722 case MoveTo:
00723 case ResizeBy:
00724 case ResizeTo:
00725 case CaptureEvents:
00726 case ReleaseEvents:
00727 case AddEventListener:
00728 case RemoveEventListener:
00729 case SetTimeout:
00730 case ClearTimeout:
00731 case SetInterval:
00732 case ClearInterval:
00733 case Print:
00734 return lookupOrCreateFunction<WindowFunc>(exec,p,this,entry->value,entry->params,entry->attr);
00735
00736 case Navigate:
00737
00738
00739 if ( exec->interpreter()->compatMode() == Interpreter::NetscapeCompat )
00740 return Undefined();
00741 return lookupOrCreateFunction<WindowFunc>(exec,p,this,entry->value,entry->params,entry->attr);
00742 case Onabort:
00743 return getListener(exec,DOM::EventImpl::ABORT_EVENT);
00744 case Onblur:
00745 return getListener(exec,DOM::EventImpl::BLUR_EVENT);
00746 case Onchange:
00747 return getListener(exec,DOM::EventImpl::CHANGE_EVENT);
00748 case Onclick:
00749 return getListener(exec,DOM::EventImpl::KHTML_ECMA_CLICK_EVENT);
00750 case Ondblclick:
00751 return getListener(exec,DOM::EventImpl::KHTML_ECMA_DBLCLICK_EVENT);
00752 case Ondragdrop:
00753 return getListener(exec,DOM::EventImpl::KHTML_DRAGDROP_EVENT);
00754 case Onerror:
00755 return getListener(exec,DOM::EventImpl::ERROR_EVENT);
00756 case Onfocus:
00757 return getListener(exec,DOM::EventImpl::FOCUS_EVENT);
00758 case Onkeydown:
00759 return getListener(exec,DOM::EventImpl::KEYDOWN_EVENT);
00760 case Onkeypress:
00761 return getListener(exec,DOM::EventImpl::KEYPRESS_EVENT);
00762 case Onkeyup:
00763 return getListener(exec,DOM::EventImpl::KEYUP_EVENT);
00764 case Onload:
00765 return getListener(exec,DOM::EventImpl::LOAD_EVENT);
00766 case Onmousedown:
00767 return getListener(exec,DOM::EventImpl::MOUSEDOWN_EVENT);
00768 case Onmousemove:
00769 return getListener(exec,DOM::EventImpl::MOUSEMOVE_EVENT);
00770 case Onmouseout:
00771 return getListener(exec,DOM::EventImpl::MOUSEOUT_EVENT);
00772 case Onmouseover:
00773 return getListener(exec,DOM::EventImpl::MOUSEOVER_EVENT);
00774 case Onmouseup:
00775 return getListener(exec,DOM::EventImpl::MOUSEUP_EVENT);
00776 case Onmove:
00777 return getListener(exec,DOM::EventImpl::KHTML_MOVE_EVENT);
00778 case Onreset:
00779 return getListener(exec,DOM::EventImpl::RESET_EVENT);
00780 case Onresize:
00781 return getListener(exec,DOM::EventImpl::RESIZE_EVENT);
00782 case Onselect:
00783 return getListener(exec,DOM::EventImpl::SELECT_EVENT);
00784 case Onsubmit:
00785 return getListener(exec,DOM::EventImpl::SUBMIT_EVENT);
00786 case Onunload:
00787 return getListener(exec,DOM::EventImpl::UNLOAD_EVENT);
00788 }
00789 }
00790
00791
00792
00793
00794 Object proto = Object::dynamicCast(prototype());
00795 assert(proto.isValid());
00796 if (p == specialPrototypePropertyName)
00797 return isSafeScript(exec) ? Value(proto) : Undefined();
00798 Value val2 = proto.get(exec, p);
00799 if (!val2.isA(UndefinedType)) {
00800 return isSafeScript(exec) ? val2 : Undefined();
00801 }
00802
00803 KParts::ReadOnlyPart *rop = part->findFramePart( p.qstring() );
00804 if (rop)
00805 return retrieve(rop);
00806
00807
00808 bool ok;
00809 unsigned int i = p.toArrayIndex(&ok);
00810 if (ok) {
00811 QPtrList<KParts::ReadOnlyPart> frames = part->frames();
00812 unsigned int len = frames.count();
00813 if (i < len) {
00814 KParts::ReadOnlyPart* frame = frames.at(i);
00815 if (frame)
00816 return Window::retrieve(frame);
00817 }
00818 }
00819
00820
00821 if (isSafeScript(exec) && part->document().isHTMLDocument()) {
00822 DOM::DocumentImpl* docImpl = part->xmlDocImpl();
00823 DOM::ElementMappingCache::ItemInfo* info = docImpl->underDocNamedCache().get(p.qstring());
00824 if (info) {
00825
00826
00827
00828 DOM::DOMString propertyDOMString = p.string();
00829 if (info->nd && DOM::HTMLMappedNameCollectionImpl::matchesName(info->nd,
00830 DOM::HTMLCollectionImpl::WINDOW_NAMED_ITEMS, propertyDOMString)) {
00831 return getDOMNode(exec, info->nd);
00832 } else {
00833
00834 DOM::HTMLMappedNameCollection coll(docImpl, DOM::HTMLCollectionImpl::WINDOW_NAMED_ITEMS, propertyDOMString);
00835
00836 if (coll.length() == 1)
00837 return getDOMNode(exec, coll.firstItem());
00838 else if (coll.length() > 1)
00839 return getHTMLCollection(exec, coll);
00840 }
00841 }
00842 DOM::Element element = part->document().getElementById(p.string());
00843 if ( !element.isNull() )
00844 return getDOMNode(exec, element );
00845 }
00846
00847
00848
00849 #ifdef KJS_VERBOSE
00850 kdDebug(6070) << "WARNING: Window::get property not found: " << p.qstring() << endl;
00851 #endif
00852 return Undefined();
00853 }
00854
00855 void Window::put(ExecState* exec, const Identifier &propertyName, const Value &value, int attr)
00856 {
00857
00858 if (m_frame.isNull() || m_frame->m_part.isNull()) {
00859
00860 return;
00861 }
00862
00863
00864
00865 if ( (attr != None && attr != DontDelete) ||
00866
00867 ( isSafeScript( exec ) && ObjectImp::getDirect(propertyName) ) )
00868 {
00869 ObjectImp::put( exec, propertyName, value, attr );
00870 return;
00871 }
00872
00873 const HashEntry* entry = Lookup::findEntry(&WindowTable, propertyName);
00874 if (entry && !m_frame.isNull() && !m_frame->m_part.isNull())
00875 {
00876 #ifdef KJS_VERBOSE
00877 kdDebug(6070) << "Window("<<this<<")::put " << propertyName.qstring() << endl;
00878 #endif
00879 switch( entry->value) {
00880 case _Location:
00881 goURL(exec, value.toString(exec).qstring(), false );
00882 return;
00883 default:
00884 break;
00885 }
00886 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
00887 if (part) {
00888 switch( entry->value ) {
00889 case Status: {
00890 if (isSafeScript(exec) && part->settings()->windowStatusPolicy(part->url().host())
00891 == KHTMLSettings::KJSWindowStatusAllow) {
00892 String s = value.toString(exec);
00893 part->setJSStatusBarText(s.value().qstring());
00894 }
00895 return;
00896 }
00897 case DefaultStatus: {
00898 if (isSafeScript(exec) && part->settings()->windowStatusPolicy(part->url().host())
00899 == KHTMLSettings::KJSWindowStatusAllow) {
00900 String s = value.toString(exec);
00901 part->setJSDefaultStatusBarText(s.value().qstring());
00902 }
00903 return;
00904 }
00905 case Onabort:
00906 if (isSafeScript(exec))
00907 setListener(exec, DOM::EventImpl::ABORT_EVENT,value);
00908 return;
00909 case Onblur:
00910 if (isSafeScript(exec))
00911 setListener(exec, DOM::EventImpl::BLUR_EVENT,value);
00912 return;
00913 case Onchange:
00914 if (isSafeScript(exec))
00915 setListener(exec, DOM::EventImpl::CHANGE_EVENT,value);
00916 return;
00917 case Onclick:
00918 if (isSafeScript(exec))
00919 setListener(exec,DOM::EventImpl::KHTML_ECMA_CLICK_EVENT,value);
00920 return;
00921 case Ondblclick:
00922 if (isSafeScript(exec))
00923 setListener(exec,DOM::EventImpl::KHTML_ECMA_DBLCLICK_EVENT,value);
00924 return;
00925 case Ondragdrop:
00926 if (isSafeScript(exec))
00927 setListener(exec,DOM::EventImpl::KHTML_DRAGDROP_EVENT,value);
00928 return;
00929 case Onerror:
00930 if (isSafeScript(exec))
00931 setListener(exec,DOM::EventImpl::ERROR_EVENT,value);
00932 return;
00933 case Onfocus:
00934 if (isSafeScript(exec))
00935 setListener(exec,DOM::EventImpl::FOCUS_EVENT,value);
00936 return;
00937 case Onkeydown:
00938 if (isSafeScript(exec))
00939 setListener(exec,DOM::EventImpl::KEYDOWN_EVENT,value);
00940 return;
00941 case Onkeypress:
00942 if (isSafeScript(exec))
00943 setListener(exec,DOM::EventImpl::KEYPRESS_EVENT,value);
00944 return;
00945 case Onkeyup:
00946 if (isSafeScript(exec))
00947 setListener(exec,DOM::EventImpl::KEYUP_EVENT,value);
00948 return;
00949 case Onload:
00950 if (isSafeScript(exec))
00951 setListener(exec,DOM::EventImpl::LOAD_EVENT,value);
00952 return;
00953 case Onmousedown:
00954 if (isSafeScript(exec))
00955 setListener(exec,DOM::EventImpl::MOUSEDOWN_EVENT,value);
00956 return;
00957 case Onmousemove:
00958 if (isSafeScript(exec))
00959 setListener(exec,DOM::EventImpl::MOUSEMOVE_EVENT,value);
00960 return;
00961 case Onmouseout:
00962 if (isSafeScript(exec))
00963 setListener(exec,DOM::EventImpl::MOUSEOUT_EVENT,value);
00964 return;
00965 case Onmouseover:
00966 if (isSafeScript(exec))
00967 setListener(exec,DOM::EventImpl::MOUSEOVER_EVENT,value);
00968 return;
00969 case Onmouseup:
00970 if (isSafeScript(exec))
00971 setListener(exec,DOM::EventImpl::MOUSEUP_EVENT,value);
00972 return;
00973 case Onmove:
00974 if (isSafeScript(exec))
00975 setListener(exec,DOM::EventImpl::KHTML_MOVE_EVENT,value);
00976 return;
00977 case Onreset:
00978 if (isSafeScript(exec))
00979 setListener(exec,DOM::EventImpl::RESET_EVENT,value);
00980 return;
00981 case Onresize:
00982 if (isSafeScript(exec))
00983 setListener(exec,DOM::EventImpl::RESIZE_EVENT,value);
00984 return;
00985 case Onselect:
00986 if (isSafeScript(exec))
00987 setListener(exec,DOM::EventImpl::SELECT_EVENT,value);
00988 return;
00989 case Onsubmit:
00990 if (isSafeScript(exec))
00991 setListener(exec,DOM::EventImpl::SUBMIT_EVENT,value);
00992 return;
00993 case Onunload:
00994 if (isSafeScript(exec))
00995 setListener(exec,DOM::EventImpl::UNLOAD_EVENT,value);
00996 return;
00997 case Name:
00998 if (isSafeScript(exec))
00999 part->setName( value.toString(exec).qstring().local8Bit().data() );
01000 return;
01001 default:
01002 break;
01003 }
01004 }
01005 }
01006 if (m_frame->m_liveconnect &&
01007 isSafeScript(exec) &&
01008 m_frame->m_liveconnect->put(0, propertyName.qstring(), value.toString(exec).qstring()))
01009 return;
01010 if (isSafeScript(exec)) {
01011
01012 ObjectImp::put(exec, propertyName, value, attr);
01013 }
01014 }
01015
01016 bool Window::toBoolean(ExecState *) const
01017 {
01018 return !m_frame.isNull() && !m_frame->m_part.isNull();
01019 }
01020
01021 DOM::AbstractView Window::toAbstractView() const
01022 {
01023 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01024 if (!part)
01025 return DOM::AbstractView();
01026 return part->document().defaultView();
01027 }
01028
01029 void Window::scheduleClose()
01030 {
01031 kdDebug(6070) << "Window::scheduleClose window.close() " << m_frame << endl;
01032 Q_ASSERT(winq);
01033 QTimer::singleShot( 0, winq, SLOT( timeoutClose() ) );
01034 }
01035
01036 void Window::closeNow()
01037 {
01038 if (m_frame.isNull() || m_frame->m_part.isNull()) {
01039 kdDebug(6070) << k_funcinfo << "part is deleted already" << endl;
01040 } else {
01041 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01042 if (!part) {
01043 kdDebug(6070) << "closeNow on non KHTML part" << endl;
01044 } else {
01045
01046
01047 part->setName( 0 );
01048 part->deleteLater();
01049 part = 0;
01050 }
01051 }
01052 }
01053
01054 void Window::afterScriptExecution()
01055 {
01056 DOM::DocumentImpl::updateDocumentsRendering();
01057 QValueList<DelayedAction> delayedActions = m_delayed;
01058 m_delayed.clear();
01059 QValueList<DelayedAction>::Iterator it = delayedActions.begin();
01060 for ( ; it != delayedActions.end() ; ++it )
01061 {
01062 switch ((*it).actionId) {
01063 case DelayedClose:
01064 scheduleClose();
01065 return;
01066 case DelayedGoHistory:
01067 goHistory( (*it).param.toInt() );
01068 break;
01069 case NullAction:
01070
01071 break;
01072 };
01073 }
01074 }
01075
01076 bool Window::checkIsSafeScript(KParts::ReadOnlyPart *activePart) const
01077 {
01078 if (m_frame.isNull() || m_frame->m_part.isNull()) {
01079 kdDebug(6070) << "Window::isSafeScript: accessing deleted part !" << endl;
01080 return false;
01081 }
01082 if (!activePart) {
01083 kdDebug(6070) << "Window::isSafeScript: current interpreter's part is 0L!" << endl;
01084 return false;
01085 }
01086 if ( activePart == m_frame->m_part )
01087 return true;
01088
01089 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01090 if (!part)
01091 return true;
01092
01093 if ( part->document().isNull() )
01094 return true;
01095
01096 DOM::HTMLDocument thisDocument = part->htmlDocument();
01097 if ( thisDocument.isNull() ) {
01098 kdDebug(6070) << "Window::isSafeScript: trying to access an XML document !?" << endl;
01099 return false;
01100 }
01101
01102 KHTMLPart *activeKHTMLPart = ::qt_cast<KHTMLPart *>(activePart);
01103 if (!activeKHTMLPart)
01104 return true;
01105
01106 DOM::HTMLDocument actDocument = activeKHTMLPart->htmlDocument();
01107 if ( actDocument.isNull() ) {
01108 kdDebug(6070) << "Window::isSafeScript: active part has no document!" << endl;
01109 return false;
01110 }
01111 DOM::DOMString actDomain = actDocument.domain();
01112 DOM::DOMString thisDomain = thisDocument.domain();
01113
01114 if ( actDomain == thisDomain ) {
01115 #ifdef KJS_VERBOSE
01116
01117 #endif
01118 return true;
01119 }
01120
01121 kdDebug(6070) << "WARNING: JavaScript: access denied for current frame '" << actDomain.string() << "' to frame '" << thisDomain.string() << "'" << endl;
01122
01123 return false;
01124 }
01125
01126 void Window::setListener(ExecState *exec, int eventId, Value func)
01127 {
01128 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01129 if (!part || !isSafeScript(exec))
01130 return;
01131 DOM::DocumentImpl *doc = static_cast<DOM::DocumentImpl*>(part->htmlDocument().handle());
01132 if (!doc)
01133 return;
01134
01135 doc->setHTMLWindowEventListener(eventId,getJSEventListener(func,true));
01136 }
01137
01138 Value Window::getListener(ExecState *exec, int eventId) const
01139 {
01140 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01141 if (!part || !isSafeScript(exec))
01142 return Undefined();
01143 DOM::DocumentImpl *doc = static_cast<DOM::DocumentImpl*>(part->htmlDocument().handle());
01144 if (!doc)
01145 return Undefined();
01146
01147 DOM::EventListener *listener = doc->getHTMLWindowEventListener(eventId);
01148 if (listener && static_cast<JSEventListener*>(listener)->listenerObjImp())
01149 return static_cast<JSEventListener*>(listener)->listenerObj();
01150 else
01151 return Null();
01152 }
01153
01154
01155 JSEventListener *Window::getJSEventListener(const Value& val, bool html)
01156 {
01157
01158 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01159 if (!part || val.type() != ObjectType)
01160 return 0;
01161
01162
01163 Object listenerObject = Object::dynamicCast(val);
01164 ObjectImp *listenerObjectImp = listenerObject.imp();
01165
01166
01167 if (!listenerObject.implementsCall() && part && part->jScript() && part->jScript()->interpreter())
01168 {
01169 Interpreter *interpreter = part->jScript()->interpreter();
01170
01171
01172 Value handleEventValue = listenerObject.get(interpreter->globalExec(), Identifier("handleEvent"));
01173 Object handleEventObject = Object::dynamicCast(handleEventValue);
01174
01175 if(handleEventObject.isValid() && handleEventObject.implementsCall())
01176 {
01177 listenerObject = handleEventObject;
01178 listenerObjectImp = handleEventObject.imp();
01179 }
01180 }
01181
01182 JSEventListener *existingListener = jsEventListeners[listenerObjectImp];
01183 if (existingListener) {
01184 if ( existingListener->isHTMLEventListener() != html )
01185
01186 kdWarning() << "getJSEventListener: event listener already found but with html=" << !html << " - please report this, we thought it would never happen" << endl;
01187 return existingListener;
01188 }
01189
01190
01191 return new JSEventListener(listenerObject, listenerObjectImp, Object(this), html);
01192 }
01193
01194 JSLazyEventListener *Window::getJSLazyEventListener(const QString& code, const QString& name, DOM::NodeImpl *node)
01195 {
01196 return new JSLazyEventListener(code, name, Object(this), node);
01197 }
01198
01199 void Window::clear( ExecState *exec )
01200 {
01201 delete winq;
01202 winq = 0L;
01203
01204 deleteAllProperties( exec );
01205
01206
01207 QPtrDictIterator<JSEventListener> it(jsEventListeners);
01208 for (; it.current(); ++it)
01209 it.current()->clear();
01210
01211 jsEventListeners.clear();
01212
01213 if (m_frame) {
01214 KJSProxy* proxy = m_frame->m_jscript;
01215 if (proxy)
01216 {
01217 winq = new WindowQObject(this);
01218
01219 KJS::Interpreter *interpreter = proxy->interpreter();
01220 interpreter->initGlobalObject();
01221 }
01222 }
01223 }
01224
01225 void Window::setCurrentEvent( DOM::Event *evt )
01226 {
01227 m_evt = evt;
01228
01229 }
01230
01231 void Window::goURL(ExecState* exec, const QString& url, bool lockHistory)
01232 {
01233 Window* active = Window::retrieveActive(exec);
01234 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01235 KHTMLPart *active_part = ::qt_cast<KHTMLPart *>(active->part());
01236
01237 if (active_part && part) {
01238 if (url[0] == QChar('#')) {
01239 part->gotoAnchor(url.mid(1));
01240 } else {
01241 QString dstUrl = active_part->htmlDocument().completeURL(url).string();
01242 kdDebug(6070) << "Window::goURL dstUrl=" << dstUrl << endl;
01243
01244
01245
01246 if ( isSafeScript(exec) ||
01247 dstUrl.find(QString::fromLatin1("javascript:"), 0, false) != 0 )
01248 part->scheduleRedirection(-1,
01249 dstUrl,
01250 lockHistory);
01251 }
01252 } else if (!part && !m_frame->m_part.isNull()) {
01253 KParts::BrowserExtension *b = KParts::BrowserExtension::childObject(m_frame->m_part);
01254 if (b)
01255 b->emit openURLRequest(m_frame->m_frame->element()->getDocument()->completeURL(url));
01256 kdDebug() << "goURL for ROPart" << endl;
01257 }
01258 }
01259
01260 KParts::ReadOnlyPart *Window::part() const {
01261 return m_frame.isNull() ? 0L : static_cast<KParts::ReadOnlyPart *>(m_frame->m_part);
01262 }
01263
01264 void Window::delayedGoHistory( int steps )
01265 {
01266 m_delayed.append( DelayedAction( DelayedGoHistory, steps ) );
01267 }
01268
01269 void Window::goHistory( int steps )
01270 {
01271 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01272 if(!part)
01273
01274 return;
01275 KParts::BrowserExtension *ext = part->browserExtension();
01276 if(!ext)
01277 return;
01278 KParts::BrowserInterface *iface = ext->browserInterface();
01279
01280 if ( !iface )
01281 return;
01282
01283 iface->callMethod( "goHistory(int)", steps );
01284
01285 }
01286
01287 void KJS::Window::resizeTo(QWidget* tl, int width, int height)
01288 {
01289 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01290 if(!part)
01291
01292 return;
01293 KParts::BrowserExtension *ext = part->browserExtension();
01294 if (!ext) {
01295 kdDebug(6070) << "Window::resizeTo found no browserExtension" << endl;
01296 return;
01297 }
01298
01299
01300 if ( width < 100 || height < 100 ) {
01301 kdDebug(6070) << "Window::resizeTo refused, window would be too small ("<<width<<","<<height<<")" << endl;
01302 return;
01303 }
01304
01305 QRect sg = KGlobalSettings::desktopGeometry(tl);
01306
01307 if ( width > sg.width() || height > sg.height() ) {
01308 kdDebug(6070) << "Window::resizeTo refused, window would be too big ("<<width<<","<<height<<")" << endl;
01309 return;
01310 }
01311
01312 kdDebug(6070) << "resizing to " << width << "x" << height << endl;
01313
01314 emit ext->resizeTopLevelWidget( width, height );
01315
01316
01317
01318 int right = tl->x() + tl->frameGeometry().width();
01319 int bottom = tl->y() + tl->frameGeometry().height();
01320 int moveByX = 0;
01321 int moveByY = 0;
01322 if ( right > sg.right() )
01323 moveByX = - right + sg.right();
01324 if ( bottom > sg.bottom() )
01325 moveByY = - bottom + sg.bottom();
01326 if ( moveByX || moveByY )
01327 emit ext->moveTopLevelWidget( tl->x() + moveByX , tl->y() + moveByY );
01328 }
01329
01330 Value Window::openWindow(ExecState *exec, const List& args)
01331 {
01332 KHTMLPart *part = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01333 if (!part)
01334 return Undefined();
01335 KHTMLView *widget = part->view();
01336 Value v = args[0];
01337 QString str = v.toString(exec).qstring();
01338
01339
01340 KURL url;
01341 if (!str.isEmpty())
01342 {
01343 KHTMLPart* p = ::qt_cast<KHTMLPart *>(Window::retrieveActive(exec)->m_frame->m_part);
01344 if ( p )
01345 url = p->htmlDocument().completeURL(str).string();
01346 if ( !p ||
01347 !static_cast<DOM::DocumentImpl*>(p->htmlDocument().handle())->isURLAllowed(url.url()) )
01348 return Undefined();
01349 }
01350
01351 KHTMLSettings::KJSWindowOpenPolicy policy =
01352 part->settings()->windowOpenPolicy(part->url().host());
01353 if ( policy == KHTMLSettings::KJSWindowOpenAsk ) {
01354 emit part->browserExtension()->requestFocus(part);
01355 QString caption;
01356 if (!part->url().host().isEmpty())
01357 caption = part->url().host() + " - ";
01358 caption += i18n( "Confirmation: JavaScript Popup" );
01359 if ( KMessageBox::questionYesNo(widget,
01360 str.isEmpty() ?
01361 i18n( "This site is requesting to open up a new browser "
01362 "window via JavaScript.\n"
01363 "Do you want to allow this?" ) :
01364 i18n( "<qt>This site is requesting to open<p>%1</p>in a new browser window via JavaScript.<br />"
01365 "Do you want to allow this?</qt>").arg(KStringHandler::csqueeze(url.htmlURL(), 100)),
01366 caption, i18n("Allow"), i18n("Do Not Allow") ) == KMessageBox::Yes )
01367 policy = KHTMLSettings::KJSWindowOpenAllow;
01368 } else if ( policy == KHTMLSettings::KJSWindowOpenSmart )
01369 {
01370
01371 if (static_cast<ScriptInterpreter *>(exec->interpreter())->isWindowOpenAllowed())
01372 policy = KHTMLSettings::KJSWindowOpenAllow;
01373 }
01374
01375 QString frameName = args.size() > 1 ? args[1].toString(exec).qstring() : QString("_blank");
01376
01377 v = args[2];
01378 QString features;
01379 if (!v.isNull() && v.type() != UndefinedType && v.toString(exec).size() > 0) {
01380 features = v.toString(exec).qstring();
01381
01382 if (features.startsWith("\'") && features.endsWith("\'"))
01383 features = features.mid(1, features.length()-2);
01384 }
01385
01386 if ( policy != KHTMLSettings::KJSWindowOpenAllow ) {
01387 if ( url.isEmpty() )
01388 part->setSuppressedPopupIndicator(true, 0);
01389 else {
01390 part->setSuppressedPopupIndicator(true, part);
01391 m_suppressedWindowInfo.append( SuppressedWindowInfo( url, frameName, features ) );
01392 }
01393 return Undefined();
01394 } else {
01395 return executeOpenWindow(exec, url, frameName, features);
01396 }
01397 }
01398
01399 Value Window::executeOpenWindow(ExecState *exec, const KURL& url, const QString& frameName, const QString& features)
01400 {
01401 KHTMLPart *p = ::qt_cast<KHTMLPart *>(m_frame->m_part);
01402 KHTMLView *widget = p->view();
01403 KParts::WindowArgs winargs;
01404
01405
01406 if (!features.isEmpty()) {
01407
01408 winargs.menuBarVisible = false;
01409 winargs.toolBarsVisible = false;
01410 winargs.statusBarVisible = false;
01411 winargs.scrollBarsVisible = false;
01412 QStringList flist = QStringList::split(',', features);
01413 QStringList::ConstIterator it = flist.begin();
01414 while (it != flist.end()) {
01415 QString s = *it++;
01416 QString key, val;
01417 int pos = s.find('=');
01418 if (pos >= 0) {
01419 key = s.left(pos).stripWhiteSpace().lower();
01420 val = s.mid(pos + 1).stripWhiteSpace().lower();
01421 QRect screen = KGlobalSettings::desktopGeometry(widget->topLevelWidget());
01422
01423 if (key == "left" || key == "screenx") {
01424 winargs.x = (int)val.toFloat() + screen.x();
01425 if (winargs.x < screen.x() || winargs.x > screen.right())
01426 winargs.x = screen.x();
01427 } else if (key == "top" || key == "screeny") {
01428 winargs.y = (int)val.toFloat() + screen.y();
01429 if (winargs.y < screen.y() || winargs.y > screen.bottom())
01430 winargs.y = screen.y();
01431 } else if (key == "height") {
01432 winargs.height = (int)val.toFloat() + 2*qApp->style().pixelMetric( QStyle::PM_DefaultFrameWidth ) + 2;
01433 if (winargs.height > screen.height())
01434 winargs.height = screen.height();
01435 if (winargs.height < 100)
01436 winargs.height = 100;
01437 } else if (key == "width") {
01438 winargs.width = (int)val.toFloat() + 2*qApp->style().pixelMetric( QStyle::PM_DefaultFrameWidth ) + 2;
01439 if (winargs.width > screen.width())
01440 winargs.width = screen.width();
01441 if (winargs.width < 100)
01442 winargs.width = 100;
01443 } else {
01444 goto boolargs;
01445 }
01446 continue;
01447 } else {
01448
01449 key = s.stripWhiteSpace().lower();
01450 val = "1";
01451 }
01452 boolargs:
01453 if (key == "menubar")
01454 winargs.menuBarVisible = (val == "1" || val == "yes");
01455 else if (key == "toolbar")
01456 winargs.toolBarsVisible = (val == "1" || val == "yes");
01457 else if (key == "location")
01458 winargs.toolBarsVisible = (val == "1" || val == "yes");
01459 else if (key == "status" || key == "statusbar")
01460 winargs.statusBarVisible = (val == "1" || val == "yes");
01461 else if (key == "scrollbars")
01462 winargs.scrollBarsVisible = (val == "1" || val == "yes");
01463 else if (key == "resizable")
01464 winargs.resizable = (val == "1" || val == "yes");
01465 else if (key == "fullscreen")
01466 winargs.fullscreen = (val == "1" || val == "yes");
01467 }
01468 }
01469
01470 KParts::URLArgs uargs;
01471 uargs.frameName = frameName;
01472
01473 if ( uargs.frameName.lower() == "_top" )
01474 {
01475 while ( p->parentPart() )
01476 p = p->parentPart();
01477 Window::retrieveWindow(p)->goURL(exec, url.url(), false );
01478 return Window::retrieve(p);
01479 }
01480 if ( uargs.frameName.lower() == "_parent" )
01481 {
01482 if ( p->parentPart() )
01483 p = p->parentPart();
01484 Window::retrieveWindow(p)->goURL(exec, url.url(), false );
01485 return Window::retrieve(p);
01486 }
01487 if ( uargs.frameName.lower() == "_self")
01488 {
01489 Window::retrieveWindow(p)->goURL(exec, url.url(), false );
01490 return Window::retrieve(p);
01491 }
01492 if ( uargs.frameName.lower() == "replace" )
01493 {
01494 Window::retrieveWindow(p)->goURL(exec, url.url(), true );
01495 return Window::retrieve(p);
01496 }
01497 uargs.serviceType = "text/html";
01498
01499
01500 KParts::ReadOnlyPart *newPart = 0L;
01501 emit p->browserExtension()->createNewWindow(KURL(), uargs,winargs,newPart);
01502 if (newPart && ::qt_cast<KHTMLPart*>(newPart)) {
01503 KHTMLPart *khtmlpart = static_cast<KHTMLPart*>(newPart);
01504
01505 khtmlpart->setOpener(p);
01506 khtmlpart->setOpenedByJS(true);
01507 if (khtmlpart->document().isNull()) {
01508 khtmlpart->begin();
01509 khtmlpart->write("<HTML><BODY>");
01510 khtmlpart->end();
01511 if ( p->docImpl() ) {
01512
01513 khtmlpart->docImpl()->setDomain( p->docImpl()->domain());
01514 khtmlpart->docImpl()->setBaseURL( p->docImpl()->baseURL() );
01515 }
01516 }
01517 uargs.serviceType = QString::null;
01518 if (uargs.frameName.lower() == "_blank")
01519 uargs.frameName = QString::null;
01520 if (!url.isEmpty())
01521 emit khtmlpart->browserExtension()->openURLRequest(url,uargs);
01522 return Window::retrieve(khtmlpart);
01523 } else
01524 return Undefined();
01525 }
01526
01527 void Window::forgetSuppressedWindows()
01528 {
01529 m_suppressedWindowInfo.clear();
01530 }
01531
01532 void Window::showSuppressedWindows()
01533 {
01534 KHTMLPart *part = ::qt_cast<KHTMLPart *>( m_frame->m_part );
01535 KJS::Interpreter *interpreter = part->jScript()->interpreter();
01536 ExecState *exec = interpreter->globalExec();
01537
01538 QValueList<SuppressedWindowInfo> suppressedWindowInfo = m_suppressedWindowInfo;
01539 m_suppressedWindowInfo.clear();
01540 QValueList<SuppressedWindowInfo>::Iterator it = suppressedWindowInfo.begin();
01541 for ( ; it != suppressedWindowInfo.end() ; ++it ) {
01542 executeOpenWindow(exec, (*it).url, (*it).frameName, (*it).features);
01543 }
01544 }
01545
01546 Value WindowFunc::tryCall(ExecState *exec, Object &thisObj, const List &args)
01547 {
01548 KJS_CHECK_THIS( Window, thisObj );
01549 Window *window = static_cast<Window *>(thisObj.imp());
01550 QString str, str2;
01551
01552 KHTMLPart *part = ::qt_cast<KHTMLPart *>(window->m_frame->m_part);
01553 if (!part)
01554 return Undefined();
01555
01556 KHTMLView *widget = part->view();
01557 Value v = args[0];
01558 UString s = v.toString(exec);
01559 str = s.qstring();
01560
01561 QString caption;
01562 if (part && !part->url().host().isEmpty())
01563 caption = part->url().host() + " - ";
01564 caption += "JavaScript";
01565
01566 switch(id) {
01567 case Window::Alert:
01568 if (!widget->dialogsAllowed())
01569 return Undefined();
01570 if ( part && part->xmlDocImpl() )
01571 part->xmlDocImpl()->updateRendering();
01572 if ( part )
01573 emit part->browserExtension()->requestFocus(part);
01574 KMessageBox::error(widget, QStyleSheet::convertFromPlainText(str), caption);
01575 return Undefined();
01576 case Window::Confirm:
01577 if (!widget->dialogsAllowed())
01578 return Undefined();
01579 if ( part && part->xmlDocImpl() )
01580 part->xmlDocImpl()->updateRendering();
01581 if ( part )
01582 emit part->browserExtension()->requestFocus(part);
01583 return Boolean((KMessageBox::warningYesNo(widget, QStyleSheet::convertFromPlainText(str), caption,
01584 KStdGuiItem::ok(), KStdGuiItem::cancel()) == KMessageBox::Yes));
01585 case Window::Prompt:
01586 #ifndef KONQ_EMBEDDED
01587 if (!widget->dialogsAllowed())
01588 return Undefined();
01589 if ( part && part->xmlDocImpl() )
01590 part->xmlDocImpl()->updateRendering();
01591 if ( part )
01592 emit part->browserExtension()->requestFocus(part);
01593 bool ok;
01594 if (args.size() >= 2)
01595 str2 = KInputDialog::getText(caption,
01596 QStyleSheet::convertFromPlainText(str),
01597 args[1].toString(exec).qstring(), &ok, widget);
01598 else
01599 str2 = KInputDialog::getText(caption,
01600 QStyleSheet::convertFromPlainText(str),
01601 QString::null, &ok, widget);
01602 if ( ok )
01603 return String(str2);
01604 else
01605 return Null();
01606 #else
01607 return Undefined();
01608 #endif
01609 case Window::GetComputedStyle: {
01610 if ( !part || !part->xmlDocImpl() )
01611 return Undefined();
01612 DOM::Node arg0 = toNode(args[0]);
01613 if (arg0.nodeType() != DOM::Node::ELEMENT_NODE)
01614 return Undefined();
01615 else
01616 return getDOMCSSStyleDeclaration(exec, part->document().defaultView().getComputedStyle(static_cast<DOM::Element>(arg0),
01617 args[1].toString(exec).string()));
01618 }
01619 case Window::Open:
01620 return window->openWindow(exec, args);
01621 case Window::Close: {
01622
01623
01624
01625
01626
01627
01628
01629
01630
01631
01632 bool doClose = false;
01633 if (!part->openedByJS())
01634 {
01635
01636
01637 History history(exec,part);
01638
01639 if ( history.get( exec, "length" ).toInt32(exec) <= 1 )
01640 {
01641 doClose = true;
01642 }
01643 else
01644 {
01645
01646 emit part->browserExtension()->requestFocus(part);
01647 if ( KMessageBox::questionYesNo( window->part()->widget(),
01648 i18n("Close window?"), i18n("Confirmation Required"),
01649 KStdGuiItem::close(), KStdGuiItem::cancel() )
01650 == KMessageBox::Yes )
01651 doClose = true;
01652 }
01653 }
01654 else
01655 doClose = true;
01656
01657 if (doClose)
01658 {
01659
01660
01661
01662 if ( Window::retrieveActive(exec) == window ) {
01663 if (widget) {
01664
01665
01666 widget->closeChildDialogs();
01667 }
01668
01669
01670 Window* w = const_cast<Window*>(window);
01671 w->m_delayed.append( Window::DelayedAction( Window::DelayedClose ) );
01672 } else {
01673
01674 (const_cast<Window*>(window))->closeNow();
01675 }
01676 }
01677 return Undefined();
01678 }
01679 case Window::Navigate:
01680 window->goURL(exec, args[0].toString(exec).qstring(), false );
01681 return Undefined();
01682 case Window::Focus: {
01683 KHTMLSettings::KJSWindowFocusPolicy policy =
01684 part->settings()->windowFocusPolicy(part->url().host());
01685 if(policy == KHTMLSettings::KJSWindowFocusAllow && widget) {
01686 widget->topLevelWidget()->raise();
01687 KWin::deIconifyWindow( widget->topLevelWidget()->winId() );
01688 widget->setActiveWindow();
01689 emit part->browserExtension()->requestFocus(part);
01690 }
01691 return Undefined();
01692 }
01693 case Window::Blur:
01694
01695 return Undefined();
01696 case Window::BToA:
01697 case Window::AToB: {
01698 if (!s.is8Bit())
01699 return Undefined();
01700 QByteArray in, out;
01701 char *binData = s.ascii();
01702 in.setRawData( binData, s.size() );
01703 if (id == Window::AToB)
01704 KCodecs::base64Decode( in, out );
01705 else
01706 KCodecs::base64Encode( in, out );
01707 in.resetRawData( binData, s.size() );
01708 UChar *d = new UChar[out.size()];
01709 for (uint i = 0; i < out.size(); i++)
01710 d[i].uc = (uchar) out[i];
01711 UString ret(d, out.size(), false );
01712 return String(ret);
01713 }
01714
01715 };
01716
01717
01718
01719 if (!window->isSafeScript(exec))
01720 return Undefined();
01721
01722 switch (id) {
01723 case Window::ScrollBy:
01724 if(args.size() == 2 && widget)
01725 widget->scrollBy(args[0].toInt32(exec), args[1].toInt32(exec));
01726 return Undefined();
01727 case Window::Scroll:
01728 case Window::ScrollTo:
01729 if(args.size() == 2 && widget)
01730 widget->setContentsPos(args[0].toInt32(exec), args[1].toInt32(exec));
01731 return Undefined();
01732 case Window::MoveBy: {
01733 KHTMLSettings::KJSWindowMovePolicy policy =
01734 part->settings()->windowMovePolicy(part->url().host());
01735 if(policy == KHTMLSettings::KJSWindowMoveAllow && args.size() == 2 && widget)
01736 {
01737 KParts::BrowserExtension *ext = part->browserExtension();
01738 if (ext) {
01739 QWidget * tl = widget->topLevelWidget();
01740 QRect sg = KGlobalSettings::desktopGeometry(tl);
01741
01742 QPoint dest = tl->pos() + QPoint( args[0].toInt32(exec), args[1].toInt32(exec) );
01743
01744 if ( dest.x() >= sg.x() && dest.y() >= sg.x() &&
01745 dest.x()+tl->width() <= sg.width()+sg.x() &&
01746 dest.y()+tl->height() <= sg.height()+sg.y() )
01747 emit ext->moveTopLevelWidget( dest.x(), dest.y() );
01748 }
01749 }
01750 return Undefined();
01751 }
01752 case Window::MoveTo: {
01753 KHTMLSettings::KJSWindowMovePolicy policy =
01754 part->settings()->windowMovePolicy(part->url().host());
01755 if(policy == KHTMLSettings::KJSWindowMoveAllow && args.size() == 2 && widget)
01756 {
01757 KParts::BrowserExtension *ext = part->browserExtension();
01758 if (ext) {
01759 QWidget * tl = widget->topLevelWidget();
01760 QRect sg = KGlobalSettings::desktopGeometry(tl);
01761
01762 QPoint dest( args[0].toInt32(exec)+sg.x(), args[1].toInt32(exec)+sg.y() );
01763
01764 if ( dest.x() >= sg.x() && dest.y() >= sg.y() &&
01765 dest.x()+tl->width() <= sg.width()+sg.x() &&
01766 dest.y()+tl->height() <= sg.height()+sg.y() )
01767 emit ext->moveTopLevelWidget( dest.x(), dest.y() );
01768 }
01769 }
01770 return Undefined();
01771 }
01772 case Window::ResizeBy: {
01773 KHTMLSettings::KJSWindowResizePolicy policy =
01774 part->settings()->windowResizePolicy(part->url().host());
01775 if(policy == KHTMLSettings::KJSWindowResizeAllow
01776 && args.size() == 2 && widget)
01777 {
01778 QWidget * tl = widget->topLevelWidget();
01779 QRect geom = tl->frameGeometry();
01780 window->resizeTo( tl,
01781 geom.width() + args[0].toInt32(exec),
01782 geom.height() + args[1].toInt32(exec) );
01783 }
01784 return Undefined();
01785 }
01786 case Window::ResizeTo: {
01787 KHTMLSettings::KJSWindowResizePolicy policy =
01788 part->settings()->windowResizePolicy(part->url().host());
01789 if(policy == KHTMLSettings::KJSWindowResizeAllow
01790 && args.size() == 2 && widget)
01791 {
01792 QWidget * tl = widget->topLevelWidget();
01793 window->resizeTo( tl, args[0].toInt32(exec), args[1].toInt32(exec) );
01794 }
01795 return Undefined();
01796 }
01797 case Window::SetTimeout:
01798 case Window::SetInterval: {
01799 bool singleShot;
01800 int i;
01801 if (args.size() == 0)
01802 return Undefined();
01803 if (args.size() > 1) {
01804 singleShot = (id == Window::SetTimeout);
01805 i = args[1].toInt32(exec);
01806 } else {
01807
01808 singleShot = true;
01809 i = 4;
01810 }
01811 if (v.isA(StringType)) {
01812 int r = (const_cast<Window*>(window))->winq->installTimeout(Identifier(s), i, singleShot );
01813 return Number(r);
01814 }
01815 else if (v.isA(ObjectType) && Object::dynamicCast(v).implementsCall()) {
01816 Object func = Object::dynamicCast(v);
01817 List funcArgs;
01818 ListIterator it = args.begin();
01819 int argno = 0;
01820 while (it != args.end()) {
01821 Value arg = it++;
01822 if (argno++ >= 2)
01823 funcArgs.append(arg);
01824 }
01825 if (args.size() < 2)
01826 funcArgs.append(Number(i));
01827 int r = (const_cast<Window*>(window))->winq->installTimeout(func, funcArgs, i, singleShot );
01828 return Number(r);
01829 }
01830 else
01831 return Undefined();
01832 }
01833 case Window::ClearTimeout:
01834 case Window::ClearInterval:
01835 (const_cast<Window*>(window))->winq->clearTimeout(v.toInt32(exec));
01836 return Undefined();
01837 case Window::Print:
01838 if ( widget ) {
01839
01840 widget->print();
01841
01842 }
01843 case Window::CaptureEvents:
01844 case Window::ReleaseEvents:
01845
01846 break;
01847 case Window::AddEventListener: {
01848 JSEventListener *listener = Window::retrieveActive(exec)->getJSEventListener(args[1]);
01849 if (listener) {
01850 DOM::DocumentImpl* docimpl = static_cast<DOM::DocumentImpl *>(part->document().handle());
01851 docimpl->addWindowEventListener(DOM::EventImpl::typeToId(args[0].toString(exec).string()),listener,args[2].toBoolean(exec));
01852 }
01853 return Undefined();
01854 }
01855 case Window::RemoveEventListener: {
01856 JSEventListener *listener = Window::retrieveActive(exec)->getJSEventListener(args[1]);
01857 if (listener) {
01858 DOM::DocumentImpl* docimpl = static_cast<DOM::DocumentImpl *>(part->document().handle());
01859 docimpl->removeWindowEventListener(DOM::EventImpl::typeToId(args[0].toString(exec).string()),listener,args[2].toBoolean(exec));
01860 }
01861 return Undefined();
01862 }
01863
01864 }
01865 return Undefined();
01866 }
01867
01869
01870
01871 ScheduledAction::ScheduledAction(Object _func, List _args, DateTimeMS _nextTime, int _interval, bool _singleShot,
01872 int _timerId)
01873 {
01874
01875 func = static_cast<ObjectImp*>(_func.imp());
01876 args = _args;
01877 isFunction = true;
01878 singleShot = _singleShot;
01879 nextTime = _nextTime;
01880 interval = _interval;
01881 executing = false;
01882 timerId = _timerId;
01883 }
01884
01885
01886 ScheduledAction::ScheduledAction(QString _code, DateTimeMS _nextTime, int _interval, bool _singleShot, int _timerId)
01887 {
01888
01889
01890
01891 func = 0;
01892 code = _code;
01893 isFunction = false;
01894 singleShot = _singleShot;
01895 nextTime = _nextTime;
01896 interval = _interval;
01897 executing = false;
01898 timerId = _timerId;
01899 }
01900
01901 bool ScheduledAction::execute(Window *window)
01902 {
01903 KHTMLPart *part = ::qt_cast<KHTMLPart *>(window->m_frame->m_part);
01904 if (!part || !part->jScriptEnabled())
01905 return false;
01906 ScriptInterpreter *interpreter = static_cast<ScriptInterpreter *>(part->jScript()->interpreter());
01907
01908 interpreter->setProcessingTimerCallback(true);
01909
01910
01911 if (isFunction) {
01912 if (func->implementsCall()) {
01913
01914 Q_ASSERT( part );
01915 if ( part )
01916 {
01917 KJS::Interpreter *interpreter = part->jScript()->interpreter();
01918 ExecState *exec = interpreter->globalExec();
01919 Q_ASSERT( window == interpreter->globalObject().imp() );
01920 Object obj( window );
01921 func->call(exec,obj,args);
01922 if (exec->hadException())
01923 exec->clearException();
01924
01925
01926 part->document().updateRendering();
01927 }
01928 }
01929 }
01930 else {
01931 part->executeScript(DOM::Node(), code);
01932 }
01933
01934 interpreter->setProcessingTimerCallback(false);
01935 return true;
01936 }
01937
01938 void ScheduledAction::mark()
01939 {
01940 if (func && !func->marked())
01941 func->mark();
01942 args.mark();
01943 }
01944
01945 ScheduledAction::~ScheduledAction()
01946 {
01947
01948 }
01949
01951
01952 WindowQObject::WindowQObject(Window *w)
01953 : parent(w)
01954 {
01955
01956 if ( !parent->m_frame )
01957 kdDebug(6070) << "WARNING: null part in " << k_funcinfo << endl;
01958 else
01959 connect( parent->m_frame, SIGNAL( destroyed() ),
01960 this, SLOT( parentDestroyed() ) );
01961 pausedTime = 0;
01962 lastTimerId = 0;
01963 currentlyDispatching = false;
01964 }
01965
01966 WindowQObject::~WindowQObject()
01967 {
01968
01969 parentDestroyed();
01970 }
01971
01972 void WindowQObject::parentDestroyed()
01973 {
01974 killTimers();
01975
01976 QPtrListIterator<ScheduledAction> it(scheduledActions);
01977 for (; it.current(); ++it)
01978 delete it.current();
01979 scheduledActions.clear();
01980 }
01981
01982 int WindowQObject::installTimeout(const Identifier &handler, int t, bool singleShot)
01983 {
01984 int id = ++lastTimerId;
01985 if (t < 10) t = 10;
01986 DateTimeMS nextTime = DateTimeMS::now().addMSecs(-pausedTime + t);
01987
01988 ScheduledAction *action = new ScheduledAction(handler.qstring(),nextTime,t,singleShot,id);
01989 scheduledActions.append(action);
01990 setNextTimer();
01991 return id;
01992 }
01993
01994 int WindowQObject::installTimeout(const Value &func, List args, int t, bool singleShot)
01995 {
01996 Object objFunc = Object::dynamicCast( func );
01997 if (!objFunc.isValid())
01998 return 0;
01999 int id = ++lastTimerId;
02000 if (t < 10) t = 10;
02001
02002 DateTimeMS nextTime = DateTimeMS::now().addMSecs(-pausedTime + t);
02003 ScheduledAction *action = new ScheduledAction(objFunc,args,nextTime,t,singleShot,id);
02004 scheduledActions.append(action);
02005 setNextTimer();
02006 return id;
02007 }
02008
02009 void WindowQObject::clearTimeout(int timerId)
02010 {
02011 QPtrListIterator<ScheduledAction> it(scheduledActions);
02012 for (; it.current(); ++it) {
02013 ScheduledAction *action = it.current();
02014 if (action->timerId == timerId) {
02015 scheduledActions.removeRef(action);
02016 if (!action->executing)
02017 delete action;
02018 return;
02019 }
02020 }
02021 }
02022
02023 bool WindowQObject::hasTimers() const
02024 {
02025 return scheduledActions.count();
02026 }
02027
02028 void WindowQObject::mark()
02029 {
02030 QPtrListIterator<ScheduledAction> it(scheduledActions);
02031 for (; it.current(); ++it)
02032 it.current()->mark();
02033 }
02034
02035 void WindowQObject::timerEvent(QTimerEvent *)
02036 {
02037 killTimers();
02038
02039 if (scheduledActions.isEmpty())
02040 return;
02041
02042 currentlyDispatching = true;
02043
02044
02045 DateTimeMS currentActual = DateTimeMS::now();
02046 DateTimeMS currentAdjusted = currentActual.addMSecs(-pausedTime);
02047
02048
02049
02050 QPtrList<ScheduledAction> toExecute;
02051 QPtrListIterator<ScheduledAction> it(scheduledActions);
02052 for (; it.current(); ++it)
02053 if (currentAdjusted >= it.current()->nextTime)
02054 toExecute.append(it.current());
02055
02056
02057 it = QPtrListIterator<ScheduledAction>(toExecute);
02058 for (; it.current(); ++it) {
02059 ScheduledAction *action = it.current();
02060 if (!scheduledActions.containsRef(action))
02061 continue;
02062
02063 action->executing = true;
02064
02065 if (parent->part()) {
02066 bool ok = action->execute(parent);
02067 if ( !ok )
02068 scheduledActions.removeRef( action );
02069 }
02070
02071 if (action->singleShot) {
02072 scheduledActions.removeRef(action);
02073 }
02074
02075 action->executing = false;
02076
02077 if (!scheduledActions.containsRef(action))
02078 delete action;
02079 else
02080 action->nextTime = action->nextTime.addMSecs(action->interval);
02081 }
02082
02083 pausedTime += currentActual.msecsTo(DateTimeMS::now());
02084
02085 currentlyDispatching = false;
02086
02087
02088 setNextTimer();
02089 }
02090
02091 DateTimeMS DateTimeMS::addMSecs(int s) const
02092 {
02093 DateTimeMS c = *this;
02094 c.mTime = mTime.addMSecs(s);
02095 if (s > 0)
02096 {
02097 if (c.mTime < mTime)
02098 c.mDate = mDate.addDays(1);
02099 }
02100 else
02101 {
02102 if (c.mTime > mTime)
02103 c.mDate = mDate.addDays(-1);
02104 }
02105 return c;
02106 }
02107
02108 bool DateTimeMS::operator >(const DateTimeMS &other) const
02109 {
02110 if (mDate > other.mDate)
02111 return true;
02112
02113 if (mDate < other.mDate)
02114 return false;
02115
02116 return mTime > other.mTime;
02117 }
02118
02119 bool DateTimeMS::operator >=(const DateTimeMS &other) const
02120 {
02121 if (mDate > other.mDate)
02122 return true;
02123
02124 if (mDate < other.mDate)
02125 return false;
02126
02127 return mTime >= other.mTime;
02128 }
02129
02130 int DateTimeMS::msecsTo(const DateTimeMS &other) const
02131 {
02132 int d = mDate.daysTo(other.mDate);
02133 int ms = mTime.msecsTo(other.mTime);
02134 return d*24*60*60*1000 + ms;
02135 }
02136
02137
02138 DateTimeMS DateTimeMS::now()
02139 {
02140 DateTimeMS t;
02141 QTime before = QTime::currentTime();
02142 t.mDate = QDate::currentDate();
02143 t.mTime = QTime::currentTime();
02144 if (t.mTime < before)
02145 t.mDate = QDate::currentDate();
02146 return t;
02147 }
02148
02149 void WindowQObject::setNextTimer()
02150 {
02151 if (currentlyDispatching)
02152 return;
02153
02154 if (scheduledActions.isEmpty())
02155 return;
02156
02157 QPtrListIterator<ScheduledAction> it(scheduledActions);
02158 DateTimeMS nextTime = it.current()->nextTime;
02159 for (++it; it.current(); ++it)
02160 if (nextTime > it.current()->nextTime)
02161 nextTime = it.current()->nextTime;
02162
02163 DateTimeMS nextTimeActual = nextTime.addMSecs(pausedTime);
02164 int nextInterval = DateTimeMS::now().msecsTo(nextTimeActual);
02165 if (nextInterval < 0)
02166 nextInterval = 0;
02167 startTimer(nextInterval);
02168 }
02169
02170 void WindowQObject::timeoutClose()
02171 {
02172 parent->closeNow();
02173 }
02174
02175 Value FrameArray::get(ExecState *exec, const Identifier &p) const
02176 {
02177 #ifdef KJS_VERBOSE
02178 kdDebug(6070) << "FrameArray::get " << p.qstring() << " part=" << (void*)part << endl;
02179 #endif
02180 if (part.isNull())
02181 return Undefined();
02182
02183 QPtrList<KParts::ReadOnlyPart> frames = part->frames();
02184 unsigned int len = frames.count();
02185 if (p == lengthPropertyName)
02186 return Number(len);
02187 else if (p== "location")
02188 {
02189 Object obj = Object::dynamicCast( Window::retrieve( part ) );
02190 if ( obj.isValid() )
02191 return obj.get( exec, "location" );
02192 return Undefined();
02193 }
02194
02195
02196 KParts::ReadOnlyPart *frame = part->findFramePart(p.qstring());
02197 if (!frame) {
02198 bool ok;
02199 unsigned int i = p.toArrayIndex(&ok);
02200 if (ok && i < len)
02201 frame = frames.at(i);
02202 }
02203
02204
02205
02206
02207 if (frame) {
02208 return Window::retrieve(frame);
02209 }
02210
02211
02212
02213
02214 DOM::DocumentImpl* doc = static_cast<DOM::DocumentImpl*>(part->document().handle());
02215 DOM::HTMLCollectionImpl docuAll(doc, DOM::HTMLCollectionImpl::DOC_ALL);
02216 DOM::NodeImpl* node = docuAll.namedItem(p.string());
02217 if (node) {
02218 if (node->id() == ID_FRAME || node->id() == ID_IFRAME) {
02219
02220 KHTMLPart* part = static_cast<DOM::HTMLFrameElementImpl*>(node)->contentPart();
02221 if (part)
02222 return Value(Window::retrieveWindow(part));
02223 else
02224 return Undefined();
02225 } else {
02226
02227 return getDOMNode(exec, node);
02228 }
02229 }
02230
02231 return ObjectImp::get(exec, p);
02232 }
02233
02235
02236 const ClassInfo Location::info = { "Location", 0, &LocationTable, 0 };
02237
02238
02239
02240
02241
02242
02243
02244
02245
02246
02247
02248
02249
02250
02251
02252
02253
02254 IMPLEMENT_PROTOFUNC_DOM(LocationFunc)
02255 Location::Location(khtml::ChildFrame *f) : m_frame(f)
02256 {
02257
02258 }
02259
02260 Location::~Location()
02261 {
02262
02263 }
02264
02265 KParts::ReadOnlyPart *Location::part() const {
02266 return m_frame ? static_cast<KParts::ReadOnlyPart *>(m_frame->m_part) : 0L;
02267 }
02268
02269 Value Location::get(ExecState *exec, const Identifier &p) const
02270 {
02271 #ifdef KJS_VERBOSE
02272 kdDebug(6070) << "Location::get " << p.qstring() << " m_part=" << (void*)m_frame->m_part << endl;
02273 #endif
02274
02275 if (m_frame.isNull() || m_frame->m_part.isNull())
02276 return Undefined();
02277
02278 const HashEntry *entry = Lookup::findEntry(&LocationTable, p);
02279
02280
02281 if ( entry && entry->value == Replace )
02282 return lookupOrCreateFunction<LocationFunc>(exec,p,this,entry->value,entry->params,entry->attr);
02283
02284
02285 const Window* window = Window::retrieveWindow( m_frame->m_part );
02286 if ( !window || !window->isSafeScript(exec) )
02287 return Undefined();
02288
02289 KURL url = m_frame->m_part->url();
02290 if (entry)
02291 switch (entry->value) {
02292 case Hash:
02293 return String( url.ref().isNull() ? QString("") : "#" + url.ref() );
02294 case Host: {
02295 UString str = url.host();
02296 if (url.port())
02297 str += ":" + QString::number((int)url.port());
02298 return String(str);
02299
02300
02301
02302 }
02303 case Hostname:
02304 return String( url.host() );
02305 case Href:
02306 if (!url.hasPath())
02307 return String( url.prettyURL()+"/" );
02308 else
02309 return String( url.prettyURL() );
02310 case Pathname:
02311 return String( url.path().isEmpty() ? QString("/") : url.path() );
02312 case Port:
02313 return String( url.port() ? QString::number((int)url.port()) : QString::fromLatin1("") );
02314 case Protocol:
02315 return String( url.protocol()+":" );
02316 case Search:
02317 return String( url.query() );
02318 case EqualEqual:
02319 return String(toString(exec));
02320 case ToString:
02321 return lookupOrCreateFunction<LocationFunc>(exec,p,this,entry->value,entry->params,entry->attr);
02322 }
02323
02324 ValueImp * val = ObjectImp::getDirect(p);
02325 if (val)
02326 return Value(val);
02327 if (entry && (entry->attr & Function))
02328 return lookupOrCreateFunction<LocationFunc>(exec,p,this,entry->value,entry->params,entry->attr);
02329
02330 return Undefined();
02331 }
02332
02333 void Location::put(ExecState *exec, const Identifier &p, const Value &v, int attr)
02334 {
02335 #ifdef KJS_VERBOSE
02336 kdDebug(6070) << "Location::put " << p.qstring() << " m_part=" << (void*)m_frame->m_part << endl;
02337 #endif
02338 if (m_frame.isNull() || m_frame->m_part.isNull())
02339 return;
02340
02341 const Window* window = Window::retrieveWindow( m_frame->m_part );
02342 if ( !window )
02343 return;
02344
02345 KURL url = m_frame->m_part->url();
02346
02347 const HashEntry *entry = Lookup::findEntry(&LocationTable, p);
02348
02349 if (entry) {
02350
02351
02352 if (entry->value != Href && !window->isSafeScript(exec))
02353 return;
02354
02355 QString str = v.toString(exec).qstring();
02356 switch (entry->value) {
02357 case Href: {
02358 KHTMLPart* p =::qt_cast<KHTMLPart*>(Window::retrieveActive(exec)->part());
02359 if ( p )
02360 url = p->htmlDocument().completeURL( str ).string();
02361 else
02362 url = str;
02363 break;
02364 }
02365 case Hash:
02366
02367 if (str == url.ref()) return;
02368 url.setRef(str);
02369 break;
02370 case Host: {
02371 QString host = str.left(str.find(":"));
02372 QString port = str.mid(str.find(":")+1);
02373 url.setHost(host);
02374 url.setPort(port.toUInt());
02375 break;
02376 }
02377 case Hostname:
02378 url.setHost(str);
02379 break;
02380 case Pathname:
02381 url.setPath(str);
02382 break;
02383 case Port:
02384 url.setPort(str.toUInt());
02385 break;
02386 case Protocol:
02387 url.setProtocol(str);
02388 break;
02389 case Search:
02390 url.setQuery(str);
02391 break;
02392 }
02393 } else {
02394 ObjectImp::put(exec, p, v, attr);
02395 return;
02396 }
02397
02398 Window::retrieveWindow(m_frame->m_part)->goURL(exec, url.url(), false );
02399 }
02400
02401 Value Location::toPrimitive(ExecState *exec, Type) const
02402 {
02403 if (m_frame) {
02404 Window* window = Window::retrieveWindow( m_frame->m_part );
02405 if ( window && window->isSafeScript(exec) )
02406 return String(toString(exec));
02407 }
02408 return Undefined();
02409 }
02410
02411 UString Location::toString(ExecState *exec) const
02412 {
02413 if (m_frame) {
02414 Window* window = Window::retrieveWindow( m_frame->m_part );
02415 if ( window && window->isSafeScript(exec) )
02416 {
02417 if (!m_frame->m_part->url().hasPath())
02418 return m_frame->m_part->url().prettyURL()+"/";
02419 else
02420 return m_frame->m_part->url().prettyURL();
02421 }
02422 }
02423 return "";
02424 }
02425
02426 Value LocationFunc::tryCall(ExecState *exec, Object &thisObj, const List &args)
02427 {
02428 KJS_CHECK_THIS( Location, thisObj );
02429 Location *location = static_cast<Location *>(thisObj.imp());
02430 KParts::ReadOnlyPart *part = location->part();
02431
02432 if (!part) return Undefined();
02433
02434 Window* window = Window::retrieveWindow(part);
02435
02436 if ( !window->isSafeScript(exec) && id != Location::Replace)
02437 return Undefined();
02438
02439 switch (id) {
02440 case Location::Assign:
02441 case Location::Replace:
02442 Window::retrieveWindow(part)->goURL(exec, args[0].toString(exec).qstring(),
02443 id == Location::Replace);
02444 break;
02445 case Location::Reload: {
02446 KHTMLPart *khtmlpart = ::qt_cast<KHTMLPart *>(part);
02447 if (part)
02448 khtmlpart->scheduleRedirection(-1, part->url().url(), true);
02449 break;
02450 }
02451 case Location::ToString:
02452 return String(location->toString(exec));
02453 }
02454 return Undefined();
02455 }
02456
02458
02459 const ClassInfo External::info = { "External", 0, 0, 0 };
02460
02461
02462
02463
02464
02465 IMPLEMENT_PROTOFUNC_DOM(ExternalFunc)
02466
02467 Value External::get(ExecState *exec, const Identifier &p) const
02468 {
02469 return lookupGetFunction<ExternalFunc,ObjectImp>(exec,p,&ExternalTable,this);
02470 }
02471
02472 Value ExternalFunc::tryCall(ExecState *exec, Object &thisObj, const List &args)
02473 {
02474 KJS_CHECK_THIS( External, thisObj );
02475 External *external = static_cast<External *>(thisObj.imp());
02476
02477 KHTMLPart *part = external->part;
02478 if (!part)
02479 return Undefined();
02480
02481 KHTMLView *widget = part->view();
02482
02483 switch (id) {
02484 case External::AddFavorite:
02485 {
02486 #ifndef KONQ_EMBEDDED
02487 if (!widget->dialogsAllowed())
02488 return Undefined();
02489 part->xmlDocImpl()->updateRendering();
02490 if (args.size() != 1 && args.size() != 2)
02491 return Undefined();
02492
02493 QString url = args[0].toString(exec).qstring();
02494 QString title;
02495 if (args.size() == 2)
02496 title = args[1].toString(exec).qstring();
02497
02498
02499
02500 return Undefined();
02501
02502 QString question;
02503 if ( title.isEmpty() )
02504 question = i18n("Do you want a bookmark pointing to the location \"%1\" to be added to your collection?")
02505 .arg(url);
02506 else
02507 question = i18n("Do you want a bookmark pointing to the location \"%1\" titled \"%2\" to be added to your collection?")
02508 .arg(url).arg(title);
02509
02510 emit part->browserExtension()->requestFocus(part);
02511
02512 QString caption;
02513 if (!part->url().host().isEmpty())
02514 caption = part->url().host() + " - ";
02515 caption += i18n("JavaScript Attempted Bookmark Insert");
02516
02517 if (KMessageBox::warningYesNo(
02518 widget, question, caption,
02519 i18n("Insert"), i18n("Disallow")) == KMessageBox::Yes)
02520 {
02521 KBookmarkManager *mgr = KBookmarkManager::userBookmarksManager();
02522 mgr->addBookmarkDialog(url,title);
02523 }
02524 #else
02525 return Undefined();
02526 #endif
02527 break;
02528 }
02529 default:
02530 return Undefined();
02531 }
02532
02533 return Undefined();
02534 }
02535
02537
02538 const ClassInfo History::info = { "History", 0, 0, 0 };
02539
02540
02541
02542
02543
02544
02545
02546
02547 IMPLEMENT_PROTOFUNC_DOM(HistoryFunc)
02548
02549 Value History::get(ExecState *exec, const Identifier &p) const
02550 {
02551 return lookupGet<HistoryFunc,History,ObjectImp>(exec,p,&HistoryTable,this);
02552 }
02553
02554 Value History::getValueProperty(ExecState *, int token) const
02555 {
02556
02557
02558 switch (token) {
02559 case Length:
02560 {
02561 if ( !part )
02562 return Number( 0 );
02563
02564 KParts::BrowserExtension *ext = part->browserExtension();
02565 if ( !ext )
02566 return Number( 0 );
02567
02568 KParts::BrowserInterface *iface = ext->browserInterface();
02569 if ( !iface )
02570 return Number( 0 );
02571
02572 QVariant length = iface->property( "historyLength" );
02573
02574 if ( length.type() != QVariant::UInt )
02575 return Number( 0 );
02576
02577 return Number( length.toUInt() );
02578 }
02579 default:
02580 kdDebug(6070) << "WARNING: Unhandled token in History::getValueProperty : " << token << endl;
02581 return Undefined();
02582 }
02583 }
02584
02585 Value HistoryFunc::tryCall(ExecState *exec, Object &thisObj, const List &args)
02586 {
02587 KJS_CHECK_THIS( History, thisObj );
02588 History *history = static_cast<History *>(thisObj.imp());
02589
02590 Value v = args[0];
02591 Number n;
02592 if(v.isValid())
02593 n = v.toInteger(exec);
02594
02595 int steps;
02596 switch (id) {
02597 case History::Back:
02598 steps = -1;
02599 break;
02600 case History::Forward:
02601 steps = 1;
02602 break;
02603 case History::Go:
02604 steps = n.intValue();
02605 break;
02606 default:
02607 return Undefined();
02608 }
02609
02610
02611
02612
02613
02614 if (!steps)
02615 {
02616 history->part->openURL( history->part->url() );
02617 } else
02618 {
02619
02620
02621 Window* window = Window::retrieveWindow( history->part );
02622 window->delayedGoHistory( steps );
02623 }
02624 return Undefined();
02625 }
02626
02628
02629 #ifdef Q_WS_QWS
02630
02631 const ClassInfo Konqueror::info = { "Konqueror", 0, 0, 0 };
02632
02633 bool Konqueror::hasProperty(ExecState *exec, const Identifier &p) const
02634 {
02635 if ( p.qstring().startsWith( "goHistory" ) ) return false;
02636
02637 return true;
02638 }
02639
02640 Value Konqueror::get(ExecState *exec, const Identifier &p) const
02641 {
02642 if ( p == "goHistory" || part->url().protocol() != "http" || part->url().host() != "localhost" )
02643 return Undefined();
02644
02645 KParts::BrowserExtension *ext = part->browserExtension();
02646 if ( ext ) {
02647 KParts::BrowserInterface *iface = ext->browserInterface();
02648 if ( iface ) {
02649 QVariant prop = iface->property( p.qstring().latin1() );
02650
02651 if ( prop.isValid() ) {
02652 switch( prop.type() ) {
02653 case QVariant::Int:
02654 return Number( prop.toInt() );
02655 case QVariant::String:
02656 return String( prop.toString() );
02657 default:
02658 break;
02659 }
02660 }
02661 }
02662 }
02663
02664 return Value( new KonquerorFunc(exec, this, p.qstring().latin1() ) );
02665 }
02666
02667 Value KonquerorFunc::tryCall(ExecState *exec, Object &, const List &args)
02668 {
02669 KParts::BrowserExtension *ext = konqueror->part->browserExtension();
02670
02671 if (!ext)
02672 return Undefined();
02673
02674 KParts::BrowserInterface *iface = ext->browserInterface();
02675
02676 if ( !iface )
02677 return Undefined();
02678
02679 QCString n = m_name.data();
02680 n += "()";
02681 iface->callMethod( n.data(), QVariant() );
02682
02683 return Undefined();
02684 }
02685
02686 UString Konqueror::toString(ExecState *) const
02687 {
02688 return UString("[object Konqueror]");
02689 }
02690
02691 #endif
02692
02693
02694 #include "kjs_window.moc"