📄 htmltokenizer.cpp
字号:
break;
case ID_STYLE:
if (beginTag) {
searchStopper = styleEnd;
searchStopperLen = 7;
style = true;
parseSpecial(src);
}
break;
case ID_TEXTAREA:
if(beginTag) {
searchStopper = textareaEnd;
searchStopperLen = 10;
textarea = true;
parseSpecial(src);
}
break;
case ID_TITLE:
if (beginTag) {
#ifdef NOKIA_CHANGES
if(slashAtEndOfTag)
break;
#endif
searchStopper = titleEnd;
searchStopperLen = 7;
title = true;
parseSpecial(src);
}
break;
case ID_XMP:
if (beginTag) {
searchStopper = xmpEnd;
searchStopperLen = 5;
xmp = true;
parseSpecial(src);
}
break;
case ID_SELECT:
select = beginTag;
break;
case ID_PLAINTEXT:
plaintext = beginTag;
break;
}
return; // Finished parsing tag!
}
} // end switch
}
return;
}
void HTMLTokenizer::addPending()
{
if ( select && !script )
{
*dest++ = ' ';
}
else if ( textarea || script )
{
switch(pending) {
case LFPending: *dest++ = '\n'; break;
case SpacePending: *dest++ = ' '; break;
case NonePending:
assert(0);
}
}
else
{
switch (pending)
{
case SpacePending:
// Insert a breaking space
*dest++ = QChar(' ');
break;
case LFPending:
*dest = '\n';
dest++;
break;
case NonePending:
assert(0);
break;
}
}
pending = NonePending;
}
void HTMLTokenizer::write(const TokenizerString &str, bool appendData)
{
#ifdef TOKEN_DEBUG
kdDebug( 6036 ) << this << " Tokenizer::write(\"" << str << "\"," << appendData << ")" << endl;
#endif
// don't do parsing if there is not enough memory
OOM_PRE_CHECK( ( src.length() + str.length() ) * 16, 0, "HTMLTokenizer::write" )
if (!buffer)
return;
if (loadStopped)
return;
if ( ( m_executingScript && appendData ) || (!cachedScript.isEmpty()
#if NOKIA_CHANGES
&& !parser->doc()->fastDisplayMode()
#endif
) ) {
// don't parse; we will do this later
if (currentPrependingSrc) {
currentPrependingSrc->append(str);
} else {
pendingSrc.append(str);
}
return;
}
if ( onHold ) {
src.append(str);
return;
}
if (!src.isEmpty())
src.append(str);
else
setSrc(str);
// Once a timer is set, it has control of when the tokenizer continues.
if (timerId)
return;
bool wasInWrite = inWrite;
inWrite = true;
#ifdef INSTRUMENT_LAYOUT_SCHEDULING
if (!parser->doc()->ownerElement())
printf("Beginning write at time %d\n", parser->doc()->elapsedTime());
#endif
// if (Entity)
// parseEntity(src, dest);
int processedCount = 0;
QTime startTime;
startTime.start();
KWQUIEventTime eventTime;
while (!src.isEmpty() && (!parser->doc()->part() || !parser->doc()->part()->isScheduledLocationChangePending())) {
if (!continueProcessing(processedCount, startTime, eventTime))
break;
// do we need to enlarge the buffer?
RETURN_IF_OOM( checkBuffer() );
ushort cc = src->unicode();
if (skipLF && (cc != '\n'))
skipLF = false;
if (skipLF) {
skipLF = false;
++src;
}
else if ( Entity )
parseEntity( src, dest );
else if ( plaintext )
parseText( src );
else if (script)
parseSpecial(src);
else if (style)
parseSpecial(src);
else if (xmp)
parseSpecial(src);
else if (textarea)
parseSpecial(src);
else if (title)
parseSpecial(src);
else if (comment)
parseComment(src);
else if (server)
parseServer(src);
else if (processingInstruction)
parseProcessingInstruction(src);
else if (tag)
parseTag(src);
else if ( startTag )
{
startTag = false;
switch(cc) {
case '/':
break;
case '!':
{
// <!-- comment -->
searchCount = 1; // Look for '<!--' sequence to start comment
break;
}
case '?':
{
// xml processing instruction
processingInstruction = true;
tquote = NoQuote;
parseProcessingInstruction(src);
continue;
break;
}
case '%':
if (!brokenServer) {
// <% server stuff, handle as comment %>
server = true;
tquote = NoQuote;
parseServer(src);
continue;
}
// else fall through
default:
{
if( ((cc >= 'a') && (cc <= 'z')) || ((cc >= 'A') && (cc <= 'Z')))
{
// Start of a Start-Tag
}
else
{
// Invalid tag
// Add as is
if (pending)
addPending();
*dest = '<';
dest++;
continue;
}
}
}; // end case
if ( pending ) {
// pre context always gets its spaces/linefeeds
if (script || (!parser->selectMode() && (!parser->noSpaces() || dest > buffer )))
addPending();
// just forget it
else
pending = NonePending;
}
if (cc == '/' && discard == AllDiscard)
discard = NoneDiscard; // A close tag. No need to discard LF.
processToken();
cBufferPos = 0;
tag = TagName;
parseTag(src);
}
else if ( cc == '&' && !src.escaped())
{
++src;
if ( pending )
addPending();
parseEntity(src, dest, true);
}
else if ( cc == '<' && !src.escaped())
{
tagStartLineno = lineno+src.lineCount();
++src;
startTag = true;
}
else if (( cc == '\n' ) || ( cc == '\r' ))
{
if (select && !script)
{
if (discard == LFDiscard)
{
// Ignore this LF
discard = NoneDiscard; // We have discarded 1 LF
}
else if(discard == AllDiscard)
{
}
else
{
// Process this LF
if (pending == NonePending)
pending = LFPending;
}
}
else {
if (discard == LFDiscard || discard == AllDiscard)
{
// Ignore this LF
discard = NoneDiscard; // We have discarded 1 LF
}
else
{
// Process this LF
if (pending)
addPending();
pending = LFPending;
}
}
/* Check for MS-DOS CRLF sequence */
if (cc == '\r')
{
skipLF = true;
}
++src;
}
else if (cc == ' ')
{
if (select && !script) {
if(discard == SpaceDiscard)
discard = NoneDiscard;
else if(discard == AllDiscard)
{ }
else
pending = SpacePending;
}
else {
if (discard == AllDiscard)
discard = NoneDiscard;
if (pending)
addPending();
pending = SpacePending;
}
++src;
}
else
{
if (pending)
addPending();
discard = NoneDiscard;
#if QT_VERSION < 300
unsigned char row = src->row();
if ( row > 0x05 && row < 0x10 || row > 0xfd )
currToken.complexText = true;
#endif
*dest = *src;
if (dest->unicode() >= 0x0080)
fixUpChar( *dest );
++dest;
++src;
}
}
#ifdef INSTRUMENT_LAYOUT_SCHEDULING
if (!parser->doc()->ownerElement())
printf("Ending write at time %d\n", parser->doc()->elapsedTime());
#endif
inWrite = wasInWrite;
if (noMoreData && !inWrite && !loadingExtScript && !m_executingScript && !timerId)
end(); // this actually causes us to be deleted
OOM_POST_CHECK_FAILED(
end();
)
}
void HTMLTokenizer::stopped()
{
if (timerId) {
killTimer(timerId);
timerId = 0;
}
}
bool HTMLTokenizer::processingData() co
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -