Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Position insertion point in input field with mouse #14291

Merged
merged 1 commit into from Jan 11, 2017

Conversation

fiji-flo
Copy link
Contributor

@fiji-flo fiji-flo commented Nov 20, 2016

Implements cursor positioning in input elements (text/password) via mouse. The related issue is #10083 but is only covered partly.
This PR does not cover:

  • positioning in textarea elements via mouse
  • text selection in input/textarea elements via mouse

  • There are tests for these changes OR
  • These changes do not require tests because I can't think of a way to test mouse interaction in the current test pipeline.

This change is Reviewable

@highfive
Copy link

Heads up! This PR modifies the following files:

  • @KiChjang: components/script/dom/htmlinputelement.rs, components/script/dom/window.rs, components/script_layout_interface/message.rs, components/script_layout_interface/rpc.rs
  • @fitzgen: components/script/dom/htmlinputelement.rs, components/script/dom/window.rs, components/script_layout_interface/message.rs, components/script_layout_interface/rpc.rs
  • @emilio: components/layout/query.rs

@highfive
Copy link

warning Warning warning

  • These commits modify unsafe code. Please review it carefully!
  • These commits modify gfx, layout, and script code, but no tests are modified. Please consider adding a test!

@highfive highfive added the S-awaiting-review There is new code that needs to be reviewed. label Nov 20, 2016
@bors-servo
Copy link
Contributor

☔ The latest upstream changes (presumably #14367) made this pull request unmergeable. Please resolve the merge conflicts.

@highfive highfive added the S-needs-rebase There are merge conflict errors. label Dec 6, 2016
@jdm
Copy link
Member

jdm commented Dec 6, 2016

@nox review ping.

@fiji-flo
Copy link
Contributor Author

fiji-flo commented Dec 7, 2016

I rebased my branch to solve some merge conflicts.

@KiChjang KiChjang removed the S-needs-rebase There are merge conflict errors. label Dec 7, 2016
@jdm
Copy link
Member

jdm commented Dec 15, 2016

@nox Review ping.

@nox
Copy link
Contributor

nox commented Dec 16, 2016

I know nothing about gfx and layout. r? @pcwalton

@highfive highfive assigned pcwalton and unassigned nox Dec 16, 2016
Copy link
Member

@emilio emilio left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Only minor nits. The approach in general makes sense to me (I'd need to review way more carefully though). Seems like @pcwalton can review this with less effort than I.

if !self.reflow(ReflowGoal::ForScriptQuery,
ReflowQueryType::TextIndexQuery(node, mouse_x, mouse_y),
ReflowReason::Query) {
println!("failed in reflow");
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

remove.

@@ -92,3 +94,6 @@ impl MarginStyleResponse {
}
}
}

#[derive(Clone)]
pub struct TextIndexResponse(pub Option<(usize)>);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not just TextIndexResponse(pub Option<usize>)?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

An early draft had tuple here. Thanks for seeing this.

@@ -304,6 +304,24 @@ impl<'a> TextRun {
})
}

/// Returns the index in the range of the first glyph advancing over given advance
pub fn range_index_of_advance(&self, range: &Range<ByteIndex>, advance: Au) -> Option<usize> {
if range.is_empty() {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this check necessary? Doesn't natural_words_in_range handle empty ranges?

Also, this function seems to always return Some(..), so why not returning just an usize?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Indeed

@fiji-flo
Copy link
Contributor Author

@emilio Thanks for the first round of feedback. I'll go over it today.

@fiji-flo
Copy link
Contributor Author

fiji-flo commented Jan 5, 2017

@jdm @pcwalton: I rebased and squashed the changes I did after emilio's comments. Could I get some feedback here?

@bors-servo
Copy link
Contributor

☔ The latest upstream changes (presumably #14938) made this pull request unmergeable. Please resolve the merge conflicts.

@highfive highfive added the S-needs-rebase There are merge conflict errors. label Jan 10, 2017
@jdm
Copy link
Member

jdm commented Jan 10, 2017

I'm really sorry about how this work has been received so far @fiji-flo ! I'll make sure it gets some traction today.

index += 1;
true
}
}).collect::<Vec<_>>();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like you're collecting this into a vector and then throwing it away.

I recommend just using a for loop:

for glyph in self.iter_glyphs_for_byte_range(range) {
    ...
}

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Indeed. My bad.

