Hashtags and Mentions in Swift
Update 11/20/2017 : The following feature is being used in Spotlight! Check it out here. https://spotlight.social/
Also, the github no longer points to latest version which fixes all the problems I had when writing this guide. I don’t plan on releasing the latest version but the current version on github will get you 95% of the functionality you want.
— — — — — — — — — — — — — — — — — — — — — — — — — — — — — — —
One of the features I recently had to implement for a yet unnamed app in development at my startup was hashtags and mentions. Here is how it looks in the product without any personalized info.
A General Overview
In order to implement the necessary functionality, I created a custom class called AttrTextView which inherits from UITextView.
The logic within AttrTextView does two main things:
- Sets text attributes on an incoming string.
- Handles the tap gesture and triggers actions upon selection of # or @
wordType is an enum we will use to refer to a word’s type, textString refers to the string you pass into AttrTextView, attrString refers to the string after attributes are applied onto it, and callBack is a function which handles what data will be displayed.
If a user clicks on a hashtag, they will be presented with search results for the hashtag, and if a user clicks on a mention, they will go to the mentioned user’s profile page if it exists.
Setting & Configuring Text
In a public setText function, you pass the string and the text attributes you want to set on it. setText will handle setting attributes and adding a tap gesture to the hashtag or mention.
Next up is setAttrWithName, a custom function that is used in setText.
Handling the Tap
After setting text attributes and adding a tap gesture recognizer, the tap is handled via a tapRecognized function. In other implementations of tap handling found on StackOverflow’s comments or on the excellent
Tape is one of our most recent iOS apps at Yeti, and one we’re very proud of because it is our largest…yeti.co
, text is checked with a .word granularity. Sadly, this means that special characters such as # and @ are omitted!
In layman’s terms, that means that while clicking on the word itself will register properly, clicking on the “#” character or “@” character in front of the word will not register. To get around around this, I use a .character granularity so I can identify if a special character is clicked. However, my function still makes sure that the callback function can receive the full word even when a special character is clicked! How I do this is shown below with a thorough explanation in the comments.
A Quick Demo and the Callback
Make sure to turn off the textView’s editable, scrollable, and selectable properties.
Also, insert a space at the end of the string you want to pass into setText.
And a very simple callBack function using that enum we created earlier, wordType.
Hope this post was useful and of course, you are free to use AttrTextView.
Note: Aug 1 2017 → Some screenshots might be out of date. Check repo and readme for more information.
Contribute to AttrTextView development by creating an account on GitHub.github.com
Shoutout again to the folks at yeti for a great guide and starting point.