/* This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. */ /* Copyright (C) 2002 Dario Abatianni Copyright (C) 2005-2008 Eike Hein */ #include "query.h" #include "channel.h" #include "server.h" #include "konversationapplication.h" #include "konversationmainwindow.h" #include "viewcontainer.h" #include "ircinput.h" #include "ircview.h" #include "ircviewbox.h" #include "common.h" #include "topiclabel.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include Query::Query(TQWidget* parent, TQString _name) : ChatWindow(parent) { name=_name; // need the name a little bit earlier for setServer // don't setName here! It will break logfiles! // setName("QueryWidget"); setType(ChatWindow::Query); setChannelEncodingSupported(true); m_headerSplitter = new TQSplitter(Qt::Vertical, this); m_initialShow = true; awayChanged=false; awayState=false; TQHBox *box = new TQHBox(m_headerSplitter); addresseeimage = new TQLabel(box, "query_image"); addresseeimage->setSizePolicy(TQSizePolicy::Fixed, TQSizePolicy::Fixed); addresseeimage->hide(); addresseelogoimage = new TQLabel(box, "query_logo_image"); addresseelogoimage->setSizePolicy(TQSizePolicy::Fixed, TQSizePolicy::Fixed); addresseelogoimage->hide(); queryHostmask=new Konversation::TopicLabel(box, "query_hostmask"); TQString whatsthis = i18n("Some details of the person you are talking to in this query is shown in this bar. The full name and hostmask is shown, along with any image or logo this person has associated with them in the TDE Addressbook.

