基于IE内核浏览器控件,自定义高亮查找

实现浏览器自定义查找功能,参见开源项目:http://www.ookii.org/Software/FindAsYouType,在此贴出相关核心代码。


BOOL LbWebNoteHandler::DoHighlightText( const CString& strText , CComPtr<IHTMLTxtRange>& pTxtRange , CComPtr<IHTMLDocument2>& pDoc )
{
    BSTR pStr = strText.AllocSysString();
    
    long t = 0; long findflag = 0 | 4; // 向下搜索、匹配大小写
    VARIANT_BOOL bFound = FALSE; BOOL bFristFind = TRUE;
    while ( pTxtRange->findText( pStr , 0 , findflag , &bFound) , bFound )
    {
        CComPtr<IHTMLElement> pElement = NULL;
        HRESULT hr = pTxtRange->parentElement( &pElement );
        if ( FAILED( hr ) || pElement == NULL  )
            break ;
        
        if ( CheckVisible(pElement) ) // 忽略不可见元素
        {
            HighlightRange( pTxtRange , pDoc );
        }
        
        pTxtRange->moveStart( (BSTR)CComBSTR( _T("Character") ) , 1, &t );
        pTxtRange->moveEnd( (BSTR)CComBSTR( _T("Textedit") ) , 1 , &t );


    }   
    
    SysFreeString( pStr );
    
    return TRUE;
}

BOOL LbWebNoteHandler::HighlightRange( CComPtr<IHTMLTxtRange>& pTxtRange , CComPtr<IHTMLDocument2>& pDoc )
{
    CComPtr<IMarkupServices> markup = NULL;
    CComPtr<IMarkupPointer> start = NULL;
    CComPtr<IMarkupPointer> end = NULL;


    HRESULT hr = pDoc->QueryInterface( __uuidof(IMarkupServices) , (void**)&markup );
    if ( FAILED( hr ) || markup == NULL  )
        return FALSE ;


    hr = markup->CreateMarkupPointer( &start );
    if ( FAILED( hr ) || start == NULL  )
        return FALSE ;


    hr = markup->CreateMarkupPointer( &end );
    if ( FAILED( hr ) || end == NULL  )
        return FALSE ;


    hr = markup->MovePointersToRange( pTxtRange , start , end );
    if ( FAILED( hr ) )
        return FALSE ;
    
    // Get display pointers from the markup pointers
    CComPtr<IDisplayPointer> displayStart = CreateDisplayPointer(pDoc, start);
    CComPtr<IDisplayPointer> displayEnd = CreateDisplayPointer(pDoc, end);
    if( displayStart == NULL || displayEnd == NULL )
        return FALSE;


    CComPtr<IHTMLDocument4> doc = NULL;
    doc = pDoc;
    
    CComPtr<IHTMLRenderStyle> style = NULL;
    hr = doc->createRenderStyle( NULL , &style );
    if ( FAILED( hr ) || style == NULL  )
        return FALSE ;


    style->put_defaultTextSelection( _bstr_t("false") );
    style->put_textBackgroundColor( _variant_t("#FFFF11") );
    style->put_textColor( _variant_t("#686868") );


    // Create a highlight segment to highlight the range
    CComPtr<IHighlightRenderingServices> highlight = NULL;
    hr = pDoc->QueryInterface( __uuidof(IHighlightRenderingServices) , (void**)&highlight );
    if ( FAILED( hr ) || highlight == NULL  )
        return FALSE ;
    
    CComPtr<IHighlightSegment> segment = NULL;
    hr = highlight->AddSegment(displayStart,displayEnd,style,&segment);
    if ( FAILED( hr ) || segment == NULL  )
        return FALSE ;


    // Store the segment so we can un-highlight it later.
    m_highlights.push_back(segment);


    return TRUE;
}


CComPtr<IDisplayPointer> LbWebNoteHandler::CreateDisplayPointer( CComPtr<IHTMLDocument2>& pDoc , CComPtr<IMarkupPointer>& markupPointer )
{
    CComPtr<IDisplayServices> display = NULL;
    HRESULT hr = pDoc->QueryInterface( __uuidof(IDisplayServices) , (void**)&display );
    if ( FAILED( hr ) || display == NULL  )
        return NULL ;


    CComPtr<IDisplayPointer> displayPointer = NULL;
    hr = display->CreateDisplayPointer( &displayPointer );
    if ( FAILED( hr ) || displayPointer == NULL  )
        return NULL ;


    hr = displayPointer->MoveToMarkupPointer( markupPointer , NULL );
    if ( FAILED( hr ) )
        return NULL ;
    
    return displayPointer;
}


BOOL LbWebNoteHandler::CancleHighlight( void )
{   
    if( m_highlights.empty() )
        return TRUE;


    CComPtr<IHTMLDocument2> pDoc = m_pIEWebBrowserRef->GetHTMLDocument2();
    if( pDoc == NULL )
        return FALSE;


    CComPtr<IHighlightRenderingServices> highlight = NULL;
    HRESULT hr = pDoc->QueryInterface( __uuidof(IHighlightRenderingServices) , (void**)&highlight );
    if ( FAILED( hr ) || highlight == NULL  )
        return FALSE;


    typedef std::vector<CComPtr<IHighlightSegment> >::iterator SegmentListIterator;


    for( SegmentListIterator segment = m_highlights.begin(); segment != m_highlights.end(); ++segment )
        highlight->RemoveSegment( *segment );
    m_highlights.clear();
    
    return TRUE;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值