'use strict';

const WorldstateObject = require('./WorldstateObject.js');
/**
 * Represents an in-game special event
 * @extends {WorldstateObject}
 */
class Event extends WorldstateObject {
  /**
   * @param   {Object}            data            The event data
   * @param   {Object}            deps            The dependencies object
   * @param   {MarkdownSettings}  deps.mdConfig   The markdown settings
   * @param   {Translator}        deps.translator The string translator
   * @param   {TimeDateFunctions} deps.timeDate   The time and date functions
   * @param   {function}          deps.Reward     The Reward parser
   */
  constructor(data, { mdConfig, translator, timeDate, Reward }) {
    super(data);

    const opts = { translator, mdConfig, Reward };

    /**
     * The markdown settings
     * @type {MarkdownSettings}
     * @private
     */
    this.mdConfig = mdConfig;
    Object.defineProperty(this, 'mdConfig', { enumerable: false, configurable: false });

    /**
     * The time and date functions
     * @type {TimeDateFunctions}
     */
    this.timeDate = timeDate;
    Object.defineProperty(this, 'timeDate', { enumerable: false, configurable: false });

    /**
     * The date and time at which the event ends
     * @type {Date}
     */
    this.expiry = timeDate.parseDate(data.Expiry);

    /**
     * The event's main score goal
     * @type {number}
     */
    this.maximumScore = data.Goal;

    /**
     * The first intermediate score goal
     * @type {?number}
     */
    this.smallInterval = data.GoalInterim;

    /**
     * The second intermediate score goal
     * @type {?number}
     */
    this.largeInterval = data.GoalInterim2;

    /**
     * The faction that the players must fight in the event
     * @type {string}
     */
    this.faction = translator.faction(data.Faction);

    /**
     * The description of the event
     * @type {string}
     */
    this.description = translator.languageString(data.Desc);

    /**
     * Tooltip for the event
     * @type {?string}
     */
    this.tooltip = translator.languageString(data.ToolTip);

    /**
     * The node where the event takes place
     * @type {?string}
     */
    this.node = translator.node(data.Node);

    /**
     * The other nodes where the event takes place
     * @type {Array.<string>}
     */
    this.concurrentNodes = data.ConcurrentNodes
      ? data.ConcurrentNodes.map(n => translator.node(n))
      : [];

    /**
     * The victim node
     * @type {?string}
     */
    this.victimNode = translator.node(data.VictimNode);

    /**
     * The score description
     * @type {?string}
     */
    this.scoreLocTag = data.Fomorian
      ? 'Fomorian Assault Score'
      : translator.languageString(data.ScoreLocTag);

    /**
     * The event's rewards
     * @type {Array.<Reward>}
     */
    this.rewards = Object.keys(data)
      .filter(k => k.includes('Reward'))
      .map(k => new Reward(data[k], opts));

    /**
     * Whether or not this is expired (at time of object creation)
     * @type {boolean}
     */
    this.expired = this.getExpired();

    this.health = ((data.HealthPct || 0.00) * 100).toFixed(2);

    this.asString = this.toString();
  }

  /**
   * Get whether or not the event has expired
   * @returns {boolean}
   */
  getExpired() {
    return this.timeDate.fromNow(this.expiry) < 0;
  }

  /**
   * The event's string representation
   * @returns {string}
   */
  toString() {
    let lines = [
      `${this.description} : ${this.faction}`,
      `${this.scoreLocTag} : ${this.maximumScore}`,
    ];

    if (this.rewards.length) {
      lines.push('Rewards:');
      lines = lines.concat(this.rewards.map(r => r.toString()));
    }
    if (this.node) {
      lines.push(`Battle on ${this.node}`);
    }
    if (this.victim) {
      lines.push(`Protect ${this.victimNode}`);
    }
    if (this.health) {
      lines.push(`${this.health}% Remaining`);
    }

    return lines.join(this.mdConfig.lineEnd);
  }
}

module.exports = Event;

@@ -67,16 +67,68 @@
 t.js');%0A
+const SyndicateJob = require('./SyndicateJob.js');%0A%0A
 /**%0A * R
@@ -2927,16 +2927,17 @@
 er(k =%3E 
+(
 k.includ
@@ -2948,16 +2948,41 @@
 Reward')
+ %7C%7C k.includes('reward'))
 )%0A      
@@ -3187,52 +3187,366 @@
 h = 
-((data.HealthPct %7C%7C 0.00) * 100).toFixed(2);
+typeof data.HealthPct !== undefined ?%0A        ((data.HealthPct %7C%7C 0.00) * 100).toFixed(2)%0A        : undefined;%0A    %0A    if (data.JobAffiliationTag) %7B%0A        this.affiliatedWith = translator.syndicate(data.JobAffiliationTag);%0A        if (data.Jobs) %7B%0A            this.jobs = (data.Jobs %7C%7C %5B%5D).map(j =%3E new SyndicateJob(j, this.expiry, deps));%0A        %7D%0A    %7D
 %0A%0A  
@@ -3894,26 +3894,100 @@
 tion%7D%60,%0A    
-  
+%5D;%0A    %0A    if (this.scoreLocTag && this.maximumScore) %7B%0A        lines.push(
 %60$%7Bthis.scor
@@ -4019,23 +4019,23 @@
 Score%7D%60,
+)
 %0A    
-%5D;
+%7D
 %0A%0A    if
@@ -4381,24 +4381,239 @@
 g%60);%0A    %7D%0A%0A
+    if (this.affiliatedWith) %7B%0A        lines.push(%60$%7Bthis.affiliatedWith%7D will reward you for performing %60 +%0A            %60$%7Bthis.jobs.map(job =%3E job.type).join(%22, %22)%7D job$%7Bthis.jobs.length %3E 1 ? 's' : ''%7D%60);%0A    %7D%0A%0A
     return l

update fields for events (add jobs)