<commit_before>data_condition = [
    {
        title: "Blinded",
        icon: "one-eyed",
        subtitle: "You can't see",
        description: "You can't see",
        bullets: [
            "You automatically fail any ability check which requires sight.",
            "You have disadvantage on attack rolls.",
            "Attack rolls against you have advantage."
        ]
    },
    {
        title: "Charmed",
        icon: "smitten",
        subtitle: "You are charmed",
        description: "You are charmed by another creature",
        bullets: [
            "You can't attack your charmer or target them with harmful abilities or magical effects.",
            "Your charmer has advantage on ability checks to interact socially with you."
        ]
    },
    {
        title: "Deafened",
        icon: "elf-ear",
        subtitle: "You can't hear",
        description: "You can't hear",
        bullets: [
            "You automatically fail any ability check which requires hearing."
        ]
    },
    {
        title: "Exhaustion",
        icon: "crawl",
        subtitle: "You are exhausted",
        description: "Exhaustion is measured in six levels",
        bullets: [
            "

Level	Effect

1	Disadvantage on ability checks

2	Speed halved

3	Disadvantage on attack rolls and saving throws

4	Hit point maximum halved

5	Speed reduced to 0

6	Death

",
            "You suffer the effect of your current level of exhaustion as well as all lower levels.",
            "Finishing a long rest reduces your exhaustion level by 1, provided that you have also had some food and drink."
        ]
    },
    {
        title: "Frightened",
        icon: "sharp-smile",
        subtitle: "You are frightened",
        description: "You are frightened",
        bullets: [
            "You have disadvantage on ability checks and attack rolls while the source of your fear is within line of sight.",
            "You can't willingly move closer to the source of your fear."
        ]
    },
    {
        title: "Grappled",
        icon: "grab",
        subtitle: "You are grappled",
        description: "You are grappled",
        bullets: [
            "Your speed becomes 0, and you can't benefit from any bonus to your speed.",
            "The condition ends if your grappler is incapacitated.",
            "The condition also ends if you are removed from the reach of your grappler."
        ]
    },
    {
        title: "Incapacitated",
        icon: "internal-injury",
        subtitle: "You can't take actions or reactions",
        description: "You can't take actions or reactions",
        bullets: [
        ]
    },
    {
        title: "Invisible",
        icon: "invisible",
        subtitle: "You can't be seen",
        description: "You can't be seen without the aid of magic or a special sense",
        bullets: [
            "For the purpose of hiding, you are heavily obscured.",
            "You can still be detected by any noise you make or tracks you leave.",
            "You have advantage on attack rolls.",
            "Attack rolls against you have disadvantage."
        ]
    },
    {
        title: "Paralyzed",
        icon: "internal-injury",
        subtitle: "You are paralyzed",
        description: "You can't do anything",
        bullets: [
            "You are incapacitated and can't move or speak.",
            "Attack rolls against you have advantage.",
            "Any attack that hits you is a critical hit if the attacker is within 5 feet of you.",
            "You automatically fail Strength and Dexterity saving throws."
        ]
    },
    {
        title: "Petrified",
        icon: "stone-pile",
        subtitle: "You are transformed into stone",
        description: "You are transformed, along with any nonmagical objects you are wearing or carrying, into a solid inanimate substance (usually stone)",
        bullets: [
            "Your weight increases by a factor of ten, and you cease aging.",
            "You are incapacitated, can't move or speak, and are unaware of your surroundings.",
            "Attack rolls against you have advantage.",
            "You automatically fail Strength and Dexterity saving throws.",
            "You have resistance to all damage.",
            "You are immune to poison and disease, though a poison or disease already in your system is only suspended, not neutralized."
        ]
    },
    {
        title: "Poisoned",
        icon: "deathcab",
        subtitle: "You are poisoned",
        description: "You are poisoned",
        bullets: [
            "You have disadvantage on attack rolls and ability checks."
        ]
    },
    {
        title: "Prone",
        icon: "crawl",
        subtitle: "You are prone",
        description: "You are prone",
        bullets: [
            "Your only movement option is to crawl, unless you stand up.",
            "You have disadvantage on attack rolls.",
            "Attack rolls against you have advantage if the attacker is within 5 feet of you, otherwise the attack roll has disadvantage."
        ]
    },
    {
        title: "Restrained",
        icon: "imprisoned",
        subtitle: "You are restrained",
        description: "You are restrained",
        bullets: [
            "Your speed becomes 0, and you can't benefit from any bonus to your speed.",
            "You have disadvantage on attack rolls.",
            "Attack rolls against you have advantage.",
            "You have disadvantage on Dexterity saving throws."
        ]
    },
    {
        title: "Stunned",
        icon: "internal-injury",
        subtitle: "You are stunned",
        description: "You are stunned",
        bullets: [
            "You are incapacitated, can't move, and can speak only falteringly.",
            "Attack rolls against you have advantage.",
            "You automatically fail Strength and Dexterity saving throws."
        ]
    },
    {
        title: "Unconscious",
        icon: "coma",
        subtitle: "You are unconscious",
        description: "You are unconscious",
        bullets: [
            "You are incapacitated, can't move or speak, and are unaware of your surroundings.",
            "You drop whatever you're holding and fall prone.",
            "Attack rolls against you have advantage.",
            "Any attack that hits you is a critical hit if the attacker is within 5 feet of you.",
            "You automatically fail Strength and Dexterity saving throws.",
        ]
    }
]
<commit_msg>Fixed layout of table in exhaustion.<commit_after>data_condition = [
    {
        title: "Blinded",
        icon: "one-eyed",
        subtitle: "You can't see",
        description: "You can't see",
        bullets: [
            "You automatically fail any ability check which requires sight.",
            "You have disadvantage on attack rolls.",
            "Attack rolls against you have advantage."
        ]
    },
    {
        title: "Charmed",
        icon: "smitten",
        subtitle: "You are charmed",
        description: "You are charmed by another creature",
        bullets: [
            "You can't attack your charmer or target them with harmful abilities or magical effects.",
            "Your charmer has advantage on ability checks to interact socially with you."
        ]
    },
    {
        title: "Deafened",
        icon: "elf-ear",
        subtitle: "You can't hear",
        description: "You can't hear",
        bullets: [
            "You automatically fail any ability check which requires hearing."
        ]
    },
    {
        title: "Exhaustion",
        icon: "crawl",
        subtitle: "You are exhausted",
        description: "Exhaustion is measured in six levels",
        bullets: [
            "

Level			Effect

1			Disadvantage on ability checks

2			Speed halved

3			Disadvantage on attack rolls and saving throws

4			Hit point maximum halved

5			Speed reduced to 0

6			Death

",
            "You suffer the effect of your current level of exhaustion as well as all lower levels.",
            "Finishing a long rest reduces your exhaustion level by 1, provided that you have also had some food and drink."
        ]
    },
    {
        title: "Frightened",
        icon: "sharp-smile",
        subtitle: "You are frightened",
        description: "You are frightened",
        bullets: [
            "You have disadvantage on ability checks and attack rolls while the source of your fear is within line of sight.",
            "You can't willingly move closer to the source of your fear."
        ]
    },
    {
        title: "Grappled",
        icon: "grab",
        subtitle: "You are grappled",
        description: "You are grappled",
        bullets: [
            "Your speed becomes 0, and you can't benefit from any bonus to your speed.",
            "The condition ends if your grappler is incapacitated.",
            "The condition also ends if you are removed from the reach of your grappler."
        ]
    },
    {
        title: "Incapacitated",
        icon: "internal-injury",
        subtitle: "You can't take actions or reactions",
        description: "You can't take actions or reactions",
        bullets: [
        ]
    },
    {
        title: "Invisible",
        icon: "invisible",
        subtitle: "You can't be seen",
        description: "You can't be seen without the aid of magic or a special sense",
        bullets: [
            "For the purpose of hiding, you are heavily obscured.",
            "You can still be detected by any noise you make or tracks you leave.",
            "You have advantage on attack rolls.",
            "Attack rolls against you have disadvantage."
        ]
    },
    {
        title: "Paralyzed",
        icon: "internal-injury",
        subtitle: "You are paralyzed",
        description: "You can't do anything",
        bullets: [
            "You are incapacitated and can't move or speak.",
            "Attack rolls against you have advantage.",
            "Any attack that hits you is a critical hit if the attacker is within 5 feet of you.",
            "You automatically fail Strength and Dexterity saving throws."
        ]
    },
    {
        title: "Petrified",
        icon: "stone-pile",
        subtitle: "You are transformed into stone",
        description: "You are transformed, along with any nonmagical objects you are wearing or carrying, into a solid inanimate substance (usually stone)",
        bullets: [
            "Your weight increases by a factor of ten, and you cease aging.",
            "You are incapacitated, can't move or speak, and are unaware of your surroundings.",
            "Attack rolls against you have advantage.",
            "You automatically fail Strength and Dexterity saving throws.",
            "You have resistance to all damage.",
            "You are immune to poison and disease, though a poison or disease already in your system is only suspended, not neutralized."
        ]
    },
    {
        title: "Poisoned",
        icon: "deathcab",
        subtitle: "You are poisoned",
        description: "You are poisoned",
        bullets: [
            "You have disadvantage on attack rolls and ability checks."
        ]
    },
    {
        title: "Prone",
        icon: "crawl",
        subtitle: "You are prone",
        description: "You are prone",
        bullets: [
            "Your only movement option is to crawl, unless you stand up.",
            "You have disadvantage on attack rolls.",
            "Attack rolls against you have advantage if the attacker is within 5 feet of you, otherwise the attack roll has disadvantage."
        ]
    },
    {
        title: "Restrained",
        icon: "imprisoned",
        subtitle: "You are restrained",
        description: "You are restrained",
        bullets: [
            "Your speed becomes 0, and you can't benefit from any bonus to your speed.",
            "You have disadvantage on attack rolls.",
            "Attack rolls against you have advantage.",
            "You have disadvantage on Dexterity saving throws."
        ]
    },
    {
        title: "Stunned",
        icon: "internal-injury",
        subtitle: "You are stunned",
        description: "You are stunned",
        bullets: [
            "You are incapacitated, can't move, and can speak only falteringly.",
            "Attack rolls against you have advantage.",
            "You automatically fail Strength and Dexterity saving throws."
        ]
    },
    {
        title: "Unconscious",
        icon: "coma",
        subtitle: "You are unconscious",
        description: "You are unconscious",
        bullets: [
            "You are incapacitated, can't move or speak, and are unaware of your surroundings.",
            "You drop whatever you're holding and fall prone.",
            "Attack rolls against you have advantage.",
            "Any attack that hits you is a critical hit if the attacker is within 5 feet of you.",
            "You automatically fail Strength and Dexterity saving throws.",
        ]
    }
]
<|endoftext|>


<commit_before>import React, { Component } from 'react'
import { Link } from 'react-router'
import { prefixLink } from 'gatsby-helpers'
import Helmet from "react-helmet"
import { config } from 'config'

