···47474848 let of' ranges =
4949 Jv.call range_set "of" [| Jv.of_array Range.to_jv ranges |] |> of_jv
5050-5151- let empty = Jv.get range_set "empty" |> of_jv
5252- let map t changes = Jv.call t "map" [| changes |] |> of_jv
5350end
-2
jsoo-code-mirror/src/decoration.mli
···2626 include Jv.CONV with type t := t
27272828 val of' : Range.t array -> t
2929- val empty : t
3030- val map : t -> Jv.t -> t
3129end
-9
jsoo-code-mirror/src/state_effect.ml
···11-type t = Jv.t
22-33-include (Jv.Id : Jv.CONV with type t := t)
44-55-let state_effect = Jv.get Jv.global "__CM__StateEffect"
66-let define () = Jv.call state_effect "define" [||]
77-let of_ t v = Jv.call t "of" [| v |]
88-let is instance t = Jv.to_bool (Jv.call instance "is" [| t |])
99-let value instance = Jv.get instance "value"
-17
jsoo-code-mirror/src/state_effect.mli
···11-type t
22-(** An effect type definition, created with {!define}. *)
33-44-include Jv.CONV with type t := t
55-66-val define : unit -> t
77-(** [define ()] creates a new effect type. *)
88-99-val of_ : t -> Jv.t -> Jv.t
1010-(** [of_ effect_type value] creates an effect instance carrying [value]. *)
1111-1212-val is : Jv.t -> t -> bool
1313-(** [is instance effect_type] returns [true] if [instance] was created from
1414- [effect_type]. *)
1515-1616-val value : Jv.t -> Jv.t
1717-(** [value instance] returns the value carried by an effect instance. *)
···11-val define :
22- create:(unit -> Jv.t) ->
33- update:(Jv.t -> Jv.t -> Jv.t) ->
44- provide:(Jv.t -> Extension.t) ->
55- Extension.t
66-(** [define ~create ~update ~provide] creates a state field extension.
77-88- - [create ()] returns the initial field value.
99- - [update value transaction] computes the new value for each transaction.
1010- - [provide field] returns an extension that derives a facet from the field
1111- (e.g. [EditorView.decorations.from(field)]). *)
+20-36
x-ocaml/src/editor.ml
···11type t = {
22 view : Code_mirror.Editor.View.t;
33+ messages_comp : Code_mirror.Compartment.t;
34 lines_comp : Code_mirror.Compartment.t;
45 merlin_comp : Code_mirror.Compartment.t;
56 mutable merlin_extension : unit -> Code_mirror.Extension.t list;
···1516 in
1617 go at
17181818-let set_messages_effect = Code_mirror.State_effect.define ()
1919-2020-let messages_field =
2121- Code_mirror.State_field.define
2222- ~create:(fun () ->
2323- Code_mirror.Decoration.Range_set.(to_jv empty))
2424- ~update:(fun decos tr ->
2525- let open Code_mirror.Decoration in
2626- let decos = Range_set.map (Range_set.of_jv decos) (Jv.get tr "changes") in
2727- let effects = Jv.to_jv_array (Jv.get tr "effects") in
2828- Range_set.to_jv
2929- (Array.fold_left
3030- (fun acc e ->
3131- if Code_mirror.State_effect.is e set_messages_effect then
3232- Range_set.of_jv (Code_mirror.State_effect.value e)
3333- else acc)
3434- decos effects))
3535- ~provide:(fun field ->
3636- let deco_facet =
3737- Jv.get (Jv.get Jv.global "__CM__view") "decorations"
3838- in
3939- Jv.call deco_facet "from" [| field |] |> Code_mirror.Extension.of_jv)
4040-4141-let build_range_set cm =
1919+let render_messages cm =
2020+ let open Code_mirror.Editor in
4221 let open Code_mirror.Decoration in
2222+ let (State.Facet ((module F), it)) = View.decorations () in
4323 let doc = cm.current_doc in
4424 let ranges =
4525 Array.of_list
···5131 @@ List.map (fun (at, msg) ->
5232 let at = min at (String.length doc) in
5333 let at = find_line_ends at doc in
3434+ (* Clamp to last character — decorations at doc.length can cause
3535+ RangeError when CodeMirror maps them through changesets *)
5436 let at = min at (max 0 (String.length doc - 1)) in
5537 (at, msg))
5638 @@ List.concat
5739 @@ List.map (fun (loc, lst) -> List.map (fun m -> (loc, m)) lst)
5840 @@ List.sort (fun (a, _) (b, _) -> Int.compare a b) cm.messages
5941 in
6060- try Range_set.of' ranges with _ -> Range_set.of' [||]
4242+ try F.of_ it (Range_set.of' ranges)
4343+ with _ -> F.of_ it (Range_set.of' [||])
61446245let refresh_messages ed =
6363- let range_set = build_range_set ed in
6464- let effect =
6565- Code_mirror.State_effect.of_ set_messages_effect
6666- (Code_mirror.Decoration.Range_set.to_jv range_set)
6767- in
6868- let txn =
6969- Jv.obj [| ("effects", effect) |]
7070- |> Code_mirror.Editor.View.Transaction.of_jv
7171- in
7272- try Code_mirror.Editor.View.dispatch ed.view txn with _ -> ()
4646+ try
4747+ Code_mirror.Editor.View.dispatch ed.view
4848+ (Code_mirror.Compartment.reconfigure ed.messages_comp
4949+ [ render_messages ed ])
5050+ with _ -> ()
5151+ (* RangeError can occur when CodeMirror maps decoration positions
5252+ through changesets if the cached doc length differs from the
5353+ actual CodeMirror document length. Swallow to prevent cascade
5454+ failures in the cell execution chain. *)
73557456let custom_ln editor =
7557 Code_mirror.Editor.View.line_numbers (fun x ->
···118100let make ?(read_only = false) parent =
119101 let open Code_mirror.Editor in
120102 let changes = Code_mirror.Compartment.make () in
103103+ let messages = Code_mirror.Compartment.make () in
121104 let lines = Code_mirror.Compartment.make () in
122105 let merlin = Code_mirror.Compartment.make () in
123106 let extensions =
···126109 basic_setup;
127110 Code_mirror.Editor.View.line_wrapping ();
128111 Code_mirror.Compartment.of' lines [];
129129- messages_field;
112112+ Code_mirror.Compartment.of' messages [];
130113 Code_mirror.Compartment.of' changes [];
131114 Code_mirror.Compartment.of' merlin [];
132115 |]
···141124 current_doc = "";
142125 messages = [];
143126 view;
127127+ messages_comp = messages;
144128 lines_comp = lines;
145129 merlin_comp = merlin;
146130 merlin_extension = (fun () -> []);