1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
use lcode_config::config::global::USER_CONFIG;
use ratatui::{
    style::{Style, Stylize},
    text::{Line, Span},
};

use super::{to_sub_sup_script, Render};
use crate::leetcode::question::qs_detail::Question;

impl Render for Question {
    fn to_md_str(&self, with_env: bool) -> String {
        let content = if USER_CONFIG.config.translate {
            self.translated_content
                .as_deref()
                .unwrap_or_default()
        }
        else {
            self.content
                .as_deref()
                .unwrap_or_default()
        };

        let content = to_sub_sup_script(content)
            .trim_matches('"')
            .replace("\\n", "\n");
        let env_info = self.env_info.to_string();

        // some content are not HTML
        let md_str = if content.contains("<p>") {
            html2text::from_read(content.as_bytes(), 80)
        }
        else {
            content
        };
        let mut res = format!("{qs}\n---\n\n{md}\n---\n", qs = self, md = md_str,);

        if !self.hints.is_empty() {
            let hints = html2text::from_read(self.hints.join("\n").as_bytes(), 80);
            res = format!("{}\n\nhints:\n{}\n---\n", res, hints);
        }
        if !self.mysql_schemas.is_empty() {
            let str = format!("\n```sql\n{}\n```\n", self.mysql_schemas.join("\n"));

            res.push_str(&str);
        }
        if with_env {
            res.push_str(&format!("EnvInfo:\n{}", env_info));
        }
        res
    }

    fn to_tui_vec(&self) -> Vec<Line> {
        use scraper::Html;

        let content = if USER_CONFIG.config.translate {
            self.translated_content
                .as_deref()
                .unwrap_or_else(|| {
                    self.content
                        .as_deref()
                        .unwrap_or_default()
                })
        }
        else {
            self.content
                .as_deref()
                .unwrap_or_default()
        };

        let content = to_sub_sup_script(content);

        let frag = Html::parse_fragment(&content);
        let res = frag
            .root_element()
            .text()
            .fold(String::new(), |acc, e| acc + e);

        let res: Vec<Line> = res
            .replace("\\\"", "\"")
            .replace("\\\\", "")
            .replace("\\n", "\n")
            .replace("\\t", "    ")
            .replace("\n\n\n", "\n")
            .trim_matches(|c| c == '"' || c == '\n' || c == ' ')
            .split('\n')
            .map(|v| v.to_owned().into())
            .collect();

        let topic = self
            .topic_tags
            .iter()
            .map(|v| {
                if USER_CONFIG.config.translate {
                    if v.translated_name.is_none() {
                        v.name.clone()
                    }
                    else {
                        v.translated_name
                            .clone()
                            .unwrap_or_default()
                    }
                }
                else {
                    v.name.clone()
                }
            })
            .collect::<Vec<String>>()
            .join(", ");

        let res1 = vec![
            vec![
                Span::styled("• ID: ", Style::default()),
                Span::styled(self.question_id.clone(), Style::default().bold()),
                Span::styled(" | Passing rate: ", Style::default()),
                Span::styled(self.stats.ac_rate.clone(), Style::default().bold()),
                Span::styled(" | PaidOnly: ", Style::default()),
                Span::styled(self.is_paid_only.to_string(), Style::default().bold()),
                Span::styled(" | Difficulty: ", Style::default()),
                Span::styled(self.difficulty.clone(), Style::default().bold()),
            ]
            .into(),
            vec![
                Span::styled("• Topic: ", Style::default().bold()),
                Span::styled(topic, Style::default()),
            ]
            .into(),
            vec![
                Span::styled("• Url: ", Style::default()),
                Span::styled(
                    USER_CONFIG.urls.get_qs_url(
                        self.qs_slug
                            .as_deref()
                            .unwrap_or_default(),
                    ),
                    Style::default().bold(),
                ),
            ]
            .into(),
            String::new().into(),
        ];

        [res1, res].concat()
    }
}