code layout
This commit is contained in:
		@@ -479,29 +479,63 @@ body {
 | 
			
		||||
    color: #656d76;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* Molokai-inspired code blocks */
 | 
			
		||||
.article-body pre {
 | 
			
		||||
    background: #f6f8fa;
 | 
			
		||||
    border: 1px solid #d1d9e0;
 | 
			
		||||
    border-radius: 6px;
 | 
			
		||||
    padding: 16px;
 | 
			
		||||
    overflow-x: auto;
 | 
			
		||||
    background: #1B1D1E;
 | 
			
		||||
    border: 1px solid #3E3D32;
 | 
			
		||||
    border-radius: 8px;
 | 
			
		||||
    padding: 0;
 | 
			
		||||
    overflow: hidden;
 | 
			
		||||
    margin: 16px 0;
 | 
			
		||||
    font-size: 14px;
 | 
			
		||||
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.3);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.article-body code {
 | 
			
		||||
    background: #f6f8fa;
 | 
			
		||||
    padding: 2px 4px;
 | 
			
		||||
    border-radius: 4px;
 | 
			
		||||
/* Code filename header */
 | 
			
		||||
.article-body pre[data-filename]::before {
 | 
			
		||||
    content: attr(data-filename);
 | 
			
		||||
    display: block;
 | 
			
		||||
    background: #272822;
 | 
			
		||||
    color: #A6E22E;
 | 
			
		||||
    padding: 8px 16px;
 | 
			
		||||
    border-bottom: 1px solid #3E3D32;
 | 
			
		||||
    font-family: 'SF Mono', 'Monaco', 'Cascadia Code', 'Roboto Mono', monospace;
 | 
			
		||||
    font-size: 14px;
 | 
			
		||||
    font-size: 12px;
 | 
			
		||||
    font-weight: 500;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.article-body pre code {
 | 
			
		||||
    display: block;
 | 
			
		||||
    background: none;
 | 
			
		||||
    padding: 0;
 | 
			
		||||
    padding: 16px;
 | 
			
		||||
    color: #F8F8F2;
 | 
			
		||||
    font-family: 'SF Mono', 'Monaco', 'Cascadia Code', 'Roboto Mono', monospace;
 | 
			
		||||
    overflow-x: auto;
 | 
			
		||||
    line-height: 1.4;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* Inline code */
 | 
			
		||||
.article-body code {
 | 
			
		||||
    background: #2F3129;
 | 
			
		||||
    color: #A6E22E;
 | 
			
		||||
    padding: 2px 6px;
 | 
			
		||||
    border-radius: 4px;
 | 
			
		||||
    font-family: 'SF Mono', 'Monaco', 'Cascadia Code', 'Roboto Mono', monospace;
 | 
			
		||||
    font-size: 13px;
 | 
			
		||||
    border: 1px solid #3E3D32;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* Molokai color scheme for syntax highlighting */
 | 
			
		||||
.article-body pre code .hljs-keyword { color: #F92672; }
 | 
			
		||||
.article-body pre code .hljs-string { color: #E6DB74; }
 | 
			
		||||
.article-body pre code .hljs-comment { color: #75715E; font-style: italic; }
 | 
			
		||||
.article-body pre code .hljs-number { color: #AE81FF; }
 | 
			
		||||
.article-body pre code .hljs-variable { color: #FD971F; }
 | 
			
		||||
.article-body pre code .hljs-function { color: #A6E22E; }
 | 
			
		||||
.article-body pre code .hljs-tag { color: #F92672; }
 | 
			
		||||
.article-body pre code .hljs-attr { color: #A6E22E; }
 | 
			
		||||
.article-body pre code .hljs-value { color: #E6DB74; }
 | 
			
		||||
 | 
			
		||||
/* Sidebar styles */
 | 
			
		||||
.article-sidebar {
 | 
			
		||||
    position: sticky;
 | 
			
		||||
 
 | 
			
		||||
@@ -92,8 +92,8 @@ impl MarkdownProcessor {
 | 
			
		||||
        for event in parser {
 | 
			
		||||
            match event {
 | 
			
		||||
                pulldown_cmark::Event::Start(pulldown_cmark::Tag::CodeBlock(kind)) => {
 | 
			
		||||
                    if let CodeBlockKind::Fenced(lang) = &kind {
 | 
			
		||||
                        code_block = Some((String::new(), lang.to_string()));
 | 
			
		||||
                    if let CodeBlockKind::Fenced(lang_info) = &kind {
 | 
			
		||||
                        code_block = Some((String::new(), lang_info.to_string()));
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                pulldown_cmark::Event::Text(text) => {
 | 
			
		||||
@@ -104,8 +104,8 @@ impl MarkdownProcessor {
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                pulldown_cmark::Event::End(pulldown_cmark::TagEnd::CodeBlock) => {
 | 
			
		||||
                    if let Some((code, lang)) = code_block.take() {
 | 
			
		||||
                        let highlighted = self.highlight_code_block(&code, &lang, theme);
 | 
			
		||||
                    if let Some((code, lang_info)) = code_block.take() {
 | 
			
		||||
                        let highlighted = self.highlight_code_block(&code, &lang_info, theme);
 | 
			
		||||
                        events.push(pulldown_cmark::Event::Html(highlighted.into()));
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
@@ -117,13 +117,29 @@ impl MarkdownProcessor {
 | 
			
		||||
        Ok(html_output)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fn highlight_code_block(&self, code: &str, lang: &str, theme: &syntect::highlighting::Theme) -> String {
 | 
			
		||||
    fn highlight_code_block(&self, code: &str, lang_info: &str, theme: &syntect::highlighting::Theme) -> String {
 | 
			
		||||
        // Parse language and filename from lang_info (e.g., "sh:/path/to/file" or "rust:main.rs")
 | 
			
		||||
        let (lang, filename) = if lang_info.contains(':') {
 | 
			
		||||
            let parts: Vec<&str> = lang_info.splitn(2, ':').collect();
 | 
			
		||||
            (parts[0], Some(parts[1]))
 | 
			
		||||
        } else {
 | 
			
		||||
            (lang_info, None)
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        let syntax = self.syntax_set
 | 
			
		||||
            .find_syntax_by_token(lang)
 | 
			
		||||
            .unwrap_or_else(|| self.syntax_set.find_syntax_plain_text());
 | 
			
		||||
 | 
			
		||||
        let mut highlighter = syntect::easy::HighlightLines::new(syntax, theme);
 | 
			
		||||
        let mut output = String::from("<pre><code>");
 | 
			
		||||
        
 | 
			
		||||
        // Create pre tag with optional filename attribute
 | 
			
		||||
        let pre_tag = if let Some(filename) = filename {
 | 
			
		||||
            format!("<pre data-filename=\"{}\">", filename)
 | 
			
		||||
        } else {
 | 
			
		||||
            "<pre>".to_string()
 | 
			
		||||
        };
 | 
			
		||||
        
 | 
			
		||||
        let mut output = format!("{}<code>", pre_tag);
 | 
			
		||||
 | 
			
		||||
        for line in code.lines() {
 | 
			
		||||
            let ranges = highlighter.highlight_line(line, &self.syntax_set).unwrap();
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user