<div id="c100x50">
  <div id="area">
    <div class="bg"></div>
    <div class="house" v-bind:style="houseStyle"></div>
    <div class="trees" v-bind:style="treesStyle"></div>
    <div class="bushes" v-bind:style="bushesStyle"></div>
    <div class="stone_flower" v-bind:style="stone_flowerStyle"></div>
    <div class="fence" v-bind:style="fenceStyle"></div>
    <div class="event-mask"
         v-on:mousemove="parallaxMove"
         v-on:mouseout="originalPos"></div>
  </div>
</div>
:root {
  --bg: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAGQAAAAyCAIAAAAlV+npAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAJcEhZcwAADsMAAA7DAcdvqGQAAAF3SURBVGhD7ZKLjcMgEERTy9WTKq+DdHVd+MCMHRiMw/hzsk/z9KRkgcDuKI/H94/tlWu7ItcnOUPrwRXoJNlz5li5PtyJYRjwLZCtB8JWDfYSSxe+yXdPleujnMDoGdhoZFSD0xnYGMGSCnXbKdd7LME01yM2R513yvVmR9DOtYmNUvOdcr3ZmyQVuERYAbRzbVKrBTRLS673eJ8/V06KK0Lj1HK9zQm8f0Ni9zRULdfbHMGzq6STH8HpPyS+SkPVcr3ZcsL4doOv1/OjOFqCq88hPkAT1XKt2obm3ykuPQLEU4K9BM04y/W6FTTS9UXf7f9p3KOpZ7lOtqG3byqGmUBOI7GmNGanjwK6+t+LsReZk8pTot/bIKJJhLBo2y6KvGjVruiwBB2WoMMSdFiCDkvQYQk6LEGHJeiwBB2WoMMSdFiCDkvQYQk6LEGHJeiwBB2WoMMSdFiCDkvQYQk6LEGHJeiwBB2WoMMSdFiCDkvQYXX7ev4CVe+2SThiYJwAAAAASUVORK5CYII=");
  --house: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAG4AAAA8BAMAAAB1M5I0AAAAAXNSR0ICQMB9xQAAABVQTFRFAAAAAAAAGBgYjDgA7Rwk7+Sw////KXRzLgAAAAF0Uk5TAEDm2GYAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAZdEVYdFNvZnR3YXJlAE1pY3Jvc29mdCBPZmZpY2V/7TVxAAAA7ElEQVRIx+2VwQ2EIBBFpQO/QgHSAdkKSGiAwxSw/TexM+iqmGwAD8ZkfSGeeP5hhoSu+3fAnPF0CP7KPEXU39nDnsqIfu5j0MvydYkKxzyUFcZE/nBKWFdxgop3GaK5us0LfYUXIV5eZ4Vn4jvl6a0vQaPoefFw9HzRM8QeB6KpUOWJ+Hzs7foiiSWPHSEevNLkVZodEHVjndJKmWE0lFHwEEPCUJu3lIl275VwlP5A39ta9hxGB4gn9mCtidZOFZ4d3TCd8E7mbee7Jk/OZ6cLvazO+vnlfWm9Z2j11o1tHn5x6m15eHh4uD8fBd+C7YPYImEAAAAASUVORK5CYII=");
  --trees: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAHgAAABGBAMAAAD1Ok08AAAAAXNSR0ICQMB9xQAAACFQTFRFAAAAAAAAHZhCHcAdHsoeIrFMbCwAhDUAlz0AokEAt0kAEVBikwAAAAF0Uk5TAEDm2GYAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAZdEVYdFNvZnR3YXJlAE1pY3Jvc29mdCBPZmZpY2V/7TVxAAAB40lEQVRYw+3WMXKrMBAGYO0N9GMDcTpzA49PwIwuQKED0NBTUb/utSldps0psxKQGGklO5Muw87gRnzSaiVLKLXHHs8GoB+9QsIr8HG9PsRHg6i/w3UOuH5yAx+NCQegxV4v3M8lo2GMaYPMv7HL3WnSwnThrGmtltOec++0EupCZo7WBqltcMldF1pM2QVsl8YXxlScI3tccJnDsIybs1DnL6yTuLQWjHW4wOuUuT2Lu6JpktgGmAJsY7yWi+sV4m29eOgI03e97HatNtjK2NzhLoUhYzyFywUjUbAcvsy4CNfqOWx9ROVeMX6B2yrCd5tkxtEuofnfCAwe6yxuwpH9UrWKel+TTRv8Ih3SI3vcQqH37dtd4nR9WJdZmLPDAPmsw0m73V1zDyi/8DncJW3VQ8TqwCfUyM9s3aTP0dAYhl7EfOJh0nSHw7y552rorYRd8wQaF4wmylspjQyuxzuMIj6/qVqwcLRjrFfcQUtnP/r5YhKuJZom3+TwP/m6GbQ6vclN9eQui3ege/kx5qFH/vkAIYHRZ3DtMc8ogateJbFaMb0ggfUT+L98zVfDLzAvxeM5p7CL05tOVHvS6tXh9KcNnW4J7NJ6/XhXmaDbLZ3VI5z/4EL2e2iPPfbY4y/FJ6cf1gztkNvPAAAAAElFTkSuQmCC");
  --bushes: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAIIAAABQBAMAAAAn27DqAAAAAXNSR0ICQMB9xQAAACFQTFRFAAAAAAAAMqsUIawRKdoWPMcYQpgOUbsRTrQQR6YPWM0SEM7QgQAAAAF0Uk5TAEDm2GYAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAZdEVYdFNvZnR3YXJlAE1pY3Jvc29mdCBPZmZpY2V/7TVxAAABMklEQVRYw+2TPXKDMBBGpRvwZQKx6awbMFyBC1BwADf0qqjdqXWpkpZTZrVC4cc4idNlZl8DI/geu9KilCAIgiAIgiD8BY1M48VIlqIhCBigwVP70TIC9ORjsPTOmzGX96Z5zBIKDthHOUlkABtgFsP6g5imadQn526rVX323kPpILDsIQOVYMxsyFeGkgwTXGCpIgj8XYENmg3Al4HUbNCxAzac2HDbGjy4Ccsegg0gQwV0iK3ovr8GwbgzaB/ZGsI+mAsaVddV19K+FVRAMrhvDIONl8EaLgJkQNeRo4+UB4bzxjAkQzrbusrJ0CUDfjTEJJbjrhEM7SzgNh66QDTEYKZ30xZmG3mLYjaU04iwk5t5wH2u+HBS48zFiS2QId1vJ/W3v86Lf5ogCIIg/Cs+AV2NnuZ7ru13AAAAAElFTkSuQmCC");
  --stone_flower: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAIwAAABaCAMAAABdeU4+AAAAAXNSR0ICQMB9xQAAAFdQTFRFAAAAAAAAT6YaV7gdnZ2dlJSUg4ODl5eXlpaWr6+vpaWls7Ozu7u7ubm5sbGxvLy8tLS0oqKixMTEw8PDzMzM2OkM7n4C7pYC8dA04vMU5/Uw5vAg6PEy0l5MKwAAAAF0Uk5TAEDm2GYAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAZdEVYdFNvZnR3YXJlAE1pY3Jvc29mdCBPZmZpY2V/7TVxAAACZElEQVRo3u2YjVKCQBRG+dDUrMwyQdH3f87u37JIOLEszTjNPU1aqMu5312WHYvCcRzHcRzHcRzHcRzHcZwpgHgcmab5TzIzRisyOb0CmjlsRIFlgOMRGdXM0WicTiepi2Wm2EgxM8qQDSq2mRK1FNJItNkXpSRToapEZ8JoHZHseIATTKbC5XJJtuEe1/QjLnkyuOHCNnY8dYA6W4bL4Vz6yQAlRg5wPnMwtcrkzBltc5QJc4ZcxsqcSaZDpksTZm4cjF1SZCyZXJleMqFJ5XiZNppa1qm8OSNU7QRGcBkpU5hIrYvmMfNqul5FxiYwrEllwuVkywznkilzZRmYjC7tZUqX2kVPmoRMGeh9QLhGl7EyiDLZ923JQmuykMqkGbMIF+Fcm0XZOwSZMiUYklmE5aCYBytNntNcWGYR1sliRkQo0YU+JDYz7B76A7crDFJKYB01+guZxFGjTjGvDd8fJ2yvhCSZ3/ua1fkxn+ysAp8EetMevf8y23y3Plvbnwn6a6s2dOgF6CguRcDeOxTM3Yrj3gfFz+0MbNwngl9fraAuz9gyFs0L2WC9XvMYS0I+tNnQwVeidWpP9TZsAxwOWtCO3vpOaMWBvTw+iQy7rMylI8PJECyz5lxYhtmwjcgAXwQ9feigb8RgAw4HtiGX3U5c3u0s4N89E2VWTE9GShYZjWapMhsl2HyJzYeiMhgMRmx2LAMJhj220WXP+Wowt6gz4pSWx6XZaDDdVziZKDMQDSyXmx2rnUq6xDLF4P2zO7lwM9HjIIPXwd2F/u4qgPaKeJwvWRzHcRzHcRzHeXi+Ae+8ILA0/qUdAAAAAElFTkSuQmCC");
  --fence: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAJYAAABkBAMAAACWddTDAAAAAXNSR0ICQMB9xQAAABtQTFRFAAAAAAAA5eXl//7y7u7u9vb28/Pz+fn58PDwX9SR3AAAAAF0Uk5TAEDm2GYAAAAJcEhZcwAADsQAAA7EAZUrDhsAAAAZdEVYdFNvZnR3YXJlAE1pY3Jvc29mdCBPZmZpY2V/7TVxAAAC7UlEQVRYw+2YQZajIBCG5Qb8bev0NrmBjxP4nhfIwgNk4xVmtr3LsUeBgoLCjCa9mff4F+mo8KXqp6iQbpqqqqqqqqqqqqr/Tfq96YpfINzFSywWSyTgol+Y37II1EgPPq6HWWx+O8T3nxMCC8XAJQu3+LQdNGONgXUpsmS03S3cU8bE99PkklTN9RoM4/MhWKqbo8nGxPfT5JLcWMEwMEN6yZrnkGRrzBBTnFyS4CxuqGRhZenIoiTVxpq2i18bC4EVTehF2XXzPNP8jYVgl0/Ssi5hRGQtd2lXZK0oStKxVvdVwjLPWGuKwTBYlg522cDUb8YCY0GwOsbaUqTBnjVqz9I0IpjUL3e9y7Ip0mDPmjzLLaQybKH7ZdF5Rcy0kHCsocgCjaCFVCvrLu3y5reepUNJWJb13hpm1zkUzZKzOsmyg9VErIaxmAeOxXenYixv1x5LkwkDLeOSGAYrb/5z1mZ+a1jR9BuLtyv7DIlcZYOz0gGuPSjLYkm2BiYXhJo50c3dXZY0Sc8afPCtKWpj3Tp6SYmxh1EVcBa/GNxmT1hIo8xZicqsKPC/CCxlDinza5cl/YLJLlBmZTm+xYJg/WCOOKImqQZeGJyFjmXdlvbQuPVVAogi4zXRHGWVQspq9SSLIeQe+jdLW1ay9Ye4tU+y1Oo9PngvHKgTnmKNaxxfj0fWV8+z4DirsMPKvE/6W5t0MMv5/tph+XbMa8J9sP1wrnDXsrIcbRvuQu1nrO+IfGQYq6xHJ1uIs8CmgUM468nWzlkhz50oG5r6dA+VkhOJYp8l/UqCS3KMLCHq/YzlRj/160+Iy776uG6dyJG7g51Miyza54f9Kn7XxmbBT2DKp7PbUT9dnxD3tdyPyj3p3LkwOZvQWU7786o7sMZDKOTeVn5RTrP6F1j4QdbYiDPmGyxxxtxlAWWWOshC8tN0W0fIuMIXbYNd1h3If17RqRHiK89/Ht1sXc8NPfylfw/Elq6bqqqqs/oLBrKDEO2DGzEAAAAASUVORK5CYII=");
}

