Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 26 additions & 0 deletions src/haz3lcore/derived/TermData.re
Original file line number Diff line number Diff line change
Expand Up @@ -97,3 +97,29 @@ let get_term_rows =
|> List.map(List.rev);
(start.row, term_rows);
};

let get_root_id_using_ranges =
(s: Base.segment, data: t, measured: Measured.t): option(Id.t) => {
let id_and_ranges =
s
|> List.filter_map((p: Piece.t) => {
let id = Piece.id(p);
let range_opt = extreme_measures(id, data, measured);
Option.map(r => (id, r), range_opt);
});
ListUtil.max(
((_, (start1, end1)), (_, (start2, end2))) =>
switch (Point.comp(start1, start2)) {
| Under => Direction.Left
| Over => Direction.Right
| Exact =>
switch (Point.comp(end1, end2)) {
| Under => Direction.Right
| Over => Direction.Left
| Exact => Direction.Right
}
},
id_and_ranges,
)
|> Option.map(fst);
};
18 changes: 18 additions & 0 deletions src/util/ListUtil.re
Original file line number Diff line number Diff line change
Expand Up @@ -587,3 +587,21 @@ let assoc_update = (key, f, assoc) => {

let remove_assoc = (key, assoc) =>
List.filter(((k, _)) => k != key, assoc);

let max = (cmp: ('a, 'a) => Direction.t, xs: list('a)): option('a) => {
switch (xs) {
| [] => None
| [x, ...xs] =>
Some(
List.fold_left(
(current_max, candidate) =>
switch (cmp(current_max, candidate)) {
| Left => current_max
| Right => candidate
},
x,
xs,
),
)
};
};
18 changes: 15 additions & 3 deletions src/web/app/editors/code/CodeEditable.re
Original file line number Diff line number Diff line change
Expand Up @@ -227,14 +227,24 @@ module View = {

module MouseState = Pointer.MkState();

let deco = (~syntax: CachedSyntax.t, ~z: Zipper.t, ~globals: Globals.t) => [
let deco =
(
~expand_selection=false,
~syntax: CachedSyntax.t,
~globals: Globals.t,
z: Zipper.t,
) => [
CaretDec.view(
~measured=syntax.measured,
~font_metrics=globals.font_metrics,
z,
),
Arms.Indicated.term(~font_metrics=globals.font_metrics, ~syntax, z),
Highlight.selection(
(
expand_selection
? Highlight.selection_expanded(~term_data=syntax.term_data)
: Highlight.selection
)(
~measured=syntax.measured,
~shape_map=syntax.shape_map,
~font_metrics=globals.font_metrics,
Expand All @@ -261,6 +271,7 @@ module View = {
~selected: bool,
~overlays: list(Node.t)=[],
~dynamics: Language.Dynamics.Map.t,
~expand_selection=?,
model: Model.t,
) => {
/* Sync document-level click listener for closing context menu */
Expand All @@ -271,9 +282,10 @@ module View = {
let edit_decos =
selected
? deco(
~z=model.editor.state.zipper,
~expand_selection?,
~syntax=model.editor.syntax,
~globals,
model.editor.state.zipper,
)
@ [
Arms.Refractors.all(
Expand Down
44 changes: 44 additions & 0 deletions src/web/app/editors/decoration/Highlight.re
Original file line number Diff line number Diff line change
Expand Up @@ -215,6 +215,50 @@ let selection =
),
);

// Explands selection to make it a subtree of the exp
let selection_expanded =
(
~measured: Measured.t,
~shape_map: ProjectorCore.Shape.Map.t,
~font_metrics: FontMetrics.t,
~term_data: TermData.t,
z: Zipper.t,
) =>
div_c(
"selects",
switch (
TermData.get_root_id_using_ranges(
z.selection.content,
term_data,
measured,
)
) {
| None => []
| Some(id) =>
let seg = TermData.segment(id, term_data);
switch (seg) {
| None => []
| Some(seg) =>
of_segment(
~measured,
~shape_map,
~font_metrics,
~shape_init=Some(fst(Siblings.shapes(z.relatives.siblings))),
~clss=["selected-expanded", Selection.buffer_cls(z.selection)],
seg,
)
@ of_segment(
~measured,
~shape_map,
~font_metrics,
~shape_init=Some(fst(Siblings.shapes(z.relatives.siblings))),
~clss=["selected", Selection.buffer_cls(z.selection)],
z.selection.content,
)
};
},
);

let indicated_refractor =
(
~measured: Measured.t,
Expand Down
1 change: 1 addition & 0 deletions src/web/app/editors/result/StepperEditor.re
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,7 @@ module View = {
model: Model.t,
) => {
CodeSelectable.View.view(
~expand_selection=true,
~dynamics=Language.Dynamics.Map.empty,
~signal=
fun
Expand Down
23 changes: 13 additions & 10 deletions src/web/app/editors/stepper/MissingStep.re
Original file line number Diff line number Diff line change
Expand Up @@ -162,16 +162,19 @@ module Update = {
// hacky way to get a currently-selected id
{
let editor: CodeSelectable.Model.t = editor |> Calc.get_value;
try({
let zipper = editor.editor.state.zipper;
let selection = zipper.selection.content;
let skel = Segment.skel(selection);
let root = Skel.root(skel);
let idx = Aba.first_a(root);
let piece = List.nth(selection, idx);
let id = Piece.id(piece);
Some(id);
}) {
try(
{
open OptUtil.Syntax;
let zipper = editor.editor.state.zipper;
let* id =
TermData.get_root_id_using_ranges(
zipper.selection.content,
editor.editor.syntax.term_data,
editor.editor.syntax.measured,
);
Some(id);
}
) {
| _ => None
};
}
Expand Down
10 changes: 10 additions & 0 deletions src/web/www/style/editor.css
Original file line number Diff line number Diff line change
Expand Up @@ -222,6 +222,16 @@ svg.shard.selected > path {
stroke: var(--shard-selected);
}

svg.shard.selected-expanded {
z-index: var(--select-z);
filter: drop-shadow(2px 2px 2px var(--shadow-selected));
}
svg.shard.selected-expanded > path {
fill: var(--shard-selected-expanded);
stroke-width: 0.5px;
stroke: var(--shard-selected-expanded);
}

.errors .errors-piece svg.shard {
z-index: var(--err-hole-z);
filter: none;
Expand Down
1 change: 1 addition & 0 deletions src/web/www/style/variables.css
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@
--shard-typ: var(--shard-caret-typ);
--shard-tpat: var(--shard-caret-tpat);
--shard-selected: var(--Y1);
--shard-selected-expanded: var(--Y0);
--shard-buffer: var(--T1);
--shard_projector: var(--T2);
--shard-rul: var(--shard-exp);
Expand Down