class Index extends Component {
  render () {
    return (

      {/* Helmet has the metadata for the index */}
        <Helmet
          title={config.siteTitle}
          meta={[
            {"name": "description", "content": "Sample"},
            {"name": "keywords", "content": "sample, something"},
          ]}
        />
      {/* Rank your 5 favorite, and least favorite, activities from this
          list: https://gist.github.com/fool/b0f254ff8c72a5765b6a9138249789d6 */}

My Top 5 Support Activities

5. Respond to 60+ support requests via email or chat every day

4. Debug a customer's build using a programming language and framework that you've never seen before

3. Write and maintain documentation for our software and blog posts for our website.

2. Work with the development team to help design a new feature based on feedback from customers

1. Work with people to figure out if Netlify's service can solve a particular workflow or integration challenge they have

      {/* What is your favorite thing about providing technical support? */}

My favorite thing about providing technical support is the variety. It’s
                difficult to pick only one thing, since I love the challenges, working with different technologies, and working with both technical and non-technical
                people. I love being in that intersection between humanity and technology. But in the end the best way to summarize
                everything I love about providing technical support is the variety. I get to work with many different types of companies,
                people, and technologies. I get to apply my skills in many ways, and the growth potential is almost limitless.

      {/* What did you think of our service during the time you used it?  Be honest!  “it sucked”
          isn’t a wrong answer unless you don’t elaborate and provide some constructive criticism ;) */}

I think Netlify is a pretty awesome service. I’m not just saying that!
                Before finding the job listing I never knew it existed. I have only recently begun looking in to learning how to use
                Docker, and github deployments. I didn’t know that a service like Netlify automated the process in addition to providing
                a CDN. Getting this single page up and running didn’t take long at all, and it’s faster than the hosting I have setup
                with digitalocean. One thing I’m curious about is what the bandwidth and storage limits are since it’s not immediately
                obvious when looking at the pricing page.

      {/* Tell about how you made your site and why you chose the tools you did.
          Briefly explain a challenge you experienced in setting up this site and how you solved it. */}

The biggest challenge I faced while building this site was using Gatsby.
                While I have experience using React to build full web apps, and I’m currently learning React Native, I have never used
                Gatsby before this project. Luckily building React components is familiar to me, but much was changed since Gatsby uses
                templates, does not give direct access to React Router, and uses a different directory structure with some new files.
                It also has a different ways of setting up the default html file. I read through the Github repo, looked at some examples,
                added materialize.css to help with styling, then I was up and running pretty quickly. I spent more time getting the Webpack
                File-loader working properly to get the _redirects file in the root directory during the build process than I did getting
                Gatsby up and running.

      {/* Could you give us a suggestion to improve this test or the job posting? */}

It's difficult to provide suggestions on the testing and job posting.
                Particularly so because I’m still a bit in the dark about what the actual moment to moment work will be like.
                Based on that, the best advice I can give is to provide more information on what a day is like for a Support Engineer
                at Netlify. That would add context to the information already given so that candidates will have a better feel for the job,
                and also be better able to answer the questions asked.

      {/* Provide a link to documentation for a technical/developer-focused product, that you think are well done,
          and briefly explain why you think they are well done. */}

                Digital Ocean Tutorials

I love the tutorials at Digital Ocean! The instructions are easy to follow and provide explanations as to what each step
                   does, and why it’s important. They also include tangential information that you may not have been looking for, but is
                   otherwise useful when performing the action you are reading the tutorial for. Where it’s applicable, they also explain
                   concepts to help you understand the tutorial better.

                https://www.digitalocean.com/community/tutorials

      {/* Why do you think SSL/HTTPS is important? */}

SSL/HTTPS is important because security and privacy are important.
                People share a lot personal information online. From private details about their lives to payment information.
                I believe that they have a right to have their data secure. They also have a right to a certain level of privacy and
                security from malicious groups and in some cases, governments. It is good practice for sites and services to encrypt
                connections via SSL and use HTTPS to ensure there that data can be transferred securely across the internet.

                I personally pushed for the company I currently work for to implement SSL everywhere, instead of only when logging in.
                This is because it also gives people peace of mind. It is more than just keeping your private information secure from
                hackers. This is particularly of importance in recent years with ISP’s selling web surfing data and logging user actions
                not just when surfing, but also the various IoT devices they are using on their neworks. More SSL and a greater emphasis
                on security and privacy is a good thing, and a net win for society as a whole, and the protection of individual liberties.

      {/* Explain, in a couple of paragraphs, what you think 2 major challenges around DNS configuration are for
          less-technical internet end-users */}

Two major challenges for non-tech savvy users configuring DNS are it's complexity,
                and the the different setup options.  The broad definition for DNS is simple to understand, but there are multiple
                ways and combinations to setup DNS for domain names, and services. “A” records for IP resolution, "CNAME" to point to another
                domain, "MX" for e-mail, "SRV" records, etc.  If you use your domain for Google Apps, or Microsoft’s 365 suite, you end up
                configuring so many things that if you aren’t trained in this technology, you’ll quickly be lost. DNS can be used not just
                for pointing a domain at an IP but to help with load balancing and other concepts that someone who is not tech-savvy will
                have a hard time understanding.

                An extension of this complexity is that there are also multiple ways of using DNS to achieve similar goals. For instance,
                you may setup "CNAME" to point your domain to another server that has a domain setup, or “A” records to point straight at
                your servers IP, the IP of your load balancer, etc., 301 redirect to send visitors to another URL, and so forth. These all
                use DNS to send people going to your domain to a particular server, but they each have slightly different use-cases.
                Because of the variety and complexity of DNS, in addition to the adjacent concepts and technologies related to using DNS,
                it can be hard for non-tech savvy users to get a handle on it.

       {/* A customer writes in saying their “site won’t build”.  Compose your best short (2-paragraph) customer-facing answer without
           any additional data, that could be useful in the generic case but would also lead to a customer providing a more actionable
           response. */}

Thank you for contacting us. I’m Gerald and I’d be happy to assist you.
                Are you able to build the site on your own development machines? If so, please note that our build environments may be
                different from yours. We have an article that describes our build environment, and some debugging suggestions, along
                with instructions on how to setup your own docker container that is configured the same as ours. You can find this
                information at: <Link style={styles.link} to="https://www.netlify.com/blog/2016/10/18/how-our-build-bots-build-sites/">
                https://www.netlify.com/blog/2016/10/18/how-our-build-bots-build-sites/</Link>

                We also provide build logs from the deploy tab of your app page. I certainly understand how frustrating this process can
                be; If you are still having trouble, feel free to reply to this e-mail with copies of your logs and we’ll go through them
                to find where the build is breaking. In either case we’ll follow up with you to see how things are coming along. If there
                is anything else that we can assist you with, or if you have any other questions, please ask. Thanks again.

                Gerald O.

    );
  }
}

const styles = {
  link: {
    color: "#f5f5f5",
    textDecoration: "underline"
  }
}

export default Index;<commit_msg>adding bottom 4 favorite support activities<commit_after>import React, { Component } from 'react'
import { Link } from 'react-router'
import { prefixLink } from 'gatsby-helpers'
import Helmet from "react-helmet"
import { config } from 'config'

class Index extends Component {
  render () {
    return (

      {/* Helmet has the metadata for the index */}
        <Helmet
          title={config.siteTitle}
          meta={[
            {"name": "description", "content": "Sample"},
            {"name": "keywords", "content": "sample, something"},
          ]}
        />
      {/* Rank your 5 favorite, and least favorite, activities from this
          list: https://gist.github.com/fool/b0f254ff8c72a5765b6a9138249789d6 */}

My Top 5 Support Activities

5. Create video tutorials to help teach users a specific feature or use case

4. Debug a customer's build using a programming language and framework that you've never seen before

3. Analyze thousands of support tickets to spot trends to improve our product

2. Work with the development team to help design a new feature based on feedback from customers

1. Work with people to figure out if Netlify's service can solve a particular workflow or integration challenge they have

      {/* What is your favorite thing about providing technical support? */}
      {/* Rank your 5 favorite, and least favorite, activities from this
          list: https://gist.github.com/fool/b0f254ff8c72a5765b6a9138249789d6 */}

My Bottom 5 Support Activities

5. Write and maintain documentation for our software and blog posts for our website.

4. Work with prospective customers to explain our service and the pricing model

3. Respond to 60+ support requests via email or chat every day

2. Submit bug reports and potentially bug fixes to closed and open source projects that Netlify maintains on GitHub

1. Receive occasional phone calls requesting support from our highest-value customers

      {/* What is your favorite thing about providing technical support? */}

My favorite thing about providing technical support is the variety. It’s
                difficult to pick only one thing, since I love the challenges, working with different technologies, and working with both technical and non-technical
                people. I love being in that intersection between humanity and technology. But in the end the best way to summarize
                everything I love about providing technical support is the variety. I get to work with many different types of companies,
                people, and technologies. I get to apply my skills in many ways, and the growth potential is almost limitless.

      {/* What did you think of our service during the time you used it?  Be honest!  “it sucked”
          isn’t a wrong answer unless you don’t elaborate and provide some constructive criticism ;) */}

I think Netlify is a pretty awesome service. I’m not just saying that!
                Before finding the job listing I never knew it existed. I have only recently begun looking in to learning how to use
                Docker, and github deployments. I didn’t know that a service like Netlify automated the process in addition to providing
                a CDN. Getting this single page up and running didn’t take long at all, and it’s faster than the hosting I have setup
                with digitalocean. One thing I’m curious about is what the bandwidth and storage limits are since it’s not immediately
                obvious when looking at the pricing page.

      {/* Tell about how you made your site and why you chose the tools you did.
          Briefly explain a challenge you experienced in setting up this site and how you solved it. */}

The biggest challenge I faced while building this site was using Gatsby.
                While I have experience using React to build full web apps, and I’m currently learning React Native, I have never used
                Gatsby before this project. Luckily building React components is familiar to me, but much was changed since Gatsby uses
                templates, does not give direct access to React Router, and uses a different directory structure with some new files.
                It also has a different ways of setting up the default html file. I read through the Github repo, looked at some examples,
                added materialize.css to help with styling, then I was up and running pretty quickly. I spent more time getting the Webpack
                File-loader working properly to get the _redirects file in the root directory during the build process than I did getting
                Gatsby up and running.

      {/* Could you give us a suggestion to improve this test or the job posting? */}

It's difficult to provide suggestions on the testing and job posting.
                Particularly so because I’m still a bit in the dark about what the actual moment to moment work will be like.
                Based on that, the best advice I can give is to provide more information on what a day is like for a Support Engineer
                at Netlify. That would add context to the information already given so that candidates will have a better feel for the job,
                and also be better able to answer the questions asked.

      {/* Provide a link to documentation for a technical/developer-focused product, that you think are well done,
          and briefly explain why you think they are well done. */}

                Digital Ocean Tutorials

I love the tutorials at Digital Ocean! The instructions are easy to follow and provide explanations as to what each step
                   does, and why it’s important. They also include tangential information that you may not have been looking for, but is
                   otherwise useful when performing the action you are reading the tutorial for. Where it’s applicable, they also explain
                   concepts to help you understand the tutorial better.

                https://www.digitalocean.com/community/tutorials

      {/* Why do you think SSL/HTTPS is important? */}

SSL/HTTPS is important because security and privacy are important.
                People share a lot personal information online. From private details about their lives to payment information.
                I believe that they have a right to have their data secure. They also have a right to a certain level of privacy and
                security from malicious groups and in some cases, governments. It is good practice for sites and services to encrypt
                connections via SSL and use HTTPS to ensure there that data can be transferred securely across the internet.

                I personally pushed for the company I currently work for to implement SSL everywhere, instead of only when logging in.
                This is because it also gives people peace of mind. It is more than just keeping your private information secure from
                hackers. This is particularly of importance in recent years with ISP’s selling web surfing data and logging user actions
                not just when surfing, but also the various IoT devices they are using on their neworks. More SSL and a greater emphasis
                on security and privacy is a good thing, and a net win for society as a whole, and the protection of individual liberties.

      {/* Explain, in a couple of paragraphs, what you think 2 major challenges around DNS configuration are for
          less-technical internet end-users */}

Two major challenges for non-tech savvy users configuring DNS are it's complexity,
                and the the different setup options.  The broad definition for DNS is simple to understand, but there are multiple
                ways and combinations to setup DNS for domain names, and services. “A” records for IP resolution, "CNAME" to point to another
                domain, "MX" for e-mail, "SRV" records, etc.  If you use your domain for Google Apps, or Microsoft’s 365 suite, you end up
                configuring so many things that if you aren’t trained in this technology, you’ll quickly be lost. DNS can be used not just
                for pointing a domain at an IP but to help with load balancing and other concepts that someone who is not tech-savvy will
                have a hard time understanding.

                An extension of this complexity is that there are also multiple ways of using DNS to achieve similar goals. For instance,
                you may setup "CNAME" to point your domain to another server that has a domain setup, or “A” records to point straight at
                your servers IP, the IP of your load balancer, etc., 301 redirect to send visitors to another URL, and so forth. These all
                use DNS to send people going to your domain to a particular server, but they each have slightly different use-cases.
                Because of the variety and complexity of DNS, in addition to the adjacent concepts and technologies related to using DNS,
                it can be hard for non-tech savvy users to get a handle on it.

       {/* A customer writes in saying their “site won’t build”.  Compose your best short (2-paragraph) customer-facing answer without
           any additional data, that could be useful in the generic case but would also lead to a customer providing a more actionable
           response. */}

Thank you for contacting us. I’m Gerald and I’d be happy to assist you.
                Are you able to build the site on your own development machines? If so, please note that our build environments may be
                different from yours. We have an article that describes our build environment, and some debugging suggestions, along
                with instructions on how to setup your own docker container that is configured the same as ours. You can find this
                information at: <Link style={styles.link} to="https://www.netlify.com/blog/2016/10/18/how-our-build-bots-build-sites/">
                https://www.netlify.com/blog/2016/10/18/how-our-build-bots-build-sites/</Link>

                We also provide build logs from the deploy tab of your app page. I certainly understand how frustrating this process can
                be; If you are still having trouble, feel free to reply to this e-mail with copies of your logs and we’ll go through them
                to find where the build is breaking. In either case we’ll follow up with you to see how things are coming along. If there
                is anything else that we can assist you with, or if you have any other questions, please ask. Thanks again.

                Gerald O.

    );
  }
}

