Giter Site home page Giter Site logo

mfm.js's People

Contributors

dependabot[bot] avatar johann150 avatar marihachi avatar mei23 avatar syuilo avatar zyoshoka avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

mfm.js's Issues

リンクラベルにPlainParserを適用したい

InlineParserを適用して受けられる恩恵が少ない
PlainParserで十分

メンションと解釈しなくていい部分で解釈される。
メンションによる間違ったリンクが生成される可能性がある。

[GitHub (@marihachi)](https://github.com/marihachi)
[
  {
    "type": "link",
    "props": {
      "silent": false,
      "url": "https://github.com/marihachi"
    },
    "children": [
      {
        "type": "text",
        "props": {
          "text": "GitHub ("
        }
      },
      {
        "type": "mention",
        "props": {
          "username": "marihachi",
          "host": null,
          "acct": "@marihachi"
        }
      },
      {
        "type": "text",
        "props": {
          "text": ")"
        }
      }
    ]
  }
]

ブランチ運用・リリースの仕方

将来的にはStable版とCanary版をnpmにリリースしていきたい。

  • Canary版: テスト向け。ガンガン機能追加・変更してテストするためのリリース。
  • Stable版: ユーザー向けのリリース。

普通どんな感じでブランチの運用とかリリースをするんだろう。
うまくGitHub Actionsも使えると管理が楽そう

旧関数構文の廃止

関数構文は2種類ある。
構文A: [fn content]
構文B: $[fn content]

どちらかの構文に統一したほうが良いと思う。
キャッシュ(packrat parsing)のおかげで、構文Aでもそこまで負荷が高くならなくなった。

構文A [fn content] の廃止を予定。

Related to #49

関数構文の変更

リンクと記号が被っていてパース時の負荷に繋がる。あと[foo bar]のような文字列は意図せず現れる場合も多いため、関数構文が誤発動してしまうこともしばしばみられる。そのため構文を変更したい

新構文の対応

ブロック

  • 引用ブロック
  • 検索ブロック
  • コードブロック
  • 数式ブロック
  • **寄せブロック

インライン

  • 揺れる字
  • 太字
  • 目立たない字
  • イタリック
  • 打ち消し線
  • インラインコード
  • インライン数式
  • メンション
  • ハッシュタグ
  • URL
  • リンク
  • カスタム絵文字
  • 機能タグ
  • Unicode絵文字

太字構文の改善

太字構文でも、イタリック構文のように前の文字が改行やスペースの時のみ太字構文として判定するようにしたい。

仕様案

**bold**
__bold__
  • 含められる文字: 任意の文字
  • 開始記号の前後の文字が(無い、改行、半角スペース)のいずれかの時に太字構文として判定される。

ハッシュタグの検出を改良する

C#​の後ろに来る文章がハッシュタグとして認識されないようにするにはどうするべきか…

のように、途中にナンバーサインを含むキーワードがあるとそれ以降すべてハッシュタグだと認識されてしまうので、何らかの改良をしたい

案としては、ナンバーサインの前に改行またはスペースを必要にするというのはどうだろう

Unicode絵文字

Unicode絵文字もtextに含めてパースした後、
textにtwemojiの正規表現を適用してUnicode絵文字をtextから分離する

参考

https://misskey.io/notes/8jaxv3bqdj

Unicode絵文字→Twemojiとして表示する だからTwemojiで対応しているのを過不足なく指定する必要があってTwemojiと同じパターンを使ってるのだわ。他のパターンだとU+FE0Eが付く付かないのあたりがうまく合致しなかった気がするのだわ。

ネスト回数の制限などの細かい制御を行う

パーサを手書きで実装する?

PEG.jsで宣言的に記述したパーサでは細かい制御ができないため、
再帰下降パーサを手書きして置き換えたい。

実験用ブランチ:
https://github.com/misskey-dev/mfm.js/tree/parser-alt-impl-1 (offsetを自動的に計算したいため実験中止)
https://github.com/misskey-dev/mfm.js/tree/parser-alt-impl-2 (offsetを自動計算できるようになった)

PEG.jsのプラグインで細かい制御を行う?

PEG.jsのプラグインを作成することで、パーサの動作を細かく制御できる可能性が出てきた。
まずはPEG.jsのプラグインでできることを調査する。
Related to #57

peg.jsリポジトリ上のドキュメント:
https://github.com/pegjs/pegjs/blob/master/docs/guides/plugins.md

peg.jsのforkのPeggyにある説明:
https://github.com/peggyjs/peggy#plugins-api

実験用ブランチ:
https://github.com/misskey-dev/mfm.js/tree/expr-pegjs-plugin-1

仕様検討

概要

MFMとしての仕様を検討します。

現状のMFMパーサーは実装に依存しています。
書き直しで全ての挙動を再現することになり、その挙動に何らかの意図があるのかどうかが現状では不明です。
仕様を決定することでパーサーの挙動が最適化・簡素化されることを狙っています。

このほうが良いなどあれば、ご意見をください。
これに沿って実装を進めていきます。

構文の定義に登場する記号・識別子の意味について

" " で囲まれた文字列 : 普通の文字列を表します。
( or ) : 選択を表しています。
+ : 1回以上の繰り返しを表しています。
? : オプションを表しています。あってもなくても大丈夫な部分です。
上記以外 : 項目毎にそれぞれ説明しています。
また、一部PEGの用語が含まれています。

ブロック構文

title(1)

タイトル行。現在位置から行末までマッチする。

beginline "【" inlines "】" endline

beginline:
行頭にマッチ(消費しない)
inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)
endline:
改行文字またはEOFにマッチ

