define(function (require, exports, module) {

  const Plugin = require('extplug/Plugin')
  const emoji = require('plug/util/emoji')
  const _ = require('underscore')
  const { around } = require('meld')
  const Tooltips = require('./tooltips')
  const Events = require('plug/core/Events')

  const MAX_EMOJI_SUGGESTIONS = 10
  const warnText = 'The Custom Emoji plugin is temporarily unavailable after ' +
                   'plug.dj updated their emoji code. ' +
                   'The plugin should receive an update later today. ' +
                   'Sorry for the inconvenience!'

  const CustomEmoji = Plugin.extend({
    name: 'Custom Emoji',
    description: 'Shows custom emoji defined by room settings.',

    settings: {
      tooltips: { type: 'boolean', label: 'Show Emoji Names on Hover', default: true }
    },

    init(id, ext) {
      this._super(id, ext)
      this.tooltips = new Tooltips(`${id}:tooltips`, ext)
    },

    enable() {
      setTimeout(() => {
        Events
          .trigger('notify', 'icon-chat-system', warnText)
          .trigger('chat:receive', {
            type: 'system',
            message: warnText
          })
      }, 500)
      return this.disable()

      this.listenTo(this.ext.roomSettings, 'change:emoji', this.update)
      this.listenTo(this.ext.roomSettings, 'change:emotes', this.update)
      this.listenTo(this.settings, 'change:tooltips', this.tooltipState)

      // remember the original emoji so we can restore them
      this.originalMap = _.clone(emoji.map)

      // plug.dj does some fancy fast lookup table thing in emoji.lookup,
      // but that doesn't seem particularly useful for a few hundred emoji.
      // so until it is, we'll just use this much simpler version...
      this.advice = around(emoji, 'lookup', joinpoint => {
        let query = joinpoint.args[0].toLowerCase()
        let results = this.emojiNames.filter(key => key.toLowerCase().indexOf(query) === 0)
        return results.sort().slice(0, MAX_EMOJI_SUGGESTIONS)
      })

      this.update()
      this.tooltipState()
    },

    disable() {
      return
      this.reset()
      this.advice.remove()
      if (this.settings.get('tooltips')) {
        this.tooltips.disable()
      }
    },

    tooltipState() {
      if (this.settings.get('tooltips')) {
        this.tooltips.enable()
      }
      else {
        this.tooltips.disable()
      }
    },

    reset() {
      // the emoji map has to be cleared to be updated, because
      // plug retains a local reference to it. (instead of looking
      // it up on the emoji module object all the time)
      // therefore simply reassigning it doesn't work
      _.each(emoji.map, (v, name) => { delete emoji.map[name] })
      _.extend(emoji.map, this.originalMap)
      if (this.tooltips) {
        this.tooltips.map = _.invert(emoji.map)
      }
    },

    update() {
      let custom = this.ext.roomSettings.get('emotes')
                || this.ext.roomSettings.get('emoji')
      this.removeStyles()
      this.reset()
      if (custom) {
        let styles = this.Style()

        _.each(custom, (emote, name) => {
          let id = _.uniqueId('cust-')
          emoji.map[name] = id

          let sel = `.emoji.emoji-${id}`
          if (typeof emote === 'string') {
            styles.set(sel, {
              'background': `url("${emote.replace(/"/g, '\"')}")`,
              'background-position': 'center center',
              'background-size': 'contain',
              'background-repeat': 'no-repeat'
            })
          }
          else if (typeof emote === 'object') {
            if (emote.sheet) {
              styles.set(sel, {
                'background-image': `url("${emote.sheet.replace(/"/g, '\"')}")`,
                'background-position': `${emote.x} ${emote.y}`,
                'background-size': 'contain',
                'background-repeat': 'no-repeat'
              })
            }
            else {
              styles.set(sel, emote)
            }
          }
        })

      }

      this.emojiNames = Object.keys(emoji.map)
      if (this.tooltips) {
        this.tooltips.map = _.invert(emoji.map)
      }
    }
  })

  module.exports = CustomEmoji

})

@@ -954,258 +954,8 @@
 ) %7B%0A
-      setTimeout(() =%3E %7B%0A        Events%0A          .trigger('notify', 'icon-chat-system', warnText)%0A          .trigger('chat:receive', %7B%0A            type: 'system',%0A            message: warnText%0A          %7D)%0A      %7D, 500)%0A      return this.disable()%0A%0A
     
@@ -1268,19 +1268,74 @@
 e(emoji.
-map
+emojiMap)%0A      this.originalPlug = _.clone(emoji.plugdata
 )%0A%0A     
@@ -1897,21 +1897,8 @@
 ) %7B%0A
-      return%0A
     
@@ -2459,92 +2459,64 @@
     
-_.each(emoji.map, (v, name) =%3E %7B delete emoji.map%5Bname%5D %7D)%0A      _.extend(emoji.map,
+emoji.emojiMap = this.originalMap%0A      emoji.plugdata =
  thi
@@ -2525,20 +2525,20 @@
 original
-Map)
+Plug
 %0A      i
@@ -2592,33 +2592,38 @@
  _.invert(emoji.
-m
+emojiM
 ap)%0A      %7D%0A    
@@ -2841,16 +2841,22 @@
  = this.
+create
 Style()%0A
@@ -2868,111 +2868,213 @@
     
-_.each(custom, (emote, name) =%3E %7B%0A          let id = _.uniqueId('cust-')%0A          emoji.map%5Bname%5D = id
+emoji.emojiMap = _.clone(emoji.emojiMap)%0A        emoji.plugdata = _.clone(emoji.plugdata)%0A        _.each(custom, (emote, name) =%3E %7B%0A          emoji.emojiMap%5Bname%5D = name%0A          emoji.plugdata.push(name)
 %0A%0A  
@@ -3097,24 +3097,38 @@
 = %60.
+g
 emoji
-.emoji-$%7Bid
+-plug.gemoji-plug-$%7Bname
 %7D%60%0A 
@@ -3909,25 +3909,24 @@
 %0A        %7D)%0A
-%0A
       %7D%0A%0A   
@@ -3922,16 +3922,40 @@
      %7D%0A%0A
+      emoji.init_hash()%0A
       th
@@ -3984,25 +3984,30 @@
 .keys(emoji.
-m
+emojiM
 ap)%0A      if
@@ -4068,17 +4068,22 @@
 t(emoji.
-m
+emojiM
 ap)%0A    

fix custom emoji with new plug, possibly maybe