table latex create
This commit is contained in:
@@ -2059,7 +2059,7 @@ class Production extends Base
|
|||||||
}elseif ($article_main_info['type']==1){//处理图片
|
}elseif ($article_main_info['type']==1){//处理图片
|
||||||
|
|
||||||
}else{//处理表格
|
}else{//处理表格
|
||||||
|
$fragContentList[] = $this->tableCovertLatex($article_main_info['amt_id'],$references);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//实际生成tex
|
//实际生成tex
|
||||||
@@ -2097,13 +2097,12 @@ class Production extends Base
|
|||||||
|
|
||||||
$content = str_replace("–","-",$content);
|
$content = str_replace("–","-",$content);
|
||||||
|
|
||||||
$content = $this->convertReferencesToLatex($content, $refArray);
|
|
||||||
|
|
||||||
// 步骤1:忽略并移除<tr>、</tr>和<nbsp/>标签
|
// 步骤1:忽略并移除<tr>、</tr>和<nbsp/>标签
|
||||||
$content = $this->removeIgnoredTags($content);
|
$content = $this->removeIgnoredTags($content);
|
||||||
|
|
||||||
// 步骤2:解析剩余标签并生成LaTeX内容
|
// 步骤2:解析剩余标签并生成LaTeX内容
|
||||||
$latexContent = $this->textRenderCreate($content);
|
$latexContent = $this->textRenderCreate($content,$refArray);
|
||||||
|
// $latexContent = $this->convertReferencesToLatex($content, $refArray);
|
||||||
|
|
||||||
return $latexContent;
|
return $latexContent;
|
||||||
}
|
}
|
||||||
@@ -2114,6 +2113,7 @@ class Production extends Base
|
|||||||
* @return string 处理后的内容
|
* @return string 处理后的内容
|
||||||
*/
|
*/
|
||||||
private function removeIgnoredTags($content) {
|
private function removeIgnoredTags($content) {
|
||||||
|
$content = html_entity_decode($content, ENT_QUOTES, 'UTF-8');
|
||||||
// 移除<tr>和</tr>(不区分大小写,处理可能的空格)
|
// 移除<tr>和</tr>(不区分大小写,处理可能的空格)
|
||||||
$content = preg_replace('/<\/?tr\s*>/i', '', $content);
|
$content = preg_replace('/<\/?tr\s*>/i', '', $content);
|
||||||
// 移除<nbsp/>
|
// 移除<nbsp/>
|
||||||
@@ -2126,8 +2126,50 @@ class Production extends Base
|
|||||||
* @param string $content 待解析的内容
|
* @param string $content 待解析的内容
|
||||||
* @return string 解析后的LaTeX内容
|
* @return string 解析后的LaTeX内容
|
||||||
*/
|
*/
|
||||||
private function textRenderCreate($content) {
|
private function textRenderCreate($content,$references) {
|
||||||
$latex = '';
|
$latex = '';
|
||||||
|
|
||||||
|
|
||||||
|
if (preg_match('/(?:<blue>)?\[(\d+(?:[-,]\d+)*)\](?:<\/blue>)?/', $content, $matches)) {
|
||||||
|
// 去除匹配中的 <blue> 和 </blue>
|
||||||
|
$cleanedMatch = str_replace(['<blue>', '</blue>'], '', $matches[0]);
|
||||||
|
// 提取引用编号部分(去掉方括号)
|
||||||
|
$referencePart = trim($cleanedMatch, '[]');
|
||||||
|
|
||||||
|
// 分割逗号分隔的不同引用项
|
||||||
|
$parts = explode(',', $referencePart);
|
||||||
|
$latexRefs = [];
|
||||||
|
|
||||||
|
foreach ($parts as $part) {
|
||||||
|
// 判断是否是范围形式如 3-5
|
||||||
|
if (strpos($part, '-') !== false) {
|
||||||
|
list($start, $end) = explode('-', $part);
|
||||||
|
$start = intval($start);
|
||||||
|
$end = intval($end);
|
||||||
|
|
||||||
|
// 展开范围并逐个查找 ref_id
|
||||||
|
for ($i = $start; $i <= $end; $i++) {
|
||||||
|
$arrayIndex = $i;
|
||||||
|
if (isset($references[$arrayIndex]) && !empty($references[$arrayIndex]['p_refer_id'])) {
|
||||||
|
$latexRefs[] = 'ref_' . $references[$arrayIndex]['p_refer_id'];
|
||||||
|
} else {
|
||||||
|
$latexRefs[] = $i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// 单个引用编号处理
|
||||||
|
$index = intval($part);
|
||||||
|
$arrayIndex = $index;
|
||||||
|
if (isset($references[$arrayIndex]) && !empty($references[$arrayIndex]['p_refer_id'])) {
|
||||||
|
$latexRefs[] = 'ref_' . $references[$arrayIndex]['p_refer_id'];
|
||||||
|
} else {
|
||||||
|
$latexRefs[] = $index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return '\parencite{' . implode(',', $latexRefs) . '}';
|
||||||
|
}
|
||||||
|
|
||||||
while (!empty($content)) {
|
while (!empty($content)) {
|
||||||
$nextTag = $this->determineNextTag($content);
|
$nextTag = $this->determineNextTag($content);
|
||||||
if ($nextTag === 'no') {
|
if ($nextTag === 'no') {
|
||||||
@@ -2407,14 +2449,14 @@ class Production extends Base
|
|||||||
*/
|
*/
|
||||||
private function escapeLatexSpecialChars($text) {
|
private function escapeLatexSpecialChars($text) {
|
||||||
$specialChars = [
|
$specialChars = [
|
||||||
// '\\' => '\\textbackslash',
|
'\\' => '\\textbackslash',
|
||||||
// '{' => '\\{',
|
'{' => '\\{',
|
||||||
// '}' => '\\}',
|
'}' => '\\}',
|
||||||
'$' => '\\$',
|
'$' => '\\$',
|
||||||
'%' => '\\%',
|
'%' => '\\%',
|
||||||
'#' => '\\#',
|
'#' => '\\#',
|
||||||
'&' => '\\&',
|
'&' => '\\&',
|
||||||
// '_' => '\\_',
|
'_' => '\\_',
|
||||||
'^' => '\\textasciicircum',
|
'^' => '\\textasciicircum',
|
||||||
'~' => '\\textasciitilde',
|
'~' => '\\textasciitilde',
|
||||||
];
|
];
|
||||||
@@ -3066,6 +3108,168 @@ class Production extends Base
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
public function myTableTest(){
|
||||||
|
$references = $this->production_article_refer_obj->where("p_article_id",3401)->where("state",0)->order("index asc")->select();
|
||||||
|
$res = $this->tableCovertLatex(1089,$references);
|
||||||
|
|
||||||
|
echo $res;
|
||||||
|
}
|
||||||
|
|
||||||
|
private function tableCovertLatex($amt_id, $references)
|
||||||
|
{
|
||||||
|
$table_info = $this->article_main_table_obj->where('amt_id', $amt_id)->find();
|
||||||
|
$tableData = json_decode($table_info['table_data'], true);
|
||||||
|
|
||||||
|
// 检查JSON解码是否成功
|
||||||
|
if (json_last_error() !== JSON_ERROR_NONE || !is_array($tableData) || empty($tableData)) {
|
||||||
|
return "% 无效的JSON数据";
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取表格最大列数(遍历所有行,找到列数最大值,处理合并后列数变化的情况)
|
||||||
|
$maxColCount = 0;
|
||||||
|
$str_list = [];
|
||||||
|
foreach ($tableData as $row) {
|
||||||
|
$colCount = 0;
|
||||||
|
foreach ($row as $cell) {
|
||||||
|
$colCount += $cell['colspan']; // 跨列会占用多个列位置
|
||||||
|
if($cell['colspan']==1){
|
||||||
|
$colIndex = $colCount; // 当前列的索引
|
||||||
|
|
||||||
|
// 计算当前单元格的字符数
|
||||||
|
$cellTextLength = strlen(strip_tags($cell['text'])); // 或者使用 mb_strlen($cell['text'], 'UTF-8') 来处理多字节字符
|
||||||
|
|
||||||
|
if(isset($str_list[$colIndex])){
|
||||||
|
$str_list[$colIndex] = max($cellTextLength, $str_list[$colIndex]);
|
||||||
|
} else {
|
||||||
|
$str_list[$colIndex] = $cellTextLength;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ($colCount > $maxColCount) {
|
||||||
|
$maxColCount = $colCount;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 根据 $str_list 计算列宽比例(比例范围:0.2-1)
|
||||||
|
$columnSpec = '';
|
||||||
|
if (!empty($str_list)) {
|
||||||
|
// 找到最大字符数,用于比例计算
|
||||||
|
$maxTextLength = max($str_list);
|
||||||
|
|
||||||
|
if ($maxTextLength > 0) {
|
||||||
|
// 为每一列计算相对宽度(比例范围:0.2-1)
|
||||||
|
for ($i = 1; $i <= $maxColCount; $i++) {
|
||||||
|
if (isset($str_list[$i]) && $str_list[$i] > 0) {
|
||||||
|
// 计算当前列的相对比例(0-1之间)
|
||||||
|
$relativeRatio = round($str_list[$i] / $maxTextLength, 1);
|
||||||
|
// 将比例调整到0.2-1范围内
|
||||||
|
$adjustedRatio = max(0.3, min(1, $relativeRatio));
|
||||||
|
// 转换为整数(乘以10便于处理小数)
|
||||||
|
// $widthValue = round($adjustedRatio * 10);
|
||||||
|
$columnSpec .= "X[$adjustedRatio] ";
|
||||||
|
} else {
|
||||||
|
// 如果某列没有数据,给一个默认最小宽度(对应0.2比例)
|
||||||
|
$columnSpec .= "X[0.3] "; // 0.2 * 10 = 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// 如果没有有效数据,使用平均分配
|
||||||
|
$columnSpec = str_repeat('X[1] ', $maxColCount);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// 如果 $str_list 为空,使用平均分配
|
||||||
|
$columnSpec = str_repeat('X[1] ', $maxColCount);
|
||||||
|
}
|
||||||
|
// 计算列宽比例(简单平均分配,可根据需要调整)
|
||||||
|
// $columnSpec = str_repeat('X[1] ', $maxColCount);
|
||||||
|
$columnSpec = rtrim($columnSpec);
|
||||||
|
|
||||||
|
// 整理title信息
|
||||||
|
$title = strip_tags($table_info['title']);
|
||||||
|
$label = "tab-".$table_info['amt_id'];
|
||||||
|
|
||||||
|
$notes = strip_tags($table_info['note']);
|
||||||
|
|
||||||
|
|
||||||
|
//确定是单栏还是双栏的表格
|
||||||
|
$oneRowString = 0;
|
||||||
|
foreach ($str_list as $v){
|
||||||
|
$oneRowString += $v;
|
||||||
|
}
|
||||||
|
$table_ss = $oneRowString < 50 ? "tmrtable" : "tmrtable*";
|
||||||
|
|
||||||
|
|
||||||
|
// 开始构建LaTeX代码
|
||||||
|
$latex = [];
|
||||||
|
$latex[] = "\\begin{".$table_ss."}{".$this->convertToLatex($title,$references)."}{".$label."}{".$columnSpec."}{1}{".$notes."}";
|
||||||
|
|
||||||
|
// 遍历表格数据,生成每一行
|
||||||
|
foreach ($tableData as $rowIndex => $row) {
|
||||||
|
$cells = [];
|
||||||
|
$currentCol = 0; // 记录当前处理到的列位置
|
||||||
|
|
||||||
|
// 处理当前行的每个单元格
|
||||||
|
foreach ($row as $cell) {
|
||||||
|
// 处理单元格文本:移除HTML标签,替换为LaTeX粗体
|
||||||
|
$text = $this->convertToLatex($cell['text'], $references);
|
||||||
|
|
||||||
|
// 处理合并单元格:跨列(colspan)和跨行(rowspan)
|
||||||
|
$colspan = $cell['colspan'] ?? 1;
|
||||||
|
$rowspan = $cell['rowspan'] ?? 1;
|
||||||
|
|
||||||
|
$cellContent = $text;
|
||||||
|
|
||||||
|
// 处理跨列(使用tabularray的c选项,跨多列)
|
||||||
|
if ($colspan > 1 && $rowspan > 1) {
|
||||||
|
// 跨行跨列
|
||||||
|
$cellContent = "\\SetCell[c={$colspan},r={$rowspan}]{l,bg=white} {$cellContent}";
|
||||||
|
} elseif ($colspan > 1) {
|
||||||
|
// 仅跨列
|
||||||
|
$cellContent = "\\SetCell[c={$colspan}]{l,bg=white} {$cellContent}";
|
||||||
|
} elseif ($rowspan > 1) {
|
||||||
|
// 仅跨行
|
||||||
|
$cellContent = "\\SetCell[r={$rowspan}]{l,bg=white} {$cellContent}";
|
||||||
|
}
|
||||||
|
|
||||||
|
$cells[] = $cellContent;
|
||||||
|
|
||||||
|
// 如果是跨列单元格,跳过后续的colspan-1个位置
|
||||||
|
$currentCol += $colspan;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 拼接单元格,行尾用\\
|
||||||
|
$rowContent = implode(' & ', $cells) . " \\\\";
|
||||||
|
$latex[] = " {$rowContent}";
|
||||||
|
}
|
||||||
|
|
||||||
|
$latex[] = "\\end{".$table_ss."}";
|
||||||
|
|
||||||
|
// 拼接所有行,返回LaTeX代码
|
||||||
|
return implode("\n", $latex);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
function extractPureTitle(string $title): string
|
||||||
|
{
|
||||||
|
// 正则表达式说明:
|
||||||
|
// ^Table\s+ :匹配以Table开头(不区分大小写),后跟一个或多个空格
|
||||||
|
// [\d.]+ :匹配一个或多个数字或小数点(支持1、1.2、2.3.4等编号)
|
||||||
|
// \s* :匹配零个或多个空格(处理编号后的空格)
|
||||||
|
// i :不区分大小写匹配
|
||||||
|
$pattern = '/^Table\s+[\d.]+\s*/i';
|
||||||
|
|
||||||
|
// 替换匹配的前缀为空字符串
|
||||||
|
$pureTitle = preg_replace($pattern, '', $title);
|
||||||
|
|
||||||
|
// 去除首尾多余的空格(处理边界情况)
|
||||||
|
return trim($pureTitle);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
private function authorFormate($p_article_id)
|
private function authorFormate($p_article_id)
|
||||||
{
|
{
|
||||||
// $authors = $this->article_author_obj->where('article_id', $article_id)->where('state', 0)->select();
|
// $authors = $this->article_author_obj->where('article_id', $article_id)->where('state', 0)->select();
|
||||||
|
|||||||
Reference in New Issue
Block a user