/*! \reimp */ bool QScriptDebuggerCodeView::event(QEvent *e) { Q_D(QScriptDebuggerCodeView); if (e->type() == QEvent::ToolTip) { if (d->editor->executionLineNumber() == -1) return false; QHelpEvent *he = static_cast<QHelpEvent*>(e); QPoint pt = he->pos(); pt.rx() -= d->editor->extraAreaWidth(); pt.ry() -= 8; QTextCursor cursor = d->editor->cursorForPosition(pt); QTextBlock block = cursor.block(); QString contents = block.text(); if (contents.isEmpty()) return false; int linePosition = cursor.position() - block.position(); linePosition -= 3; if (linePosition < 0) linePosition = 0; // ### generalize -- same as in completiontask int pos = linePosition; if ((pos > 0) && contents.at(pos-1).isNumber()) { // tooltips for numbers is pointless return false; } while ((pos > 0) && isIdentChar(contents.at(pos-1))) --pos; if ((pos > 0) && ((contents.at(pos-1) == QLatin1Char('\'')) || (contents.at(pos-1) == QLatin1Char('\"')))) { // ignore string literals return false; } int pos2 = linePosition; while ((pos2 < contents.size()-1) && isIdentChar(contents.at(pos2+1))) ++pos2; QString ident = contents.mid(pos, pos2 - pos + 1); QStringList path; path.append(ident); while ((pos > 0) && (contents.at(pos-1) == QLatin1Char('.'))) { --pos; pos2 = pos; while ((pos > 0) && isIdentChar(contents.at(pos-1))) --pos; path.prepend(contents.mid(pos, pos2 - pos)); } if (!path.isEmpty()) { int lineNumber = cursor.blockNumber() + d->editor->baseLineNumber(); emit toolTipRequest(he->globalPos(), lineNumber, path); } } return false; }
void VPreviewManager::fetchImageLinksFromRegions(QVector<VElementRegion> p_imageRegions, QVector<ImageLinkInfo> &p_imageLinks) { p_imageLinks.clear(); if (p_imageRegions.isEmpty()) { return; } p_imageLinks.reserve(p_imageRegions.size()); QTextDocument *doc = m_editor->document(); for (int i = 0; i < p_imageRegions.size(); ++i) { const VElementRegion ® = p_imageRegions[i]; QTextBlock block = doc->findBlock(reg.m_startPos); if (!block.isValid()) { continue; } int blockStart = block.position(); int blockEnd = blockStart + block.length() - 1; QString text = block.text(); // Since the image links update signal is emitted after a timer, during which // the content may be changed. if (reg.m_endPos > blockEnd) { continue; } ImageLinkInfo info(reg.m_startPos, reg.m_endPos, blockStart, block.blockNumber(), calculateBlockMargin(block, m_editor->tabStopWidthW())); if ((reg.m_startPos == blockStart || isAllSpaces(text, 0, reg.m_startPos - blockStart)) && (reg.m_endPos == blockEnd || isAllSpaces(text, reg.m_endPos - blockStart, blockEnd - blockStart))) { // Image block. info.m_isBlock = true; fetchImageInfoToPreview(text, info); } else { // Inline image. info.m_isBlock = false; fetchImageInfoToPreview(text.mid(reg.m_startPos - blockStart, reg.m_endPos - reg.m_startPos), info); } if (info.m_linkUrl.isEmpty() || info.m_linkShortUrl.isEmpty()) { continue; } p_imageLinks.append(info); } }
void Document::dictionaryChanged() { for (QTextBlock i = m_text->document()->begin(); i != m_text->document()->end(); i = i.next()) { if (i.userData()) { static_cast<BlockStats*>(i.userData())->checkSpelling(i.text(), m_dictionary); } } m_highlighter->rehighlight(); }
void MessagesDialog::sinkMessage( const MsgEvent *msg ) { QMutexLocker locker( &messageLocker ); QPlainTextEdit *messages = ui.messages; /* Only scroll if the viewport is at the end. Don't bug user by auto-changing/losing viewport on insert(). */ bool b_autoscroll = ( messages->verticalScrollBar()->value() + messages->verticalScrollBar()->pageStep() >= messages->verticalScrollBar()->maximum() ); /* Copy selected text to the clipboard */ if( messages->textCursor().hasSelection() ) messages->copy(); /* Fix selected text bug */ if( !messages->textCursor().atEnd() || messages->textCursor().anchor() != messages->textCursor().position() ) messages->moveCursor( QTextCursor::End ); /* Start a new logic block so we can hide it on-demand */ messages->textCursor().insertBlock(); QString buf = QString( "<i><font color='darkblue'>%1</font>" ).arg( msg->module ); switch ( msg->priority ) { case VLC_MSG_INFO: buf += "<font color='blue'> info: </font>"; break; case VLC_MSG_ERR: buf += "<font color='red'> error: </font>"; break; case VLC_MSG_WARN: buf += "<font color='green'> warning: </font>"; break; case VLC_MSG_DBG: default: buf += "<font color='grey'> debug: </font>"; break; } /* Insert the prefix */ messages->textCursor().insertHtml( buf /* + "</i>" */ ); /* Insert the message */ messages->textCursor().insertHtml( msg->text ); /* Pass the new message thru the filter */ QTextBlock b = messages->document()->lastBlock(); b.setVisible( matchFilter( b.text() ) ); /* Tell the QTextDocument to recompute the size of the given area */ messages->document()->markContentsDirty( b.position(), b.length() ); if ( b_autoscroll ) messages->ensureCursorVisible(); }
std::vector<std::string> CodeEditor::getEditorContent() { std::vector<std::string> list; for (QTextBlock block = document()->begin(); block.isValid(); block = block.next()) { list.push_back(block.text().toStdString()); } return list; }
static inline int _firstNwsPos( const QTextBlock& b ) { const QString str = b.text(); for( int i = 0; i < str.size(); i++ ) { if( !str[i].isSpace() ) return b.position() + i; } return b.position() + b.length(); // Es ist nur WS vorhanden }
int BAbstractFileType::indentation(const QTextBlock &previousBlock) const { if (!previousBlock.isValid()) return 0; QString text = previousBlock.text(); int i = 0; while (i < text.length() && text.at(i) == ' ') ++i; return i; }
qreal TextDocumentLayout::indentWidth(const QTextBlock &block) { QRegExp exp("^[ \\t]*"); if(exp.indexIn(block.text()) == -1) { return 0; } QFontMetrics fm(block.charFormat().font()); return fm.width(exp.capturedTexts().at(0)); }
static void indentDocument(QTextDocument *doc) { QStringList allCode; for (QTextBlock block = doc->begin(); block.isValid(); block = block.next()) allCode << block.text(); QTextBlock block = doc->begin(); for (int line = 0; line < allCode.count() && block.isValid(); ++line, block = block.next()) { const QStringList previousCode = allCode.mid(0, line + 1); indent(block, previousCode); } }
void CodeEditor::keyPressEvent(QKeyEvent *e) { // SHIFT+TAB kommt hier nie an aus nicht nachvollziehbaren Grnden. Auch in event und viewPortEvent nicht. // NOTE: Qt macht daraus automatisch BackTab und versendet das! if( e->key() == Qt::Key_Tab ) { if( e->modifiers() & Qt::ControlModifier ) { // Wir brauchen CTRL+TAB fr Umschalten der Scripts e->ignore(); return; } if( !isReadOnly() && ( hasSelection() || textCursor().position() <= _firstNwsPos( textCursor().block() ) ) ) { if( e->modifiers() == Qt::NoModifier ) { indent(); e->accept(); return; } } }else if( e->key() == Qt::Key_Backtab ) { if( e->modifiers() & Qt::ControlModifier ) { // Wir brauchen CTRL+TAB fr Umschalten der Scripts e->ignore(); return; } if( !isReadOnly() && ( hasSelection() || textCursor().position() <= _firstNwsPos( textCursor().block() ) ) ) { unindent(); e->accept(); return; } }else if( !isReadOnly() && ( e->key() == Qt::Key_Enter || e->key() == Qt::Key_Return ) ) { e->accept(); if( e->modifiers() != Qt::NoModifier ) return; // Verschlucke Return mit Ctrl etc. textCursor().beginEditBlock(); QPlainTextEdit::keyPressEvent( e ); // Lasse Qt den neuen Block einfgen QTextBlock prev = textCursor().block().previous(); if( prev.isValid() ) { const int ws = _firstNwsPos( prev ); textCursor().insertText( prev.text().left( ws - prev.position() ) ); } textCursor().endEditBlock(); return; } QPlainTextEdit::keyPressEvent( e ); }
int CMakeIndenter::indentFor(const QTextBlock &block, const TextEditor::TabSettings &tabSettings) { QTextBlock previousBlock = block.previous(); // find the next previous block that is non-empty (contains non-whitespace characters) while (previousBlock.isValid() && lineIsEmpty(previousBlock.text())) previousBlock = previousBlock.previous(); if (!previousBlock.isValid()) return 0; const QString previousLine = previousBlock.text(); const QString currentLine = block.text(); int indentation = tabSettings.indentationColumn(previousLine); if (lineStartsBlock(previousLine)) indentation += tabSettings.m_indentSize; if (lineEndsBlock(currentLine)) indentation = qMax(0, indentation - tabSettings.m_indentSize); // increase/decrease/keep the indentation level depending on if we have more opening or closing parantheses return qMax(0, indentation + tabSettings.m_indentSize * paranthesesLevel(previousLine)); }
/** * Parses a text document and builds the navigation tree for it */ void NavigationWidget::parse(QTextDocument *document) { const QSignalBlocker blocker(this); Q_UNUSED(blocker); setDocument(document); clear(); _lastHeadingItemList.clear(); for (int i = 0; i < document->blockCount(); i++) { QTextBlock block = document->findBlockByNumber(i); int elementType = block.userState(); // ignore all non headline types if ((elementType < pmh_H1) || (elementType > pmh_H6)) { continue; } QString text = block.text(); text.remove(QRegularExpression("^#+")) .remove(QRegularExpression("#+$")) .remove(QRegularExpression("^\\s+")) .remove(QRegularExpression("^=+$")) .remove(QRegularExpression("^-+$")); if (text.isEmpty()) { continue; } QTreeWidgetItem *item = new QTreeWidgetItem(); item->setText(0, text); item->setData(0, Qt::UserRole, block.position()); item->setToolTip(0, tr("headline %1").arg(elementType - pmh_H1 + 1)); // attempt to find a suitable parent item for the element type QTreeWidgetItem *lastHigherItem = findSuitableParentItem(elementType); if (lastHigherItem == NULL) { // if there wasn't a last higher level item then add the current // item to the top level addTopLevelItem(item); } else { // if there was a last higher level item then add the current // item as child of that item lastHigherItem->addChild(item); } _lastHeadingItemList[elementType] = item; } expandAll(); }
int main(int argv, char **args) { QString contentString("One\nTwp\nThree"); QTextDocument *doc = new QTextDocument(contentString); //! [0] for (QTextBlock it = doc->begin(); it != doc->end(); it = it.next()) cout << it.text().toStdString() << endl; //! [0] return 0; }
QString GitEditorWidget::fileNameForLine(int line) const { // 7971b6e7 share/qtcreator/dumper/dumper.py (hjk QTextBlock block = document()->findBlockByLineNumber(line - 1); QTC_ASSERT(block.isValid(), return source()); static QRegExp renameExp(QLatin1String("^" CHANGE_PATTERN "\\s+([^(]+)")); if (renameExp.indexIn(block.text()) != -1) { const QString fileName = renameExp.cap(1).trimmed(); if (!fileName.isEmpty()) return fileName; } return source(); }
void LirchChannel::persist() const { if (stream) { int num_blocks = document->blockCount(); QTextBlock block = document->begin(); for (int i = 0; i < num_blocks; ++i) { endl(*stream << block.text()); emit progress(i * 100 / num_blocks); block = block.next(); } emit progress(100); } emit persisted(); }
// 遍历文本块 void MainWindow::showTextBlock() { QTextDocument *document = ui->textEdit->document(); // 获取文档的第一个文本块 QTextBlock block = document->firstBlock(); for(int i=0; i<document->blockCount(); i++){ qDebug() << tr("文本块%1,文本块首行行号为:%2,长度为:%3,内容为:") .arg(i).arg(block.firstLineNumber()).arg(block.length()) << block.text(); // 获取下一个文本块 block = block.next(); } }
void JavaIndenter::indentBlock(QTextDocument *doc, const QTextBlock &block, const QChar &typedChar, const TextEditor::TabSettings &tabSettings) { // At beginning: Leave as is. if (block == doc->begin()) return; const int tabsize = tabSettings.m_indentSize; QTextBlock previous = block.previous(); QString previousText = previous.text(); while (previousText.trimmed().isEmpty()) { previous = previous.previous(); if (previous == doc->begin()) return; previousText = previous.text(); } int adjust = 0; if (previousText.contains(QLatin1Char('{'))) adjust = tabsize; if (block.text().contains(QLatin1Char('}')) || typedChar == QLatin1Char('}')) adjust += -tabsize; // Count the indentation of the previous line. int i = 0; while (i < previousText.size()) { if (!previousText.at(i).isSpace()) { tabSettings.indentLine(block, tabSettings.columnAt(previousText, i) + adjust); break; } ++i; } }
int ScCodeEditor::indentedStartOfLine( const QTextBlock &b ) { QString t(b.text()); int n = t.size(); int i = 0; while (i < n) { QChar c(t[i]); if (c != ' ' && c != '\t') break; ++i; } return i; }
/* Returns the recommended indent for the bottom line of yyProgram assuming that it starts in a C-style comment, a condition that is tested elsewhere. Essentially, we're trying to align against some text on the previous line. */ int QmlJSIndenter::indentWhenBottomLineStartsInMultiLineComment() { QTextBlock block = yyProgram.lastBlock().previous(); QString blockText; for (; block.isValid(); block = block.previous()) { blockText = block.text(); if (! isOnlyWhiteSpace(blockText)) break; } return indentOfLine(blockText); }
QString GitEditor::fileNameFromDiffSpecification(const QTextBlock &inBlock) const { // Check for "+++ b/src/plugins/git/giteditor.cpp" (blame and diff) // Go back chunks. const QString newFileIndicator = QLatin1String("+++ b/"); for (QTextBlock block = inBlock; block.isValid(); block = block.previous()) { QString diffFileName = block.text(); if (diffFileName.startsWith(newFileIndicator)) { diffFileName.remove(0, newFileIndicator.size()); return findDiffFile(diffFileName, GitPlugin::instance()->versionControl()); } } return QString(); }
bool Autocorrect::singleSpaces() { if (! m_singleSpaces) return false; if (!m_cursor.atBlockStart() && m_word.length() == 1 && m_word.at(0) == ' ') { // then when the prev char is also a space, don't insert one. QTextBlock block = m_cursor.block(); QString text = block.text(); if (text.at(m_cursor.position() -1 - block.position()) == ' ') { m_word.clear(); return true; } } return false; }
int GoCodeFormatter::tokenizeBlock(const QTextBlock &block) { int previousState = TextDocumentLayout::lexerState(block.previous()); if (block.blockNumber() == 0) previousState = 0; m_line = block.text(); GoLexer *lexer = GoLexer::instance(); m_tokens = lexer->tokenize(m_line, previousState); int currentState = lexer->lexerState().state(); TextEditor::TextDocumentLayout::setLexerState(block, currentState); return currentState; }
void messages_widget::pushMessage() { QString msg; QStringList lines; for ( QTextBlock block = textMsg->document()->begin(); block.isValid(); block = block.next()) { lines.append(block.text()); } msg = lines.join("\n"); if (msg.toUtf8().size() > libed2k::client_message::CLIENT_MAX_MESSAGE_LENGTH) { QMessageBox::warning(this, tr("Send message"), tr("Message contains %1 bytes with limit %2").arg(msg.toUtf8().size()).arg(libed2k::client_message::CLIENT_MAX_MESSAGE_LENGTH)); return; } if (tabWidget->currentIndex() < 0 || !msg.length()) return; USER& user = users[tabWidget->currentIndex()]; if (user.post_msg.length()) return; textMsg->clear(); QTextEdit* edit = qobject_cast<QTextEdit*>(tabWidget->widget(tabWidget->currentIndex())); if (user.connected > 0) { Preferences pref; addMessage(edit, pref.nick(), msg, greenColor); } else { user.post_msg = msg; user.connected = -1; addSystemMessage(edit, tr("*** Connecting... ")); } QED2KPeerHandle::getPeerHandle(user.netPoint).sendMessageToPeer(msg); textMsg->setFocus(); }
QString DoxygenGenerator::generate(QTextCursor cursor) { const QChar &c = cursor.document()->characterAt(cursor.position()); if (!c.isLetter() && c != QLatin1Char('_')) return QString(); // Try to find what would be the declaration we are interested in. SimpleLexer lexer; QTextBlock block = cursor.block(); while (block.isValid()) { const QString &text = block.text(); const QList<Token> &tks = lexer(text); foreach (const Token &tk, tks) { if (tk.is(T_SEMICOLON) || tk.is(T_LBRACE)) { // No need to continue beyond this, we might already have something meaningful. cursor.setPosition(block.position() + tk.end(), QTextCursor::KeepAnchor); break; } } if (cursor.hasSelection()) break; block = block.next(); } if (!cursor.hasSelection()) return QString(); QString declCandidate = cursor.selectedText(); declCandidate.replace(QChar::ParagraphSeparator, QLatin1Char('\n')); // Let's append a closing brace in the case we got content like 'class MyType {' if (declCandidate.endsWith(QLatin1Char('{'))) declCandidate.append(QLatin1Char('}')); Document::Ptr doc = Document::create(QLatin1String("<doxygen>")); doc->setUtf8Source(declCandidate.toUtf8()); doc->parse(Document::ParseDeclaration); doc->check(Document::FastCheck); if (!doc->translationUnit() || !doc->translationUnit()->ast() || !doc->translationUnit()->ast()->asDeclaration()) { return QString(); } return generate(cursor, doc->translationUnit()->ast()->asDeclaration()); }
int NormalIndenter::indentFor(const QTextBlock &block, const TabSettings &tabSettings) { Q_UNUSED(tabSettings); QTextBlock previous = block.previous(); if (!previous.isValid()) return 0; const QString previousText = previous.text(); // Empty line indicates a start of a new paragraph. Leave as is. if (previousText.isEmpty() || previousText.trimmed().isEmpty()) return 0; return tabSettings.indentationColumn(previousText); }
static inline int _indents( const QTextBlock& b ) { const QString text = b.text(); int spaces = 0; for( int i = 0; i < text.size(); i++ ) { if( text[i] == QChar('\t') ) spaces += s_charPerTab; else if( text[i] == QChar( ' ' ) ) spaces++; else break; } return spaces / s_charPerTab; }
QString MercurialEditor::fileNameFromDiffSpecification(const QTextBlock &inBlock) const { // git-compatible format: check for "+++ b/src/plugins/git/giteditor.cpp" (blame and diff) // Go back chunks. const QString newFileIndicator = QLatin1String("+++ b/"); for (QTextBlock block = inBlock; block.isValid(); block = block.previous()) { QString diffFileName = block.text(); if (diffFileName.startsWith(newFileIndicator)) { diffFileName.remove(0, newFileIndicator.size()); return findDiffFile(diffFileName); } } return QString(); }
QString CodeEditor::getCode() { QTextDocument *doc = this->document(); int bc = doc->blockCount(); QString str; for(int i=0; i<bc; ++i){ QTextBlock block = doc->findBlockByNumber(i); QString s = block.text(); str.append(s); if(!s.trimmed().isEmpty()) str.append('\n'); } return str; }
void BarDescriptorEditor::updateCursorPosition() { BarDescriptorEditorWidget *editorWidget = qobject_cast<BarDescriptorEditorWidget *>(widget()); QTC_ASSERT(editorWidget, return); const QTextCursor cursor = editorWidget->sourceWidget()->textCursor(); const QTextBlock block = cursor.block(); const int line = block.blockNumber() + 1; const int column = cursor.position() - block.position(); m_cursorPositionLabel->setText(tr("Line: %1, Col: %2").arg(line) .arg(editorWidget->sourceWidget()->textDocument() ->tabSettings().columnAt(block.text(), column)+1), tr("Line: 9999, Col: 999")); if (!block.isVisible()) editorWidget->sourceWidget()->ensureCursorVisible(); }
static void indent(QTextDocument *doc, QTextBlock block) { QStringList code; QTextBlock currentBlock = block; block = doc->begin(); while (block.isValid()) { code << block.text(); if (block == currentBlock) break; block = block.next(); } indent(currentBlock, code); }