⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dw_page.c

📁 嵌入式浏览器Dillo源码
💻 C
📖 第 1 页 / 共 4 页
字号:
   Dw_page_get_word_extremes (word, &word_extremes);   last_space = (word_ind > 0) ? page->words[word_ind - 1].orig_space : 0;   if (word->content_type == DW_PAGE_CONTENT_BREAK)      last_line->break_space = MAX (word->content.break_space,                                    last_line->break_space);   page->last_line_width += word->size.width;   if (!new_line)      page->last_line_width += last_space;   last_line->par_max += word_extremes.max_width;   if (!new_par)      last_line->par_max += last_space;   if (word->style->nowrap)      last_line->par_min += word_extremes.min_width;   else      last_line->max_word_min =         MAX (last_line->max_word_min, word_extremes.min_width);   /* Finally, justify the line. Breaks are ignored, since the HTML    * parser sometimes assignes the wrong style to them. (todo: ) */   if (word->content_type != DW_PAGE_CONTENT_BREAK) {      switch (word->style->text_align) {      case DW_STYLE_TEXT_ALIGN_LEFT:      case DW_STYLE_TEXT_ALIGN_JUSTIFY:  /* see some lines above */      case DW_STYLE_TEXT_ALIGN_STRING:   /* handled elsewhere (in future) */         left_offset = 0;         break;      case DW_STYLE_TEXT_ALIGN_RIGHT:         left_offset = avail_width - page->last_line_width;         break;      case DW_STYLE_TEXT_ALIGN_CENTER:         left_offset = (avail_width - page->last_line_width) / 2;         break;      default:         /* compiler happiness */         left_offset = 0;      }      /* For large lines (images etc), which do not fit into the viewport: */      if (left_offset < 0)         left_offset = 0;      if (page->list_item && last_line == page->lines) {         /* List item markers are always on the left. */         last_line->left_offset = 0;         page->words[0].eff_space = page->words[0].orig_space + left_offset;      } else         last_line->left_offset = left_offset;   }   page->must_queue_resize = TRUE;}/* * Calculate the size of a widget within the page. * (Subject of change in the near future!) */static void Dw_page_calc_widget_size (DwPage *page,                                      DwWidget *widget,                                      DwRequisition *size){   DwRequisition requisition;   gint32 avail_width, avail_ascent, avail_descent;   avail_width =      page->avail_width - p_Dw_style_box_diff_width(DW_WIDGET(page)->style);   avail_ascent =      page->avail_ascent - p_Dw_style_box_diff_height(DW_WIDGET(page)->style);   avail_descent = page->avail_descent;   if (DW_WIDGET_USES_HINTS (widget)) {      a_Dw_widget_set_width (widget, avail_width);      a_Dw_widget_set_ascent (widget, avail_ascent);      a_Dw_widget_set_descent (widget, avail_descent);      a_Dw_widget_size_request (widget, size);   } else {      if (widget->style->width == DW_STYLE_UNDEF_LENGTH ||          widget->style->height == DW_STYLE_UNDEF_LENGTH)         a_Dw_widget_size_request (widget, &requisition);      if (widget->style->width == DW_STYLE_UNDEF_LENGTH)         size->width = requisition.width;      else if (DW_STYLE_IS_LENGTH (widget->style->width))         size->width =            DW_STYLE_GET_LENGTH (widget->style->width, widget->style->font)            + p_Dw_style_box_diff_width (widget->style);      else         size->width =            DW_STYLE_GET_PERCENTAGE (widget->style->width) *  avail_width;      if (widget->style->height == DW_STYLE_UNDEF_LENGTH) {         size->ascent = requisition.ascent;         size->descent = requisition.descent;      } else if (DW_STYLE_IS_LENGTH (widget->style->width)) {         size->ascent =            DW_STYLE_GET_LENGTH (widget->style->height, widget->style->font)            + p_Dw_style_box_diff_height (widget->style);         size->descent = 0;      } else {         size->ascent =            DW_STYLE_GET_PERCENTAGE (widget->style->height) * avail_ascent;         size->descent =            DW_STYLE_GET_PERCENTAGE (widget->style->height) * avail_descent;      }   }}/* * Rewrap the page from the line from which this is necessary. * There are basically two times we'll want to do this: * either when the viewport is resized, or when the size changes on one * of the child widgets. */static void Dw_page_rewrap(DwPage *page){   DwWidget *widget;   gint word_index;   DwPageWord *word;   if (page->wrap_ref == -1)      return;   widget = DW_WIDGET (page);   page->num_lines = page->wrap_ref;   page->last_line_width = 0;   if (page->num_lines > 0)      word_index = page->lines[page->num_lines - 1].first_word;   else      word_index = 0;   for (; word_index < page->num_words; word_index++) {      word = &page->words[word_index];      if (word->content_type == DW_PAGE_CONTENT_WIDGET)         Dw_page_calc_widget_size (page, word->content.widget, &word->size);      Dw_page_word_wrap(page, word_index);      if (word->content_type == DW_PAGE_CONTENT_WIDGET)         word->content.widget->parent_ref = page->num_lines - 1;      if ( word->content_type == DW_PAGE_CONTENT_ANCHOR ) {         p_Dw_widget_set_anchor(widget, word->content.anchor,                                page->lines[page->num_lines - 1].top);      }   }}/* * Paint a line * - x and y are toplevel dw coordinates (Question: what Dw? Changed. Test!) * - area is used always (ev. set it to event->area) * - event is only used when is_expose */static void Dw_page_draw_line (DwPage *page,                               DwPageLine *line,                               DwRectangle *area,                               GdkEventExpose *event){   DwWidget *widget;   DwPageWord *word;   gint word_index;   gint x_cursor, y_cursor;   gint diff;   DwWidget *child;   DwRectangle child_area;   GdkWindow *window;   /* Here's an idea on how to optimize this routine to minimize the number    * of calls to gdk_draw_string:    *    * Copy the text from the words into a buffer, adding a new word    * only if: the attributes match, and the spacing is either zero or    * equal to the width of ' '. In the latter case, copy a " " into    * the buffer. Then draw the buffer. */   widget = DW_WIDGET (page);   window = DW_WIDGET_WINDOW (widget);   x_cursor =      p_Dw_widget_x_world_to_viewport (widget,                                       widget->allocation.x +                                       Dw_page_line_total_x_offset(page,line));   y_cursor =      p_Dw_widget_y_world_to_viewport (widget,                                       widget->allocation.y                                       + line->top + line->ascent);   for (word_index = line->first_word; word_index < line->last_word;        word_index++) {      word = &page->words[word_index];      diff = 0;      switch (word->content_type) {      case DW_PAGE_CONTENT_TEXT:         /* Adjust the text baseline if the word is <SUP>-ed or <SUB>-ed */         if (word->style->SubSup == TEXT_SUB)            diff = word->size.ascent / 2;         else if (word->style->SubSup == TEXT_SUP)            diff -= word->size.ascent / 3;         gdk_draw_string(window,                         word->style->font->font,                         word->style->color->gc,                         x_cursor,                         y_cursor + diff,                         word->content.text);         /* underline */         if (word->style->uline)            gdk_draw_line(window,                          word->style->color->gc,                          x_cursor,                          y_cursor + 1 + diff,                          x_cursor + word->size.width - 1,                          y_cursor + 1 + diff);         if (word_index + 1 < line->last_word && word->space_style->uline)            gdk_draw_line(window,                          word->style->color->gc,                          x_cursor + word->size.width,                          y_cursor + 1 + diff,                          x_cursor + word->size.width + word->eff_space - 1,                          y_cursor + 1 + diff);         /* strike-through */         if (word->style->strike)            gdk_draw_line(window,                          word->style->color->gc,                          x_cursor,                          y_cursor - word->size.ascent / 2 + diff,                          x_cursor + word->size.width - 1,                          y_cursor - word->size.ascent / 2 + diff);         if (word_index + 1 < line->last_word && word->space_style->strike)            gdk_draw_line(window,                          word->style->color->gc,                          x_cursor + word->size.width,                          y_cursor - word->size.ascent / 2 + diff,                          x_cursor + word->size.width + word->eff_space - 1,                          y_cursor - word->size.ascent / 2 + diff);         break;      case DW_PAGE_CONTENT_WIDGET:         child = word->content.widget;         if (p_Dw_widget_intersect (child, area, &child_area))            a_Dw_widget_draw (child, &child_area, event);         break;      case DW_PAGE_CONTENT_ANCHOR: case DW_PAGE_CONTENT_BREAK:         /* nothing - an anchor/break isn't seen */         /* BUG: sometimes anchors have x_space;          * we subtract that just in case --EG */         x_cursor -= word->size.width + word->eff_space;#if 0         /* Useful for testing: draw breaks. */         if (word->content_type == DW_PAGE_CONTENT_BREAK)            gdk_draw_rectangle (window, word->style->color->gc, TRUE,                                Dw_widget_x_world_to_viewport(widget,                                   widget->allocation.x +                                      Dw_page_line_total_x_offset(page, line)),                                y_cursor + line->descent,                                widget->allocation.width -                                   Dw_style_box_diff_width(widget->style),                                word->content.break_space);#endif         break;      default:         g_warning ("BUG!!! at (%d, %d).", x_cursor, y_cursor + diff);         break;      }      x_cursor += word->size.width + word->eff_space;   }}/* * Find the first line index that includes y, relative to top of widget. */static gint Dw_page_find_line_index(DwPage *page, gint y){   gint max_index = page->num_lines - 1;   gint step, index, low = 0;   step = (page->num_lines+1) >> 1;   while ( step > 1 ) {      index = low + step;      if (index <= max_index && page->lines[index].top < y)         low = index;      step = (step + 1) >> 1;   }   if (low < max_index && page->lines[low+1].top < y)      low++;   /*    * This new routine returns the line number between (top) and    * (top + size.ascent + size.descent + break_space): the space    * _below_ the line is considered part of the line.  Old routine    * returned line number between (top - previous_line->break_space)    * and (top + size.ascent + size.descent): the space _above_ the    * line was considered part of the line.  This is important for    * Dw_page_find_link() --EG    */   return low;}/* * Draw the actual lines, starting at (x, y) in toplevel Dw coords. * (former Dw_page_expose_lines) */static void Dw_page_draw (DwWidget *widget,                          DwRectangle *area,                          GdkEventExpose *event){   DwPage *page;   gint line_index;   DwPageLine *line;   p_Dw_widget_draw_widget_box (widget, area);   page = DW_PAGE (widget);   line_index = Dw_page_find_line_index(page, area->y);   for (; line_index < page->num_lines; line_index++) {      line = &(page->lines[line_index]);      if (line->top >= area->y + area->height)         break;      Dw_page_draw_line (page, line, area, event);   }}/* * Find a link given a coordinate location relative to the window */static gint Dw_page_find_link(DwPage *page, gint x, gint y){   gint line_index, word_index;   gint x_cursor, last_x_cursor;   DwPageLine *line;   DwPageWord *word;   if ( (line_index = Dw_page_find_line_index(page, y)) >= page->num_lines )      return -1;   line = &page->lines[line_index];   if (line->top + line->ascent + line->descent <= y)      return -1;   x_cursor = Dw_page_line_total_x_offset(page, line);   for (word_index = line->first_word; word_index < line->last_word;        word_index++) {      word = &page->words[word_index];      last_x_cursor = x_cursor;      x_cursor += word->size.width + word->eff_space;      if (last_x_cursor <= x && x_cursor > x)         return word->style->link;   }   return -1;}/* * Standard Dw function. */static gint Dw_page_button_press  (DwWidget *widget,                                   gint32 x,                                   gint32 y,                                   GdkEventButton *event){   DwPage *page = DW_PAGE (widget);#ifdef VERBOSE   g_print("Dw_page_button_press: button (%d, %d) +%d\n",           x, y, button->button);#endif   page->link_pressed = Dw_page_find_link(page, x, y);   if (page->link_pressed >= 0) {      gtk_signal_emit (GTK_OBJECT (widget), page_signals[LINK_PRESSED],                       page->link_pressed, -1, -1, event);      return TRUE;   } else      return FALSE;}/* * Standard Dw function. */static gint Dw_page_button_release(DwWidget *widget,                                   gint32 x,

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -