IE 解析 Web Page DOM结构 (二)

来源:互联网 发布:淘宝怎么运作 编辑:程序博客网 时间:2024/05/24 04:26

接下来的两篇我将介绍怎样从DOM流中解析出组成网页的最基本的两种元素:文字和图像。

 

上一篇我说过网页是由许多嵌套的frame组成,而每一个frame都是一个独立的单元,他们包含自己的文字和图片。解析文字和图片有以下两种情况:

1.         他们都直接放置在网页“BODY”层,此时我不用考虑这些frame导致的布局影响。这是最简单的一种情形。

2.         而常见的情形是他们被放置于嵌套的frame中,比如Button控件上的文字,TextBox控件中的文字等。

 

l   文字

1.    BODY“层的文字

文字在DOM语言中有好多种标签可以代表他,比如LabelTitle,和Anchor等等。他们都表示有文字。

·         首先,我需要得到文字的位置以及他的本体文字,这可一从IHTMLElement接口中获得。

          IHTMLElement Members(从MSDN摘录的片段)

offsetParent

Retrieves a reference to the container object that defines the IHTMLElement::offsetTop and IHTMLElement::offsetLeft properties of the object.

offsetHeight

Retrieves the height of the object relative to the layout or coordinate parent, as specified by the IHTMLElement::offsetParent property.

offsetLeft

Retrieves the calculated left position of the object relative to the layout or coordinate parent, as specified by the IHTMLElement::offsetParent property.

offsetParent

Retrieves a reference to the container object that defines the IHTMLElement::offsetTop and IHTMLElement::offsetLeft properties of the object.

offsetTop

Retrieves the calculated top position of the object relative to the layout or coordinate parent, as specified by the IHTMLElement::offsetParent property.

offsetWidth

Retrieves the width of the object relative to the layout or coordinate parent, as specified by the IHTMLElement::offsetParent property.

innerText

Sets or retrieves the text between the start and end tags of the object.

下面是可行的伪代码:

                 long ltop, lleft, lHeight, lwidth;

                 hr = spElement->get_offsetLeft(&lleft);

                 hr = spElement->get_offsetTop(&ltop);

                 hr = spElement->get_offsetHeight(&lHeight);

                 hr = spElement->get_offsetWidth(&lwidth);

 

                 BSTR bstrInnerText;

                 hr = spElement->get_innerText(&bstrInnerText);

·         关于文字的字体风格,如字体大小,字体族,是否加粗,倾斜等等,我就只能从CSS流中解析。而CSS流的代表接口就是IHTMLCurrentStyle

 

            IHTMLCurrentStyle Members(从MSDN摘录的片段)

fontFamily

Sets or retrieves the name of the font used for text in the object.

fontSize

Sets or retrieves a value that indicates the font size used for text in the object.

fontStyle

Sets or retrieves the font style of the object as italic, normal, or oblique.

fontVariant

Sets or retrieves whether the text of the object is in small capital letters.

fontWeight

Sets or retrieves the weight of the font of the object.

下面是可行伪代码:

            CComQIPtr<IHTMLElement> spElement;

                          CComQIPtr<IHTMLElement2> spElement2(spElement);        

                          CComQIPtr<IHTMLCurrentStyle>spCurrentStyle;

                          spElement2->get_currentStyle(&spCurrentStyle);

                          VARIANT  varfontSize;

                          varfontSize.vt = VT_BSTR;

                          spCurrentStyle->get_fontSize(&varfontSize);

                          VARIANT varfontWeight;

                          varfontWeight.vt = VT_BSTR;

                          spCurrentStyle->get_fontWeight(&varfontWeight);

                          VARIANT varHeight;

                          varHeight.vt = VT_BSTR

                          spCurrentStyle->get_height(&varHeight);

 

这里你所取得的fontFamily的值是一个字体族列表,其中的每个字体族用分号隔开以防止当有多种字体族混杂在一起。此值主要由两部分组成:字体族名称和通用字体族名称。如果字体族名称包含空白符,它应该出现一个或两个引号;通用字体族名称不用包含在引号中。

为什么要这样组织字体族名称呢?这主要是因为你不知道客户端安装了什么字体, 你应该提供用户一个备用的字体族 通用字体族名称在字体族名称列表的末尾,防止如果客户端没有安装字体族名称指定的字体时,可以用通用字体族名称来替代。

这个字体族名称列表也可以包含嵌入字体。此外,关于fontFamily的默认值可以通过Microsoft Internet Explorer->Internet Options menu->General tab->Fonts button来设置。

综上所述,IE浏览器是这样来应用字体的:首先他会从DOM中解析出fontFamily的字体列表,然后他会尝试其中的每一个字体,直到找到一种客户端已经安装的字体族。如果到列表末尾,IE浏览器依然没有找到相应的字体,那么他就会使用IE设置的那个默认字体。

