From d2549f5ea26f55d98c9106448002adfc023793d7 Mon Sep 17 00:00:00 2001 From: Yuchen Pei Date: Sun, 9 Jul 2023 10:34:03 +1000 Subject: first commit --- wiki-markup.el | 121 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 121 insertions(+) create mode 100644 wiki-markup.el (limited to 'wiki-markup.el') diff --git a/wiki-markup.el b/wiki-markup.el new file mode 100644 index 0000000..45bc740 --- /dev/null +++ b/wiki-markup.el @@ -0,0 +1,121 @@ +;;; wiki-markup.el -- A wikitext mode -*- lexical-binding: t -*- + +;; Copyright (C) 2023 Free Software Foundation. + +;; Author: Yuchen Pei +;; Package-Requires: ((emacs "28.2")) + +;; This file is part of wiki-markup.el. + +;; wiki-markup.el is free software: you can redistribute it and/or modify it under +;; the terms of the GNU Affero General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; wiki-markup.el is distributed in the hope that it will be useful, but WITHOUT +;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY +;; or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General +;; Public License for more details. + +;; You should have received a copy of the GNU Affero General Public +;; License along with wiki-markup.el. If not, see . + +;;; Commentary: + +;; A wikitext mode for wiki-markup + +;;; Code: +(require 'wiki-faces) + +(defvar wiki-url-regexp "https?://[^ ]+") + +(defvar wiki-external-link-re + (rx (seq "[[" + (group (seq "http" + (opt "s") + "://" + (+ (not " ")))) + (opt (seq " " (group (+? anything)))) + "]]"))) + +(defvar wiki-internal-link-re + (rx (seq "[[" + ;; Target + (group + (one-or-more + (not (any "[|]")))) + ;; Label (optional) + (opt (seq "|" (group (+? anything)))) + "]]")) + ) + +(defvar wiki-font-lock-keywords + (list + (cons "^======.*======\\ *$" 'wiki-level-6) + (cons "^=====.*=====\\ *$" 'wiki-level-5) + (cons "^====.*====\\ *$" 'wiki-level-4) + (cons "^===.*===\\ *$" 'wiki-level-3) + (cons "^==.*==\\ *$" 'wiki-level-2) + (cons "^=.*=\\ *$" 'wiki-level-1) + (cons "^----+\\ *$" 'wiki-hr-face) + (cons "'''''[^ \t\n].*?[^ \t\n]'''''" 'wiki-bold-italic) + (cons "'''[^ \t\n'].*?[^ \t\n']'''" 'wiki-bold) + (cons "''[^ \t\n'].*?[^ \t\n']''" 'wiki-italic) + (cons "^ .*$" 'wiki-pre-face) + '(wiki-activate-external-links) + '(wiki-activate-internal-links) + )) + +(defvar wiki-outline-regexp "=+.*=+\ *$") + +(defun wiki-outline-level () + (when (looking-at "\\(=+\\).*\\(=+\\)\ *$") + (min (length (match-string 1)) + (length (match-string 2)) + 6))) + +;; Like `org-activate-links' +(defun wiki-activate-links (link-re limit) + (save-excursion + (goto-char (point-min)) + (while (re-search-forward link-re limit t) + (let ((start (match-beginning 0)) + (end (match-end 0)) + (visible-start (or (match-beginning 2) (match-beginning 1))) + (visible-end (or (match-end 2) (match-end 1))) + ) + (put-text-property start visible-start 'invisible t) + (put-text-property start end 'font-lock-face 'wiki-link) + (put-text-property visible-end end 'invisible t) + (add-text-properties (1- visible-start) visible-start + '(rear-nonsticky (invisible))) + (add-text-properties (1- visible-end) visible-end + '(rear-nonsticky (invisible))) + )))) + +(defun wiki-activate-internal-links (limit) + (wiki-activate-links wiki-internal-link-re limit)) + +(defun wiki-activate-external-links (limit) + (wiki-activate-links wiki-external-link-re limit)) + +(define-derived-mode wiki-mode outline-mode "Wiki" + "A wikitext mode." + + (setq-local comment-start "") + + ;; FIXME: this should not be necessary in outline mode + (setq-local font-lock-defaults + '(wiki-font-lock-keywords + t + nil + nil + (font-lock-extra-managed-props invisible font-lock-face))) + (setq-local outline-regexp wiki-outline-regexp) + (setq-local outline-level 'wiki-outline-level) + ) + +(provide 'wiki-markup) +;;; wiki-markup.el ends here + -- cgit v1.2.3