Twitter如何实施Tweet Box? [英] How does Twitter implement its Tweet Box?

查看:163
本文介绍了Twitter如何实施Tweet Box?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图实现类似Twitter的推文框,特别是:


  • 当总长度自动突出显示红色背景中的文本时超过140个字符。

  • 自动将链接,提及和标签以蓝色突出显示。
    应该会在用户输入时自动发生。

    通过我在Twitter上看到的语义标记,看起来他们正在使用 contentEditable div。而且,只要检测到提及/ hashtag /链接或者超过140个字符的长度,就会修改DOM内部:

      < div aria-labelledby =tweet-box-mini-home-profile-labelid =tweet-box-mini-home-profileclass =tweet-box rich-editor notiecontenteditable =truespellcheck =truerole =textboxaria-multiline =truedir =ltraria-autocomplete =listaria-expanded =falsearia-owns =typeahead-dropdown-6> 
    < div> hello world< a>< />< s>< / s> testMention< / a>< / s> ;文字< a href =/ search?q =%23helloWorldclass =twitter-hashtag pretty-linkrole =presentation>< s>#< / s> helloWorld< / a> text< a href =http://www.google.comclass =twitter-timeline-linkrole =presentation> http://www.google.com< / a>文本文本文本文本文本文本文本文本文本文本文本文本文本文本< em>溢出红色文本此处< / em>
    < / div>
    < / div>

    到目前为止所做的工作

    目前,我正在使用contentEditable字段。它触发一个解析文本的函数 onChange / onInput 。通过regexr检查它是否有用户名/链接/ hashtag,并用相应的标签替换它们(我只是使用一个简单的< i> 标签来附上用户名和标签目前)。
    我遇到的问题是因为我正在修改/修改contentEditable的DOM,所以插入光标位置会丢失。
    我看了这个主题在HTML中选择后继续对范围对象进行更改,并且只有在DOM没有改变的情况下才能正常工作(在我的情况中,包含< i> 标签的标签/主题标签, < a> 标记,并且使用< b> 标记进行溢出。



    小提琴: http://jsfiddle.net/4Lsqjkjb/



    有没有人有解决方案/方法来解决这个问题?也许我不应该使用 contentEditable ?或者某种方式不直接修改 contentEditable 字段的DOM,因此c目标位置是否维持?任何帮助,将不胜感激!我尝试过使用 window.getSelection()并在DOM更改之前保存它,但在应用DOM更改后似乎总是重置。

    解决方案



    这不是直接回应源代码构建您的应用程序的一部分到您的规范。 >这是真的,而不是简单的事情。



    你是对的 - 解决这个问题的方法问题是使用 contenteditable =true容器。但是我担心从那里得到很多要复杂得多



    输入DraftJS - 一种用于富文本编辑的javascript解决方案,它为您完成大部分繁重的工作。



    我的解决方案需要使用React和DraftJS






    即插即用解决方案:



    React + DraftJS + 其他人的插件解决方案已在此处。您可以查看 draft-js-plugins.com 这里是Github源代码



    就我个人而言,我不会这样。我宁愿学习他们的GitHub源代码并实现我自己的DraftJS 实体 。因为我认为React-JS-Plugins对链接和提及感觉有点笨重和超重。另外,你在哪里提及?你自己的申请?推特?这样做可以让你控制你抓住所谓的提及的位置。




    DIY解决方案:



    我发现的最佳方式是建立自己的一套工作 entities 的应用程序。



    这当然也要求您使用 React



    原谅我没有真正构建一组完整的工作代码。我有兴趣为前端的React在Meteor建立的应用做类似的工作。所以这对我来说真的很有意义,因为我只会增加一个库(DraftJS),剩下的就是我的自定义 entities 编码出来。


    I'm trying to implement something like Twitter's tweet box, specifically:

    • Automatically highlights text in a red background when the overall length exceeds 140 characters.
    • Automatically highlights links, mentions, and hashtags in blue.

    These should happen automatically aka when a user types.

    By the semantic markup I'm seeing on Twitter, it looks like they're using a contentEditable div. And the DOM inside is modified whenever a mention/hashtag/link is detected, or when the length is exceeded over 140 characters:

    <div aria-labelledby="tweet-box-mini-home-profile-label" id="tweet-box-mini-home-profile" class="tweet-box rich-editor  notie" contenteditable="true" spellcheck="true" role="textbox" aria-multiline="true" dir="ltr" aria-autocomplete="list" aria-expanded="false" aria-owns="typeahead-dropdown-6">
        <div>hello world <a class="twitter-atreply pretty-link" href="/testMention" role="presentation"><s>@</s>testMention</a> text <a href="/search?q=%23helloWorld" class="twitter-hashtag pretty-link" role="presentation"><s>#</s>helloWorld</a> text <a href="http://www.google.com" class="twitter-timeline-link" role="presentation">http://www.google.com</a> text text text text text text text text text text text text text text <em>overflow red text here</em>
        </div>
    </div>
    

    What I have done so far

    Currently, I'm using a contentEditable field. It triggers a function onChange/onInput that parses the text. Check if it has a username/link/hashtag via regexr and replace them with the respective tags (I'm just using a simple <i> tag to enclose username and hashtag for now). The problem I'm having is that because I'm changing/modifying the DOM of the contentEditable, the caret cursor position becomes lost. I looked at this thread Persisting the changes of range objects after selection in HTML and it works fine only if the DOM isn't changed (which it is in my case, surrounding tags/hashtags with <i> tags, links with <a> tags, and overflow with <b> tags.

    Fiddle: http://jsfiddle.net/4Lsqjkjb/

    Does anyone have any alternative solutions/approaches on how to tackle this problem? Maybe I shouldn't use contentEditable? Or some way that doesn't directly modify the DOM of the contentEditable field so the caret position is maintained? Any help would be appreciated! I tried playing around with window.getSelection() and saving it before DOM change, but it always seem to reset after DOM changes are applied.

    解决方案

    This is not a direct answer with source code building the part of your application to your spec.

    This is really not an easy thing to do.

    You're right - the way to solving this problem is to use a contenteditable="true" container. But I'm afraid that from there it gets much much more complicated.

    Enter DraftJS - A javascript solution to rich-text editing which does most of the heavy lifting for you.

    Both of my solutions below require the use of both React and DraftJS


    The Plug-&-Play Solution:

    The React + DraftJS + Someone Else's "Plugin" solution is already here. You can check out draft-js-plugins.com. And here's the Github source code.

    Personally, I wouldn't go this way. I would rather study their GitHub source code and implement my own DraftJS entities. Because I think that React-JS-Plugins feels a little bit clunky and overweight for just Links and Mentions. Plus, where are you "mentioning" from? Your own Application? Twitter? Doing it this way lets you have control over where you're grabbing the so-called "mentions".


    The DIY Solution:

    The best way I have found is to build your own set of working entities on top of a DraftJS based rich-text editor.

    This of course also requires that you're using React.

    Forgive me for not actually building a complete set of working code. I was interested in doing something similar for an App I'm building in Meteor with React on the front-end. So this really made sense to me because I'd only be adding one more library (DraftJS) and the rest would be my custom entities coded out.

    这篇关于Twitter如何实施Tweet Box?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