此外,在上面的伪代码中所得到的字体大小,高度,宽度等数据,他们返回的值有可能不是绝对的数值,如8pt。相反,它可能是一种相对值(相对上一层字体),比如:xx-smallx-smalllargersmaller等等。这不可避免地要求我们自己将这些抽象概念转化为绝对数值。特别是,如果给出的是百分比,我们可能需要递归算出这些数值。

最糟糕的是,有时候你可能取得的是负值,比如:“-1”,“-2”。这意味着字体大小必须转化为设备单位,而且匹配它的绝对数值通过可用字体字符的高度。

·         文字颜色是个很麻烦的问题,可以用下面的代码:

CComQIPtr<IHTMLCurrentStyle>spCurrentStyle;

VARIANT varColor;

varColor.vt = VT_BSTR|VT_I4;

spCurrentStyle->get_color(&varColor);

但是请注意返回的varColor是一个BSTR值,而且是专属于网页设计的一组颜色值,如果你想使用RGB颜色值,必须自己进行转换。而且,DOM常常会简写这个颜色值,比如#00ccff,从上面的代码取出来的值可能是#0cf

·         文字编码问题

我们可以在IE浏览器中设置网页的编码,这些信息我们也可以从DOM中获取.

 

BSTR bstrCharset;

  spHTMLDocument2->get_charset(&bstrCharset);

 

2.    嵌套容器中的文字

我打算以Table控件中的文字为例,其他控件容器中的文字可以按类似的方法来处理

·         Get text in Table

许多网页中都有Table控件,每个Table都有自己的文字。比如,下面这个Table

Hanna Strategies, Ltd. is among the first software outsourcing service providers in China 's IT industry, specializing in the research and development of computer aided design (CAD) and data management software......

这个TableDOM树如下所示:(通过IE Dev Toolbar取得)

 

·         文字分行

网页中的文字是没有分行符让你判断文字该到哪个字分行,这是一个大麻烦,尤其对于那些做文件格式转化的程序员而言。因为这意味着虽然你可以得到上面的那一大段文字,但是,你不知道怎么来断行。唯一可行的办法就是自己设计算法来分行,但只是一件非常复杂的事。

你想一想,你既要考虑字体目前的大小,还要调整Table一行是多宽,从而计算每一行最多可以放几个字。其中,还要加上字跟字,行跟行之间的间距值。这实在是个很烦琐的事。

·         Table中文字的位置

现在文字的位置需要考虑连个因素:一个是文字相对于Table的位置;另一个是整个Table相对于网页的位置。

                 IHTMLTable Members(从MSDN摘录)

align

Sets or retrieves a value that indicates the table alignment.

cellPadding

Sets or retrieves the amount of space between the border of the cell and the content of the cell.

cellSpacing

Sets or retrieves the amount of space between cells in a table.

height

Sets or retrieves the height of the object.

width

Sets or retrieves the width of the object.

 

                 IHTMLTableCell Members(从MSDN摘录)

colSpan

Sets or retrieves the number columns in the table that the object should span.

height

Sets or retrieves the height of the object.

noWrap

Sets or retrieves whether the browser automatically performs wordwrap.

rowSpan

Sets or retrieves how many rows in a table the cell should span.

vAlign

Sets or retrieves how text and other content are vertically aligned within the object that contains them.

width

Sets or retrieves the width of the object.

 

关于这一点我会在后面详细讨论,这也是一个浩大的解析过程。

 

 

 
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 单招没有考上怎么办 浙江单考单招报名序号怎么办 考上大学不想上怎么办 煤改气没钱的户怎么办 生病要住院工作怎么办 今天儿子高考想要怎么办 高考失败不想复读怎么办 高考复读失败了怎么办 小孩子太笨了怎么办 孩子不去舞蹈班怎么办 二年级成绩下降怎么办 叛逆期的初中生怎么办? 60岁没养老保险怎么办 职工医保辞职后怎么办 门诊医保超20000怎么办 单位倒闭供暖费怎么办 异地办医保怎么办手续 毕业照不会化妆怎么办 照相照不到耳朵怎么办 申请户口期间结婚怎么办 老人户口投靠社保怎么办 房子户口没迁走怎么办 小孩是流动户口怎么办 离婚孩子上户口怎么办 夫妻离婚想孩子怎么办 有孩子不想离婚怎么办 前夫不给户口簿怎么办 大庆户口不迁走怎么办 爸妈要和我住怎么办 离婚后宝宝户口怎么办 离婚后再婚户口怎么办 大学修够学分怎么办 遇到叛逆的孩子怎么办 没有儿子的老人怎么办 失业就业登记证怎么办 我无故被开除怎么办 就业登记证过期怎么办 40岁下岗了怎么办 被直接领导压制怎么办 领导调换岗位该怎么办 单位领导硬压工作怎么办