Peta gambar responsif


145

Saya memiliki peta gambar yang ada dalam tata letak html responsif. Skala gambar sesuai dengan ukuran browser, tetapi koordinat gambar jelas-jelas berukuran piksel tetap. Opsi apa yang harus saya ubah ukuran koordinat peta gambar?


6
Pertanyaan ini bukan tentang peta geografis tetapi tag html <map>
jdog

4
Lihatlah plugin gambar-peta . Ini bekerja dengan Javascript, Node, dan jQuery
Travis Clarke

2
Sebagai alternatif, Anda dapat menggunakan gambar SVG. Saya sarankan membaca Menggunakan SVG sebagai Alternatif Untuk Imagemaps
Mawg mengatakan mengembalikan Monica

1
Kedengarannya seperti yang kita inginkan adalah kemampuan untuk mengunggah JPEG atau mirip dengan aplikasi yang memungkinkan Anda menentukan lokasi peta pada gambar (seperti pada gambar-peta dot net) - di latar belakang, ini menghasilkan file SVG yang pada dasarnya transparan . Kami kemudian ingin peta diterapkan ke SVG dan membuat SVG di atas JPG di browser web. Saat browser mengubah ukuran JPG, SVG juga diubah ukurannya dan SVG selalu menjadi yang dipanggil saat mengklik peta gambar. Adakah saran untuk bagian ini?
youcantryreachingme

2
Ya itulah yang saya inginkan pada tahun 2011
jdog

Jawaban:


89

Untuk peta gambar yang responsif, Anda perlu menggunakan plugin:

https://github.com/stowball/jQuery-rwdImageMaps (Tidak lagi dipertahankan)

Atau

https://github.com/davidjbradshaw/imagemap-resizer


Tidak ada peramban besar yang memahami koordinat persentase dengan benar, dan semua menafsirkan koordinat persentase sebagai koordinat piksel.

http://www.howtocreate.co.uk/tutorials/html/imagemaps

Dan juga halaman ini untuk menguji apakah browser diimplementasikan

http://home.comcast.net/~urbanjost/IMG/resizeimg3.html


5
apakah semua ini masih relevan? bisakah Anda memberikan pembaruan?
Maleakhi

1
@Malachi Ya ini masih relevan
Tom

terima kasih Tom, kami sedang berdiskusi tentang pertanyaan tentang CodeReview, sekarang saya berharap saya bisa mengingat pertanyaan itu ....
Maleakhi

@ Tom ini hanya berfungsi untuk satu gambar .. jika kita menempatkan gambar lain maka tidak berfungsi untuk gambar kedua dan ketiga dll ... periksa saja ..
User2413

1
Saya telah menemukan alat generator online yang menggunakan SVG yang semua peramban utama mengerti imagemapper.noc.io
frthjf

43

Anda juga dapat menggunakan svg alih-alih peta gambar. ;)

Ada tutorial tentang cara melakukan ini.

.hover_group:hover {
  opacity: 1;
}
#projectsvg {
  position: relative;
  width: 100%;
  padding-bottom: 77%;
  vertical-align: middle;
  margin: 0;
  overflow: hidden;
}
#projectsvg svg {
  display: inline-block;
  position: absolute;
  top: 0;
  left: 0;
}
<figure id="projectsvg">
  <svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 1920 1080" preserveAspectRatio="xMinYMin meet" >
<!-- set your background image -->
<image width="1920" height="1080" xlink:href="http://placehold.it/1920x1080" />
<g class="hover_group" opacity="0">
  <a xlink:href="https://example.com/link1.html">
    <text x="652" y="706.9" font-size="20">First zone</text>
    <rect x="572" y="324.1" opacity="0.2" fill="#FFFFFF" width="264.6" height="387.8"></rect>
  </a>
</g>
<g class="hover_group" opacity="0">
  <a xlink:href="https://example.com/link2.html">
    <text x="1230.7" y="952" font-size="20">Second zone</text>
    <rect x="1081.7" y="507" opacity="0.2" fill="#FFFFFF" width="390.2" height="450"></rect>
  </a>
</g>
  </svg>
</figure>


1
Tautan tutorial rusak. Gambar dari jsfiddle juga.
Cristiano Maia

Saya memberi isyarat bahwa tautan tutorial rusak dan memperbarui jsfiddle dan cuplikan kode. Terima kasih untuk
semuanya

Ini solusi luar biasa. Saya telah menggunakannya dengan sukses dan bekerja seperti pesona. Terima kasih!
Jaume Mussons Abad

3
Sejauh ini solusi terbaik di tahun 2020. Coba pembuat kode ini untuk membuatnya super sederhana. imagemapper.noc.io/#
Brett Donald

1
Ini harus menjadi solusi responsif terbaik terbaik pada tahun 2020.
mythicalcoder

39

1
Adil dan FYI untuk eveyrone ... Saya telah menemukan bahwa ini bekerja dengan baik, tetapi tidak di dalam akordeon. Saya menggunakan Bootstrap 3 dan jika Anda tidak memuat halaman dengan akordeon terbuka pada gambar, ketika Anda membuka akordeon, peta gambar tidak ada kecuali jendela browser diubah ukurannya.
jasonflaherty

1
@jasonflaherty, bisakah Anda memicu acara pengubahan ukuran untuk memaksa peta ditampilkan? $(window).trigger('resize');
Steve Meisner

@SteveMeisner Saya belum mencobanya ... tapi bukankah itu memaksakan penyegaran?
jasonflaherty

@jasonflaherty nggak! Itu hanya "memicu" acara mengubah ukuran pada elemen yang Anda ikat ( windowdalam kasus ini). Semoga berhasil.
Steve Meisner

Baru saja membuat modul Drupal yang super dasar, tetapi praktis menggunakan plugin ini: drupal.org/project/responsive_imagemaps
Joshua Stewardson

19

Saya menemukan solusi yang tidak menggunakan peta gambar sama sekali melainkan tag anchor yang benar-benar diposisikan di atas gambar. Satu-satunya kelemahan adalah hotspot harus persegi panjang, tetapi plus adalah bahwa solusi ini tidak bergantung pada Javascript, hanya CSS. Ada situs web yang dapat Anda gunakan untuk menghasilkan kode HTML untuk jangkar: http://www.zaneray.com/responsive-image-map/

Saya meletakkan gambar dan tag anchor yang dihasilkan dalam tag div yang diposisikan relatif dan semuanya bekerja dengan baik pada ukuran jendela dan pada ponsel saya.


2
Temuan yang bagus! Terima kasih telah berkontribusi pada daftar ini
jdog

1
Saya tidak bisa cukup membenarkan naswer ini !! Sebuah sangat baik tutorial; komprehensif dan mudah undertsand. Orang harus membaca semuanya, tetapi yang menarik adalah tutorials.jenkov.com/svg/scripting.html
Mawg mengatakan mengembalikan Monica

Ini adalah solusi yang sangat sederhana namun bagus jika area yang diklik adalah persegi panjang.
user2875289

Ini luar biasa. Bekerja untuk saya juga dengan situs DNN. Seperti yang dikatakan Jeffrey, saya baru saja menjatuhkan <img> dan html yang dihasilkan di dalam div yang diposisikan relatif. Terima kasih!
Ted Krapf

18

Saya menemukan cara no-JS untuk mengatasi ini jika Anda setuju dengan area klik persegi panjang.

Pertama-tama, pastikan gambar Anda berada dalam div yang diposisikan relatif. Kemudian letakkan gambar di dalam div ini, yang berarti akan mengambil semua ruang di div. Terakhir, tambahkan div yang benar-benar diposisikan di bawah gambar, di dalam div utama, dan gunakan persentase untuk bagian atas, kiri, lebar, dan tinggi untuk mendapatkan area klik tautan ukuran dan posisi yang Anda inginkan.

Saya merasa paling mudah untuk memberikan div warna latar belakang hitam (idealnya dengan beberapa alpha fading sehingga Anda dapat melihat konten yang ditautkan di bawah) ketika Anda pertama kali bekerja, dan menggunakan inspektur kode di browser Anda untuk menyesuaikan persentase secara real time , sehingga Anda bisa melakukannya dengan benar.

Inilah garis besar dasar yang bisa Anda kerjakan. Dengan melakukan semuanya dengan persentase, Anda memastikan semua elemen tetap memiliki ukuran dan posisi relatif yang sama dengan skala gambar.

<div style="position: relative;">
  <img src="background-image.png" style="width: 100%; height: auto;">
  <a href="/link1"><div style="position: absolute; left: 15%; top: 20%; width: 12%; height: 8%; background-color: rgba(0, 0, 0, .25);"></div></a>
  <a href="/link2"><div style="position: absolute; left: 52%; top: 38%; width: 14%; height: 20%; background-color: rgba(0, 0, 0, .25);"></div></a>
</div>

Gunakan kode ini dengan inspektur kode Anda di Chrome atau browser pilihan Anda, dan sesuaikan persentasenya (Anda dapat menggunakan persentase desimal menjadi lebih tepat) sampai kotak-kotaknya tepat. Juga memilih background-colordari transparentketika Anda siap untuk menggunakannya karena Anda ingin daerah hit Anda akan terlihat.


Ini solusi hebat! Terima kasih
xims

Solusi bagus! UIkit menggunakan teknik yang sama untuk spidol mereka: getuikit.com/docs/marker
xela84

Solusi brilian, terima kasih sudah berbagi! Saya menggunakan ini di aplikasi seluler dan ini memecahkan masalah layar yang berbeda.
JohnGIS


7

Metode berikut ini berfungsi dengan baik untuk saya, jadi inilah implementasi penuh saya:

<img id="my_image" style="display: none;" src="my.png" width="924" height="330" border="0" usemap="#map" />

<map name="map" id="map">
    <area shape="poly" coords="774,49,810,21,922,130,920,222,894,212,885,156,874,146" href="#mylink" />
    <area shape="poly" coords="649,20,791,157,805,160,809,217,851,214,847,135,709,1,666,3" href="#myotherlink" />
</map>

<script>
$(function(){
    var image_is_loaded = false;
    $("#my_image").on('load',function() {
        $(this).data('width', $(this).attr('width')).data('height', $(this).attr('height'));
        $($(this).attr('usemap')+" area").each(function(){
            $(this).data('coords', $(this).attr('coords'));
        });

        $(this).css('width', '100%').css('height','auto').show();

        image_is_loaded = true;
        $(window).trigger('resize');
    });


    function ratioCoords (coords, ratio) {
        coord_arr = coords.split(",");

        for(i=0; i < coord_arr.length; i++) {
            coord_arr[i] = Math.round(ratio * coord_arr[i]);
        }

        return coord_arr.join(',');
    }
    $(window).on('resize', function(){
        if (image_is_loaded) {
            var img = $("#my_image");
            var ratio = img.width()/img.data('width');

            $(img.attr('usemap')+" area").each(function(){
                console.log('1: '+$(this).attr('coords'));
                $(this).attr('coords', ratioCoords($(this).data('coords'), ratio));
            });
        }
    });
});
</script>

4

Bekerja untuk saya (jangan lupa mengubah 3 hal dalam kode):

  • PreviousWidth (ukuran gambar asli)

  • map_ID (id dari peta gambar Anda)

  • img_ID (id dari gambar Anda)

HTML:

<div style="width:100%;">
    <img id="img_ID" src="http://www.gravatar.com/avatar/0865e7bad648eab23c7d4a843144de48?s=128&d=identicon&r=PG" usemap="#map" border="0" width="100%" alt="" />
</div>
<map id="map_ID" name="map">
<area shape="poly" coords="48,10,80,10,65,42" href="javascript:;" alt="Bandcamp" title="Bandcamp" />
<area shape="poly" coords="30,50,62,50,46,82" href="javascript:;" alt="Facebook" title="Facebook" />
<area shape="poly" coords="66,50,98,50,82,82" href="javascript:;" alt="Soundcloud" title="Soundcloud" />
</map>

Javascript:

window.onload = function () {
    var ImageMap = function (map, img) {
            var n,
                areas = map.getElementsByTagName('area'),
                len = areas.length,
                coords = [],
                previousWidth = 128;
            for (n = 0; n < len; n++) {
                coords[n] = areas[n].coords.split(',');
            }
            this.resize = function () {
                var n, m, clen,
                    x = img.offsetWidth / previousWidth;
                for (n = 0; n < len; n++) {
                    clen = coords[n].length;
                    for (m = 0; m < clen; m++) {
                        coords[n][m] *= x;
                    }
                    areas[n].coords = coords[n].join(',');
                }
                previousWidth = img.offsetWidth;
                return true;
            };
            window.onresize = this.resize;
        },
        imageMap = new ImageMap(document.getElementById('map_ID'), document.getElementById('img_ID'));
    imageMap.resize();
    return;
}

JSFiddle: http://jsfiddle.net/p7EyT/154/


3

Saya menemukan dengan persyaratan yang sama di mana, saya ingin menunjukkan peta gambar responsif yang dapat mengubah ukuran dengan ukuran layar dan yang penting adalah, saya ingin menyoroti koordinat itu .

Jadi saya mencoba banyak perpustakaan yang dapat mengubah ukuran koordinat sesuai dengan ukuran layar dan acara. Dan saya mendapat solusi terbaik (jquery.imagemapster.min.js) yang berfungsi baik dengan hampir semua browser. Juga saya telah mengintegrasikannya dengan Summer Plgin yang membuat peta gambar.

 var resizeTime = 100;
 var resizeDelay = 100;    

$('img').mapster({
        areas: [
            {
                key: 'tbl',
                fillColor: 'ff0000',
                staticState: true,
                stroke: true
            }
        ],
        mapKey: 'state'
    });

    // Resize the map to fit within the boundaries provided

    function resize(maxWidth, maxHeight) {
        var image = $('img'),
            imgWidth = image.width(),
            imgHeight = image.height(),
            newWidth = 0,
            newHeight = 0;

        if (imgWidth / maxWidth > imgHeight / maxHeight) {
            newWidth = maxWidth;
        } else {
            newHeight = maxHeight;
        }
        image.mapster('resize', newWidth, newHeight, resizeTime);
    }

    function onWindowResize() {

        var curWidth = $(window).width(),
            curHeight = $(window).height(),
            checking = false;
        if (checking) {
            return;
        }
        checking = true;
        window.setTimeout(function () {
            var newWidth = $(window).width(),
                newHeight = $(window).height();
            if (newWidth === curWidth &&
                newHeight === curHeight) {
                resize(newWidth, newHeight);
            }
            checking = false;
        }, resizeDelay);
    }

    $(window).bind('resize', onWindowResize);
img[usemap] {
        border: none;
        height: auto;
        max-width: 100%;
        width: auto;
    }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<script src="https://cdn.jsdelivr.net/npm/jquery-imagemapster@1.2.10/dist/jquery.imagemapster.min.js"></script>

<img src="https://discover.luxury/wp-content/uploads/2016/11/Cities-With-the-Most-Michelin-Star-Restaurants-1024x581.jpg" alt="" usemap="#map" />
<map name="map">
    <area shape="poly" coords="777, 219, 707, 309, 750, 395, 847, 431, 916, 378, 923, 295, 870, 220" href="#" alt="poly" title="Polygon" data-maphilight='' state="tbl"/>
    <area shape="circle" coords="548, 317, 72" href="#" alt="circle" title="Circle" data-maphilight='' state="tbl"/>
    <area shape="rect" coords="182, 283, 398, 385" href="#" alt="rect" title="Rectangle" data-maphilight='' state="tbl"/>
</map>

Semoga bisa membantu seseorang.


2