const styles = {
  link: {
    color: "#f5f5f5",
    textDecoration: "underline"
  }
}

export default Index;<|endoftext|>


<commit_before>// https://github.com/DevExpress/DevExtreme.AspNet.Data
// Copyright (c) Developer Express Inc.

(function($, DX) {

    function createStore(options) {
        var store = new DX.data.CustomStore(createStoreConfig(options));
        store._useDefaultSearch = true;
        return store;
    }

    function createStoreConfig(options) {
        var keyExpr = options.key,
            loadUrl = options.loadUrl,
            loadParams = options.loadParams,
            updateUrl = options.updateUrl,
            insertUrl = options.insertUrl,
            deleteUrl = options.deleteUrl,
            onBeforeSend = options.onBeforeSend;

        function send(operation, settings) {
            if(onBeforeSend)
                onBeforeSend(operation, settings);

            return $.ajax(settings);
        }

        function filterByKey(keyValue) {
            if(!$.isArray(keyExpr))
                return [keyExpr, keyValue];

            return $.map(keyExpr, function(i) {
                return [[i, keyValue[i]]];
            });
        }

        function loadOptionsToActionParams(options, isCountQuery) {
            var result = {
                requireTotalCount: options.requireTotalCount,
                isCountQuery: isCountQuery,
                skip: options.skip,
                take: options.take,
            };

            var normalizeSorting = DX.data.utils.normalizeSortingInfo,
                group = options.group;

            if(options.sort)
                result.sort = JSON.stringify(normalizeSorting(options.sort));

            if(group) {
                if(!isAdvancedGrouping(group))
                    group = normalizeSorting(group);
                result.group = JSON.stringify(group);
            }

            if($.isArray(options.filter))
                result.filter = JSON.stringify(options.filter);

            if(options.totalSummary)
                result.totalSummary = JSON.stringify(options.totalSummary);

            if(options.groupSummary)
                result.groupSummary = JSON.stringify(options.groupSummary);

            $.extend(result, loadParams);

            return result;
        }

        return {
            key: keyExpr,

            load: function(loadOptions) {
                var d = new $.Deferred();

                send("load", {
                    url: loadUrl,
                    data: loadOptionsToActionParams(loadOptions)
                }).done(function(res) {
                    if("data" in res)
                        d.resolve(res.data, { totalCount: res.totalCount, summary: res.summary });
                    else
                        d.resolve(res);
                }).fail(function(error) {
                    d.reject(error);
                });

                return d.promise();
            },

            totalCount: function(loadOptions) {
                return send("load", {
                    url: loadUrl,
                    data: loadOptionsToActionParams(loadOptions, true)
                });
            },

            byKey: function(key) {
                var d = new $.Deferred();

                if(!keyExpr)
                    return makeMissingKeyPromise("byKey", loadUrl);

                send("load", {
                    url: loadUrl,
                    data: loadOptionsToActionParams({ filter: filterByKey(key) })
                }).done(function(res) {
                    d.resolve(res[0]);
                }).fail(function(error) {
                    d.reject(error);
                });

                return d.promise();
            },

            update: updateUrl && function(key, values) {
                if(!keyExpr)
                    return makeMissingKeyPromise("update", updateUrl);

                return send("update", {
                    url: updateUrl,
                    type: options.updateMethod || "PUT",
                    data: {
                        key: serializeKey(key),
                        values: JSON.stringify(values)
                    }
                });
            },

            insert: insertUrl && function(values) {
                if(!keyExpr)
                    return makeMissingKeyPromise("insert", insertUrl);

                return send("insert", {
                    url: insertUrl,
                    type: options.insertMethod || "POST",
                    data: { values: JSON.stringify(values) }
                });
            },

            remove: deleteUrl && function(key) {
                if(!keyExpr)
                    return makeMissingKeyPromise("remove", deleteUrl);

                return send("delete", {
                    url: deleteUrl,
                    type: options.deleteMethod || "DELETE",
                    data: { key: serializeKey(key) }
                });
            }

        };
    }

    function serializeKey(key) {
        if(typeof key === "object")
            return JSON.stringify(key);

        return key;
    }

    function isAdvancedGrouping(expr) {
        if(!$.isArray(expr))
            return false;

        for(var i = 0; i < expr.length; i++) {
            if("groupInterval" in expr[i] || "isExpanded" in expr[i])
                return true;
        }

        return false;
    }

    function makeMissingKeyPromise(operation, url) {
        var text = "Primary key is not specified (operation: '" + operation + "', url: '" + url + "')";

        return $.Deferred()
            .reject(new Error(text))
            .promise();
    }

    $.extend(DX.data, {
        AspNet: {
            createStore: createStore
        }
    });

})(jQuery, DevExpress);<commit_msg>strict mode + jshint config<commit_after>// https://github.com/DevExpress/DevExtreme.AspNet.Data
// Copyright (c) Developer Express Inc.

// jshint strict: true, browser: true, jquery: true, undef: true, unused: true, eqeqeq: true

(function($, DX) {
    "use strict";

    function createStore(options) {
        var store = new DX.data.CustomStore(createStoreConfig(options));
        store._useDefaultSearch = true;
        return store;
    }

    function createStoreConfig(options) {
        var keyExpr = options.key,
            loadUrl = options.loadUrl,
            loadParams = options.loadParams,
            updateUrl = options.updateUrl,
            insertUrl = options.insertUrl,
            deleteUrl = options.deleteUrl,
            onBeforeSend = options.onBeforeSend;

        function send(operation, settings) {
            if(onBeforeSend)
                onBeforeSend(operation, settings);

            return $.ajax(settings);
        }

        function filterByKey(keyValue) {
            if(!$.isArray(keyExpr))
                return [keyExpr, keyValue];

            return $.map(keyExpr, function(i) {
                return [[i, keyValue[i]]];
            });
        }

        function loadOptionsToActionParams(options, isCountQuery) {
            var result = {
                requireTotalCount: options.requireTotalCount,
                isCountQuery: isCountQuery,
                skip: options.skip,
                take: options.take,
            };

            var normalizeSorting = DX.data.utils.normalizeSortingInfo,
                group = options.group;

            if(options.sort)
                result.sort = JSON.stringify(normalizeSorting(options.sort));

            if(group) {
                if(!isAdvancedGrouping(group))
                    group = normalizeSorting(group);
                result.group = JSON.stringify(group);
            }

            if($.isArray(options.filter))
                result.filter = JSON.stringify(options.filter);

            if(options.totalSummary)
                result.totalSummary = JSON.stringify(options.totalSummary);

            if(options.groupSummary)
                result.groupSummary = JSON.stringify(options.groupSummary);

            $.extend(result, loadParams);

            return result;
        }

        return {
            key: keyExpr,

            load: function(loadOptions) {
                var d = new $.Deferred();

                send("load", {
                    url: loadUrl,
                    data: loadOptionsToActionParams(loadOptions)
                }).done(function(res) {
                    if("data" in res)
                        d.resolve(res.data, { totalCount: res.totalCount, summary: res.summary });
                    else
                        d.resolve(res);
                }).fail(function(error) {
                    d.reject(error);
                });

                return d.promise();
            },

            totalCount: function(loadOptions) {
                return send("load", {
                    url: loadUrl,
                    data: loadOptionsToActionParams(loadOptions, true)
                });
            },

            byKey: function(key) {
                var d = new $.Deferred();

                if(!keyExpr)
                    return makeMissingKeyPromise("byKey", loadUrl);

                send("load", {
                    url: loadUrl,
                    data: loadOptionsToActionParams({ filter: filterByKey(key) })
                }).done(function(res) {
                    d.resolve(res[0]);
                }).fail(function(error) {
                    d.reject(error);
                });

                return d.promise();
            },

            update: updateUrl && function(key, values) {
                if(!keyExpr)
                    return makeMissingKeyPromise("update", updateUrl);

                return send("update", {
                    url: updateUrl,
                    type: options.updateMethod || "PUT",
                    data: {
                        key: serializeKey(key),
                        values: JSON.stringify(values)
                    }
                });
            },

            insert: insertUrl && function(values) {
                if(!keyExpr)
                    return makeMissingKeyPromise("insert", insertUrl);

                return send("insert", {
                    url: insertUrl,
                    type: options.insertMethod || "POST",
                    data: { values: JSON.stringify(values) }
                });
            },

            remove: deleteUrl && function(key) {
                if(!keyExpr)
                    return makeMissingKeyPromise("remove", deleteUrl);

                return send("delete", {
                    url: deleteUrl,
                    type: options.deleteMethod || "DELETE",
                    data: { key: serializeKey(key) }
                });
            }

        };
    }

    function serializeKey(key) {
        if(typeof key === "object")
            return JSON.stringify(key);

        return key;
    }

    function isAdvancedGrouping(expr) {
        if(!$.isArray(expr))
            return false;

        for(var i = 0; i < expr.length; i++) {
            if("groupInterval" in expr[i] || "isExpanded" in expr[i])
                return true;
        }

        return false;
    }

    function makeMissingKeyPromise(operation, url) {
        var text = "Primary key is not specified (operation: '" + operation + "', url: '" + url + "')";

        return $.Deferred()
            .reject(new Error(text))
            .promise();
    }

    $.extend(DX.data, {
        AspNet: {
            createStore: createStore
        }
    });

})(jQuery, window.DevExpress);<|endoftext|>