See the Konversation Handbook for information on associating a nick with a contact in the Addressbook, and for an explanation of what the hostmask is."); TQWhatsThis::add(addresseeimage, whatsthis); TQWhatsThis::add(addresseelogoimage, whatsthis); TQWhatsThis::add(queryHostmask, whatsthis); IRCViewBox* ircBox = new IRCViewBox(m_headerSplitter,0); setTextView(ircBox->ircView()); // Server will be set later in setServer(); textView->setAcceptDrops(true); connect(textView,TQT_SIGNAL(filesDropped(const TQStrList&)),this,TQT_SLOT(filesDropped(const TQStrList&))); connect(textView,TQT_SIGNAL(popupCommand(int)),this,TQT_SLOT(popup(int))); // link "Whois", "Ignore" ... menu items into ircview popup TQPopupMenu* popup=textView->getPopup(); popup->insertSeparator(); popup->insertItem(i18n("&Whois"),Konversation::Whois); popup->insertItem(i18n("&Version"),Konversation::Version); popup->insertItem(i18n("&Ping"),Konversation::Ping); popup->insertSeparator(); popup->insertItem(i18n("Ignore"), Konversation::IgnoreNick); popup->insertItem(i18n("Unignore"), Konversation::UnignoreNick); popup->setItemVisible(Konversation::IgnoreNick, false); popup->setItemVisible(Konversation::UnignoreNick, false); if (kapp->authorize("allow_downloading")) popup->insertItem(SmallIcon("2rightarrow"),i18n("Send &File..."),Konversation::DccSend); popup->insertItem(i18n("Add to Watched Nicks"), Konversation::AddNotify); // This box holds the input line TQHBox* inputBox=new TQHBox(this, "input_log_box"); inputBox->setSpacing(spacing()); awayLabel=new TQLabel(i18n("(away)"),inputBox); awayLabel->hide(); blowfishLabel = new TQLabel(inputBox); blowfishLabel->hide(); blowfishLabel->setPixmap(TDEGlobal::iconLoader()->loadIcon("encrypted", KIcon::Toolbar)); queryInput=new IRCInput(inputBox); getTextView()->installEventFilter(queryInput); queryInput->installEventFilter(this); // connect the signals and slots connect(queryInput,TQT_SIGNAL (submit()),this,TQT_SLOT (queryTextEntered()) ); connect(queryInput,TQT_SIGNAL (envelopeCommand()),this,TQT_SLOT (queryPassthroughCommand()) ); connect(queryInput,TQT_SIGNAL (textPasted(const TQString&)),this,TQT_SLOT (textPasted(const TQString&)) ); connect(getTextView(), TQT_SIGNAL(textPasted(bool)), queryInput, TQT_SLOT(paste(bool))); connect(getTextView(),TQT_SIGNAL (gotFocus()),queryInput,TQT_SLOT (setFocus()) ); connect(textView,TQT_SIGNAL (sendFile()),this,TQT_SLOT (sendFileMenu()) ); connect(textView,TQT_SIGNAL (extendedPopup(int)),this,TQT_SLOT (popup(int)) ); connect(textView,TQT_SIGNAL (autoText(const TQString&)),this,TQT_SLOT (sendQueryText(const TQString&)) ); updateAppearance(); setLog(Preferences::log()); } Query::~Query() { } void Query::setServer(Server* newServer) { if (m_server != newServer) connect(newServer, TQT_SIGNAL(connectionStateChanged(Server*, Konversation::ConnectionState)), TQT_SLOT(connectionStateChanged(Server*, Konversation::ConnectionState))); ChatWindow::setServer(newServer); if (!newServer->getKeyForRecipient(getName()).isNull()) blowfishLabel->show(); } void Query::connectionStateChanged(Server* server, Konversation::ConnectionState state) { if (server == m_server) { if (state == Konversation::SSConnected) { //HACK the way the notification priorities work sucks, this forces the tab text color to ungray right now. if (m_currentTabNotify == Konversation::tnfNone || !Preferences::tabNotificationsEvents()) KonversationApplication::instance()->getMainWindow()->getViewContainer()->unsetViewNotification(this); } else { //HACK the way the notification priorities work sucks, this forces the tab text color to gray right now. if (m_currentTabNotify == Konversation::tnfNone || (!Preferences::tabNotificationsEvents() && m_currentTabNotify == Konversation::tnfControl)) KonversationApplication::instance()->getMainWindow()->getViewContainer()->unsetViewNotification(this); } } } void Query::setName(const TQString& newName) { //if(ChatWindow::getName() == newName) return; // no change, so return ChatWindow::setName(newName); // don't change logfile name if query name changes // This will prevent Nick-Changers to create more than one log file, if (logName.isEmpty()) { TQString logName = (Preferences::lowerLog()) ? getName().lower() : getName() ; if(Preferences::addHostnameToLog()) { if(m_nickInfo) logName += m_nickInfo->getHostmask(); } setLogfileName(logName); } } void Query::setEncryptedOutput(bool e) { if (e) blowfishLabel->show(); else blowfishLabel->hide(); } void Query::queryTextEntered() { TQString line=queryInput->text(); queryInput->setText(""); if(line.lower()==Preferences::commandChar()+"clear") { textView->clear(); } else if(line.lower()==Preferences::commandChar()+"part") { m_server->closeQuery(getName()); } else if(line.length()) { sendQueryText(line); } } void Query::queryPassthroughCommand() { TQString commandChar = Preferences::commandChar(); TQString line = queryInput->text(); queryInput->setText(""); if(!line.isEmpty()) { // Prepend commandChar on Ctrl+Enter to bypass outputfilter command recognition if (line.startsWith(commandChar)) { line = commandChar + line; } sendQueryText(line); } } void Query::sendQueryText(const TQString& sendLine) { // create a work copy TQString outputAll(sendLine); // replace aliases and wildcards if(m_server->getOutputFilter()->replaceAliases(outputAll)) { outputAll = m_server->parseWildcards(outputAll, m_server->getNickname(), getName(), TQString(), TQString(), TQString()); } // Send all strings, one after another TQStringList outList=TQStringList::split('\n',outputAll); for(unsigned int index=0;indexgetOutputFilter()->parse(m_server->getNickname(), output, getName()); if(!result.output.isEmpty()) { if(result.type == Konversation::Action) appendAction(m_server->getNickname(), result.output); else if(result.type == Konversation::Command) appendCommandMessage(result.typeString, result.output); else if(result.type == Konversation::Program) appendServerMessage(result.typeString, result.output); else if(!result.typeString.isEmpty()) appendQuery(result.typeString, result.output); else appendQuery(m_server->getNickname(), result.output); } else if (result.outputList.count()) { Q_ASSERT(result.type==Konversation::Message); for ( TQStringList::Iterator it = result.outputList.begin(); it != result.outputList.end(); ++it ) { append(m_server->getNickname(), *it); } } if (!result.toServerList.empty()) { m_server->queueList(result.toServerList); } else { m_server->queue(result.toServer); } } // for } void Query::updateAppearance() { TQColor fg; TQColor bg; if(Preferences::inputFieldsBackgroundColor()) { fg=Preferences::color(Preferences::ChannelMessage); bg=Preferences::color(Preferences::TextViewBackground); } else { fg=colorGroup().foreground(); bg=colorGroup().base(); } queryInput->unsetPalette(); queryInput->setPaletteForegroundColor(fg); queryInput->setPaletteBackgroundColor(bg); getTextView()->unsetPalette(); if (Preferences::showBackgroundImage()) { getTextView()->setViewBackground(Preferences::color(Preferences::TextViewBackground), Preferences::backgroundImage()); } else { getTextView()->setViewBackground(Preferences::color(Preferences::TextViewBackground), TQString()); } if (Preferences::customTextFont()) { getTextView()->setFont(Preferences::textFont()); queryInput->setFont(Preferences::textFont()); } else { getTextView()->setFont(TDEGlobalSettings::generalFont()); queryInput->setFont(TDEGlobalSettings::generalFont()); } ChatWindow::updateAppearance(); } void Query::textPasted(const TQString& text) { if(m_server) { TQStringList multiline=TQStringList::split('\n',text); for(unsigned int index=0;indexshow(); else awayLabel->hide(); } } // fix TQTs broken behavior on hidden TQListView pages void Query::showEvent(TQShowEvent*) { if(awayChanged) { awayChanged=false; indicateAway(awayState); } if(m_initialShow) { m_initialShow = false; TQValueList sizes; sizes << queryHostmask->sizeHint().height() << (height() - queryHostmask->sizeHint().height()); m_headerSplitter->setSizes(sizes); } } void Query::popup(int id) { // get the nickname to the context menu popup TQString name = textView->getContextNick(); // if there was none (right click into the text view) assume query partner if (name.isEmpty()) name = getName(); switch (id) { case Konversation::Whois: sendQueryText(Preferences::commandChar()+"WHOIS "+name+' '+name); break; case Konversation::IgnoreNick: { if (KMessageBox::warningContinueCancel(this, i18n("Do you want to ignore %1?").arg(name), i18n("Ignore"), i18n("Ignore"), "IgnoreNick") == KMessageBox::Continue) { sendQueryText(Preferences::commandChar()+"IGNORE -ALL "+name); int rc = KMessageBox::questionYesNo(this, i18n("Do you want to close this query after ignoring this nickname?"), i18n("Close This Query"), i18n("Close"), i18n("Keep Open"), "CloseQueryAfterIgnore"); if (rc == KMessageBox::Yes && m_server) TQTimer::singleShot(0, this, TQT_SLOT(closeWithoutAsking())); } break; } case Konversation::UnignoreNick: { TQString question = i18n("Do you want to stop ignoring %1?").arg(name); if (KMessageBox::warningContinueCancel(this, question, i18n("Unignore"), i18n("Unignore"), "UnignoreNick") == KMessageBox::Continue) { sendQueryText(Preferences::commandChar()+"UNIGNORE "+name); } break; } case Konversation::AddNotify: { if (m_server->getServerGroup()) { if (!Preferences::isNotify(m_server->getServerGroup()->id(), name)) Preferences::addNotify(m_server->getServerGroup()->id(),name); } break; } case Konversation::DccSend: sendQueryText(Preferences::commandChar()+"DCC SEND "+name); break; case Konversation::Version: sendQueryText(Preferences::commandChar()+"CTCP "+name+" VERSION"); break; case Konversation::Ping: sendQueryText(Preferences::commandChar()+"CTCP "+name+" PING"); break; case Konversation::Topic: m_server->requestTopic(getTextView()->currentChannel()); break; case Konversation::Names: m_server->queue("NAMES " + getTextView()->currentChannel(), Server::LowPriority); break; case Konversation::Join: m_server->queue("JOIN " + getTextView()->currentChannel()); break; default: kdDebug() << "Query::popup(): Popup id " << id << " does not belong to me!" << endl; break; } // delete context menu nickname textView->clearContextNick(); } void Query::sendFileMenu() { emit sendFile(getName()); } void Query::childAdjustFocus() { queryInput->setFocus(); } void Query::setNickInfo(const NickInfoPtr & nickInfo) { if(m_nickInfo) disconnect(m_nickInfo, TQT_SIGNAL(nickInfoChanged()), this, TQT_SLOT(nickInfoChanged())); m_nickInfo = nickInfo; Q_ASSERT(m_nickInfo); if(!m_nickInfo) return; setName(m_nickInfo->getNickname()); connect(m_nickInfo, TQT_SIGNAL(nickInfoChanged()), this, TQT_SLOT(nickInfoChanged())); nickInfoChanged(); } void Query::nickInfoChanged() { if(m_nickInfo) { setName(m_nickInfo->getNickname()); TQString text = m_nickInfo->getBestAddresseeName(); if(!m_nickInfo->getHostmask().isEmpty() && !text.isEmpty()) text += " - "; text += m_nickInfo->getHostmask(); if(m_nickInfo->isAway() && !m_nickInfo->getAwayMessage().isEmpty()) text += " (" + KStringHandler::rsqueeze(m_nickInfo->getAwayMessage(),100) + ") "; queryHostmask->setText(Konversation::removeIrcMarkup(text)); KABC::Picture pic = m_nickInfo->getAddressee().photo(); if(pic.isIntern()) { TQPixmap qpixmap(pic.data().scaleHeight(queryHostmask->height())); if(!qpixmap.isNull()) { addresseeimage->setPixmap(qpixmap); addresseeimage->show(); } else { addresseeimage->hide(); } } else { addresseeimage->hide(); } KABC::Picture logo = m_nickInfo->getAddressee().logo(); if(logo.isIntern()) { TQPixmap qpixmap(logo.data().scaleHeight(queryHostmask->height())); if(!qpixmap.isNull()) { addresseelogoimage->setPixmap(qpixmap); addresseelogoimage->show(); } else { addresseelogoimage->hide(); } } else { addresseelogoimage->hide(); } TQString strTooltip; TQTextStream tooltip( &strTooltip, IO_WriteOnly ); tooltip << ""; tooltip << ""; m_nickInfo->tooltipTableData(tooltip); tooltip << "
"; TQToolTip::add(queryHostmask, strTooltip); TQToolTip::add(addresseeimage, strTooltip); TQToolTip::add(addresseelogoimage, strTooltip); } else { addresseeimage->hide(); addresseelogoimage->hide(); } emit updateQueryChrome(this,getName()); emitUpdateInfo(); } NickInfoPtr Query::getNickInfo() { return m_nickInfo; } TQString Query::getTextInLine() { return queryInput->text(); } bool Query::canBeFrontView() { return true; } bool Query::searchView() { return true; } void Query::appendInputText(const TQString& s, bool fromCursor) { if(!fromCursor) { queryInput->append(s); } else { int para = 0, index = 0; queryInput->getCursorPosition(¶, &index); queryInput->insertAt(s, para, index); queryInput->setCursorPosition(para, index + s.length()); } } // virtual void Query::setChannelEncoding(const TQString& encoding) { Preferences::setChannelEncoding(m_server->getDisplayName(), getName(), encoding); } TQString Query::getChannelEncoding() // virtual { return Preferences::channelEncoding(m_server->getDisplayName(), getName()); } TQString Query::getChannelEncodingDefaultDesc() // virtual { return i18n("Identity Default ( %1 )").arg(getServer()->getIdentity()->getCodecName()); } bool Query::closeYourself(bool confirm) { int result = KMessageBox::Continue; if (confirm) result=KMessageBox::warningContinueCancel(this, i18n("Do you want to close your query with %1?").arg(getName()), i18n("Close Query"), i18n("Close"), "QuitQueryTab"); if (result == KMessageBox::Continue) { m_server->removeQuery(this); return true; } return false; } void Query::closeWithoutAsking() { m_server->removeQuery(this); } void Query::filesDropped(const TQStrList& files) { m_server->sendURIs(files,getName()); } void Query::serverOnline(bool online) { //queryInput->setEnabled(online); getTextView()->setNickAndChannelContextMenusEnabled(online); TQPopupMenu* popup = getTextView()->getPopup(); if (popup) { popup->setItemEnabled(Konversation::Whois, online); popup->setItemEnabled(Konversation::Version, online); popup->setItemEnabled(Konversation::Ping, online); popup->setItemEnabled(Konversation::IgnoreNick, online); popup->setItemEnabled(Konversation::UnignoreNick, online); popup->setItemEnabled(Konversation::AddNotify, online); if (kapp->authorize("allow_downloading")) popup->setItemEnabled(Konversation::DccSend, online); } } void Query::emitUpdateInfo() { TQString info; if(m_nickInfo->loweredNickname() == m_server->loweredNickname()) info = i18n("Talking to yourself"); else if(m_nickInfo) info = m_nickInfo->getBestAddresseeName(); else info = getName(); emit updateInfo(info); } // show quit message of nick if we see it void Query::quitNick(const TQString& reason) { TQString displayReason = reason; if (displayReason.isEmpty()) { appendCommandMessage(i18n("Quit"),i18n("%1 has left this server.").arg(getName()),false); } else { if (displayReason.find(TQRegExp("[\\0000-\\0037]"))!=-1) displayReason+="\017"; appendCommandMessage(i18n("Quit"),i18n("%1 has left this server (%2).").arg(getName()).arg(displayReason),false); } } #include "query.moc"