📄 kjs_window.cpp
字号:
// If yes, save time and jump directly to ObjectImp. if ( (attr != None && attr != DontDelete) // Same thing if we have a local override (e.g. "var location") || ( ObjectImp::getDirect(propertyName) && isSafeScript(exec)) ) { ObjectImp::put( exec, propertyName, value, attr ); return; } const HashEntry* entry = Lookup::findEntry(&WindowTable, propertyName); if (entry) {#ifdef KJS_VERBOSE kdDebug(6070) << "Window("<<this<<")::put " << propertyName.qstring() << endl;#endif switch( entry->value ) { case Status: { String s = value.toString(exec); m_part->setJSStatusBarText(s.value().qstring()); return; } case DefaultStatus: { String s = value.toString(exec); m_part->setJSDefaultStatusBarText(s.value().qstring()); return; } case _Location: { KHTMLPart* p = Window::retrieveActive(exec)->m_part; if (p) { QString dstUrl = p->htmlDocument().completeURL(value.toString(exec).string()).string(); if (dstUrl.find("javascript:", 0, false) || isSafeScript(exec)) { bool userGesture = static_cast<ScriptInterpreter *>(exec->dynamicInterpreter())->wasRunByUserGesture();#if APPLE_CHANGES // We want a new history item if this JS was called via a user gesture m_part->scheduleRedirection(0, dstUrl, !userGesture, userGesture);#else m_part->scheduleRedirection(0, dstUrl, false /*don't lock history*/, userGesture);#endif } } return; } case Onabort: if (isSafeScript(exec)) setListener(exec, DOM::EventImpl::ABORT_EVENT,value); return; case Onblur: if (isSafeScript(exec)) setListener(exec, DOM::EventImpl::BLUR_EVENT,value); return; case Onchange: if (isSafeScript(exec)) setListener(exec, DOM::EventImpl::CHANGE_EVENT,value); return; case Onclick: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KHTML_CLICK_EVENT,value); return; case Ondblclick: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KHTML_DBLCLICK_EVENT,value); return; case Ondragdrop: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KHTML_DRAGDROP_EVENT,value); return; case Onerror: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KHTML_ERROR_EVENT,value); return; case Onfocus: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::FOCUS_EVENT,value); return; case Onkeydown: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KEYDOWN_EVENT,value); return; case Onkeypress: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KEYPRESS_EVENT,value); return; case Onkeyup: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KEYUP_EVENT,value); return; case Onload: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::LOAD_EVENT,value); return; case Onmousedown: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::MOUSEDOWN_EVENT,value); return; case Onmousemove: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::MOUSEMOVE_EVENT,value); return; case Onmouseout: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::MOUSEOUT_EVENT,value); return; case Onmouseover: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::MOUSEOVER_EVENT,value); return; case Onmouseup: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::MOUSEUP_EVENT,value); return; case Onmove: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::KHTML_MOVE_EVENT,value); return; case Onreset: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::RESET_EVENT,value); return; case Onresize: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::RESIZE_EVENT,value); return; case Onscroll: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::SCROLL_EVENT,value); return;#if APPLE_CHANGES case Onsearch: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::SEARCH_EVENT,value); return;#endif case Onselect: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::SELECT_EVENT,value); return; case Onsubmit: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::SUBMIT_EVENT,value); return; case Onunload: if (isSafeScript(exec)) setListener(exec,DOM::EventImpl::UNLOAD_EVENT,value); return; case Name: if (isSafeScript(exec))#if APPLE_CHANGES m_part->setName( value.toString(exec).qstring() );#else m_part->setName( value.toString(exec).qstring().local8Bit().data() );#endif return; default: break; } } if (isSafeScript(exec)) { //kdDebug(6070) << "Window("<<this<<")::put storing " << propertyName.qstring() << endl; ObjectImp::put(exec, propertyName, value, attr); }}bool Window::toBoolean(ExecState *) const{ return !m_part.isNull();}int Window::installTimeout(const UString &handler, int t, bool singleShot){ return winq->installTimeout(handler, t, singleShot);}int Window::installTimeout(const Value &function, List &args, int t, bool singleShot){ return winq->installTimeout(function, args, t, singleShot);}void Window::clearTimeout(int timerId){ winq->clearTimeout(timerId);}#if APPLE_CHANGESbool Window::hasTimeouts(){ return winq->hasTimeouts();}QMap<int, ScheduledAction*> *Window::pauseTimeouts(const void *key){ return winq->pauseTimeouts(key);}void Window::resumeTimeouts(QMap<int, ScheduledAction*> *sa, const void *key){ return winq->resumeTimeouts(sa, key);}#endifvoid Window::scheduleClose(){ kdDebug(6070) << "Window::scheduleClose window.close() " << m_part << endl; Q_ASSERT(winq);#if APPLE_CHANGES KWQ(m_part)->scheduleClose();#else QTimer::singleShot( 0, winq, SLOT( timeoutClose() ) );#endif}static bool shouldLoadAsEmptyDocument(const KURL &url){ return url.protocol().lower() == "about" || url.isEmpty();}bool Window::isSafeScript(ExecState *exec) const{ if (m_part.isNull()) { // part deleted ? can't grant access kdDebug(6070) << "Window::isSafeScript: accessing deleted part !" << endl; return false; } KHTMLPart *activePart = static_cast<KJS::ScriptInterpreter *>( exec->dynamicInterpreter() )->part(); if (!activePart) { kdDebug(6070) << "Window::isSafeScript: current interpreter's part is 0L!" << endl; return false; } if ( activePart == m_part ) // Not calling from another frame, no problem. return true; // JS may be attempting to access the "window" object, which should be valid, // even if the document hasn't been constructed yet. If the document doesn't // exist yet allow JS to access the window object. if (!m_part->xmlDocImpl()) return true; DOM::DocumentImpl* thisDocument = m_part->xmlDocImpl(); DOM::DocumentImpl* actDocument = activePart->xmlDocImpl(); if (!actDocument) { kdDebug(6070) << "Window::isSafeScript: active part has no document!" << endl; return false; } DOM::DOMString actDomain = actDocument->domain(); // Always allow local pages to execute any JS. if (actDomain.isNull()) return true; DOM::DOMString thisDomain = thisDocument->domain(); // if this document is being initially loaded as empty by its parent // or opener, allow access from any document in the same domain as // the parent or opener. if (shouldLoadAsEmptyDocument(m_part->url())) { KHTMLPart *ancestorPart = m_part->opener() ? m_part->opener() : m_part->parentPart(); while (ancestorPart && shouldLoadAsEmptyDocument(ancestorPart->url())) { ancestorPart = ancestorPart->parentPart(); } if (ancestorPart) thisDomain = ancestorPart->docImpl()->domain(); } //kdDebug(6070) << "current domain:" << actDomain.string() << ", frame domain:" << thisDomain.string() << endl; if ( actDomain == thisDomain ) return true;#if APPLE_CHANGES if (Interpreter::shouldPrintExceptions()) { printf("Unsafe JavaScript attempt to access frame with URL %s from frame with URL %s. Domains must match.\n", thisDocument->URL().latin1(), actDocument->URL().latin1()); QString message; message.sprintf("Unsafe JavaScript attempt to access frame with URL %s from frame with URL %s. Domains must match.\n", thisDocument->URL().latin1(), actDocument->URL().latin1()); KWQ(m_part)->addMessageToConsole(message, 1, QString()); //fixme: provide a real line number and sourceurl }#endif kdWarning(6070) << "Javascript: access denied for current frame '" << actDomain.string() << "' to frame '" << thisDomain.string() << "'" << endl; return false;}void Window::setListener(ExecState *exec, int eventId, Value func){ if (!isSafeScript(exec)) return; DOM::DocumentImpl *doc = static_cast<DOM::DocumentImpl*>(m_part->htmlDocument().handle()); if (!doc) return; doc->setHTMLWindowEventListener(eventId,getJSEventListener(func,true));}Value Window::getListener(ExecState *exec, int eventId) const{ if (!isSafeScript(exec)) return Undefined(); DOM::DocumentImpl *doc = static_cast<DOM::DocumentImpl*>(m_part->htmlDocument().handle()); if (!doc) return Undefined(); DOM::EventListener *listener = doc->getHTMLWindowEventListener(eventId); if (listener && static_cast<JSEventListener*>(listener)->listenerObjImp()) return static_cast<JSEventListener*>(listener)->listenerObj(); else return Null();}JSEventListener *Window::getJSEventListener(const Value& val, bool html){ // This function is so hot that it's worth coding it directly with imps. if (val.type() != ObjectType) return 0; ObjectImp *listenerObject = static_cast<ObjectImp *>(val.imp()); JSEventListener *existingListener = jsEventListeners[listenerObject]; if (existingListener) return existingListener; // Note that the JSEventListener constructor adds it to our jsEventListeners list return new JSEventListener(Object(listenerObject), Object(this), html);}JSLazyEventListener *Window::getJSLazyEventListener(const QString& code, bool html){ return new JSLazyEventListener(code, Object(this), html);}void Window::clear( ExecState *exec ){ KJS::Interpreter::lock(); kdDebug(6070) << "Window::clear " << this << endl; delete winq; winq = new WindowQObject(this);; // Get rid of everything, those user vars could hold references to DOM nodes deleteAllProperties( exec ); // Really delete those properties, so that the DOM nodes get deref'ed KJS::Collector::collect(); // Now recreate a working global object for the next URL that will use us KJS::Interpreter *interpreter = KJSProxy::proxy( m_part )->interpreter(); interpreter->initGlobalObject(); KJS::Interpreter::unlock();}void Window::setCurrentEvent( DOM::Event *evt ){ m_evt = evt; //kdDebug(6070) << "Window " << this << " (part=" << m_part << ")::setCurrentEvent m_evt=" << evt << endl;}Value WindowFunc::tryCall(ExecState *exec, Object &thisObj, const List &args){ if (!thisObj.inherits(&Window::info)) { Object err = Error::create(exec,TypeError); exec->setException(err); return err; } Window *window = static_cast<Window *>(thisObj.imp()); QString str, str2; KHTMLPart *part = window->m_part; if (!part) return Undefined(); KHTMLView *widget = part->view(); Value v = args[0]; UString s = v.toString(exec); str = s.qstring(); switch (id) { case Window::Alert: if (part && part->xmlDocImpl()) part->xmlDocImpl()->updateRendering();#if APPLE_CHANGES KWQ(part)->runJavaScriptAlert(str);#else KMessageBox::error(widget, QStyleSheet::convertFromPlainText(str), "JavaScript");#endif return Undefined(); case Window::Confirm: if (part && part->xmlDocImpl()) part->xmlDocImpl()->updateRendering();#if APPLE_CHANGES return Boolean(KWQ(part)->runJavaScriptConfirm(str));
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -