GithubHelp home page GithubHelp logo

signavio / react-mentions Goto Github PK

View Code? Open in Web Editor NEW
2.4K 25.0 552.0 34.67 MB

@mention people in a textarea

Home Page: https://react-mentions.vercel.app

License: Other

JavaScript 100.00%
react mentions tags inline-styles

react-mentions's Introduction

REUSE status

A React component that let's you mention people in a textarea like you are used to on Facebook or Twitter.

Used in production at Signavio, State, Snips, Swat.io, GotDone, Volinspire, Marvin, Timely, GuideFitter, Evite, Publer, Kontentino, Wix.com, Highlight and you?

Getting started

Install the react-mentions package via npm:

npm install react-mentions --save

Or yarn:

yarn add react-mentions

The package exports two React components for rendering the mentions textarea:

import { MentionsInput, Mention } from 'react-mentions'

MentionsInput is the main component rendering the textarea control. It takes one or multiple Mention components as its children. Each Mention component represents a data source for a specific class of mentionable objects, such as users, template variables, issues, etc.

Example:

<MentionsInput value={this.state.value} onChange={this.handleChange}>
  <Mention
    trigger="@"
    data={this.props.users}
    renderSuggestion={this.renderUserSuggestion}
  />
  <Mention
    trigger="#"
    data={this.requestTag}
    renderSuggestion={this.renderTagSuggestion}
  />
</MentionsInput>

You can find more examples here: demo/src/examples

Configuration

The MentionsInput supports the following props for configuring the widget:

Prop name Type Default value Description
value string '' The value containing markup for mentions
onChange function (event, newValue, newPlainTextValue, mentions) empty function A callback that is invoked when the user changes the value in the mentions input
onKeyDown function (event) empty function A callback that is invoked when the user presses a key in the mentions input
singleLine boolean false Renders a single line text input instead of a textarea, if set to true
onBlur function (event, clickedSuggestion) empty function Passes true as second argument if the blur was caused by a mousedown on a suggestion
allowSpaceInQuery boolean false Keep suggestions open even if the user separates keywords with spaces.
suggestionsPortalHost DOM Element undefined Render suggestions into the DOM in the supplied host element.
inputRef React ref undefined Accepts a React ref to forward to the underlying input element
allowSuggestionsAboveCursor boolean false Renders the SuggestionList above the cursor if there is not enough space below
forceSuggestionsAboveCursor boolean false Forces the SuggestionList to be rendered above the cursor
a11ySuggestionsListLabel string '' This label would be exposed to screen readers when suggestion popup appears
customSuggestionsContainer function(children) empty function Allows customizing the container of the suggestions

Each data source is configured using a Mention component, which has the following props:

Prop name Type Default value Description
trigger regexp or string '@' Defines the char sequence upon which to trigger querying the data source
data array or function (search, callback) null An array of the mentionable data entries (objects with id & display keys, or a filtering function that returns an array based on a query parameter
renderSuggestion function (entry, search, highlightedDisplay, index, focused) null Allows customizing how mention suggestions are rendered (optional)
markup string '@[__display__](__id__)' A template string for the markup to use for mentions
displayTransform function (id, display) returns display Accepts a function for customizing the string that is displayed for a mention
regex RegExp automatically derived from markup pattern Allows providing a custom regular expression for parsing your markup and extracting the placeholder interpolations (optional)
onAdd function (id, display, startPos, endPos) empty function Callback invoked when a suggestion has been added (optional)
appendSpaceOnAdd boolean false Append a space when a suggestion has been added (optional)

If a function is passed as the data prop, that function will be called with the current search query as first, and a callback function as second argument. The callback can be used to provide results asynchronously, e.g., after fetch requests. (It can even be called multiple times to update the list of suggestions.)

Styling

react-mentions supports css, css modules, and inline styles. It is shipped with only some essential inline style definitions and without any css. Some example inline styles demonstrating how to customize the appearance of the MentionsInput can be found at demo/src/examples/defaultStyle.js.

If you want to use css, simply assign a className prop to MentionsInput. All DOM nodes rendered by the component will then receive class name attributes that are derived from the base class name you provided.

If you want to avoid global class names and use css modules instead, you can provide the automatically generated class names as classNames to the MentionsInput. See demo/src/examples/CssModules.js for an example of using react-mentions with css modules.

You can also assign className and style props to the Mention elements to define how to highlight the mentioned words.

Testing

Due to react-mentions' internal cursor tracking it is not good enough to simulate the editing of the textarea value using ReactTestUtils.Simulate.change. We recommend using @testing-library/user-event for a realistic simulation of events as they would happen in the browser as the user interacts the textarea.


If you want to contribute, first of all: thank you ❤️. Please check CONTRIBUTING.md and/or create an issue.

react-mentions's People

Contributors

atilafassina avatar dependabot[bot] avatar develra avatar frontendphil avatar gisaklement avatar github-actions[bot] avatar glifchits avatar jfschwarz avatar jmblog avatar klacointe avatar koshkarik avatar matthewtmoran avatar methyl avatar nassimbenkirane avatar niekert avatar nikgraf avatar nikhil2kumar avatar niknokseyer avatar onoufriosm avatar pitbi avatar sigrsig avatar stefansundin avatar steffektif avatar t1mmen avatar thibautmarechal avatar willmruzek avatar wtr7 avatar wxnchen11 avatar yannaialter avatar yannbriancon avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

react-mentions's Issues

React 0.13 warning

I'm getting the following warning using react 0.13.3 and react-mentions 0.1.4.

Warning: Don't set .props.children of the React component <span />. Instead, specify the correct value when initially creating the element or use React.cloneElement to make a new element with updated props. The element was created by MentionsInput.

Probably because of https://github.com/effektif/react-mentions/blob/master/lib/MentionsInput.js#L184?

I will try to investigate further later on :)

Strange behavior with markup option

Hi,

I'm having an strange behavior with the next configuration:

<MentionsInput
          value={this.state.textAreaValue}
          onChange={this.handleTextAreaChange}
          markup="@__display__"
          displayTransform={this.mentionDisplayTransform}>

            <Mention
              type="user"
              trigger="@"
              renderSuggestion={this.renderSuggestion}
              data={mentionNames}
             />
          </MentionsInput>

// functions
handleTextAreaChange: function(ev, newValue) {
    this.setState({textAreaValue: newValue});
  },

  renderSuggestion: function(id, display, search, highlightedDisplay) {
    return (
      <div className="suggestion-item">
        @{highlightedDisplay}
      </div>
    );
  },

  mentionDisplayTransform: function(id, display, type) {
    return "@" + display;
  }

The caret is sometimes blocked, and you can't type anymore after add a mention. If I remove the markup property it works fine, but that's breaking some stuff in our backend.

Could you take a look at this?

Thanks and congrats for this library, despite this and #18 it works pretty well.

Issue with JSX in /lib

I have added: "react-mentions": "*" to my "dependencies" in my package.json. Then I run npm install, which correctly pulls down the files. When I try to reference via var ReactMentions = require('react-mentions'); I receive a compilation error: /node_modules/react-mentions/lib/MentionsInput.js: Unexpected token (99:6) when browserify builds a bundle. It appears this is because there is JSX in MentionsInput.js . An attempt to include the dist file directly results in another error because I do not have a global reference to React.

Any chance you guys are interested in getting compiled jsx in the /lib directory? It appears react-bootstrap developers in /src and populates /lib and /dist with compiled files.

ReactJS 0.14 issues

Hi. Before I was using the dist/react-mentions.js in our project and was working fine. now with the update toReactJS v0.14.0 and this new update in react-mentions (v0.2.0) I keep receiving this error:

Uncaught TypeError: Cannot read property 'firstChild' of undefinedReactMount.findComponentRoot @ react-mentions.js:11877ReactMount.findReactNodeByID @ react-mentions.js:11841getNodeFromInstance @ react-mentions.js:11347findDOMNode @ react-mentions.js:16361module.exports.React.createClass.updateSuggestionsPosition @ react-mentions.js:504module.exports.React.createClass.componentDidUpdate @ react-mentions.js:534assign.notifyAll @ react-with-addons.js:889ON_DOM_READY_QUEUEING.close @ react-with-addons.js:13487Mixin.closeAll @ react-with-addons.js:17301Mixin.perform @ react-with-addons.js:17248Mixin.perform @ react-with-addons.js:17235assign.perform @ react-with-addons.js:15303flushBatchedUpdates @ react-with-addons.js:15364ReactPerf.measure.wrapper @ react-with-addons.js:12861Mixin.closeAll @ react-with-addons.js:17301Mixin.perform @ react-with-addons.js:17248ReactDefaultBatchingStrategy.batchedUpdates @ react-with-addons.js:8833batchedUpdates @ react-with-addons.js:15311ReactEventListener.dispatchEvent @ react-with-addons.js:10334

JS Error when navigating with Cmd+Tab

Focus the mentions input. Open the suggestions with # or @, then navigate to another window using cmd+tab, select the window with the mentions input again and hit any key. BAM! 💥

Suggestions header & footer elements

Hey there! Thanks for the component. I've had a lot of success with it. However I have two use-cases that I haven't been able to solve with it. I plan on forking the component and providing a PR, but before I do that I thought I'd share my use cases just incase you know of a better approach.

Context

  • My suggestions list has a max-height with overflow-y: auto to show a scroll bar if my list items expand beyond the max-height.

Use-cases

  • Keyboard-scrolling down or up to items in the "hidden" areas of the suggestion list does not scroll the container. I need the container to scroll when the "focus"ed list-item is outside the container's view.
  • I need a way to add a header to the suggestion overlay.

Solutions

  • Expose on event shiftFocus that passes the "focus"ed list item. I should then be able to conditionally scrollTop.
  • Add a prop header to Mention that accepts a react component that will be inserted before the <ul>.

Let me know what you think. Thanks again.

Open suggestions above cursor

I would be great if the suggestions box will be opened above the cursor if there are not enough space below.

Example:
We have a comment stream with a "insert comment" form at the bottom of the body. if a user want to add a mention, the suggestions-box opens out of the body.

Add support for more HTML input attributes

Currently, only some selected props are passed through to the actual DOM input component (readOnly , disabled, placeholder). Instead, all props that are valid for a textarea / input should be supported.

Cursor position jumps back on white spaces in Mobile Chrome on Android

Typing in any MentionsInput field in the Chrome browser on Android jumps the cursor position backwards on white spaces, making it impossible to type free form text.

Steps to reproduce:

  1. Open latest Chrome (43.0.2357.93, updated 10 Jun) on an Android phone (tested on Nexus 5, Android 5.1)
  2. Go to http://effektif.github.io/react-mentions/
  3. Focus any of the example input fields and start typing a sentence

Expected: the cursor position stays at the end of whatever you've typed
Actual: the cursor jumps back (typically by the previous words' length) and breaks the typing flow

Add multiple trigger support?

Is it possible to listen to more than one trigger?
e.g. How to autocomplete both "@" and "#" from different sources?
Say, "@" listens to user ajax source.
Whilst "#" listens to tags source.

Support readOnly

Currently mentions are always editable. So support for a readOnly attribute would be great.

Example usage?

I've been trying to figure this component out. I had problems with retrieving the value of the input text, and had to check the code provided. I'm not sure if what I did was correct, but I ended up with:

this.refs.mentionsinput.refs.input

Then after that I had problems when triggering the suggestion overlay by pressing '@'. It seems my data was expected to have both 'display' and 'id'.

After that it still wouldn't work. It would be great if there was example usage.

Chinese/Japanese characters not supported

To reproduce:
Switch language to Katakana (Japanese) and type "ka".

Output: "k" (Doesn't input the a and caret jumps back before "k")
Expected output: カ (Should combine "ka" to this)

Update:

  • Seems to be connected to all accents as well
  • Works "Single line input" / "Adv. options" - demo but not in the "Multiple trigger patterns" - demo

Any ideas on how test cases should be written?

Hi,

Thanks for the promising library.

Recently I'm trying to use it in my project. However, it seems hard for me to figure out how a test case should be written. I'd like to have the following test case:

when a user types in `@tom`, it should show up a selection

and my test case is written as follows (in karma + mocha + sinon),

var component = React.render(
    <MyMentionComponent // Uses MentionsInput internally
        renderAtSuggestion={callbackSpy} // Delegates to Mention.props.renderSuggestion
    />,
    div
);

expect(callbackSpy.called).to.be.false();
var textareaEl = React.findDOMNode(TestUtils.findRenderedDOMComponentWithTag(component, "textarea"));
textareaEl.focus();

textareaEl.value = "Initial text ...";
TestUtils.Simulate.change(textareaEl);
expect(textareaEl.value).to.equal("Initial text ...");

textareaEl.value = "Initial text ... @tom";
TestUtils.Simulate.change(textareaEl);
expect(textareaEl.value).to.equal("Initial text ... @tom");

expect(callbackSpy.called).to.be.true(); // fails here

I also tried to change the value of textarea.value using Chrome's console, and using jquery to trigger change event afterwards. It doesn't help either. Do you have any ideas on how to get it right?

Thanks

AMD style

any guide on how to use this with amd style?

i do have react.createClass is undefined with integrate with amd style. any idea?

Add support for custom regex

The regex generically derived from the markup is sometimes not right. E.g. for markup @__id__ and value "@johndoe " it would only match "@j". In such situations, the user should be able to provide a customized regex, such as /@(\w+)/g.

Async data provider

Is it possible to use ajax request as a data provider? I can see that I can pass array or function in data prop but I don't know how async could be handled.

Enable copy paste

It would be great if the mentions component would somehow support a copy and paste scenario in which the mentions are preserved. This is probably not easy to achieve but I would like to explore this possibility.

Broken build?

Hi,

sorry, I'm having problems today trying to use your libary:

~  npm install react-mentions
[email protected] node_modules/react-mentions
➜  ~  node
> require('react-mentions')
Error: Cannot find module 'react-mentions'
    at Function.Module._resolveFilename (module.js:338:15)
    at Function.Module._load (module.js:280:25)
    at Module.require (module.js:364:17)
    at require (module.js:380:17)
    at repl:1:2
    at REPLServer.self.eval (repl.js:110:21)
    at Interface.<anonymous> (repl.js:239:12)
    at Interface.emit (events.js:95:17)
    at Interface._onLine (readline.js:202:10)
    at Interface._line (readline.js:531:8)

Have you broken the build maybe? I couldn't use it in two different hosts.

Programmatically style highlighter exactly the same as the textarea

At the moment it has to be manually ensured that the highlighter has the same values set for all relevant CSS properties, so that the characters in the textarea and highlighter lie exactly on top of each other.

Not really sure whether it is actually wanted, but, this can also be done automatically by programmatically setting the style of the highlighter based on the style of the textarea. This has already been done by others, e.g.: https://github.com/component/textarea-caret-position/blob/master/index.js

Safe pasting

Just to make sure everything works as expected ;) Alma just reported that our current implementation still has some problems when she pastes any of the Mail body texts in the attached document. Might be a good test case :)

Line breaks are inserted at random spots and the formatting in general is messed up.


Email de confirmation :
Madame / Monsieur Trigger email / From name,

Nous vous remercions pour votre candidature et votre intérêt pour rejoindre notre organisation.
Nous évaluons votre profil et reviendrons vers vous dès que possible. Cela peut prendre un peu de temps donc nous vous remercions de votre patience.
Sincères salutation,
Ressources humaines
Signavio GmbH

Email d’invitation :
Madame / Monsieur Trigger email / From name,

Merci pour votre candidature. Votre profil nous a interpellés et nous aimerions vous rencontrer. Nous vous invitons donc pour un entretien dans nos bureaux le Proposition date d'entretien.
Dans l'attente de votre confirmation, nous vous souhaitons une agréable journée.
Cordialement,
Ressources humaines
Signavio GmbH

Email de rejet:
Madame / Monsieur Trigger email / From name,

Nous vous remercions de nouveau pour votre candidature. Nous avons évalué vos compétences par rapport au poste requis, et malheureusement nous ne pouvons pas donner suite à votre candidature.
Nous vous souhaitons beaucoup de réussite.
Sincères salutation,
Ressources humaines
Signavio GmbH

Email de candidature :

Candidature

Madame / Monsieur le Directeur des Ressources Humaines,
Je vous envoie en pièce jointe ma candidature pour le poste de Secrétaire Commercial que j’ai trouvé sur votre site.
Je me tiens à votre disposition pour toute question et espère vous rencontrer prochainement pour un entretien d’embauche.
Respectueuses salutations,

Backspace deletes everything in IE

In IE, when you try to delete something using backspace, then everything before the current cursor position is being deleted. Not cool.

Only a ReactOwner can have refs error.

Hi guys,

Installed react-mentions on in my React app and get this weird error:

Uncaught Error: Invariant Violation: addComponentAsRefTo(...): Only a ReactOwner can have refs. This usually means that you're trying to add a ref to a component that doesn't have an owner (that is, was not created inside of another component's render method). Try rendering this component inside of a new top-level component which will hold the ref.

I guess it has something to do with my setup but I have never seen this with other imports.

My package.json looks as follows:

{
"dependencies": {
"react": "0.13.x",
"react-router": "0.13.x"
},
"devDependencies": {
"del": "1.1.x",
"envify": "3.2.x",
"gulp": "3.8.x",
"gulp-bower": "0.0.x",
"gulp-browserify": "0.5.x",
"gulp-concat": "2.4.x",
"gulp-minify-css": "0.3.x",
"gulp-rename": "1.2.x",
"gulp-sass": "1.2.x",
"gulp-uglify": "1.0.x",
"gulp-util": "3.0.x",
"reactify": "0.17.x",
"underscore": "1.7.x",
"flux": "2.0.x",
"object-assign": "^1.0.0",
"keymirror": "~0.1.0",
"moment": "2.10.x",
"react-select": "0.5.x",
"react-loader": "~1.4.0",
"js-striphtml": "~1.1.2",
"react-mentions": "0.1.17"
},
"name": "my-demo",
"private": false,
"scripts": {
"postinstall": "gulp install",
"watch": "gulp"
},
"version": "1.0.0"
}

Any ideas?

Thanks!

Emoji's appear double in mobile Safari

Problem

screen shot 2015-08-18 at 14 23 49
Emojis appear double in mobile Safari.

Why it happens

screen shot 2015-08-18 at 14 23 11
(manually hidden the textarea element in screenshot above - only highlight remains)
color: transparent doesn't hide emojis in Safari (it does in Chrome and Firefox). This in combination with that the emojis in highlighter don't align with the ones in textarea in mobile Safari is what causes this issue.

Fix

Css fix, which I'm currently using:

.highlighter span {
  // visually hide everything but the actual highlight, which is rendered as a <strong>
  opacity: 0; 
}

This solution is quite fragile. Given your no-css approach for this module, could you just output the opacity:0; (or visibility:hidden) inline directly on these elements? I would have forked a PR, but not sure where in your library to add that code. :)

Cheers

Warning: React.findDOMNode is deprecated. Please use ReactDOM.findDOMNode from require('react-dom') instead.

Hi, I'm getting this warning here:

  updateSuggestionsPosition: function updateSuggestionsPosition() {
    if (!this.refs.caret || !this.refs.suggestions) return;

    var containerEl = this.refs.container;
    var caretEl = this.refs.caret;
    var suggestionsEl = React.findDOMNode(this.refs.suggestions); // <<<<<< Warning here.
    var highligherEl = this.refs.highlighter;
    if (!suggestionsEl) return;

    var leftPos = caretEl.offsetLeft - highligherEl.scrollLeft;
    // guard for mentions suggestions list clipped by right edge of window
    if (leftPos + suggestionsEl.offsetWidth > containerEl.offsetWidth) {
      suggestionsEl.style.right = "0px";
    } else {
      suggestionsEl.style.left = leftPos + "px";
    }
    suggestionsEl.style.top = caretEl.offsetTop - highligherEl.scrollTop + "px";
  },

Can potentially be fixed by using:

    var suggestionsEl = ReactDOM.findDOMNode(this.refs.suggestions);

cmd/alt + delete do not work

The regular shortcuts should work:

  • alt + delete removes a whole word
  • cmd (ctrl) + delete removes a whole line

autogrowTextarea messes up scroll position for long textareas

Hi, thanks for awesome library! We currently use it on state.com, kudos!

The issue is this line - setting the textarea height to auto (before then reapplying the actual height).

If textarea had a lot of content, pushing the height of the page, and the user was scrolled down towards the bottom of the page, then setting the height to auto will produce a scroll position outside of the page, and the browser will update it to be in range. The scroll position is then never updated again after the textarea is given back it's height. Result: Scroll position jumps up.

Steps to reproduce:
0. Have a page with a react-mentions textarea on it.

  1. Write a looooot of text in it, enough so that it pushes the height of the page.
  2. Scroll down to the bottom of the page.
  3. Cause react-mentions to render

So I'm a bit curious - why are you resetting the height like this in the first place; what does it achieve?

Cheers

Support for [email protected]

npm WARN peerDependencies The peer dependency [email protected] included from react-mentions will no
npm WARN peerDependencies longer be automatically installed to fulfill the peerDependency
npm WARN peerDependencies in npm 3+. Your application will need to depend on it explicitly.
npm ERR! Linux 3.16.0-34-generic
npm ERR! argv "/home/leesiongchan/.nvm/versions/io.js/v1.6.4/bin/iojs" "/home/leesiongchan/.nvm/versions/io.js/v1.6.4/bin/npm" "install" "--save" "react-mentions"
npm ERR! node v1.6.4
npm ERR! npm v2.7.6
npm ERR! code EPEERINVALID

npm ERR! peerinvalid The package react does not satisfy its siblings' peerDependencies requirements!
npm ERR! peerinvalid Peer [email protected] wants [email protected]
npm ERR! peerinvalid Peer [email protected] wants [email protected]

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.