[英]text of a nested bullet-point list to HTML
我有这个:输入示例:
* First item
* Second item
* Subitem 1
* sub-subitem!
* Subitem 3
* Third item
输出示例:
<ul>
<li>First item</li>
<li>Second item
<ul>
<li>Subitem 1
<ul>
<li>sub-subitem!</li>
</ul>
</li>
<li>Subitem 3</li>
</ul>
</li>
<li>Third item</li>
</ul>
我创建了一个Java类,该类将每个String行发送到一个char数组,并且我单独对待每个字符。 我的问题是何时关闭标签?
这是我的代码:
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
public class TextToHtml {
StringBuilder itemName = new StringBuilder();
String sCurrentLine;
int usingUlTAG=0;
public TextToHtml(){
BufferedReader br = null;
try {
boolean closeLItag=false;
br = new BufferedReader(new FileReader("NestedText.txt"));
System.out.println("<ul>");
while ((sCurrentLine = br.readLine()) != null) {
char[] item = sCurrentLine.toCharArray();
for(int i=0; i<item.length;i++){
if(item[i]!='*' && item[i]!='\n' && item[i]!='\t'){
itemName.append(item[i]);
continue;
}
if(item[i]=='*'){
itemName.append("<li>");
closeLItag=true;
}
else if(item[i]=='\t'){
if(item[i+1]=='*'){
if(usingUlTAG<1)
itemName.append("\t<ul>\n\t\t");
itemName.append("\t\n\t\t");
usingUlTAG= 1;
continue;
}
if(item[i+1]=='\t'){
itemName.append("\t\t<ul>\n\n\t\t");
usingUlTAG=2;
continue;
}
}
}
if(closeLItag){
itemName.append("</li>\n");
}
}
System.out.println(itemName+"/ul>");
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (br != null)br.close();
} catch (IOException ex) {
ex.printStackTrace();
}
}
}
public static void main(String[] args) {
new TextToHtml();
}
}
您必须先查看下一行,然后查看其列表级别是否与当前项目的列表级别不同。 然后,您可以根据级别差异(如果有)添加或关闭标签。 这是执行此操作的代码:
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
public class TextToHtml
{
StringBuilder itemName = new StringBuilder();
String sCurrentLine;
String sNextLine; // A "peek" at what's next to determine if </li> is needed
public TextToHtml()
{
BufferedReader br = null;
try
{
br = new BufferedReader(new FileReader("NestedText.txt"));
System.out.println("<ul>");
sNextLine = br.readLine();
while ((sCurrentLine = sNextLine) != null)
{
sNextLine = br.readLine();
char[] item = sCurrentLine.toCharArray();
int itemLevel = 0;
for (int i = 0; i < item.length; i++)
{
if (item[i] != '*' && item[i] != '\n' && item[i] != '\t')
{
itemName.append(item[i]);
}
else if (item[i] == '*')
{
itemName.append("\t<li>");
// Trim leading space character
if (item[i + 1] == ' ')
i++;
}
else if (item[i] == '\t')
{
itemLevel++;
itemName.append("\t\t");
}
}
int nextItemLevel = 0;
if (sNextLine != null)
{
char[] nextItem = sNextLine.toCharArray();
for (int i = 0; i < nextItem.length; i++)
{
if (nextItem[i] == '\t')
nextItemLevel++;
else
break;
}
}
// Next is the same level; there are no subitems
if (itemLevel == nextItemLevel)
itemName.append("</li>");
// Next is a deeper level; there are subitems
else if (itemLevel < nextItemLevel)
{
// In case the next item is more than 1 level deeper
for (int i = itemLevel + 1; i <= nextItemLevel; i++)
{
itemName.append("\n");
for (int j = 0; j < i; j++)
itemName.append("\t\t");
itemName.append("<ul>");
// If the next item's level is reached, it will create its own <li>
if (i != nextItemLevel)
{
itemName.append("\n");
for (int j = 0; j < i; j++)
itemName.append("\t\t");
itemName.append("\t<li>");
}
}
}
// Next is a higher level; there are tags to close
else // (itemLevel > nextItemLevel)
{
itemName.append("</li>");
for (int i = itemLevel - 1; i >= nextItemLevel; i--)
{
itemName.append("\n");
for (int j = 0; j <= i; j++)
itemName.append("\t\t");
itemName.append("</ul>\n");
for (int j = 0; j < i; j++)
itemName.append("\t\t");
itemName.append("\t</li>");
}
}
itemName.append("\n");
}
System.out.println(itemName + "</ul>");
}
catch (IOException e)
{
e.printStackTrace();
}
finally
{
try
{
if (br != null)
br.close();
}
catch (IOException ex)
{
ex.printStackTrace();
}
}
}
public static void main(String[] args)
{
new TextToHtml();
}
}
请注意,这仅在级别使用制表符而不是空格缩进时才有效。
如果,按照您当前的代码建议,如果原始文本中的列表项行都使用硬标签进行缩进,那么您要做的就是一次一行地处理文本,并跟踪缩进级别(标签数) 上一行。 这段代码不会在生成的HTML中产生好的缩进,但是它正确地嵌套了<ul>
和<li>
,这是HTML浏览器真正关心的所有问题
import java.io.*;
import java.util.regex.*;
public class Main {
public static void main(String[] args) throws Exception {
StringBuilder result = new StringBuilder();
BufferedReader br = new BufferedReader(new FileReader("NestedText.txt"));
try {
int lastIndent = -1; // indent level of last line
int depth = 0; // number of levels of <ul> we are currently inside
String line;
Pattern indentPattern = Pattern.compile("((\\t*)\\* )?(.*)");
while((line = br.readLine()) != null) {
Matcher m = indentPattern.matcher(line);
m.matches(); // guaranteed to be true, but needed to update matcher state
if(m.group(1) != null) { // this is a new list item
int thisIndent = m.end(2); // number of leading tabs, may be zero
// there are three possible cases
if(thisIndent == lastIndent) {
// same level as last list item
result.append("</li>");
} else if(thisIndent > lastIndent) {
// starting a child list
result.append("<ul>");
depth++;
} else {
// returning to parent list
result.append("</li>");
depth--;
result.append("</ul>");
result.append("</li>");
}
result.append("<li>");
lastIndent = thisIndent;
} else { // this is a continuation of the previous list item
result.append(" ");
}
// append this line's text (not including the indent and *)
result.append(m.group(3));
}
// run out of items, close any outstanding lists
while(depth-- > 0) {
result.append("</li>");
result.append("</ul>");
}
System.out.println(result);
} finally {
br.close();
}
}
}
在这里,我将任何以制表符和星号开头的行都不是前一个<li>
的延续,即
* This is a very long list
item that continues over several
lines
* This is a second item
* this is a child item
that also continues
over several lines
还可以
我已根据Jan Dvorak的建议解决了此问题。 以下代码适用于此,如果有帮助,我在下面说明。 感谢您的所有贡献
MarkdownProcessor m = new MarkdownProcessor();
String html = null;
try {
html = m.markdown(MyString));
} catch (IOException e) {
e.printStackTrace();
}
System.out.println(html);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.