html, body {
  padding: 0;
  margin: 0;
}

#c100x50 {
  background-color: #303030;
  min-height: 100vh;
  margin: 0;
}

#area {
  width: 100px;
  height: 50px;
  border: 3px solid black;
  overflow: hidden;
  position: absolute;
  top: 50%;
  left: 50%;
  box-shadow: 0 8px 20px #000000;
  transform: translate(-50%, -50%);
}

.bg {
  background-image: var(--bg);
  width: 100px;
  height: 50px;
  position: absolute;
  top: 0;
  left: 0;
}

.house {
  background-image: var(--house);
  width: 110px;
  height: 60px;
}

.trees {
  background-image: var(--trees);
  width: 120px;
  height: 70px;
}

.bushes {
  background-image: var(--bushes);
  width: 130px;
  height: 80px;
}

.stone_flower {
  background-image: var(--stone_flower);
  width: 140px;
  height: 90px;
}

.fence {
  background-image: var(--fence);
  width: 150px;
  height: 100px;
}

.house, .trees, .bushes, .stone_flower, .fence {
  position: absolute;
  top: 50%;
  left: 50%;
  transition: top 400ms ease-out, left 400ms ease-out;
}

.event-mask {
  width: 100%;
  height: 100%;
  position: absolute;
  top: 0;
  left: 0;
}
const els = {
  house:        { w: 110, h: 60,  o: -5  }, 
  trees:        { w: 120, h: 70,  o: -10 }, 
  bushes:       { w: 130, h: 80,  o: -15 }, 
  stone_flower: { w: 140, h: 90,  o: -20 }, 
  fence:        { w: 150, h: 100, o: -25 }
};

