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

Custom EditableStyledDocument #277

Merged
merged 12 commits into from
Apr 1, 2016
Merged

Conversation

JordanMartinez
Copy link
Contributor

I used EditableStyledDocument's methods as the base for the new interface.

@JordanMartinez
Copy link
Contributor Author

I didn't include replaceText(int, int, String) because that seems to be handled by StyledTextAreaModel now and you seem to only have it in EditableStyledDocumentImpl as a convenience method to use when testing that class

@JordanMartinez
Copy link
Contributor Author

I'd also like to rename plainTextChanges to plainChanges in StyledTextAreaModel and StyledTextArea. I know it introduces a breaking change, but it seems to be a more consistent naming scheme (e.g. plainChanges and richChanges).

// only allow changes that added/removed text; exclude style changes
.filter(c -> c.insertedLength() != 0 || c.removedLength() != 0)
.map(c -> new PlainTextChange(c.position, c.removed.getText(), c.inserted.getText()));
}
Copy link
Member

Choose a reason for hiding this comment

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

If there is a rich-text change, then insertedLength or removedLength is non-zero already. You probably want to first map and then filter out plain-text changes where removed.equals(inserted).

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Wouldn't it be more efficient to filter it first? Otherwise, we're creating unneeded PlainTextChangees:

default EventStream<PlainTextChange> plainChanges() {
    return richChanges()
            // exclude style changes
            .filter(c -> !c.inserted.getText().equals(c.removed.getText()))
            .map(c -> new PlainTextChange(c.position, c.removed.getText(), c.inserted.getText()));
}

Copy link
Member

Choose a reason for hiding this comment

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

Yes, slightly. On the other hand there is a slight repetition of code in calling getText().

And if you want to avoid an intermediate EventStream, use filterMap.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yes, slightly. On the other hand there is a slight repetition of code in calling getText().

Yeah... I noticed that, too. One way to get around it 😜

    default EventStream<PlainTextChange> plainChanges() {
        return richChanges()
                // exclude style changes
                .map(c -> {
                    String inserted = c.inserted.getText();
                    String removed = c.removed.getText();
                    if (!inserted.equals(removed)) {
                        return new PlainTextChange(c.position, removed, inserted);
                    } else {
                        return null;
                    }
                })
                .filter(c -> c != null);
    }

Copy link
Member

Choose a reason for hiding this comment

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

I don't care so much, do what you think is right ;)

Copy link
Member

Choose a reason for hiding this comment

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

I wouldn't care too much about optimizing one object allocation, since there are already other much higher costs paid anyway.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

With the most recent approach used, does that lead to higher costs due to the EventStreams?

Copy link
Member

Choose a reason for hiding this comment

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

An extra EventStream adds a few stack frames to the call stack when propagating the event. But even by the time an edit reaches the plainChanges() stream, so many objects have been allocated and dismissed that one more or less doesn't make any difference. Therefore, I would go for code clarity.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

So you do care 😉

Ok. I didn't factor that into consideration. Code clarity it is.

Copy link
Member

Choose a reason for hiding this comment

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

I guess I do care, when I see how much noise 4e6ce6b adds in the name of saving one object allocation per change. Also, code comments can go out of sync with code very easily, so self-documenting code is better :)

@JordanMartinez
Copy link
Contributor Author

On another note, does StyledTextArea#getModel() need to be protected? I feel like it should be package-private now (it was used to get the underlying document, but we have a better API for that now)

@TomasMikula
Copy link
Member

Agreed.

* Content model for {@link StyledTextArea}. Implements edit operations
* on styled text, but not worrying about additional aspects such as
* caret or selection.
* Provides an efficient implementation of {@link EditableStyledDocument}
Copy link
Member

Choose a reason for hiding this comment

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

I don't think it is very efficient :) Could be improved.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Lol... that was my assumption since you wrote it 😄

@JordanMartinez
Copy link
Contributor Author

Whoops... that commit message should be "package-private" not "private"...

@JordanMartinez
Copy link
Contributor Author

If there's nothing else that needs to be fixed, I'd like to open a new PR that fixes the "package-private not private" erroneous commit message.

@TomasMikula
Copy link
Member

You can also

git rebase -i HEAD~14

to reorder and squash some of the last 14 commits and then

git push -f

to rewrite the history of this PR.

@JordanMartinez
Copy link
Contributor Author

Sorry that it took so long to update the PR. I almost finished updating the history, but then I had to leave for something and wasn't able to complete the update.

@TomasMikula
Copy link
Member

No worries, my reaction periods tend to be much longer ;)

EventStream<PlainTextChange> plainChanges();
default EventStream<PlainTextChange> plainChanges() {
return richChanges()
// map is used to prevent code repetition: StyledDocument#getText()
Copy link
Member

Choose a reason for hiding this comment

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

Out of context of our previous discussion, this comment does not make much sense, does it? ;)

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 suppose not... should it be removed entirely?

@JordanMartinez
Copy link
Contributor Author

Is there anything else to do before merging this PR? I still haven't heard back from you about the "out of context" mapping comment.

@TomasMikula
Copy link
Member

Yeah, I think that comment is better removed entirely.

…t and can be confusing.

The goal is code clarity. There are at least three different ways to achieve the same result.
- Pros: The two other ways use less memory or don't have code repetition
- Cons: The resulting code is quirky and not easily understandable.

 One could write comments to explain the quirkiness of the code used, but those comments might not be updated in future commits. So, self-documenting code that is slightly less efficient was chosen as the best option.
@JordanMartinez
Copy link
Contributor Author

The commit message gives more context to the comment removal. So, that should suffice for now.

@TomasMikula
Copy link
Member

👍

Going to merge now. Though EditableStyledDocument as it stands now is a hell of an interface asking someone to implement. It should be gradually simplified.

@TomasMikula TomasMikula merged commit c9918ac into FXMisc:master Apr 1, 2016
@JordanMartinez
Copy link
Contributor Author

Though EditableStyledDocument as it stands now is a hell of an interface asking someone to implement. It should be gradually simplified.

That is true.... On one hand, StyledTextAreaModel does seem to make use of all of them at some point or another (whether directly or through some other call within a method call). Still, I didn't check to insure that it was as simple as StyledTextAreaModel would currently allow.
On another hand, making StyledDocumentBase public (or perhaps an EditableStyledDocumentBase) could help with that.

@JordanMartinez JordanMartinez deleted the customESD branch April 1, 2016 20:32
@JordanMartinez
Copy link
Contributor Author

When you have time, could you update the snapshot release?

@TomasMikula
Copy link
Member

Updated.

@JordanMartinez
Copy link
Contributor Author

Thanks! 👍

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.

2 participants