texinfo-commits
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[no subject]


From: Patrice Dumas
Date: Thu, 4 Jan 2024 10:19:39 -0500 (EST)

branch: master
commit 8b8f24f89e7faabad058c01f33e22fd258511a50
Author: Patrice Dumas <pertusus@free.fr>
AuthorDate: Thu Jan 4 16:19:35 2024 +0100

    * tp/Texinfo/Convert/HTML.pm (_preformatted_class): fix prototype.
    
    * tp/Texinfo/Convert/HTML.pm (_convert_preformatted_type): rearrange
    code.
    
    * tp/Texinfo/XS/convert/convert_html.c (trim_trailing_content): add
    from convert_tab_command.
    
    * tp/Texinfo/XS/convert/convert_html.c (convert_paragraph_type):
    change code to use a TEXT and free memory in all the situations.
    
    * tp/Texinfo/XS/convert/convert_html.c (preformatted_class)
    (convert_preformatted_type, types_internal_conversion_table):
    add preformatted_class, implement convert_preformatted_type.
---
 ChangeLog                            |  17 +++
 tp/Texinfo/Convert/HTML.pm           |  16 +--
 tp/Texinfo/XS/convert/convert_html.c | 234 ++++++++++++++++++++++++++++++-----
 3 files changed, 228 insertions(+), 39 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 68cf583fb5..e70a041cde 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,20 @@
+2024-01-04  Patrice Dumas  <pertusus@free.fr>
+
+       * tp/Texinfo/Convert/HTML.pm (_preformatted_class): fix prototype.
+
+       * tp/Texinfo/Convert/HTML.pm (_convert_preformatted_type): rearrange
+       code.
+
+       * tp/Texinfo/XS/convert/convert_html.c (trim_trailing_content): add
+       from convert_tab_command.
+
+       * tp/Texinfo/XS/convert/convert_html.c (convert_paragraph_type):
+       change code to use a TEXT and free memory in all the situations.
+
+       * tp/Texinfo/XS/convert/convert_html.c (preformatted_class)
+       (convert_preformatted_type, types_internal_conversion_table):
+       add preformatted_class, implement convert_preformatted_type.
+
 2024-01-04  Patrice Dumas  <pertusus@free.fr>
 
        * tp/Texinfo/XS/convert/convert_html.c (convert_paragraph_type),
diff --git a/tp/Texinfo/Convert/HTML.pm b/tp/Texinfo/Convert/HTML.pm
index 376f5bf61f..860b4b3410 100644
--- a/tp/Texinfo/Convert/HTML.pm
+++ b/tp/Texinfo/Convert/HTML.pm
@@ -6828,7 +6828,7 @@ $default_types_open{'paragraph'} = 
\&_open_inline_container_type;
 $default_types_open{'preformatted'} = \&_open_inline_container_type;
 
 
-sub _preformatted_class()
+sub _preformatted_class($)
 {
   my $self = shift;
   my $pre_class;
@@ -6857,13 +6857,16 @@ sub _convert_preformatted_type($$$$)
 
   return '' if ($content eq '');
 
-  my $pre_class = $self->_preformatted_class();
-
   if (top_block_command($self) eq 'multitable') {
     $content =~ s/^\s*//;
     $content =~ s/\s*$//;
   }
 
+  if (in_string($self)) {
+    return $content;
+  }
+
+  my $pre_class;
   # menu_entry_description is always in a preformatted container
   # in the tree, as the whole menu is meant to be an
   # environment where spaces and newlines are preserved.
@@ -6881,10 +6884,9 @@ sub _convert_preformatted_type($$$$)
     }
   }
 
-  if (in_string($self)) {
-    return $content;
-  }
   $content =~ s/^\n/\n\n/; # a newline immediately after a <pre> is ignored.
+
+  $pre_class = _preformatted_class($self) if (!defined($pre_class));
   my $result = $self->html_attribute_class('pre', [$pre_class]).'>'
                                                    . $content . '</pre>';
 
@@ -7286,7 +7288,7 @@ sub _convert_menu_entry_type($$$)
     }
 
     if (not $in_string) {
-      my $pre_class = $self->_preformatted_class();
+      my $pre_class = _preformatted_class($self);
       $result_name_node = $self->html_attribute_class('pre', [$pre_class]).'>'
                                                . $result_name_node . '</pre>';
     }
diff --git a/tp/Texinfo/XS/convert/convert_html.c 
b/tp/Texinfo/XS/convert/convert_html.c
index c82fd3a3d4..0a89cf8924 100644
--- a/tp/Texinfo/XS/convert/convert_html.c
+++ b/tp/Texinfo/XS/convert/convert_html.c
@@ -10966,6 +10966,27 @@ convert_item_command (CONVERTER *self, const enum 
command_id cmd,
     }
 }
 
