ajout app flask pour prévisualiser le livre

This commit is contained in:
Tykayn 2025-03-04 22:36:16 +01:00 committed by tykayn
parent 375fbb3a7a
commit 9f1b265a21
29 changed files with 4533 additions and 137 deletions

2078
static/css/lib/bootstrap-icons.min.css vendored Normal file

File diff suppressed because it is too large Load diff

6
static/css/lib/bootstrap.min.css vendored Normal file

File diff suppressed because one or more lines are too long

1
static/css/lib/codemirror.min.css vendored Normal file

File diff suppressed because one or more lines are too long

1
static/css/lib/eclipse.min.css vendored Normal file
View file

@ -0,0 +1 @@
.cm-s-eclipse span.cm-meta{color:#ff1717}.cm-s-eclipse span.cm-keyword{line-height:1em;font-weight:700;color:#7f0055}.cm-s-eclipse span.cm-atom{color:#219}.cm-s-eclipse span.cm-number{color:#164}.cm-s-eclipse span.cm-def{color:#00f}.cm-s-eclipse span.cm-variable{color:#000}.cm-s-eclipse span.cm-variable-2{color:#0000c0}.cm-s-eclipse span.cm-type,.cm-s-eclipse span.cm-variable-3{color:#0000c0}.cm-s-eclipse span.cm-property{color:#000}.cm-s-eclipse span.cm-operator{color:#000}.cm-s-eclipse span.cm-comment{color:#3f7f5f}.cm-s-eclipse span.cm-string{color:#2a00ff}.cm-s-eclipse span.cm-string-2{color:#f50}.cm-s-eclipse span.cm-qualifier{color:#555}.cm-s-eclipse span.cm-builtin{color:#30a}.cm-s-eclipse span.cm-bracket{color:#cc7}.cm-s-eclipse span.cm-tag{color:#170}.cm-s-eclipse span.cm-attribute{color:#00c}.cm-s-eclipse span.cm-link{color:#219}.cm-s-eclipse span.cm-error{color:red}.cm-s-eclipse .CodeMirror-activeline-background{background:#e8f2ff}.cm-s-eclipse .CodeMirror-matchingbracket{outline:1px solid grey;color:#000!important}

6
static/css/lib/fontawesome.min.css vendored Normal file

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

1
static/css/lib/monokai.min.css vendored Normal file
View file

@ -0,0 +1 @@
.cm-s-monokai.CodeMirror{background:#272822;color:#f8f8f2}.cm-s-monokai div.CodeMirror-selected{background:#49483e}.cm-s-monokai .CodeMirror-line::selection,.cm-s-monokai .CodeMirror-line>span::selection,.cm-s-monokai .CodeMirror-line>span>span::selection{background:rgba(73,72,62,.99)}.cm-s-monokai .CodeMirror-line::-moz-selection,.cm-s-monokai .CodeMirror-line>span::-moz-selection,.cm-s-monokai .CodeMirror-line>span>span::-moz-selection{background:rgba(73,72,62,.99)}.cm-s-monokai .CodeMirror-gutters{background:#272822;border-right:0}.cm-s-monokai .CodeMirror-guttermarker{color:#fff}.cm-s-monokai .CodeMirror-guttermarker-subtle{color:#d0d0d0}.cm-s-monokai .CodeMirror-linenumber{color:#d0d0d0}.cm-s-monokai .CodeMirror-cursor{border-left:1px solid #f8f8f0}.cm-s-monokai span.cm-comment{color:#75715e}.cm-s-monokai span.cm-atom{color:#ae81ff}.cm-s-monokai span.cm-number{color:#ae81ff}.cm-s-monokai span.cm-comment.cm-attribute{color:#97b757}.cm-s-monokai span.cm-comment.cm-def{color:#bc9262}.cm-s-monokai span.cm-comment.cm-tag{color:#bc6283}.cm-s-monokai span.cm-comment.cm-type{color:#5998a6}.cm-s-monokai span.cm-attribute,.cm-s-monokai span.cm-property{color:#a6e22e}.cm-s-monokai span.cm-keyword{color:#f92672}.cm-s-monokai span.cm-builtin{color:#66d9ef}.cm-s-monokai span.cm-string{color:#e6db74}.cm-s-monokai span.cm-variable{color:#f8f8f2}.cm-s-monokai span.cm-variable-2{color:#9effff}.cm-s-monokai span.cm-type,.cm-s-monokai span.cm-variable-3{color:#66d9ef}.cm-s-monokai span.cm-def{color:#fd971f}.cm-s-monokai span.cm-bracket{color:#f8f8f2}.cm-s-monokai span.cm-tag{color:#f92672}.cm-s-monokai span.cm-header{color:#ae81ff}.cm-s-monokai span.cm-link{color:#ae81ff}.cm-s-monokai span.cm-error{background:#f92672;color:#f8f8f0}.cm-s-monokai .CodeMirror-activeline-background{background:#373831}.cm-s-monokai .CodeMirror-matchingbracket{text-decoration:underline;color:#fff!important}

View file

@ -7,6 +7,14 @@
--preview-bg: #ffffff;
--code-bg: #f8f9fa;
--blockquote-color: #6c757d;
--link-color: #0d6efd;
--link-hover-color: #0a58ca;
--progress-bg: #e9ecef;
--progress-bar-bg: #0d6efd;
--title-bg: #e3f2fd;
--title-color: #1976d2;
--comment-bg: #f5f5f5;
--comment-color: #757575;
}
[data-theme="dark"] {
@ -18,6 +26,14 @@
--preview-bg: #2b3035;
--code-bg: #343a40;
--blockquote-color: #adb5bd;
--link-color: #6ea8fe;
--link-hover-color: #8bb9fe;
--progress-bg: #495057;
--progress-bar-bg: #6ea8fe;
--title-bg: #1a237e;
--title-color: #90caf9;
--comment-bg: #424242;
--comment-color: #bdbdbd;
}
body {
@ -30,6 +46,7 @@ body {
background-color: var(--sidebar-bg);
padding: 20px;
border-right: 1px solid var(--border-color);
overflow-y: auto;
}
.editor {
@ -49,6 +66,142 @@ body {
color: var(--text-color);
}
/* Styles pour CodeMirror */
.CodeMirror {
height: calc(100vh - 100px);
font-family: monospace;
font-size: 14px;
line-height: 1.6;
border: 1px solid var(--border-color);
border-radius: 4px;
}
.CodeMirror-scroll {
height: 100%;
}
.CodeMirror-gutters {
background-color: var(--sidebar-bg);
border-right: 1px solid var(--border-color);
}
.CodeMirror-linenumber {
color: var(--text-color);
opacity: 0.7;
}
.CodeMirror-cursor {
border-left: 2px solid var(--text-color);
}
/* Thème clair */
[data-theme="light"] .CodeMirror {
background-color: var(--editor-bg);
color: var(--text-color);
}
[data-theme="light"] .cm-header-1 {
color: #1976d2;
}
[data-theme="light"] .cm-header-2 {
color: #2196f3;
}
[data-theme="light"] .cm-header-3 {
color: #42a5f5;
}
[data-theme="light"] .cm-header-4 {
color: #64b5f6;
}
[data-theme="light"] .cm-header-5 {
color: #90caf9;
}
[data-theme="light"] .cm-header-6 {
color: #bbdefb;
}
[data-theme="light"] .cm-comment {
color: #757575;
}
[data-theme="light"] .cm-keyword {
color: #7b1fa2;
}
[data-theme="light"] .cm-string {
color: #2e7d32;
}
[data-theme="light"] .cm-property {
color: #1976d2;
}
[data-theme="light"] .cm-variable {
color: #1976d2;
}
[data-theme="light"] .cm-number {
color: #f57c00;
}
/* Thème sombre */
[data-theme="dark"] .CodeMirror {
background-color: var(--editor-bg);
color: var(--text-color);
}
[data-theme="dark"] .cm-header-1 {
color: #90caf9;
}
[data-theme="dark"] .cm-header-2 {
color: #64b5f6;
}
[data-theme="dark"] .cm-header-3 {
color: #42a5f5;
}
[data-theme="dark"] .cm-header-4 {
color: #2196f3;
}
[data-theme="dark"] .cm-header-5 {
color: #1976d2;
}
[data-theme="dark"] .cm-header-6 {
color: #1565c0;
}
[data-theme="dark"] .cm-comment {
color: #bdbdbd;
}
[data-theme="dark"] .cm-keyword {
color: #ce93d8;
}
[data-theme="dark"] .cm-string {
color: #81c784;
}
[data-theme="dark"] .cm-property {
color: #90caf9;
}
[data-theme="dark"] .cm-variable {
color: #90caf9;
}
[data-theme="dark"] .cm-number {
color: #ffb74d;
}
.word-count {
background-color: var(--code-bg);
padding: 15px;
@ -56,6 +209,37 @@ body {
margin-bottom: 20px;
}
.word-count .progress {
height: 8px;
background-color: var(--progress-bg);
border-radius: 4px;
overflow: hidden;
}
.word-count .progress-bar {
background-color: var(--progress-bar-bg);
transition: width 0.3s ease;
}
.word-count input[type="number"] {
background-color: var(--editor-bg);
border-color: var(--border-color);
color: var(--text-color);
}
.word-count input[type="number"]:focus {
background-color: var(--editor-bg);
border-color: var(--link-color);
color: var(--text-color);
box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);
}
.word-count .input-group-text {
background-color: var(--code-bg);
border-color: var(--border-color);
color: var(--text-color);
}
.preview-panel {
height: 100vh;
padding: 20px;
@ -124,9 +308,361 @@ body {
margin: 1em 0;
}
.theme-switch {
position: fixed;
top: 20px;
right: 20px;
z-index: 1000;
/* Styles pour la table des matières */
.table-of-contents {
margin-bottom: 20px;
padding: 15px;
background-color: var(--code-bg);
border-radius: 4px;
}
.table-of-contents h5 {
margin-bottom: 10px;
color: var(--text-color);
}
.toc-list {
list-style: none;
padding: 0;
margin: 0;
}
.toc-item {
margin: 5px 0;
}
.toc-item a {
color: var(--link-color);
text-decoration: none;
display: block;
padding: 2px 0;
transition: color 0.2s;
}
.toc-item a:hover {
color: var(--link-hover-color);
}
.level-1 {
font-weight: bold;
margin-left: 0;
}
.level-2 {
margin-left: 15px;
}
.level-3 {
margin-left: 30px;
font-size: 0.9em;
}
.level-4 {
margin-left: 45px;
font-size: 0.85em;
}
.level-5 {
margin-left: 60px;
font-size: 0.8em;
}
/* Styles pour les titres et commentaires */
.preview-content .title-section {
background-color: var(--title-bg);
color: var(--title-color);
padding: 10px 15px;
margin: 10px 0;
border-radius: 4px;
border-left: 4px solid var(--title-color);
}
.preview-content .comment-section {
background-color: var(--comment-bg);
color: var(--comment-color);
padding: 10px 15px;
margin: 10px 0;
border-radius: 4px;
border-left: 4px solid var(--comment-color);
font-style: italic;
}
.preview-content .hidden {
display: none;
}
/* Styles pour les filtres */
.filters {
background-color: var(--code-bg);
padding: 15px;
border-radius: 4px;
}
.filters h5 {
margin-bottom: 10px;
color: var(--text-color);
}
.filters .form-check-label {
color: var(--text-color);
}
.filters .form-check {
position: relative;
display: flex;
align-items: center;
gap: 5px;
}
.info-icon {
color: var(--text-color);
opacity: 0.7;
cursor: help;
font-size: 0.9em;
transition: opacity 0.2s;
}
.info-icon:hover,
.info-icon:focus {
opacity: 1;
}
/* Styles pour les tooltips */
.tooltip {
font-size: 0.875rem;
}
.tooltip-inner {
max-width: 300px;
padding: 0.5rem 1rem;
background-color: var(--bg-color);
color: var(--text-color);
border: 1px solid var(--border-color);
box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}
.tooltip.bs-tooltip-end .tooltip-arrow::before {
border-right-color: var(--border-color);
}
.tooltip.bs-tooltip-end .tooltip-arrow::after {
border-right-color: var(--bg-color);
}
.progress-chart {
background-color: var(--code-bg);
padding: 15px;
border-radius: 4px;
height: 200px;
}
.progress-chart h5 {
margin-bottom: 10px;
color: var(--text-color);
}
/* Styles pour le graphique en mode sombre */
[data-theme="dark"] .progress-chart canvas {
filter: brightness(0.8) contrast(1.2);
}
/* Styles pour les sections de personnages et d'intrigues */
.characters-section,
.plots-section {
background-color: var(--code-bg);
padding: 15px;
border-radius: 4px;
}
.characters-section h5,
.plots-section h5 {
margin-bottom: 10px;
color: var(--text-color);
}
.list-group-item {
background-color: var(--editor-bg);
border-color: var(--border-color);
color: var(--text-color);
transition: all 0.2s;
}
.list-group-item:hover {
background-color: var(--sidebar-bg);
border-color: var(--link-color);
color: var(--link-color);
}
/* Styles pour les modales */
.modal-content {
background-color: var(--bg-color);
color: var(--text-color);
}
.modal-header {
border-bottom-color: var(--border-color);
}
.modal-footer {
border-top-color: var(--border-color);
}
.modal .form-control {
background-color: var(--editor-bg);
border-color: var(--border-color);
color: var(--text-color);
}
.modal .form-control:focus {
background-color: var(--editor-bg);
border-color: var(--link-color);
color: var(--text-color);
box-shadow: 0 0 0 0.25rem rgba(13, 110, 253, 0.25);
}
.modal .btn-close {
filter: var(--btn-close-filter);
}
.characters-toc {
background-color: var(--bg-secondary);
padding: 1rem;
border-radius: 0.5rem;
margin-bottom: 1rem;
}
.characters-toc h6 {
margin-bottom: 0.5rem;
color: var(--text-primary);
}
.word-count-badge {
display: inline-block;
padding: 0.25rem 0.5rem;
border-radius: 0.25rem;
background-color: var(--bg-secondary);
font-size: 0.8em;
}
.plots-toc {
background-color: var(--bg-secondary);
padding: 1rem;
border-radius: 0.5rem;
margin-bottom: 1rem;
}
.plots-toc h6 {
margin-bottom: 0.5rem;
color: var(--text-primary);
}
.subplot-count-badge {
display: inline-block;
padding: 0.25rem 0.5rem;
border-radius: 0.25rem;
background-color: var(--bg-secondary);
font-size: 0.8em;
color: var(--text-secondary);
}
.toc-list {
list-style: none;
padding-left: 1rem;
}
.toc-item {
margin: 0.5rem 0;
}
.toc-item a {
color: var(--text-primary);
text-decoration: none;
display: flex;
align-items: center;
justify-content: space-between;
}
.toc-item a:hover {
color: var(--primary);
}
.level-1 {
margin-left: 0;
}
.level-2 {
margin-left: 1rem;
}
.level-3 {
margin-left: 2rem;
}
.level-4 {
margin-left: 3rem;
}
.level-5 {
margin-left: 4rem;
}
.regular-title {
color: #ccc;
}
.plots-file-link {
float: right;
font-size: 0.8em;
color: var(--text-secondary);
text-decoration: none;
padding: 0.25rem 0.5rem;
border-radius: 0.25rem;
transition: all 0.2s ease;
}
.plots-file-link:hover {
color: var(--primary);
background-color: var(--bg-secondary);
}
.plots-section h5 {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 1rem;
}
.comment-section {
margin-bottom: 1rem;
}
#add-comment-btn {
display: flex;
align-items: center;
justify-content: center;
gap: 0.5rem;
padding: 0.5rem;
transition: all 0.2s ease;
}
#add-comment-btn:hover {
background-color: var(--bg-secondary);
color: var(--primary);
}
#add-comment-btn i {
font-size: 1.1em;
}
/* Styles pour les boutons désactivés */
.btn:disabled {
opacity: 0.5;
cursor: not-allowed;
pointer-events: none;
}
.btn:disabled:hover {
background-color: var(--bg-secondary);
color: var(--text-color);
}

Binary file not shown.

Binary file not shown.

7
static/js/lib/bootstrap.bundle.min.js vendored Normal file

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

13
static/js/lib/chart.min.js vendored Normal file

File diff suppressed because one or more lines are too long

1
static/js/lib/codemirror.min.js vendored Normal file

File diff suppressed because one or more lines are too long

1
static/js/lib/commonlisp.min.js vendored Normal file
View file

@ -0,0 +1 @@
!function(t){"object"==typeof exports&&"object"==typeof module?t(require("../../lib/codemirror")):"function"==typeof define&&define.amd?define(["../../lib/codemirror"],t):t(CodeMirror)}(function(t){"use strict";t.defineMode("commonlisp",function(r){var o,i=/^(block|let*|return-from|catch|load-time-value|setq|eval-when|locally|symbol-macrolet|flet|macrolet|tagbody|function|multiple-value-call|the|go|multiple-value-prog1|throw|if|progn|unwind-protect|labels|progv|let|quote)$/,c=/^with|^def|^do|^prog|case$|^cond$|bind$|when$|unless$/,l=/^(?:[+\-]?(?:\d+|\d*\.\d+)(?:[efd][+\-]?\d+)?|[+\-]?\d+(?:\/[+\-]?\d+)?|#b[+\-]?[01]+|#o[+\-]?[0-7]+|#x[+\-]?[\da-f]+)/,n=/[^\s'`,@()\[\]";]/;function u(t){for(var e;e=t.next();)if("\\"==e)t.next();else if(!n.test(e)){t.backUp(1);break}return t.current()}function a(t,e){if(t.eatSpace())return o="ws",null;if(t.match(l))return"number";var n=t.next();if('"'==(n="\\"==n?t.next():n))return(e.tokenize=s)(t,e);if("("==n)return o="open","bracket";if(")"==n||"]"==n)return o="close","bracket";if(";"==n)return t.skipToEnd(),o="ws","comment";if(/['`,@]/.test(n))return null;if("|"==n)return t.skipTo("|")?(t.next(),"symbol"):(t.skipToEnd(),"error");if("#"==n)return"("==(n=t.next())?(o="open","bracket"):/[+\-=\.']/.test(n)||/\d/.test(n)&&t.match(/^\d*#/)?null:"|"==n?(e.tokenize=d)(t,e):":"==n?(u(t),"meta"):"\\"==n?(t.next(),u(t),"string-2"):"error";t=u(t);return"."==t?null:(o="symbol","nil"==t||"t"==t||":"==t.charAt(0)?"atom":"open"==e.lastType&&(i.test(t)||c.test(t))?"keyword":"&"==t.charAt(0)?"variable-2":"variable")}function s(t,e){for(var n,r=!1;n=t.next();){if('"'==n&&!r){e.tokenize=a;break}r=!r&&"\\"==n}return"string"}function d(t,e){for(var n,r;n=t.next();){if("#"==n&&"|"==r){e.tokenize=a;break}r=n}return o="ws","comment"}return{startState:function(){return{ctx:{prev:null,start:0,indentTo:0},lastType:null,tokenize:a}},token:function(t,e){t.sol()&&"number"!=typeof e.ctx.indentTo&&(e.ctx.indentTo=e.ctx.start+1),o=null;var n=e.tokenize(t,e);return"ws"!=o&&(null==e.ctx.indentTo?"symbol"==o&&c.test(t.current())?e.ctx.indentTo=e.ctx.start+r.indentUnit:e.ctx.indentTo="next":"next"==e.ctx.indentTo&&(e.ctx.indentTo=t.column()),e.lastType=o),"open"==o?e.ctx={prev:e.ctx,start:t.column(),indentTo:null}:"close"==o&&(e.ctx=e.ctx.prev||e.ctx),n},indent:function(t,e){var n=t.ctx.indentTo;return"number"==typeof n?n:t.ctx.start+1},closeBrackets:{pairs:'()[]{}""'},lineComment:";;",fold:"brace-paren",blockCommentStart:"#|",blockCommentEnd:"|#"}}),t.defineMIME("text/x-common-lisp","commonlisp")});

1
static/js/lib/css.min.js vendored Normal file

File diff suppressed because one or more lines are too long

1
static/js/lib/javascript.min.js vendored Normal file

File diff suppressed because one or more lines are too long

1
static/js/lib/markdown.min.js vendored Normal file

File diff suppressed because one or more lines are too long

83
static/js/lib/org.min.js vendored Normal file
View file

@ -0,0 +1,83 @@
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx</center>
</body>
</html>
CodeMirror.defineMode("org", function () {
return {
token: function (stream, state) {
// Titres
if (stream.match(/^\*+\s/)) {
stream.skipToEnd();
return "header";
}
// Commentaires
if (stream.match(/^#\s/)) {
stream.skipToEnd();
return "comment";
}
// Blocs de commentaires
if (stream.match(/^#\+BEGIN_COMMENT/)) {
state.inComment = true;
return "comment";
}
if (state.inComment && stream.match(/^#\+END_COMMENT/)) {
state.inComment = false;
return "comment";
}
if (state.inComment) {
stream.skipToEnd();
return "comment";
}
// Blocs de code
if (stream.match(/^#\+BEGIN_SRC/)) {
state.inCode = true;
return "comment";
}
if (state.inCode && stream.match(/^#\+END_SRC/)) {
state.inCode = false;
return "comment";
}
if (state.inCode) {
stream.skipToEnd();
return "string";
}
// Citations
if (stream.match(/^#\+BEGIN_QUOTE/)) {
state.inQuote = true;
return "comment";
}
if (state.inQuote && stream.match(/^#\+END_QUOTE/)) {
state.inQuote = false;
return "comment";
}
if (state.inQuote) {
stream.skipToEnd();
return "string";
}
// Liens
if (stream.match(/\[\[(.*?)\]\]/)) {
return "link";
}
// Texte normal
stream.next();
return null;
},
startState: function () {
return {
inComment: false,
inCode: false,
inQuote: false
};
}
};
});

1
static/js/lib/scheme.min.js vendored Normal file

File diff suppressed because one or more lines are too long

1
static/js/lib/xml.min.js vendored Normal file

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

138
static/js/mode/org.js Normal file
View file

@ -0,0 +1,138 @@
(function (mod) {
if (typeof exports == "object" && typeof module == "object") // CommonJS
mod(require("../../lib/codemirror"));
else if (typeof define == "function" && define.amd) // AMD
define(["../../lib/codemirror"], mod);
else // Plain browser env
mod(CodeMirror);
})(function (CodeMirror) {
"use strict";
CodeMirror.defineMode("org", function () {
return {
startState: function () {
return {
inComment: false,
inBlock: false,
blockType: null
};
},
token: function (stream, state) {
// Gestion des commentaires en ligne
if (stream.match(/^# /)) {
stream.skipToEnd();
return "comment";
}
// Gestion des lignes de paramètres
if (stream.match(/^:PROPERTIES:|^:END:|^:ID:|^#\+[A-Z_]+:/)) {
stream.skipToEnd();
return "comment";
}
// Gestion des paramètres d'export
if (stream.match(/^:title|^:author|^:email|^:language|^:encoding|^:subject|^:description|^:keywords|^:cover/)) {
stream.skipToEnd();
return "comment";
}
// Gestion des blocs de commentaires
if (stream.match(/^#\+begin_comment/)) {
state.inComment = true;
return "comment";
}
if (state.inComment && stream.match(/^#\+end_comment/)) {
state.inComment = false;
return "comment";
}
if (state.inComment) {
stream.skipToEnd();
return "comment";
}
// Gestion des blocs de code
if (stream.match(/^#\+BEGIN_SRC/)) {
state.inBlock = true;
state.blockType = "src";
return "keyword";
}
if (stream.match(/^#\+BEGIN_QUOTE/)) {
state.inBlock = true;
state.blockType = "quote";
return "keyword";
}
if (state.inBlock && stream.match(/^#\+END_(SRC|QUOTE)/)) {
state.inBlock = false;
state.blockType = null;
return "keyword";
}
if (state.inBlock) {
stream.skipToEnd();
return state.blockType === "src" ? "string" : "quote";
}
// Gestion des titres
if (stream.match(/^\*+\s/)) {
const level = stream.current().length - 1;
stream.skipToEnd();
return `header-${level}`;
}
// Gestion des listes
if (stream.match(/^-\s/)) {
stream.skipToEnd();
return "list";
}
// Gestion des liens
if (stream.match(/\[\[(.*?)\]\]/)) {
return "link";
}
// Gestion des propriétés
if (stream.match(/^:PROPERTIES:/)) {
stream.skipToEnd();
return "property";
}
if (stream.match(/^:END:/)) {
stream.skipToEnd();
return "property";
}
// Gestion des tags
if (stream.match(/:[a-zA-Z0-9_@#%:]+:/)) {
return "tag";
}
// Gestion des dates
if (stream.match(/<\d{4}-\d{2}-\d{2}(?: \w+)?>/)) {
return "date";
}
// Gestion des mots-clés
if (stream.match(/^#\+[A-Z_]+:/)) {
stream.skipToEnd();
return "keyword";
}
// Gestion des nombres
if (stream.match(/\b\d+\b/)) {
return "number";
}
// Texte normal
stream.next();
return null;
}
};
});
CodeMirror.defineMIME("text/x-org", "org");
});