@@ -16,6 +16,7 @@ use helix_view::{
1616use helix_lsp::{
1717 lsp,
1818 util::{lsp_pos_to_pos, pos_to_lsp_pos, range_to_lsp_range},
19+ OffsetEncoding,
1920};
2021
2122use crate::{
@@ -1117,18 +1118,24 @@ pub fn exit_select_mode(cx: &mut Context) {
11171118 cx.doc().mode = Mode::Normal;
11181119}
11191120
1120−fn _goto(cx: &mut Context, locations: Vec<lsp::Location>) {
1121+fn _goto(cx: &mut Context, locations: Vec<lsp::Location>, offset_encoding: OffsetEncoding) {
11211122 use helix_view::editor::Action;
11221123
11231124 push_jump(cx);
11241125
1125− fn jump_to(editor: &mut Editor, location: &lsp::Location, action: Action) {
1126+ fn jump_to(
1127+ editor: &mut Editor,
1128+ location: &lsp::Location,
1129+ offset_encoding: OffsetEncoding,
1130+ action: Action,
1131+ ) {
11261132 let id = editor
11271133 .open(PathBuf::from(location.uri.path()), action)
11281134 .expect("editor.open failed");
11291135 let (view, doc) = editor.current();
11301136 let definition_pos = location.range.start;
1131− let new_pos = lsp_pos_to_pos(doc.text(), definition_pos);
1137+ // TODO: convert inside server
1138+ let new_pos = lsp_pos_to_pos(doc.text(), definition_pos, offset_encoding);
11321139 doc.set_selection(view.id, Selection::point(new_pos));
11331140 let line = doc.text().char_to_line(new_pos);
11341141 view.first_line = line.saturating_sub(view.area.height as usize / 2);
@@ -1136,7 +1143,7 @@ fn _goto(cx: &mut Context, locations: Vec<lsp::Location>) {
11361143
11371144 match locations.as_slice() {
11381145 [location] => {
1139− jump_to(cx.editor, location, Action::Replace);
1146+ jump_to(cx.editor, location, offset_encoding, Action::Replace);
11401147 }
11411148 [] => (), // maybe show user message that no definition was found?
11421149 _locations => {
@@ -1147,7 +1154,9 @@ fn _goto(cx: &mut Context, locations: Vec<lsp::Location>) {
11471154 let line = location.range.start.line;
11481155 format!("{}:{}", file, line).into()
11491156 },
1150− move |editor: &mut Editor, location, action| jump_to(editor, location, action),
1157+ move |editor: &mut Editor, location, action| {
1158+ jump_to(editor, location, offset_encoding, action)
1159+ },
11511160 );
11521161 cx.push_layer(Box::new(picker));
11531162 }
@@ -1161,12 +1170,14 @@ pub fn goto_definition(cx: &mut Context) {
11611170 None => return,
11621171 };
11631172
1164− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1173+ let offset_encoding = language_server.offset_encoding();
1174+
1175+ let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor(), offset_encoding);
11651176
11661177 // TODO: handle fails
11671178 let res =
11681179 smol::block_on(language_server.goto_definition(doc.identifier(), pos)).unwrap_or_default();
1169− _goto(cx, res);
1180+ _goto(cx, res, offset_encoding);
11701181}
11711182
11721183pub fn goto_type_definition(cx: &mut Context) {
@@ -1176,12 +1187,14 @@ pub fn goto_type_definition(cx: &mut Context) {
11761187 None => return,
11771188 };
11781189
1179− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1190+ let offset_encoding = language_server.offset_encoding();
1191+
1192+ let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor(), offset_encoding);
11801193
11811194 // TODO: handle fails
11821195 let res = smol::block_on(language_server.goto_type_definition(doc.identifier(), pos))
11831196 .unwrap_or_default();
1184− _goto(cx, res);
1197+ _goto(cx, res, offset_encoding);
11851198}
11861199
11871200pub fn goto_implementation(cx: &mut Context) {
@@ -1191,12 +1204,14 @@ pub fn goto_implementation(cx: &mut Context) {
11911204 None => return,
11921205 };
11931206
1194− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1207+ let offset_encoding = language_server.offset_encoding();
1208+
1209+ let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor(), offset_encoding);
11951210
11961211 // TODO: handle fails
11971212 let res = smol::block_on(language_server.goto_implementation(doc.identifier(), pos))
11981213 .unwrap_or_default();
1199− _goto(cx, res);
1214+ _goto(cx, res, offset_encoding);
12001215}
12011216
12021217pub fn goto_reference(cx: &mut Context) {
@@ -1206,12 +1221,14 @@ pub fn goto_reference(cx: &mut Context) {
12061221 None => return,
12071222 };
12081223
1209− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1224+ let offset_encoding = language_server.offset_encoding();
1225+
1226+ let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor(), offset_encoding);
12101227
12111228 // TODO: handle fails
12121229 let res =
12131230 smol::block_on(language_server.goto_reference(doc.identifier(), pos)).unwrap_or_default();
1214− _goto(cx, res);
1231+ _goto(cx, res, offset_encoding);
12151232}
12161233
12171234pub fn signature_help(cx: &mut Context) {
@@ -1222,7 +1239,11 @@ pub fn signature_help(cx: &mut Context) {
12221239 None => return,
12231240 };
12241241
1225− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1242+ let pos = pos_to_lsp_pos(
1243+ doc.text(),
1244+ doc.selection(view.id).cursor(),
1245+ language_server.offset_encoding(),
1246+ );
12261247
12271248 // TODO: handle fails
12281249
@@ -1579,10 +1600,15 @@ pub fn format_selections(cx: &mut Context) {
15791600 // via lsp if available
15801601 // else via tree-sitter indentation calculations
15811602
1603+ let language_server = match doc.language_server() {
1604+ Some(language_server) => language_server,
1605+ None => return,
1606+ };
1607+
15821608 let ranges: Vec<lsp::Range> = doc
15831609 .selection(view.id)
15841610 .iter()
1585− .map(|range| range_to_lsp_range(doc.text(), *range))
1611+ .map(|range| range_to_lsp_range(doc.text(), *range, language_server.offset_encoding()))
15861612 .collect();
15871613
15881614 for range in ranges {
@@ -1590,7 +1616,6 @@ pub fn format_selections(cx: &mut Context) {
15901616 Some(language_server) => language_server,
15911617 None => return,
15921618 };
1593−
15941619 // TODO: handle fails
15951620 // TODO: concurrent map
15961621 let edits = smol::block_on(language_server.text_document_range_formatting(
@@ -1600,7 +1625,11 @@ pub fn format_selections(cx: &mut Context) {
16001625 ))
16011626 .unwrap_or_default();
16021627
1603− let transaction = helix_lsp::util::generate_transaction_from_edits(doc.text(), edits);
1628+ let transaction = helix_lsp::util::generate_transaction_from_edits(
1629+ doc.text(),
1630+ edits,
1631+ language_server.offset_encoding(),
1632+ );
16041633
16051634 doc.apply(&transaction, view.id);
16061635 }
@@ -1726,7 +1755,13 @@ pub fn completion(cx: &mut Context) {
17261755 None => return,
17271756 };
17281757
1729− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1758+ let offset_encoding = language_server.offset_encoding();
1759+
1760+ let pos = pos_to_lsp_pos(
1761+ doc.text(),
1762+ doc.selection(view.id).cursor(),
1763+ language_server.offset_encoding(),
1764+ );
17301765
17311766 // TODO: handle fails
17321767 let res = smol::block_on(language_server.completion(doc.identifier(), pos)).unwrap();
@@ -1754,7 +1789,7 @@ pub fn completion(cx: &mut Context) {
17541789 let size = compositor.size();
17551790 let ui = compositor.find("hx::ui::editor::EditorView").unwrap();
17561791 if let Some(ui) = ui.as_any_mut().downcast_mut::<ui::EditorView>() {
1757− ui.set_completion(items, trigger_offset, size);
1792+ ui.set_completion(items, offset_encoding, trigger_offset, size);
17581793 };
17591794 }
17601795 },
@@ -1779,7 +1814,11 @@ pub fn hover(cx: &mut Context) {
17791814
17801815 // TODO: blocking here is not ideal, make commands async fn?
17811816 // not like we can process additional input meanwhile though
1782− let pos = pos_to_lsp_pos(doc.text(), doc.selection(view.id).cursor());
1817+ let pos = pos_to_lsp_pos(
1818+ doc.text(),
1819+ doc.selection(view.id).cursor(),
1820+ language_server.offset_encoding(),
1821+ );
17831822
17841823 // TODO: handle fails
17851824 let res = smol::block_on(language_server.text_document_hover(doc.identifier(), pos))