new Vue({
  el: '#c100x50',
  data: {
    houseStyle:        { top: '-5px',  left: '-5px'  },
    treesStyle:        { top: '-10px', left: '-10px' },
    bushesStyle:       { top: '-15px', left: '-15px' },
    stone_flowerStyle: { top: '-20px', left: '-20px' },
    fenceStyle:        { top: '-25px', left: '-25px' }
  },
  methods: {
    calc: function(el, w2, h2, x, y) {
      const w1 = el.w;
      const h1 = el.h;
      const w  = w1 - w2;
      const h  = h1 - h2;
      
      return {
        top:  (w * y * -1) + 'px',
        left: (w * x * -1) + 'px'
      };
    },
    originalPos: function(e) {
      for (let i in els) {
        this[i + 'Style'] = {
          top:  els[i].o + 'px',
          left: els[i].o + 'px'
        };
      }
    },
    parallaxMove: function(e) {
      const el = e.target;
      const x  = e.offsetX + 1;
      const y  = e.offsetY + 1;
      const w  = el.clientWidth;
      const h  = el.clientHeight;
      const px = x / w;
      const py = y / h;

      for (let i in els) {
        this[i + 'Style'] =  this.calc(els[i], w, h, px, py);
      }
    }
  }
});
View Compiled

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

  1. https://cdnjs.cloudflare.com/ajax/libs/vue/2.6.10/vue.min.js