<commit_before>import React from 'react'
import withData from 'lib/withData'
import DefaultLayout from 'components/DefaultLayout'
import {
  Container,
  Header,
  Message,
  Loader
} from 'semantic-ui-react'
import { Router } from 'routes'
import PlayerLoginPasswordForm from 'components/PlayerLoginPasswordForm'
import PlayerLoginPinForm from 'components/PlayerLoginPinForm'
import ServersQuery from 'components/queries/ServersQuery'
import withSession from 'lib/withSession'

export class LoginPage extends React.Component {
  async handleOnSubmit(e, { email, password, server, name, pin }) {
    let data

    if (email) {
      data = { email, password }
    } else {
      data = { server, name, pin }
    }

    const response = await fetch(process.env.API_HOST + '/session',
      { method: 'POST'
      , body: JSON.stringify(data)
      , headers: new Headers({ 'Content-Type': 'application/json' })
      , credentials: 'include'
      })

    if (email && response.status === 204) {
      window.location.replace('/')
    } else if ((email && response.status !== 204) || response.status !== 200) {
      const responseData = await response.json()

      throw new Error(responseData.error)
    } else {
      const responseData = await response.json()

      if (responseData.hasAccount) return window.location.replace('/')

      window.location.replace('/register')
    }

  }

  render() {
    if (this.props.session.exists && Router.router) {
      window.location.replace('/')
      return <Loader />
    }

    return (
      <DefaultLayout title='Login' displayNavTitle>
        <Container style={{ marginTop: '2em' }}>
          Have an account?
          <PlayerLoginPasswordForm onSubmit={this.handleOnSubmit} />
          <Message
            info
            header='Banned?'
            content='Attempt to join the server in Minecraft, type in the pin number contained within your ban message'
          />
          <Message
            info
            header='Forgot password?'
            content='Join the server in Minecraft, type /bmpin in chat and type the generated pin number below'
          />
          <ServersQuery>
            {({ servers }) => (
              <PlayerLoginPinForm servers={servers} onSubmit={this.handleOnSubmit} />
            )}
          </ServersQuery>
        </Container>
      </DefaultLayout>
    )
  }
}

export default withData(withSession(LoginPage))
<commit_msg>fixed login pin<commit_after>import React from 'react'
import withData from 'lib/withData'
import DefaultLayout from 'components/DefaultLayout'
import {
  Container,
  Header,
  Message,
  Loader
} from 'semantic-ui-react'
import { Router } from 'routes'
import PlayerLoginPasswordForm from 'components/PlayerLoginPasswordForm'
import PlayerLoginPinForm from 'components/PlayerLoginPinForm'
import ServersQuery from 'components/queries/ServersQuery'
import withSession from 'lib/withSession'

export class LoginPage extends React.Component {
  async handleOnSubmit(e, { email, password, server, name, pin }) {
    let data

    if (email) {
      data = { email, password }
    } else {
      data = { serverId: server, name, pin }
    }

    const response = await fetch(process.env.API_HOST + '/session',
      { method: 'POST'
      , body: JSON.stringify(data)
      , headers: new Headers({ 'Content-Type': 'application/json' })
      , credentials: 'include'
      })

    if (email && response.status === 204) {
      window.location.replace('/')
    } else if ((email && response.status !== 204) || response.status !== 200) {
      const responseData = await response.json()

      throw new Error(responseData.error)
    } else {
      const responseData = await response.json()

      if (responseData.hasAccount) return window.location.replace('/')

      window.location.replace('/register')
    }

  }

  render() {
    if (this.props.session.exists && Router.router) {
      window.location.replace('/')
      return <Loader />
    }

    return (
      <DefaultLayout title='Login' displayNavTitle>
        <Container style={{ marginTop: '2em' }}>
          Have an account?
          <PlayerLoginPasswordForm onSubmit={this.handleOnSubmit} />
          <Message
            info
            header='Banned?'
            content='Attempt to join the server in Minecraft, type in the pin number contained within your ban message'
          />
          <Message
            info
            header='Forgot password?'
            content='Join the server in Minecraft, type /bmpin in chat and type the generated pin number below'
          />
          <ServersQuery>
            {({ servers }) => (
              <PlayerLoginPinForm servers={servers} onSubmit={this.handleOnSubmit} />
            )}
          </ServersQuery>
        </Container>
      </DefaultLayout>
    )
  }
}

export default withData(withSession(LoginPage))
<|endoftext|>


<commit_before>import _ from 'lodash';
import React from 'react';
import Field from '../Field';
import { Checkbox, FormField, FormInput, FormNote, FormRow } from 'elemental';
import CollapsedFieldLabel from '../../components/CollapsedFieldLabel';
import NestedFormField from '../../components/NestedFormField';

/**
 * TODO:
 * - Remove dependency on underscore
 * - Custom path support
 */

module.exports = Field.create({

	displayName: 'LocationField',
	statics: {
		type: 'Location',
	},

	getInitialState () {
		return {
			collapsedFields: {},
			improve: false,
			overwrite: false,
		};
	},

	componentWillMount () {
		const { value = [] } = this.props;
		var collapsedFields = {};
		_.forEach(['number', 'name', 'street2', 'geo'], (i) => {
			if (!value[i]) {
				collapsedFields[i] = true;
			}
		}, this);
		this.setState({ collapsedFields });
	},

	shouldCollapse () {
		return this.props.collapse && !this.formatValue();
	},

	uncollapseFields () {
		this.setState({
			collapsedFields: {},
		});
	},

	fieldChanged (fieldPath, event) {
		const { value = {}, path, onChange } = this.props;
		onChange({
			path,
			value: {
				...value,
				[fieldPath]: event.target.value,
			},
		});
	},

	makeChanger (fieldPath) {
		return this.fieldChanged.bind(this, fieldPath);
	},

	geoChanged (i, event) {
		const { value = {}, path, onChange } = this.props;
		const newVal = event.target.value;
		const geo = [
			i === 0 ? newVal : value.geo ? value.geo[0] : '',
			i === 1 ? newVal : value.geo ? value.geo[1] : '',
		];
		onChange({
			path,
			value: {
				...value,
				geo,
			},
		});
	},

	makeGeoChanger (fieldPath) {
		return this.geoChanged.bind(this, fieldPath);
	},

	formatValue () {
		const { value = {} } = this.props;
		return _.compact([
			value.number,
			value.name,
			value.street1,
			value.street2,
			value.suburb,
			value.state,
			value.postcode,
			value.country,
		]).join(', ');
	},

	renderValue () {
		return <FormInput noedit>{this.formatValue() || '(no value)'}</FormInput>;
	},

	renderField (fieldPath, label, collapse, autoFocus) {
		if (this.state.collapsedFields[fieldPath]) {
			return null;
		}
		const { value = {}, path } = this.props;
		return (
			<NestedFormField label={label} data-field-location-path={path + '.' + fieldPath}>
				<FormInput autoFocus={autoFocus} name={path + '.' + fieldPath} value={value[fieldPath]} onChange={this.makeChanger(fieldPath)} placeholder={label} />
			</NestedFormField>
		);
	},

	renderSuburbState () {
		const { value = {}, path } = this.props;
		return (
			<NestedFormField label="Suburb / State" data-field-location-path={path + '.suburb_state'}>
				<FormRow>
					<FormField width="two-thirds" data-field-location-path={path + '.suburb'}>
						<FormInput name={path + '.suburb'} value={value.suburb} onChange={this.makeChanger('suburb')} placeholder="Suburb" />
					</FormField>
					<FormField width="one-third" data-field-location-path={path + '.state'}>
						<FormInput name={path + '.state'} value={value.state} onChange={this.makeChanger('state')} placeholder="State" />
					</FormField>
				</FormRow>
			</NestedFormField>
		);
	},

	renderPostcodeCountry () {
		const { value = {}, path } = this.props;
		return (
			<NestedFormField label="Postcode / Country" data-field-location-path={path + '.postcode_country'}>
				<FormRow>
					<FormField width="one-third" data-field-location-path={path + '.postcode'}>
						<FormInput name={path + '.postcode'} value={value.postcode} onChange={this.makeChanger('postcode')} placeholder="Post Code" />
					</FormField>
					<FormField width="two-thirds" data-field-location-path={path + '.country'}>
						<FormInput name={path + '.country'} value={value.country} onChange={this.makeChanger('country')} placeholder="Country" />
					</FormField>
				</FormRow>
			</NestedFormField>
		);
	},

	renderGeo () {
		if (this.state.collapsedFields.geo) {
			return null;
		}
		const { value = {}, path, paths } = this.props;
		const geo = value.geo || [];
		return (
			<NestedFormField label="Lat / Lng" data-field-location-path={path + '.geo'}>
				<FormRow>
					<FormField width="one-half" data-field-location-path="latitude">
						<FormInput name={paths.geo} value={geo[1]} onChange={this.makeGeoChanger(1)} placeholder="Latitude" />
					</FormField>
					<FormField width="one-half" data-field-location-path="longitude">
						<FormInput name={paths.geo} value={geo[0]} onChange={this.makeGeoChanger(0)} placeholder="Longitude" />
					</FormField>
				</FormRow>
			</NestedFormField>
		);
	},

	updateGoogleOption (key, e) {
		var newState = {};
		newState[key] = e.target.checked;
		this.setState(newState);
	},

	makeGoogler (key) {
		return this.updateGoogleOption.bind(this, key);
	},

	renderGoogleOptions () {
		const { paths, enableMapsAPI } = this.props;
		if (!enableMapsAPI) return null;
		var replace = this.state.improve ? (
			<Checkbox
				label="Replace existing data"
				name={paths.overwrite}
				onChange={this.makeGoogler('overwrite')}
				checked={this.state.overwrite} />
		) : null;
		return (
			<FormField offsetAbsentLabel>
				<Checkbox
					label="Autodetect and improve location on save"
					name={paths.improve}
					onChange={this.makeGoogler('improve')}
					checked={this.state.improve}
					title="When checked, this will attempt to fill missing fields. It will also get the lat/long" />
				{replace}
			</FormField>
		);
	},

	renderNote () {
		const { note } = this.props;
		if (!note) return null;
		return (
			<FormField offsetAbsentLabel>
				<FormNote note={note} />
			</FormField>
		);
	},

	renderUI () {

		if (!this.shouldRenderField()) {
			return (
				<FormField label={this.props.label}>{this.renderValue()}</FormField>
			);
		}

		/* eslint-disable no-script-url */
		var showMore = !_.isEmpty(this.state.collapsedFields)
			? <CollapsedFieldLabel onClick={this.uncollapseFields}>(show more fields)</CollapsedFieldLabel>
			: null;
		/* eslint-enable */

		const { label, path } = this.props;
		return (

				<FormField label={label}>
					{showMore}
				</FormField>
				{this.renderField('number', 'PO Box / Shop', true, true)}
				{this.renderField('name', 'Building Name', true)}
				{this.renderField('street1', 'Street Address')}
				{this.renderField('street2', 'Street Address 2', true)}
				{this.renderSuburbState()}
				{this.renderPostcodeCountry()}
				{this.renderGeo()}
				{this.renderGoogleOptions()}
				{this.renderNote()}

		);
	},

});
<commit_msg>Fix location field geo latitude/longitude display issue.<commit_after>import _ from 'lodash';
import React from 'react';
import Field from '../Field';
import { Checkbox, FormField, FormInput, FormNote, FormRow } from 'elemental';
import CollapsedFieldLabel from '../../components/CollapsedFieldLabel';
import NestedFormField from '../../components/NestedFormField';