http://home.comcast.net/~urbanjost/semaphore.html adalah halaman teratas untuk diskusi, dan sebenarnya memiliki tautan ke solusi berbasis JavaScript untuk masalah tersebut. Saya telah menerima pemberitahuan bahwa HTML akan mendukung persen unit di masa mendatang, tetapi saya belum melihat kemajuan dalam hal ini dalam beberapa waktu (mungkin sudah lebih dari setahun sejak saya mendengar dukungan akan datang) sehingga penyelesaiannya adalah mungkin layak dilihat jika Anda merasa nyaman dengan JavaScript / ECMAScript.


2

Lihatlah plugin gambar-peta di Github. Ini berfungsi baik dengan JavaScript vanilla dan sebagai plugin jQuery.

$('img[usemap]').imageMap();     // jQuery

ImageMap('img[usemap]')          // JavaScript

Lihat demo .


1

Tergantung, Anda dapat menggunakan jQuery untuk menyesuaikan rentang secara proporsional menurut saya. Ngomong-ngomong, mengapa Anda menggunakan peta gambar? Tidak bisakah Anda menggunakan scaling divs atau elemen lain untuk itu?


sementara solusi yang tepat akan bekerja dengan div skala, peta gambar adalah "konten yang dikelola" dan memang memungkinkan untuk segala jenis wilayah. Terima kasih, saya akan memeriksa jquery untuk ini.
jdog


0

Mirip dengan jawaban Orland di sini: https://stackoverflow.com/a/32870380/462781

Dikombinasikan dengan kode Chris di sini: https://stackoverflow.com/a/12121309/462781

Jika area-area tersebut pas dalam kisi, Anda dapat menindih area dengan gambar transparan menggunakan lebar dalam% yang menjaga rasio aspeknya.

    .wrapperspace {
      width: 100%;
      display: inline-block;
      position: relative;
    }
    .mainspace {
      position: absolute;
      top: 0;
      bottom: 0;
      right: 0;
      left: 0;
    }
<div class="wrapperspace">
 <img style="float: left;" title="" src="background-image.png" width="100%" />
 <div class="mainspace">
     <div>
         <img src="space-top.png" style="margin-left:6%;width:15%;"/>
     </div>
     <div>
       <a href="http://www.example.com"><img src="space-company.png" style="margin-left:6%;width:15%;"></a>
     </div>
  <div>
   <a href="http://www.example.com"><img src="space-company.png" style="margin-left:6%;width:10%;"></a>
   <a href="http://www.example.com"><img src="space-company.png" style="width:20%;"></a>
  </div>
 </div>
</div>

Anda dapat menggunakan margin dalam%. Selain itu, gambar "spasi" dapat ditempatkan bersebelahan di dalam div level ke-3.


0

Untuk beberapa alasan tidak ada solusi ini bekerja untuk saya. Saya sudah sukses menggunakan transformasi.

transform: translateX(-5.8%) translateY(-5%) scale(0.884);

0

lebar && tinggi responsif

window.onload = function () {
        var ImageMap = function (map, img) {
                var n,
                    areas = map.getElementsByTagName('area'),
                    len = areas.length,
                    coords = [],
                    imgWidth = img.naturalWidth,
                    imgHeight = img.naturalHeight;
                for (n = 0; n < len; n++) {
                    coords[n] = areas[n].coords.split(',');
                }
            this.resize = function () {
                var n, m, clen,
                    x = img.offsetWidth / imgWidth,
                    y = img.offsetHeight / imgHeight;
                    imgWidth = img.offsetWidth;
                    imgHeight = img.offsetHeight;
                for (n = 0; n < len; n++) {
                    clen = coords[n].length;
                    for (m = 0; m < clen; m +=2) {
                        coords[n][m] *= x;
                        coords[n][m+1] *= y;
                    }
                    areas[n].coords = coords[n].join(',');
                }
                    return true;
                };
                window.onresize = this.resize;
            },
        imageMap = new ImageMap(document.getElementById('map_region'), document.getElementById('prepay_region'));
        imageMap.resize();
        return;
    }

Bisakah Anda menambahkan lebih banyak konten yang menunjukkan perbedaan antara kode Anda dan jawaban Niente0 dari 2015?
Michael - Di mana Clay Shirky
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.