title(2)

タイトル行。現在位置から行末までマッチする。

beginline "[" inlines "]" endline

beginline:
行頭にマッチ(消費しない)
inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)
endline:
改行文字またはEOFにマッチ

quote

引用ブロック。現在位置から行末までマッチする。
複数行で連結して1つの引用ブロックを形成する。
例外として、head">"に続いて"<"が出てきた場合や、head">"に続いて"<"が出てきた場合にはマッチしない。

beginline head content endline

beginline:
行頭にマッチ(消費しない)
head:
">" or ">"
content:
改行文字を除く任意の文字にマッチ(複数)
1文字目がスペースなら、2文字目から取り込む
取り込まれた文字列をブロック構文orインライン構文(複数)として処理
endline:
改行文字またはEOFにマッチ

search

検索ボックス。現在位置から行末までマッチする。

beginline query " " ("検索" or "search") endline

beginline:
行頭にマッチ(消費しない)
query:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をそのまま保持
endline:
改行文字またはEOFにマッチ

blockCode

コードブロック。「```」で囲まれた複数の行をコードブロックとして扱う

beginline "```" endline
(line endline)+
"```" endline

beginline:
行頭にマッチ(消費しない)
line:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をそのまま保持
endline:
改行文字またはEOFにマッチ

mathBlock

数式ブロック

"\[" content "\]"

content:
任意の文字にマッチ(複数)
マッチした文字列を数式として処理

conter

**寄せブロック

"<center>" content "</center>"

content:
任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

インライン構文

big

拡大して揺れる太文字

"***" inlines "***"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

bold(1)

太文字

"**" inlines "**"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

bold(2)

太文字

"__" inlines "__"

inlines:
アルファベット(大文字 小文字) 数字 スペース のいずれかの文字にマッチ (複数)
マッチした文字列をインライン構文として処理(複数)

small

小さな文字

"<small>" inlines "</small>"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

italic(1)

イタリック文字

"<i>" inlines "</i>"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

italic(2)

"*" inlines "*"

inlines:
アルファベット(大文字 小文字) 数字 スペース のいずれかの文字にマッチ (複数)
マッチした文字列をインライン構文として処理(複数)

italic(3)

"_" inlines "_"

inlines:
アルファベット(大文字 小文字) 数字 スペース のいずれかの文字にマッチ (複数)
マッチした文字列をインライン構文として処理(複数)

strike

打ち消し線の付いた文字

"~~" inlines "~~"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

motion(1)

動く文字

"<motion>" inlines "</motion>"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

motion(2)

"(((" inlines ")))"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

spin

"<spin" (" " attr)? ">" inlines "</spin>"

attr:
改行文字を除く任意の文字にマッチ(複数)
inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

jump

跳ねる文字

"<jump>" inlines "</jump>"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

flip

反転する

"<flip>" inlines "</flip>"

inlines:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をインライン構文として処理(複数)

inlineCode

コード

"`" chars "`"

chars:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列をコードの内容として処理

mathInline

数式

"\(" chars "\)"

chars:
改行文字を除く任意の文字にマッチ(複数)
マッチした文字列を数式の内容として処理

mention

hashtag

ハッシュタグ。
ネストされたかっこの開始と終了が対になっている場合のみハッシュタグの内容に含める処理を持つ。

"#" content

content:
基本的には以下の正規表現にマッチする文字を内容として取り込みます。
正規表現: [^\s!"#$%&'*+,\-./:;<=>?@\\^_`{|}~【】<>]
その中で、ネストされたかっこ()[]「」の開始と終了が対になっている場合、その部分は内容に含めます。
それ以外の場合は、改行文字を除くかっこ()[]「」に一致しない文字を内容に含めます。

url

link

customEmoji

emoji

text

プレーンな文字。他のルールに一致しなかった場合にフォールバックしてマッチする。

chars

chars:
改行文字を除く任意の文字にマッチ(複数)

引用の後の空行を無視したい

引用構文を使う時、

> foo

bar

のように、直後に空行を設けるユーザーが多いが、そうすると視覚上無駄なスペースが生まれるため、パース結果では直後の空行は無いものとして扱うようにしたい。

メモ

ブロック

ブロックの枠だけ処理して中身をテキストで返すパーサーを用意する
インラインのみの部分は一度で処理する
パーサーのアクション内でパーサーを呼び出すことができたので不要になりました

The implementation status of syntax

Parser

  • rootParser : block / inline
  • plainParser : emoji / text
  • (Internal) inlineParser : inline

Block

Name Progress Comment
title Done
quote Done
search Done
blockCode Done
mathBlock Done
center Done

Inline

Name Progress Comment
big Done
bold Done
small Done
italic Done
strike Done
motion Done
spin Done
jump Done
flip Done
inlineCode Done
mathInline Done
mention Not yet
hashtag Done
url Not yet
link Not yet
emoji Done
text Done

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.