5
$\begingroup$
ExportString[Grid[{{a, b}}], "HTMLFragment"]
"<table><tbody>
     <tr><td>a</td><td>b</td></tr>
 </tbody></table>" 

This is what I expect, but what if I want to convert Grid[{ {c[b, 1], 1} }] and I want an expression with head c to be exported with custom rule, like:

c[x_,y___] :> StringJoin["<div>",ToString[x], "</div>"]

So for

ExportString[Grid[{{c[d, 1], b}}], "HTMLFragment"]

I'd get:

"<table><tbody>
     <tr><td> <div>d</div> </td> <td> b </td></tr>
 </tbody></table>"

or for:

a[ Grid[{ {c[b, 1], 1} }], 1 ]
"<div>
    <table><tbody>
       <tr>
          <td> <div>b</div> </td> 
          <td> 1 </td>
       </tr>
    </tbody></table>
 </div>"

Solution returning XMLElement structure is ok too.

I know I can create a parser and convert everything from top to down but then I have to rewrite rules for things that could've been translated automatically.

Is there simpler approach?


Key words: Export HTML HTMLFragment conversion XML XMLElement tag tags

$\endgroup$
  • $\begingroup$ Why don't you just ExportString[expr /. rules, "HTMLFragment"]? $\endgroup$ – C. E. Jan 6 '16 at 8:37
  • 1
    $\begingroup$ @Pickett because it will fail for more complex examples: a[ Grid[{ {a[b, 1], 1} }], 1 ]. This should return div - table.../table - /div. $\endgroup$ – Kuba Jan 6 '16 at 8:40
  • $\begingroup$ @Pickett there is something like "XMLTransformationFunction" but it works only for things that are already translated to some tags. $\endgroup$ – Kuba Jan 6 '16 at 9:00
  • $\begingroup$ yes, this is a tricky question. +1 $\endgroup$ – C. E. Jan 6 '16 at 9:19
2
$\begingroup$

Here's what I've cooked up. Feedback appreciated.

exportWithRules[expr_,rules_]:=Module[{xMLElement,pre,convert},

    convert[s_]:=ExportString[s,"HTMLFragment"];

        (*applying custom rules*)
    pre = ReplaceRepeated[expr,rules];

        (*introducing temporary head to avoid recursion in 
          the evaluation of next XMLElement's conversion*)
    pre = pre /. XMLElement -> xMLElement;

    xMLElement[tag_,opt_, {content___}]:=convert @ XMLElement[ 
        tag, opt, convert /@ {content}
    ];

    convert @ pre
];

exportWithRules[
   c[ Grid[ {{c[b, 1], 1}} ], 1]
   ,
   c[x_, y___] :> XMLElement["div", {}, {x}]
   }
]
 "<div><table><tbody><tr><td><div>b</div></td><td>1</td></tr></tbody></table></div>" 

If one need's indenting:

ExportString[
 ImportString[%, "XML"],
 "XML",
 "ElementFormatting" -> Automatic
 ]

.

 <div>
 <table>
  <tbody>
   <tr>
    <td>
     <div>b</div>
    </td>
    <td>1</td>
   </tr>
  </tbody>
 </table>
</div>
$\endgroup$
  • $\begingroup$ This works, well done! $\endgroup$ – C. E. Jan 6 '16 at 13:09
  • $\begingroup$ @Pickett Thanks, it's far from being the fastest way but at least it is short. $\endgroup$ – Kuba Jan 6 '16 at 13:12

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.