+static char *
+trim_trailing_content (const char *content)
+{
+  char *trimmed_content = strdup (content);
+  size_t str_len = strlen (trimmed_content);
+  if (str_len > 0)
+    {
+      char *q = trimmed_content + str_len - 1;
+      while (q > trimmed_content)
+        {
+          if (!strchr (whitespace_chars, *q))
+            {
+              break;
+            }
+          q--;
+        }
+      *(q +1) = '\0';
+    }
+  return trimmed_content;
+}
+
 void
 convert_tab_command (CONVERTER *self, const enum command_id cmd,
                     const ELEMENT *element,
@@ -10983,23 +11004,8 @@ convert_tab_command (CONVERTER *self, const enum 
command_id cmd,
   if (content)
     {
       const char *p = content;
-      size_t str_len;
       p += strspn (p, whitespace_chars);
-      trimmed_content = strdup (p);
-      str_len = strlen (trimmed_content);
-      if (str_len > 0)
-        {
-          char *q = trimmed_content + str_len - 1;
-          while (q > trimmed_content)
-            {
-              if (!strchr (whitespace_chars, *q))
-                {
-                  break;
-                }
-              q--;
-            }
-          *(q +1) = '\0';
-        }
+      trimmed_content = trim_trailing_content (p);
     }
   else
     trimmed_content = strdup ("");
@@ -12720,10 +12726,27 @@ convert_paragraph_type (CONVERTER *self, const enum 
element_type type,
                        const ELEMENT *element, const char *content,
                        TEXT *result)
 {
+  TEXT content_text;
   enum command_id align_cmd;
   char *associated_content
    = html_get_associated_formatted_inline_content (self, element, 0);
 
+  text_init (&content_text);
+
+  if (associated_content)
+    {
+      text_append (&content_text, associated_content);
+      free (associated_content);
+    }
+  if (content)
+    text_append (&content_text, content);
+
+  if (content_text.end <= 0)
+    {
+      free (content_text.text);
+      return;
+    }
+
   if (html_paragraph_number (self) == 1)
     {
       enum command_id in_format_cmd = html_top_block_command (self);
@@ -12737,10 +12760,8 @@ convert_paragraph_type (CONVERTER *self, const enum 
element_type type,
              there are no paragraphs, but preformatted */
               || in_format_cmd == CM_menu)
             {
-              if (associated_content)
-                text_append (result, associated_content);
-              if (content)
-                text_append (result, content);
+              text_append (result, content_text.text);
+              free (content_text.text);
               return;
             }
         }
@@ -12748,18 +12769,16 @@ convert_paragraph_type (CONVERTER *self, const enum 
element_type type,
 
   if (html_in_string (self))
     {
-      if (associated_content)
-        text_append (result, associated_content);
-      if (content)
-        text_append (result, content);
+      text_append (result, content_text.text);
+      free (content_text.text);
       return;
     }
 
-  if ((!content || content[strspn (content, whitespace_chars)] == '\0')
-      && (!associated_content
-          || associated_content[strspn
-                     (associated_content, whitespace_chars)] == '\0'))
-    return;
+  if (content_text.text[strspn (content_text.text, whitespace_chars)] == '\0')
+    {
+      free (content_text.text);
+      return;
+    }
 
   align_cmd = html_in_align (self);
 
@@ -12783,12 +12802,162 @@ convert_paragraph_type (CONVERTER *self, const enum 
element_type type,
   else
     text_append_n (result, "<p>", 3);
 
+  text_append (result, content_text.text);
+  free (content_text.text);
+
+  text_append_n (result, "</p>", 4);
+}
+
+static char *
+preformatted_class (CONVERTER *self)
+{
+  COMMAND_OR_TYPE *cur_pre_class = 0;
+  COMMAND_OR_TYPE_STACK *pre_classes
+        = html_preformatted_classes_stack (self);
+  size_t i;
+  for (i = 0; i < pre_classes->top; i++)
+    {
+      COMMAND_OR_TYPE *cmd_or_type = &pre_classes->stack[i];
+      if (!(cur_pre_class
+            && (cur_pre_class->variety == CTV_type_command
+                && builtin_command_data[cur_pre_class->cmd].flags
+                                   & CF_preformatted_code)
+            && (!((cmd_or_type->variety == CTV_type_command
+                   && builtin_command_data[cmd_or_type->cmd].flags
+                                     & CF_preformatted_code)
+                  || cmd_or_type->cmd == CM_menu))))
+         cur_pre_class = cmd_or_type;
+    }
+  if (cur_pre_class)
+    {
+      char *pre_class = 0;
+      if (cur_pre_class->variety == CTV_type_command)
+        {
+          xasprintf (&pre_class, "%s-preformatted",
+                     builtin_command_name (cur_pre_class->cmd));
+        }
+      else if (cur_pre_class->variety == CTV_type_type)
+
+        {
+          xasprintf (&pre_class, "%s-preformatted",
+                     self->pre_class_types[cur_pre_class->type]);
+        }
+      if (pre_class)
+        return pre_class;
+    }
+  /* shold not happen */
+  return 0;
+}
+
+void
+convert_preformatted_type (CONVERTER *self, const enum element_type type,
+                       const ELEMENT *element, const char *content,
+                       TEXT *result)
+{
+  TEXT content_text;
+  char *trimmed_content;
+  enum command_id in_format_cmd;
+  char *pre_class = 0;
+  int in_def = 0;
+  char *attribute_class;
+  STRING_LIST *classes;
+
+  char *associated_content
+   = html_get_associated_formatted_inline_content (self, element, 0);
+
+  text_init (&content_text);
+
   if (associated_content)
-    text_append (result, associated_content);
+    {
+      text_append (&content_text, associated_content);
+      free (associated_content);
+    }
   if (content)
-    text_append (result, content);
+    text_append (&content_text, content);
 
-  text_append_n (result, "</p>", 4);
+  if (content_text.end <= 0)
+    {
+      free (content_text.text);
+      return;
+    }
+
+  in_format_cmd = html_top_block_command (self);
+  if (in_format_cmd == CM_multitable)
+    {
+      const char *p = content_text.text;
+      p += strspn (p, whitespace_chars);
+      trimmed_content = trim_trailing_content (p);
+      free (content_text.text);
+    }
+  else
+    trimmed_content = content_text.text;
+
+  if (html_in_string (self))
+    {
+      text_append (result, trimmed_content);
+      free (trimmed_content);
+      return;
+    }
+
+  /* menu_entry_description is always in a preformatted container
+     in the tree, as the whole menu is meant to be an
+     environment where spaces and newlines are preserved. */
+  if (element->parent && element->parent->type == ET_menu_entry_description)
+    {
+      if (!html_inside_preformatted (self))
+        {
+ /* If not in preformatted block command,
+    we don't preserve spaces and newlines in menu_entry_description,
+    instead the whole menu_entry is in a table, so no <pre> in that situation
+  */
+          text_append (result, trimmed_content);
+          free (trimmed_content);
+          return;
+        }
+      else
+        {
+     /* if directly in description, we want to avoid the linebreak that
+        comes with pre being a block level element, so set a special class */
+          pre_class = strdup ("menu-entry-description-preformatted");
+        }
+    }
+
+  if (!pre_class)
+    pre_class = preformatted_class (self);
+
+  /* this may happen with lines without textual content
+     between a def* and def*x. */
+  if (element->parent
+      && (builtin_command_data[element->parent->cmd].flags & CF_def
+          || element->parent->cmd == CM_defblock))
+    {
+      in_def = 1;
+      text_append_n (result, "<dd>", 4);
+    }
+
+  classes = (STRING_LIST *) malloc (sizeof (STRING_LIST));
+  memset (classes, 0, sizeof (STRING_LIST));
+  if (pre_class)
+    {
+      add_string (pre_class, classes);
+      free (pre_class);
+    }
+  attribute_class = html_attribute_class (self, "pre", classes);
+  text_append (result, attribute_class);
+  text_append_n (result, ">", 1);
+  free (attribute_class);
+  destroy_strings_list (classes);
+
+  /* a newline immediately after a <pre> is ignored. */
+  if (trimmed_content[0] == '\n')
+    text_append_n (result, "\n", 1);
+  text_append (result, trimmed_content);
+  free (trimmed_content);
+
+  text_append_n (result, "</pre>", 6);
+
+  if (in_def)
+    text_append_n (result, "</dd>", 5);
 }
 
 #define static_class(name, class) \
@@ -13205,6 +13374,7 @@ convert_row_type (CONVERTER *self, const enum 
element_type type,
 static TYPE_INTERNAL_CONVERSION types_internal_conversion_table[] = {
   {ET_def_line, &convert_def_line_type},
   {ET_paragraph, &convert_paragraph_type},
+  {ET_preformatted, &convert_preformatted_type},
   {ET_row, &convert_row_type},
   {ET_table_term, &convert_table_term_type},
   {ET_text, &convert_text},



reply via email to

[Prev in Thread] Current Thread [Next in Thread]