/**
 * TODO:
 * - Remove dependency on underscore
 * - Custom path support
 */

module.exports = Field.create({

	displayName: 'LocationField',
	statics: {
		type: 'Location',
	},

	getInitialState () {
		return {
			collapsedFields: {},
			improve: false,
			overwrite: false,
		};
	},

	componentWillMount () {
		const { value = [] } = this.props;
		var collapsedFields = {};
		_.forEach(['number', 'name', 'street2', 'geo'], (i) => {
			if (!value[i]) {
				collapsedFields[i] = true;
			}
		}, this);
		this.setState({ collapsedFields });
	},

	shouldCollapse () {
		return this.props.collapse && !this.formatValue();
	},

	uncollapseFields () {
		this.setState({
			collapsedFields: {},
		});
	},

	fieldChanged (fieldPath, event) {
		const { value = {}, path, onChange } = this.props;
		onChange({
			path,
			value: {
				...value,
				[fieldPath]: event.target.value,
			},
		});
	},

	makeChanger (fieldPath) {
		return this.fieldChanged.bind(this, fieldPath);
	},

	geoChanged (i, event) {
		const { value = {}, path, onChange } = this.props;
		const newVal = event.target.value;
		const geo = [
			i === 0 ? newVal : value.geo ? value.geo[0] : '',
			i === 1 ? newVal : value.geo ? value.geo[1] : '',
		];
		onChange({
			path,
			value: {
				...value,
				geo,
			},
		});
	},

	makeGeoChanger (fieldPath) {
		return this.geoChanged.bind(this, fieldPath);
	},

	formatValue () {
		const { value = {} } = this.props;
		return _.compact([
			value.number,
			value.name,
			value.street1,
			value.street2,
			value.suburb,
			value.state,
			value.postcode,
			value.country,
		]).join(', ');
	},

	renderValue () {
		return <FormInput noedit>{this.formatValue() || '(no value)'}</FormInput>;
	},

	renderField (fieldPath, label, collapse, autoFocus) {
		if (this.state.collapsedFields[fieldPath]) {
			return null;
		}
		const { value = {}, path } = this.props;
		return (
			<NestedFormField label={label} data-field-location-path={path + '.' + fieldPath}>
				<FormInput autoFocus={autoFocus} name={path + '.' + fieldPath} value={value[fieldPath]} onChange={this.makeChanger(fieldPath)} placeholder={label} />
			</NestedFormField>
		);
	},

	renderSuburbState () {
		const { value = {}, path } = this.props;
		return (
			<NestedFormField label="Suburb / State" data-field-location-path={path + '.suburb_state'}>
				<FormRow>
					<FormField width="two-thirds" data-field-location-path={path + '.suburb'}>
						<FormInput name={path + '.suburb'} value={value.suburb} onChange={this.makeChanger('suburb')} placeholder="Suburb" />
					</FormField>
					<FormField width="one-third" data-field-location-path={path + '.state'}>
						<FormInput name={path + '.state'} value={value.state} onChange={this.makeChanger('state')} placeholder="State" />
					</FormField>
				</FormRow>
			</NestedFormField>
		);
	},

	renderPostcodeCountry () {
		const { value = {}, path } = this.props;
		return (
			<NestedFormField label="Postcode / Country" data-field-location-path={path + '.postcode_country'}>
				<FormRow>
					<FormField width="one-third" data-field-location-path={path + '.postcode'}>
						<FormInput name={path + '.postcode'} value={value.postcode} onChange={this.makeChanger('postcode')} placeholder="Post Code" />
					</FormField>
					<FormField width="two-thirds" data-field-location-path={path + '.country'}>
						<FormInput name={path + '.country'} value={value.country} onChange={this.makeChanger('country')} placeholder="Country" />
					</FormField>
				</FormRow>
			</NestedFormField>
		);
	},

	renderGeo () {
		if (this.state.collapsedFields.geo) {
			return null;
		}
		const { value = {}, path, paths } = this.props;
		const geo = value.geo || [];
		return (
			<NestedFormField label="Lat / Lng" data-field-location-path={path + '.geo'}>
				<FormRow>
					<FormField width="one-half" data-field-location-path="latitude">
						<FormInput name={paths.geo + '[1]'} value={geo[1]} onChange={this.makeGeoChanger(1)} placeholder="Latitude" />
					</FormField>
					<FormField width="one-half" data-field-location-path="longitude">
						<FormInput name={paths.geo + '[0]'} value={geo[0]} onChange={this.makeGeoChanger(0)} placeholder="Longitude" />
					</FormField>
				</FormRow>
			</NestedFormField>
		);
	},

	updateGoogleOption (key, e) {
		var newState = {};
		newState[key] = e.target.checked;
		this.setState(newState);
	},

	makeGoogler (key) {
		return this.updateGoogleOption.bind(this, key);
	},

	renderGoogleOptions () {
		const { paths, enableMapsAPI } = this.props;
		if (!enableMapsAPI) return null;
		var replace = this.state.improve ? (
			<Checkbox
				label="Replace existing data"
				name={paths.overwrite}
				onChange={this.makeGoogler('overwrite')}
				checked={this.state.overwrite} />
		) : null;
		return (
			<FormField offsetAbsentLabel>
				<Checkbox
					label="Autodetect and improve location on save"
					name={paths.improve}
					onChange={this.makeGoogler('improve')}
					checked={this.state.improve}
					title="When checked, this will attempt to fill missing fields. It will also get the lat/long" />
				{replace}
			</FormField>
		);
	},

	renderNote () {
		const { note } = this.props;
		if (!note) return null;
		return (
			<FormField offsetAbsentLabel>
				<FormNote note={note} />
			</FormField>
		);
	},

	renderUI () {

		if (!this.shouldRenderField()) {
			return (
				<FormField label={this.props.label}>{this.renderValue()}</FormField>
			);
		}

		/* eslint-disable no-script-url */
		var showMore = !_.isEmpty(this.state.collapsedFields)
			? <CollapsedFieldLabel onClick={this.uncollapseFields}>(show more fields)</CollapsedFieldLabel>
			: null;
		/* eslint-enable */

		const { label, path } = this.props;
		return (

				<FormField label={label}>
					{showMore}
				</FormField>
				{this.renderField('number', 'PO Box / Shop', true, true)}
				{this.renderField('name', 'Building Name', true)}
				{this.renderField('street1', 'Street Address')}
				{this.renderField('street2', 'Street Address 2', true)}
				{this.renderSuburbState()}
				{this.renderPostcodeCountry()}
				{this.renderGeo()}
				{this.renderGoogleOptions()}
				{this.renderNote()}

		);
	},

});
<|endoftext|>


<commit_before>const express = require('express'),
	winston = require('winston'),
	urljoin = require('url-join'),
	request = require('request'),
	xml2js = require('xml2js'),
	parseString = xml2js.parseString,
	jsonpath = require('jsonpath'),
	config = require('./conf/default'),
	requestID = require('express-request-id')(),
	uuid = require('uuid'),
	app = express(),
	builder = new xml2js.Builder({
		renderOpts: {
			pretty: false
		}
	});

const cache = {};

function generateGUID(req, item) {
	/* eslint no-param-reassign: off */
	const guidCache = cache[req.id] || [];
	let guid = item.guid[0]._;
	if (guidCache.length && guidCache.indexOf(guid) > -1) {
		// since we have more than one item based on this node we need a new guid
		guid += `_rss2rss_${uuid.v4()}`;
	}
	// set the value in the cache
	guidCache.push(guid);
	return guid;
}

function clearGUIDCache(req) {
	delete cache[req.id];
}

winston.level = 'debug';

if (!config.feeds || !config.feeds.length) {
	winston.error('No configured feeds to serve. Add some to config.feeds in conf/default.js and try again');
	process.exit(0);
}

