1

I'm busy building a website for a friend of mine and he is not that computer literate. So I thought of an idea to make it easy for him.

I want to create a JSON file where I can save all the text and image paths in the JSON file so that he can go into the file and apply the changes that he wants instead of searching through the code (like you normally do) and applying the changes there.

I'm using the landing page as an example.

<template>
  <div class="home">
    <div v-for="data in myJson.hero" :key="data">
      <v-card tile flat>
        <v-img
          height="885"
          gradient="to top left, rgba(100,115,201,.13), rgba(25,32,72,.7)"
          :src="data.image"
        >
          <template v-slot:placeholder>
            <v-row class="fill-height ma-0" align="center" justify="center">
              <v-progress-circular
                indeterminate
                color="grey lighten-5"
              ></v-progress-circular>
            </v-row>
          </template>
          <v-row>
            <v-col cols="12">
              <div class="centered">
                <h2 class="display-2 text-center white--text">
                  {{ data.firstHeading }}
                </h2>
                <h1
                  data-aos="zoom-in"
                  class="display-4 font-weight-bold text-center white--text"
                >
                  {{ data.secondHeading }}
                </h1>
                <h3 class="subtitle-4 text-center white--text">
                  {{ data.subHeading }}
                </h3>

                <v-btn large class="btnCentered" outlined fab dark>
                  <v-icon>mdi-arrow-down</v-icon>
                </v-btn>
              </div>
            </v-col>
          </v-row>
        </v-img>
      </v-card>
    </div>
  </div>
</template>

<script>
import json from "../json/controller.json";
export default {
  name: "Home",
  data() {
    return {
      myJson: json,
    };
  },
  components: {},
  methods: {},
};
</script>

<style scoped>
.centered {
  position: absolute;
  top: 45%;
  left: 50%;
  transform: translate(-50%, -50%);
}
.btnCentered {
  position: absolute;
  top: 250%;
  left: 50%;
  transform: translate(-50%, -50%);
}
</style>

My JSON file:

{
    "hero": [{
            "name": "heroImage",
            "alt": "telescopeImage",
            "image": "@/assets/background/telescope.jpg"
        },
        {
            "firstHeading": "HeroText",
            "secondHeading": "HeroText",
            "subHeading": "telescopeImage"
        }
    ],
}

I have done this before, but within a Vue.js file, not from another file

FirstTime

Somehow I'm doing it wrong... so, if someone kindly can enlighten my stupidity that would be great. And if someone knows of a better way please don't keep it a secret.

Edit**

I followed @Daniel_Knights advice it's working, KINDA... just that there is an unwanted feature that came with it.

Duplication

The landing page duplicates itself twice. Like a famous gaming company would say its a surprise mechanic. The text shows on the second one but not the image...

Edit*** X2

Figured out why it duplicates itself twice. but the image is still an issue.

The reason why it duplicated itself is that the JSON file wasn't like this.

    "hero": [{
        "name": "heroImage",
        "alt": "telescopeImage",
        "image": "@/assets/background/telescope.jpg",
        "firstHeading": "HeroText",
        "secondHeading": "HeroText",
        "subHeading": "telescopeImage"

    }],
4
  • What's this line: :src="data(myJson.image)"? data isn't a function, it should be data.image Commented Sep 29, 2020 at 11:13
  • Also, if you're just looping through "hero" you'd have to do v-for="data in myJson.hero" Commented Sep 29, 2020 at 11:16
  • Otherwise, you're just looping over that single object Commented Sep 29, 2020 at 11:16
  • I've tried that and then the Hero image iterates itself 6 times and the images don't show Commented Sep 29, 2020 at 11:17

1 Answer 1

1

Fixed it!

@Daniel_Knights pointed me in the right direction, you sir thank you for your enlightenment.

My issue was the JSON file was incorrect so it iterated itself twice. Secondly my image did not want to disply so I figured its to do with the path in the JSON file.

I created a method that adds @/ after the item that is a path.

My landing page

<template>
  <div class="home">
    <div v-for="data in myJson.hero" :key="data">
      <v-card tile flat>
        <v-img
          height="885"
          gradient="to top left, rgba(100,115,201,.13), rgba(25,32,72,.7)"
          :src="letterIcon(data.image)"
        >
          <template v-slot:placeholder>
            <v-row class="fill-height ma-0" align="center" justify="center">
              <v-progress-circular
                indeterminate
                color="grey lighten-5"
              ></v-progress-circular>
            </v-row>
          </template>
          <v-row>
            <v-col cols="12">
              <div class="centered">
                <h2 class="display-2 text-center white--text">
                  {{ data.firstHeading }}
                </h2>
                <h1
                  data-aos="zoom-in"
                  class="display-4 font-weight-bold text-center white--text"
                >
                  {{ data.secondHeading }}
                </h1>
                <h3 class="subtitle-4 text-center white--text">
                  {{ data.subHeading }}
                </h3>

                <v-btn large class="btnCentered" outlined fab dark>
                  <v-icon>mdi-arrow-down</v-icon>
                </v-btn>
              </div>
            </v-col>
          </v-row>
        </v-img>
      </v-card>
    </div>
  </div>
</template>

<script>
import json from "../json/controller.json";
export default {
  name: "Home",
  data() {
    return {
      myJson: json,
    };
  },
  components: {},
  methods: {
    letterIcon: function (path) {
      return require("@/" + path);
    },
  },
};
</script>

<style scoped>
.centered {
  position: absolute;
  top: 45%;
  left: 50%;
  transform: translate(-50%, -50%);
}
.btnCentered {
  position: absolute;
  top: 250%;
  left: 50%;
  transform: translate(-50%, -50%);
}
</style>

My JSON file

{
    "hero": [{
        "alt": "telescopeImage",
        "image": "assets/background/telescope.jpg",
        "firstHeading": "HeroText",
        "secondHeading": "HeroText",
        "subHeading": "telescopeImage"
    }]


}
Sign up to request clarification or add additional context in comments.

1 Comment

Just Note using a JSON file will cause you to lose the responsiveness from vuejs. Rather use a .js file that you import into your store and create a mapstate that you can call upon in your files.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.