translated_point: &mut Point2D<Au>,
scroll_offsets: &ScrollOffsetMap) {
// Adjust the translated point to account for the scroll offset if
// necessary. This can only happen when WebRender is in use.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While you're here, could you remove the "This can only happen when WebRender is in use." bit? WebRender is always enabled now.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure.

}
self.hit_test_contents(traversal, &translated_point, client_point, scroll_offsets, result);
}

fn hit_test_stacking_context<'a>(&self,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you add a comment explaining that this function translates the point to account for the scroll offset?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure if get which function you're referring to? While adopting to your comments if removed hit_test_stacking_context to make it more readable.

@jdm jdm added S-needs-code-changes Changes have not yet been made that were requested by a reviewer. and removed S-awaiting-review There is new code that needs to be reviewed. labels Jan 10, 2017
@highfive highfive added S-awaiting-review There is new code that needs to be reviewed. and removed S-needs-code-changes Changes have not yet been made that were requested by a reviewer. labels Jan 10, 2017
@fiji-flo
Copy link
Contributor Author

@jdm thanks for pushing
@pcwalton thanks for the feedback

I adopted my changes to the feedback, rebased and squashed.

@jdm jdm removed the S-needs-rebase There are merge conflict errors. label Jan 11, 2017
Copy link
Contributor

@pcwalton pcwalton left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is looking pretty good, just a couple more nits

}
if current_advance > advance {
break;
} else {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: No need for else after break.

@@ -547,6 +547,25 @@ impl<'a> GlyphStore {
}

#[inline]
pub fn range_index_of_advance(&self, range: &Range<ByteIndex>, advance: Au, extra_word_spacing: Au) -> (usize, Au) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please document what the return values of this function are in a comment.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While describing what this function returns I realized that it's more intuitive if it returns (index, current_advance) instead of (index, advance -current_advance). This just needed a slight modification in the part that invokes this.
I'll add some comments after I push the modifications.

let (new_index, new_remaining) =
slice.glyphs.range_index_of_advance(&slice.range, remaining, self.extra_word_spacing);
remaining = new_remaining;
new_index + index
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Isn't there a sum method on iterators?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess you mean doing a map and sum which would indeed look nicer. That's just a habit from my early haskell days.

@fiji-flo
Copy link
Contributor Author

Thanks for the feedback. Adopted and squashed.

.map(|slice| {
let (slice_index, slice_advance) =
slice.glyphs.range_index_of_advance(&slice.range, remaining, self.extra_word_spacing);
remaining -= slice_advance;
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pcwalton glyphs.range_index_of_advance now returns (index, advanced) instead of (index, remaining) to make it more intuitive. Therefore we need to update remaining here.

@pcwalton
Copy link
Contributor

@bors-servo: r+

@bors-servo
Copy link
Contributor

📌 Commit b40db5b has been approved by pcwalton

@highfive highfive added S-awaiting-merge The PR is in the process of compiling and running tests on the automated CI. and removed S-awaiting-review There is new code that needs to be reviewed. labels Jan 11, 2017
@bors-servo
Copy link
Contributor

⌛ Testing commit b40db5b with merge 68a8e1b...

bors-servo pushed a commit that referenced this pull request Jan 11, 2017
Position insertion point in input field with mouse

<!-- Please describe your changes on the following line: -->
Implements cursor positioning in input elements (text/password) via mouse. The related issue is #10083 but is only covered partly.
This PR does **not** cover:
* positioning in textarea elements via mouse
* text selection in input/textarea elements via mouse

---
<!-- Thank you for contributing to Servo! Please replace each `[ ]` by `[X]` when the step is complete, and replace `__` with appropriate data: -->
- [X] `./mach build -d` does not report any errors
- [X] `./mach test-tidy` does not report any errors
- [ ] These changes fix #10083 (github issue number if applicable).

<!-- Either: -->
- [ ] There are tests for these changes OR
- [ ] These changes do not require tests because I can't think of a way to test mouse interaction in the current test pipeline.

<!-- Pull requests that do not address these steps are welcome, but they will require additional verification as part of the review process. -->

<!-- Reviewable:start -->
---
This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/servo/servo/14291)
<!-- Reviewable:end -->
@bors-servo
Copy link
Contributor

@bors-servo bors-servo merged commit b40db5b into servo:master Jan 11, 2017
@highfive highfive removed the S-awaiting-merge The PR is in the process of compiling and running tests on the automated CI. label Jan 11, 2017
@paulrouget
Copy link
Contributor

This caused a regression: #15015

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

input / textarea - mouse interaction doesn't work
9 participants