function unescapeHTML(string) {
	return string
	.replace(/&/g, '&')
	.replace(/</g, '<')
	.replace(/>/g, '>')
	.replace(/"/g, '"')
	.replace(/'/g, "'");
}

function getNewItem(req, regexResult, originalItemNode, opts) {
	const item = JSON.parse(JSON.stringify(originalItemNode));

	// set the guid on the item
	item.guid[0]._ = generateGUID(req, item);

	// set custom values
	if (opts.replace && opts.replace.title) {
		item.title = opts.replace.title(regexResult, originalItemNode);
	}

	if (opts.replace && opts.replace.link) {
		item.link = [opts.replace.link(regexResult, originalItemNode)];
	}

	return item;
}

function getRegexMatches(node, opts) {
	// get all matches
	const filterResults = [];
	let matched;
	do {
		matched = opts.regex.exec(node);
		if (matched && matched[0]) {
			matched = matched[0];
			if (opts.unescape) {
				matched = unescapeHTML(matched);
			}
			filterResults.push(matched);
		}
	} while (matched && opts.multi);
	return filterResults;
}

function setFeedItems(xml, items) {
	const channel = jsonpath.query(xml, '$.rss.channel[0]')[0];
	channel.item = items;
}

function sendResponse(req, res, err, xml) {
	clearGUIDCache(req);
	if (err || !xml) {
		winston.error(err || 'No XML sent with response');
		return res.status(500).send();
	}
	res.contentType('application/rss+xml');
	return res.status(200).send(xml);
}

// set a request ID for caching
app.use(requestID);

config.feeds.forEach((feed) => {
	const url = urljoin(config.base || '', feed.url);
	winston.info('Configuring source', feed.source, 'on', url);
	app.get(url, (req, res) => {
		winston.info('request for', url);
		request(feed.source, (err, result) => {
			if (err) {
				return sendResponse(req, res, err);
			}
			if (!feed.filters || !feed.filters.length) {
				// send back original feed
				winston.info('No filters specified for feed');
				return sendResponse(res, null, result.body);
			}
			parseString(result.body, (parseErr, xmlObj) => {
				if (parseErr) {
					return sendResponse(req, res, parseErr);
				}
				const itemsToReturn = [];
				feed.filters.forEach((opts) => {
					const items = jsonpath.query(xmlObj, '$.rss.channel[0].item[*]');
					items.forEach((item) => {
						const node = item[opts.key || 'description'];
						if (!node) {
							return;
						}
						const regexMatches = getRegexMatches(node[0], opts);
						if (!regexMatches.length) {
							return;
						}
						regexMatches.forEach((filterResult) => {
							const newNode = getNewItem(req, filterResult, item, opts);
							itemsToReturn.push(newNode);
						});
					});
				});

				setFeedItems(xmlObj, itemsToReturn);
				const XMLString = builder.buildObject(xmlObj);
				return sendResponse(req, res, null, XMLString);
			});
		});
	});
});

app.listen(config.port || 80, () => {
	winston.info('rss2rss listening on port 80');
});
<commit_msg>fix issue with unique GUID not being assigned<commit_after>const express = require('express'),
	winston = require('winston'),
	urljoin = require('url-join'),
	request = require('request'),
	xml2js = require('xml2js'),
	parseString = xml2js.parseString,
	jsonpath = require('jsonpath'),
	config = require('./conf/default'),
	requestID = require('express-request-id')(),
	uuid = require('uuid'),
	app = express(),
	builder = new xml2js.Builder({
		renderOpts: {
			pretty: false
		}
	});

const cache = {};

function generateGUID(req, item) {
	if (!cache[req.id]) {
		cache[req.id] = [];
	}
	const guidCache = cache[req.id];
	let guid = item.guid[0]._;
	if (guidCache.length && guidCache.indexOf(guid) > -1) {
		// since we have more than one item based on this node we need a new guid
		guid += `_rss2rss_${uuid.v4()}`;
	}
	// set the value in the cache
	cache[req.id].push(guid);
	return guid;
}

function clearGUIDCache(req) {
	delete cache[req.id];
}

winston.level = 'debug';

if (!config.feeds || !config.feeds.length) {
	winston.error('No configured feeds to serve. Add some to config.feeds in conf/default.js and try again');
	process.exit(0);
}

function unescapeHTML(string) {
	return string
	.replace(/&/g, '&')
	.replace(/</g, '<')
	.replace(/>/g, '>')
	.replace(/"/g, '"')
	.replace(/'/g, "'");
}

function getNewItem(req, regexResult, originalItemNode, opts) {
	const item = JSON.parse(JSON.stringify(originalItemNode));

	// set the guid on the item
	item.guid[0]._ = generateGUID(req, item);

	// set custom values
	if (opts.replace && opts.replace.title) {
		item.title = opts.replace.title(regexResult, originalItemNode);
	}

	if (opts.replace && opts.replace.link) {
		item.link = [opts.replace.link(regexResult, originalItemNode)];
	}

	return item;
}

function getRegexMatches(node, opts) {
	// get all matches
	const filterResults = [];
	let matched;
	do {
		matched = opts.regex.exec(node);
		if (matched && matched[0]) {
			matched = matched[0];
			if (opts.unescape) {
				matched = unescapeHTML(matched);
			}
			filterResults.push(matched);
		}
	} while (matched && opts.multi);
	return filterResults;
}

function setFeedItems(xml, items) {
	const channel = jsonpath.query(xml, '$.rss.channel[0]')[0];
	channel.item = items;
}

function sendResponse(req, res, err, xml) {
	clearGUIDCache(req);
	if (err || !xml) {
		winston.error(err || 'No XML sent with response');
		return res.status(500).send();
	}
	res.contentType('application/rss+xml');
	return res.status(200).send(xml);
}

// set a request ID for caching
app.use(requestID);

config.feeds.forEach((feed) => {
	const url = urljoin(config.base || '', feed.url);
	winston.info('Configuring source', feed.source, 'on', url);
	app.get(url, (req, res) => {
		winston.info('request for', url);
		request(feed.source, (err, result) => {
			if (err) {
				return sendResponse(req, res, err);
			}
			if (!feed.filters || !feed.filters.length) {
				// send back original feed
				winston.info('No filters specified for feed');
				return sendResponse(res, null, result.body);
			}
			parseString(result.body, (parseErr, xmlObj) => {
				if (parseErr) {
					return sendResponse(req, res, parseErr);
				}
				const itemsToReturn = [];
				feed.filters.forEach((opts) => {
					const items = jsonpath.query(xmlObj, '$.rss.channel[0].item[*]');
					items.forEach((item) => {
						const node = item[opts.key || 'description'];
						if (!node) {
							return;
						}
						const regexMatches = getRegexMatches(node[0], opts);
						if (!regexMatches.length) {
							return;
						}
						regexMatches.forEach((filterResult) => {
							const newNode = getNewItem(req, filterResult, item, opts);
							itemsToReturn.push(newNode);
						});
					});
				});

				setFeedItems(xmlObj, itemsToReturn);
				const XMLString = builder.buildObject(xmlObj);
				return sendResponse(req, res, null, XMLString);
			});
		});
	});
});

app.listen(config.port || 80, () => {
	winston.info('rss2rss listening on port 80');
});
<|endoftext|>


<commit_before>( function ( window, doc, undef ) {
  // Takes a preloaded css obj (changes in different browsers) and injects it into the head
  yepnope.injectCss = function( href, cb, attrs, timeout, /* Internal use */ err, internal ) {

    // Create stylesheet link
    var link = document.createElement( "link" ),
        onload = function() {
          if ( ! done ) {
            done = 1;
            link.removeAttribute("id");
            setTimeout( cb, 0 );
          }
        },
        id = "yn" + new Date,
        ref, done, i;

    cb = internal ? yepnope.executeStack : ( cb || function(){} );
    timeout = timeout || yepnope.errorTimeout;
    // Add attributes
    link.href = href;
    link.rel  = "stylesheet";
    link.type = "text/css";
    link.id = id;

    // Add our extra attributes to the link element
    for ( i in attrs ) {
      link.setAttribute( i, attrs[ i ] );
    }

    if ( ! err ) {
      ref = document.getElementsByTagName('base')[0] || document.getElementsByTagName('script')[0];
      ref.parentNode.insertBefore( link, ref );
      link.onload = onload;

      function poll() {
        try {
            var sheets = document.styleSheets;
            for(var j=0, k=sheets.length; j<k; j++) {
                if(sheets[j].ownerNode.id == id) {
                    sheets[j].cssRules;
                }
            }
            // If you made it here, success!
            onload();
        } catch(e) {
            // Keep polling
            setTimeout(poll, 20);
        }
      }
      poll();
    }
  }
})( this, this.document );
<commit_msg>fix css plugin to handle when injected stylesheet isnt present in the document.styleSheet on first poll<commit_after>( function ( window, doc, undef ) {
  // Takes a preloaded css obj (changes in different browsers) and injects it into the head
  yepnope.injectCss = function( href, cb, attrs, timeout, /* Internal use */ err, internal ) {

    // Create stylesheet link
    var link = document.createElement( "link" ),
        onload = function() {
          if ( ! done ) {
            done = 1;
            link.removeAttribute("id");
            setTimeout( cb, 0 );
          }
        },
        id = "yn" + new Date,
        ref, done, i;

    cb = internal ? yepnope.executeStack : ( cb || function(){} );
    timeout = timeout || yepnope.errorTimeout;
    // Add attributes
    link.href = href;
    link.rel  = "stylesheet";
    link.type = "text/css";
    link.id = id;

    // Add our extra attributes to the link element
    for ( i in attrs ) {
      link.setAttribute( i, attrs[ i ] );
    }

    if ( ! err ) {
      ref = document.getElementsByTagName('base')[0] || document.getElementsByTagName('script')[0];
      ref.parentNode.insertBefore( link, ref );
      link.onload = onload;

      function poll() {
        try {
            var sheets = document.styleSheets;
            for(var j=0, k=sheets.length; j<k; j++) {
                if(sheets[j].ownerNode.id == id) {
                    // this throws an exception? was originally just a statement of "sheets[j].cssRules;"
                    if (sheets[j].cssRules.length)
                        return onload();
                }
            }
            // if we get here, its not in document.styleSheets (we never saw the ID)
            throw new Error;
        } catch(e) {
            // Keep polling
            setTimeout(poll, 20);
        }
      }
      poll();
    }
  }
})( this, this.document );
<|endoftext|>


<commit_before>// Get Canvas
var canvas = document.getElementById("canvas"),
  ctx = canvas.getContext("2d"),
  width = 512,
  height = 480;

canvas.tabIndex = 1;
canvas.width = width;
canvas.height = height;

// Background Image
var bgReady = false;
var bgImage = new Image();
bgImage.onload = function () {
  bgReady = true;
};
bgImage.src = "http://placekitten.com/512/480";
// Hero Image
var heroReady = false;
var heroImage = new Image();
heroImage.onload = function () {
  heroReady = true;
};
heroImage.src = "http://placekitten.com/32/32";

// Kitty Image
var kittyReady = false;
var kittyImage = new Image();
kittyImage.onload = function () {
  kittyReady = true;
};
kittyImage.src = "http://placekitten.com/30/32";

// Game objects
var hero = {
  speed: 256,
  x: 0,
  y: 0
};

var kitty = {
  x: 0,
  y: 0
};
var kittyCaught = 0;

// Handle keyboard controls
var keysDown = {};

addEventListener("keydown", function (e) {
  keysDown[e.keyCode] = true;
  e.preventDefault();
}, false);

addEventListener("keyup", function (e) {
  delete keysDown[e.keyCode];
}, false);

var reset = function () {
  hero.x = (canvas.width / 2) - 16;
  hero.y = (canvas.height / 2) - 16;

  kitty.x = 32 + (Math.random() * (canvas.width - 64));
  kitty.y = 32 + (Math.random() * (canvas.height - 64));
};

// Update game objects
var update = function (modifier) {
  if (38 in keysDown) {
    hero.y -= hero.speed * modifier;
  }
  if (40 in keysDown) {
    hero.y += hero.speed * modifier;
  }
  if (37 in keysDown) {
    hero.x -= hero.speed * modifier;
  }
  if (39 in keysDown) {
    hero.x += hero.speed * modifier;
  }

  // Stop from going off the page
  if (hero.x >= canvas.width - 32) {
    hero.x = canvas.width - 32;
  } else if (hero.x <= 0) {
    hero.x = 0;
  }

  if (hero.y >= canvas.height - 32) {
    hero.y = canvas.height - 32;
  } else if (hero.y <= 0) {
    hero.y = 0;
  }

  // Collision
  if (hero.x <= (kitty.x + 32) && kitty.x <= (hero.x + 32) && hero.y <= (kitty.y + 32) && kitty.y <= (hero.y + 32)) {
    ++kittyCaught;
    nowSwitch = thenSwitch;
    reset();
  }
};

// Render
var render = function () {
  if (bgReady) {
    ctx.drawImage(bgImage, 0, 0);
  }

  if (heroReady) {
    ctx.drawImage(heroImage, hero.x, hero.y);
  }

  if (kittyReady) {
    ctx.drawImage(kittyImage, kitty.x, kitty.y);
  }

  ctx.fillStyle = "#EEE";
  ctx.font = "24px Ubuntu";
  ctx.textAlign = "left";
  ctx.textBaseline = "top";
  ctx.fillText("Kitties caught : " + kittyCaught, 32, 32);
  ctx.fillText("Lives : " + lives, 365, 32);
  ctx.fillText("Timer : " + parseInt(countDown / 100), 32, 64);
};

var gameOver = function () {
  document.write("Game Over. Kitties only have nine lives.");
};

var main = function () {
  now = Date.now();
  var delta = now - then;

  var nowSwitch = Date.now();
  countDown = nowSwitch - thenSwitch;

  update(delta / 1000);
  if (countDown >= 1300) {
    lives--;
    if (lives ==  0) {
      gameOver();
    }
    thenSwitch = nowSwitch;
    reset();
  }
  render();

  then = now;

  requestAnimationFrame(main);
};

var w = window;
requestAnimationFrame = w.requestAnimationFrame || w.webkitRequestAnimationFrame || w.msRequestAnimationFrame || w.mozRequestAnimationFrame;

// Initalized Variables
var then, thenSwitch, nowSwitch;
var countDown;
var lives;

var start = function() {
  then = thenSwitch = nowSwitch = Date.now();
  reset();
  countDown = 0;
  lives = 9;
  kittyCaught = 0;
  //hero.x = (canvas.width / 2) - 16;
  //hero.y = (canvas.height / 2) - 16;
  main();
}

start();
<commit_msg>Update canvas.js<commit_after>// Get Canvas
var canvas = document.getElementById("canvas"),
  ctx = canvas.getContext("2d"),
  width = 512,
  height = 480;

canvas.tabIndex = 1;
canvas.width = width;
canvas.height = height;

// Background Image
var bgReady = false;
var bgImage = new Image();
bgImage.onload = function () {
  bgReady = true;
};
bgImage.src = "http://placekitten.com/512/480";
// Hero Image
var heroReady = false;
var heroImage = new Image();
heroImage.onload = function () {
  heroReady = true;
};
heroImage.src = "http://placekitten.com/32/32";

// Kitty Image
var kittyReady = false;
var kittyImage = new Image();
kittyImage.onload = function () {
  kittyReady = true;
};
kittyImage.src = "http://placekitten.com/30/32";

// Game objects
var hero = {
  speed: 256,
  x: 0,
  y: 0
};

var kitty = {
  x: 0,
  y: 0
};
var kittyCaught = 0;

// Handle keyboard controls
var keysDown = {};

addEventListener("keydown", function (e) {
  keysDown[e.keyCode] = true;
  e.preventDefault();
}, false);

addEventListener("keyup", function (e) {
  delete keysDown[e.keyCode];
}, false);

var reset = function () {
  hero.x = (canvas.width / 2) - 16;
  hero.y = (canvas.height / 2) - 16;

  kitty.x = 32 + (Math.random() * (canvas.width - 64));
  kitty.y = 32 + (Math.random() * (canvas.height - 64));
};

// Update game objects
var update = function (modifier) {
  if (38 in keysDown) {
    hero.y -= hero.speed * modifier;
  }
  if (40 in keysDown) {
    hero.y += hero.speed * modifier;
  }
  if (37 in keysDown) {
    hero.x -= hero.speed * modifier;
  }
  if (39 in keysDown) {
    hero.x += hero.speed * modifier;
  }

  // Stop from going off the page
  if (hero.x >= canvas.width - 32) {
    hero.x = canvas.width - 32;
  } else if (hero.x <= 0) {
    hero.x = 0;
  }

  if (hero.y >= canvas.height - 32) {
    hero.y = canvas.height - 32;
  } else if (hero.y <= 0) {
    hero.y = 0;
  }

  // Collision
  if (hero.x <= (kitty.x + 32) && kitty.x <= (hero.x + 32) && hero.y <= (kitty.y + 32) && kitty.y <= (hero.y + 32)) {
    ++kittyCaught;
    nowSwitch = thenSwitch;
    reset();
  }
};

// Render
var render = function () {
  if (bgReady) {
    ctx.drawImage(bgImage, 0, 0);
  }

  if (heroReady) {
    ctx.drawImage(heroImage, hero.x, hero.y);
  }

  if (kittyReady) {
    ctx.drawImage(kittyImage, kitty.x, kitty.y);
  }

  ctx.fillStyle = "#EEE";
  ctx.font = "24px Ubuntu";
  ctx.textAlign = "left";
  ctx.textBaseline = "top";
  ctx.fillText("Kitties caught : " + kittyCaught, 32, 32);
  ctx.fillText("Lives : " + lives, 365, 32);
  ctx.fillText("Timer : " + parseInt(countDown / 100), 32, 64);
};

var gameOver = function () {
  document.write("Game Over. Kitties only have nine lives.");
};

var main = function () {
  now = Date.now();
  var delta = now - then;

  var nowSwitch = Date.now();
  countDown = nowSwitch - thenSwitch;

  update(delta / 1000);
  if (countDown >= 1200) {
    lives--;
    if (lives ==  0) {
      gameOver();
    }
    thenSwitch = nowSwitch;
    reset();
  }
  render();

  then = now;

  requestAnimationFrame(main);
};

var w = window;
requestAnimationFrame = w.requestAnimationFrame || w.webkitRequestAnimationFrame || w.msRequestAnimationFrame || w.mozRequestAnimationFrame;

// Initalized Variables
var then, thenSwitch, nowSwitch;
var countDown;
var lives;

var start = function() {
  then = thenSwitch = nowSwitch = Date.now();
  reset();
  countDown = 0;
  lives = 9;
  kittyCaught = 0;
  //hero.x = (canvas.width / 2) - 16;
  //hero.y = (canvas.height / 2) - 16;
  main();
}

start();
<|endoftext|>


<commit_before>var nest = require('depnest')

exports.needs = nest({
  'config.sync.load': 'first'
})

exports.gives = nest('blob.sync.url')

exports.create = function (api) {
  return nest('blob.sync.url', function (link) {
    var config = api.config.sync.load()
    var prefix = config.blobsPrefix != null ? config.blobsPrefix : `http://localhost:${config.ws.port}/blobs/get`
    if (link && typeof link.link === 'string') {
      link = link.link
    }
    return `${prefix}/${link}`
  })
}
<commit_msg>only generate blob urls if valid blob ID passed<commit_after>var nest = require('depnest')
var ref = require('ssb-ref')

exports.needs = nest({
  'config.sync.load': 'first'
})

exports.gives = nest('blob.sync.url')

exports.create = function (api) {
  return nest('blob.sync.url', function (link) {
    var config = api.config.sync.load()
    var prefix = config.blobsPrefix != null ? config.blobsPrefix : `http://localhost:${config.ws.port}/blobs/get`
    if (link && typeof link.link === 'string') {
      link = link.link
    }

    var parsed = ref.parseLink(link)
    if (parsed && ref.isBlob(parsed.link)) {
      return `${prefix}/${parsed.link}`
    }
  })
}
<|endoftext|>


<commit_before>import Floor from 'javascript/floor';

var attribution = new ol.Attribution({
  html: '
The source code for this project is released as ' +
  'open source under the AGPL 3.0 license.
' +
  '
The graphical assets of the map and icons as well as the data is property of ArenaNet and subject to ' +
  'the following copyright:

"© 2014 ArenaNet, LLC. All rights reserved. NCSOFT, the interlocking NC l' +
  'ogo, ArenaNet, Guild Wars, Guild Wars Factions, Guild Wars Nightfall, Guild Wars: Eye of the North, Guil' +
  'd Wars 2, and all associated logos and designs are trademarks or registered trademarks of NCSOFT Corpora' +
  'tion. All other trademarks are the property of their respective owners."
'
});

const falseMaps = Immutable.Set([37, 55, 61, 77, 79, 80, 89, 92, 97, 110,
  113, 120, 138, 140, 142, 143, 144, 145, 147, 148, 149, 152, 153, 154,
  157, 159, 161, 162, 163, 171, 172, 178, 179, 180, 182, 184, 185, 186,
  190, 191, 192, 193, 195, 196, 198, 199, 201, 202, 203, 211, 212, 215,
  216, 217, 222, 224, 225, 226, 232, 234, 237, 238, 239, 242, 244, 248,
  249, 250, 251, 252, 254, 255, 256, 257, 258, 259, 260, 262, 263, 264,
  267, 269, 271, 272, 274, 275, 276, 282, 283, 284, 287, 288, 290, 294,
  330, 327, 334, 363, 364, 365, 371, 372, 373, 374, 375, 376, 378, 379,
  380, 381, 382, 385, 386, 387, 388, 389, 390, 391, 392, 393, 394, 396,
  397, 399, 400, 401, 405, 407, 410, 411, 412, 413, 414, 415, 416, 417,
  418, 419, 420, 421, 422, 423, 424, 425, 427, 428, 429, 430, 434, 435,
  436, 439, 440, 441, 444, 447, 449, 453, 454, 455, 458, 459, 460, 464,
  465, 466, 470, 471, 474, 476, 477, 480, 481, 483, 485, 487, 488, 490,
  492, 497, 498, 499, 502, 503, 504, 505, 507, 509, 511, 512, 513, 514,
  515, 516, 517, 518, 519, 520, 521, 522, 523, 524, 525, 527, 528, 529,
  532, 533, 534, 535, 536, 537, 538, 539, 540, 542, 543, 544, 545, 546,
  547, 548, 552, 556, 557, 558, 559, 560, 561, 563, 564, 567, 569, 570,
  571, 573, 574, 575, 576, 577, 578, 579, 581, 582, 583, 584, 586, 587,
  588, 589, 590, 591, 592, 594, 595, 596, 597, 598, 599, 606, 607, 608,
  609, 610, 611, 613, 614, 617, 618, 620, 621, 622, 623, 624, 625, 628,
  629, 630, 631, 634, 635, 636, 638, 642, 643, 644, 645, 648, 649, 650,
  651, 652, 653, 655, 656, 657, 659, 662, 663, 664, 666, 667, 668, 669,
  670, 672, 673, 674, 675, 676, 677, 678, 680, 681, 682, 683, 684, 685,
  686, 687, 691, 692, 693, 694, 698, 700, 703, 706, 707, 708, 709, 710,
  711, 712, 713, 714, 715, 719, 726, 727, 728, 729, 730, 731, 732, 733,
  735, 736, 737, 738, 739, 743, 744, 745, 746, 747, 750, 751, 758, 760,
  761, 762, 763, 767, 768, 769, 772, 775, 777, 778, 779, 781, 783, 784,
  785, 786, 787, 788, 790, 792, 793, 797, 799, 806, 807, 820, 821, 825,
  827, 828, 830, 833, 845, 849, 905, 914, 938, 939, 980, 989, 990, 991,
  992, 993, 994, 997, 999, 1000, 1001, 1002, 1003, 1004, 1005, 1006,
  1007, 1009, 1010, 1016, 1017, 1018, 1021, 1022, 1023, 1024, 1025, 1026,
  1027, 1028, 1029, 1032, 1033, 1037, 1048, 1050, 1051, 1054, 1058, 1062,
  1063, 1064, 1065, 1066, 1067, 1069, 1070, 1071, 1072, 1073, 1074, 1076,
  1079, 1080, 1081, 1082, 1083, 1084, 1087, 1088, 1089, 1090, 1092, 1094,
  1095, 1097, 1098, 1100, 1101, 1104, 1106, 1107, 1108, 1109, 1110, 1113,
  1115, 1117, 1121, 1122, 1123, 1124, 1125, 1128, 1129, 1130, 1133, 1134,
  1135, 1136, 1137, 1139, 1140, 1142, 1144, 1146]);

  var continentsPromise = axios.get('https://api.guildwars2.com/v2/continents', {params: {ids: 'all'}})
  .then(x => x.data)
  .then(Immutable.fromJS);

  var iconPromise = axios.get('https://api.guildwars2.com/v2/files', {
    params: {
      ids: Immutable.List([
        'map_waypoint',
        'map_dungeon',
        'map_heart_empty',
        'map_poi',
        'map_heropoint',
        'map_vista'
      ]).join(',')
    }
  }).then(x => x.data).then(Immutable.fromJS).then(x=>x.groupBy(y=>y.get('id')).map(x=>x.first().get('icon')));

  var tileUrl = 'https://tiles{s}.guildwars2.com/1/1/{z}/{x}/{y}.jpg';

  continentsPromise.then(function(continents) {
    var floor = axios.get('https://api.guildwars2.com/v2/continents/1/floors/0')
    .then(floorResponse => floorResponse.data)
    .then(Immutable.fromJS)

    floor.then(function(floor) {
      var tileSize = 256;
      var projection = new ol.proj.Projection({
        code: 'ZOOMIFY',
        units: 'pixels',
        extent: [0, 0, continents.getIn([0, 'continent_dims', 0]), continents.getIn([0, 'continent_dims', 1])]
      });
      var projectionExtent = projection.getExtent();
      var maxResolution = ol.extent.getWidth(projectionExtent) / tileSize;
      var resolutions = [];
      for(var z = 0; z <= 8; z++) {
        resolutions[z] = maxResolution / Math.pow(2, z)
      }

      var map = new ol.Map({
        target: "map",
        layers : [
          new ol.layer.Tile({
            source: new ol.source.TileImage({
              attributions: [attribution],
              tileUrlFunction: function(tileCoord, pixelRatio, projection) {
                var xEven = tileCoord[1] % 2;
                var yEven = (-tileCoord[2] - 1) % 2;
                return tileUrl.replace('{s}', (2 * xEven + yEven + 1).toString())
                .replace('{z}', tileCoord[0].toString())
                .replace('{x}', tileCoord[1].toString())
                .replace('{y}', (-tileCoord[2] - 1).toString());
              },
              projection: projection,
              tileGrid: new ol.tilegrid.TileGrid({
                origin: ol.extent.getTopLeft(projectionExtent),
                resolutions: resolutions,
                tileSize: tileSize
              })
            }),
            extent: projectionExtent
          })
        ],
        view: new ol.View({
          projection: projection,
          center: [16384, 16384],
          zoom: 2,
          minZoom: continents.getIn([0, 'min_zoom']),
          maxZoom: continents.getIn([0, 'max_zoom']),
          extent: projectionExtent
        })
      });

      map.getView().on('change:resolution', function() {
        console.log(map.getView().getResolution())
      });

      function flipCoordinate(coord) {
        return Immutable.List([coord.get(0), continents.getIn([0, 'continent_dims', 1]) - coord.get(1)]);
      }

      function getCenterOfRect(rect) {
        return Immutable.List([
          (rect.getIn([0, 0]) + rect.getIn([1, 0])) / 2,
          (rect.getIn([0, 1]) + rect.getIn([1, 1])) / 2
        ]);
      }

      var regions = Immutable.Map(floor.get('regions'));
      var zones = regions.map(x=>x.get('maps'))
      .reduce((res, val)=>res.merge(val), Immutable.Map())
      .filter(x=>!falseMaps.has(x.get('id')));

      var regionFeatures = regions.map(function(region, regionId) {
        return new ol.Feature({
          geometry: new ol.geom.Point(flipCoordinate(region.get('label_coord')).toJS()),
          name: region.get('name')
        });
      }).valueSeq();

      var zoneFeatures = zones.map(function(zone) {
        return new ol.Feature({
          geometry: new ol.geom.Point(flipCoordinate(getCenterOfRect(zone.get('continent_rect'))).toJS()),
          name: zone.get('name')
        })
      }).valueSeq();

      var regionLayer = new ol.layer.Vector({
        source: new ol.source.Vector({
          features: regionFeatures.toJS(),
          wrapX: false
        }),
        extent: projectionExtent,
        style: function(feature) {
          return [new ol.style.Style({
            text: new ol.style.Text({
              textAlign: "center",
              textBaseline: "middle",
              font: 'normal 0.8em sans-serif',
              text: feature.get('name'),
              fill: new ol.style.Fill({color: "#ffffff"}),
              stroke: new ol.style.Stroke({color: "#000000", width: 2}),
              offsetX: 0,
              offsetY: 0,
              rotation: 0
            })
          })]
        },
        minResolution: 16
      });

      var zoneLayer = new ol.layer.Vector({
        source: new ol.source.Vector({
          features: zoneFeatures.toJS(),
          wrapX: false
        }),
        extent: projectionExtent,
        style: function(feature) {
          return [new ol.style.Style({
            text: new ol.style.Text({
              textAlign: "center",
              textBaseline: "middle",
              font: 'normal 0.8em sans-serif',
              text: feature.get('name'),
              fill: new ol.style.Fill({color: "#ffff00"}),
              stroke: new ol.style.Stroke({color: "#000000", width: 2}),
              offsetX: 0,
              offsetY: 0,
              rotation: 0
            })
          })]
        },
        minResolution: 4,
        maxResolution: 32
      });

      map.addLayer(regionLayer);
      map.addLayer(zoneLayer)
    }).catch(function(e, response) {
      console.error(e)
    })

  }).catch(function(e, response) {
    console.error(e)
  });
<commit_msg>Used the false zone list from the domain object.<commit_after>import Floor from 'javascript/floor'
import Zone from 'javascript/zone'

var attribution = new ol.Attribution({
  html: '
The source code for this project is released as ' +
  'open source under the AGPL 3.0 license.
' +
  '
The graphical assets of the map and icons as well as the data is property of ArenaNet and subject to ' +
  'the following copyright:

"© 2014 ArenaNet, LLC. All rights reserved. NCSOFT, the interlocking NC l' +
  'ogo, ArenaNet, Guild Wars, Guild Wars Factions, Guild Wars Nightfall, Guild Wars: Eye of the North, Guil' +
  'd Wars 2, and all associated logos and designs are trademarks or registered trademarks of NCSOFT Corpora' +
  'tion. All other trademarks are the property of their respective owners."
'
});

  var continentsPromise = axios.get('https://api.guildwars2.com/v2/continents', {params: {ids: 'all'}})
  .then(x => x.data)
  .then(Immutable.fromJS);

  var iconPromise = axios.get('https://api.guildwars2.com/v2/files', {
    params: {
      ids: Immutable.List([
        'map_waypoint',
        'map_dungeon',
        'map_heart_empty',
        'map_poi',
        'map_heropoint',
        'map_vista'
      ]).join(',')
    }
  }).then(x => x.data).then(Immutable.fromJS).then(x=>x.groupBy(y=>y.get('id')).map(x=>x.first().get('icon')));

  var tileUrl = 'https://tiles{s}.guildwars2.com/1/1/{z}/{x}/{y}.jpg';

  continentsPromise.then(function(continents) {
    var floor = axios.get('https://api.guildwars2.com/v2/continents/1/floors/0')
    .then(floorResponse => floorResponse.data)
    .then(Immutable.fromJS)

    floor.then(function(floor) {
      var tileSize = 256;
      var projection = new ol.proj.Projection({
        code: 'ZOOMIFY',
        units: 'pixels',
        extent: [0, 0, continents.getIn([0, 'continent_dims', 0]), continents.getIn([0, 'continent_dims', 1])]
      });
      var projectionExtent = projection.getExtent();
      var maxResolution = ol.extent.getWidth(projectionExtent) / tileSize;
      var resolutions = [];
      for(var z = 0; z <= 8; z++) {
        resolutions[z] = maxResolution / Math.pow(2, z)
      }

      var map = new ol.Map({
        target: "map",
        layers : [
          new ol.layer.Tile({
            source: new ol.source.TileImage({
              attributions: [attribution],
              tileUrlFunction: function(tileCoord, pixelRatio, projection) {
                var xEven = tileCoord[1] % 2;
                var yEven = (-tileCoord[2] - 1) % 2;
                return tileUrl.replace('{s}', (2 * xEven + yEven + 1).toString())
                .replace('{z}', tileCoord[0].toString())
                .replace('{x}', tileCoord[1].toString())
                .replace('{y}', (-tileCoord[2] - 1).toString());
              },
              projection: projection,
              tileGrid: new ol.tilegrid.TileGrid({
                origin: ol.extent.getTopLeft(projectionExtent),
                resolutions: resolutions,
                tileSize: tileSize
              })
            }),
            extent: projectionExtent
          })
        ],
        view: new ol.View({
          projection: projection,
          center: [16384, 16384],
          zoom: 2,
          minZoom: continents.getIn([0, 'min_zoom']),
          maxZoom: continents.getIn([0, 'max_zoom']),
          extent: projectionExtent
        })
      });

      map.getView().on('change:resolution', function() {
        console.log(map.getView().getResolution())
      });

      function flipCoordinate(coord) {
        return Immutable.List([coord.get(0), continents.getIn([0, 'continent_dims', 1]) - coord.get(1)]);
      }

      function getCenterOfRect(rect) {
        return Immutable.List([
          (rect.getIn([0, 0]) + rect.getIn([1, 0])) / 2,
          (rect.getIn([0, 1]) + rect.getIn([1, 1])) / 2
        ]);
      }

      var regions = Immutable.Map(floor.get('regions'));
      var zones = regions.map(x=>x.get('maps'))
      .reduce((res, val)=>res.merge(val), Immutable.Map())
      .filter(x=>!(Zone.falseZones().has(x.get('id'))));

      var regionFeatures = regions.map(function(region, regionId) {
        return new ol.Feature({
          geometry: new ol.geom.Point(flipCoordinate(region.get('label_coord')).toJS()),
          name: region.get('name')
        });
      }).valueSeq();

      var zoneFeatures = zones.map(function(zone) {
        return new ol.Feature({
          geometry: new ol.geom.Point(flipCoordinate(getCenterOfRect(zone.get('continent_rect'))).toJS()),
          name: zone.get('name')
        })
      }).valueSeq();

      var regionLayer = new ol.layer.Vector({
        source: new ol.source.Vector({
          features: regionFeatures.toJS(),
          wrapX: false
        }),
        extent: projectionExtent,
        style: function(feature) {
          return [new ol.style.Style({
            text: new ol.style.Text({
              textAlign: "center",
              textBaseline: "middle",
              font: 'normal 0.8em sans-serif',
              text: feature.get('name'),
              fill: new ol.style.Fill({color: "#ffffff"}),
              stroke: new ol.style.Stroke({color: "#000000", width: 2}),
              offsetX: 0,
              offsetY: 0,
              rotation: 0
            })
          })]
        },
        minResolution: 16
      });

      var zoneLayer = new ol.layer.Vector({
        source: new ol.source.Vector({
          features: zoneFeatures.toJS(),
          wrapX: false
        }),
        extent: projectionExtent,
        style: function(feature) {
          return [new ol.style.Style({
            text: new ol.style.Text({
              textAlign: "center",
              textBaseline: "middle",
              font: 'normal 0.8em sans-serif',
              text: feature.get('name'),
              fill: new ol.style.Fill({color: "#ffff00"}),
              stroke: new ol.style.Stroke({color: "#000000", width: 2}),
              offsetX: 0,
              offsetY: 0,
              rotation: 0
            })
          })]
        },
        minResolution: 4,
        maxResolution: 32
      });

      map.addLayer(regionLayer);
      map.addLayer(zoneLayer)
    }).catch(function(e, response) {
      console.error(e)
    })

  }).catch(function(e, response) {
    console.error(e)
  });
<|endoftext|>