Web sitesi favicon'unu dinamik olarak değiştirme


347

Şu anda giriş yapmış olan kullanıcıya göre markalı bir web uygulamam var. Sayfanın favicon'unu özel etiketin logosu olacak şekilde değiştirmek istiyorum, ancak herhangi bir kod veya nasıl bir örnek bulamıyorum Bunu yapmak için. Bunu daha önce başarılı bir şekilde yapan var mı?

Bir klasörde bir düzine simgeler sahip resim ve ben kullanmak için favicon.ico dosya sadece HTML sayfası ile birlikte dinamik olarak oluşturulan başvuru. Düşünceler?


41
Favicon'da bir arcade oyunu var .
Corey Trager

Chrome'un dinamik favicon uygulamasının hatalı olduğunu ve çok fazla CPU kullandığını unutmayın. Bkz code.google.com/p/chromium/issues/detail?id=121333
brillout

6
Arcade oyununun bağlantısı değişti. Bu doğru olanı.
Basil

Tuvalle şablon görüntüsünün üstüne çizim yaparak favicon'un dinamik olarak nasıl güncelleneceği hakkında stackoverflow.com/questions/6296574/… adresine bakın .
işlemek

1
Kabul edilen cevapta verilen kod örneğindeki küçük hata. Cevaplar hakkında yorum yapmak için yeterli itibar puanım yok, bunun yerine buraya yazıyorum. Son satırda parantezler değiştirildi:} ()); okumalı })(); Büyük olasılıkla başkaları tarafından kopyalanıp yapıştırıldığı için kod örneğinin güncellenmesi iyi olur.
Goran K

Yanıtlar:


396

Neden olmasın?

(function() {
    var link = document.querySelector("link[rel*='icon']") || document.createElement('link');
    link.type = 'image/x-icon';
    link.rel = 'shortcut icon';
    link.href = 'http://www.stackoverflow.com/favicon.ico';
    document.getElementsByTagName('head')[0].appendChild(link);
})();

Firefox onunla iyi olmalı.

mevcut simgelerin üzerine yazmak için düzenlendi


2
Bunun aradığım şeye yakın olduğunu düşünüyorum, ancak veritabanından uygun HREF'i nasıl alabilirim. Ben javascript bir sunucu arama yapmak zorunda kalacağım, ama çok karmaşık olmasını istemiyorum. Bahşiş için teşekkürler.
SqlRyan

34
Bu zaten IE'de çalışmadığından shortcut, relöznitelikten kaldırabilirsiniz . shortcutgeçersiz bir IE'ye özel bağlantı ilişkisidir!
Mathias Bynens

8
Mevcut bir favicon bağlantısını kolayca arayabilir ve güncelleyebilir veya değiştirebilirsiniz.
Mart'ta

5
Google, bu URL'yi kullanarak size bir sitenin favicon'unu verebilir
kirb

5
Bunu Chrome'daki Javascript konsoluna girmeniz gerekir mi? Bu şekilde çeşitli sitelerde favicons değiştirmek için alamıyorum.
powerj1984

88

Firefox, Opera ve Chrome'da çalışan bazı kodlar (burada yayınlanan diğer yanıtların aksine). IE11'de de çalışan farklı bir kod demosu . Aşağıdaki örnek Safari veya Internet Explorer'da çalışmayabilir.

/*!
 * Dynamically changing favicons with JavaScript
 * Works in all A-grade browsers except Safari and Internet Explorer
 * Demo: http://mathiasbynens.be/demo/dynamic-favicons
 */

// HTML5™, baby! http://mathiasbynens.be/notes/document-head
document.head = document.head || document.getElementsByTagName('head')[0];

function changeFavicon(src) {
 var link = document.createElement('link'),
     oldLink = document.getElementById('dynamic-favicon');
 link.id = 'dynamic-favicon';
 link.rel = 'shortcut icon';
 link.href = src;
 if (oldLink) {
  document.head.removeChild(oldLink);
 }
 document.head.appendChild(link);
}

Daha sonra aşağıdaki gibi kullanabilirsiniz:

var btn = document.getElementsByTagName('button')[0];
btn.onclick = function() {
 changeFavicon('http://www.google.com/favicon.ico');
};

Uzaklaşın veya bir demo görüntüleyin .


Krom böcek ileriye düğmeye kırar çünkü aslında, şiddetle kullanılmasını önermiyoruz ediyorum - Krom kesmek artık gerçekten gerekli değildir bu yüzden, Chrome 6 (serbest 10 Eylül) giderilmiştir.
josh3736

Chrome hatası düzeltilmiş olabilir, ancak 14.0.835.187'de tekrar bozuldu.
danorton

Demo Krom 21 / WinXP ile benim için çalışmıyor.
Hugo

Demo, Chrome 26 / Win7'de benim için çalışmıyor. document.head || document.head = document.getElementsByTagName('head')[0]; Uncaught ReferenceError: Invalid left-hand side in assignment
Patrick

2
Bu, şu anda desteklenen tüm tarayıcılarda (IE 11, Edge, FF ve Chrome) safari ile test edememektedir
Aaron

46

Aşağıdaki HTML snippet'iniz varsa:

<link id="favicon" rel="shortcut icon" type="image/png" href="favicon.png" />

Favicon'u bu bağlantıdaki HREF öğesini değiştirerek Javascript kullanarak değiştirebilirsiniz, örneğin (JQuery kullandığınızı varsayarak):

$("#favicon").attr("href","favicon2.png");

Ayrıca bir Canvas öğesi oluşturabilir ve HREF'i, Favicon Defender'ın yaptığı gibi tuvalin bir ToDataURL () olarak ayarlayabilirsiniz .


1
JS çalıştığında, tarayıcı zaten bağlantıyı görecek ve yüklemeye çalışacaktı favicon.png. Bunun sunucu tarafında yapılması gerekebilir.
cHao

JQuery kullanmıyorsanız , yazı kullanma hrefözelliğini değiştirebilirsiniz Belki yazı @fserb? #favicondocument.getElementById('favicon').setAttribute('href','favicon2.png')
johannchopin

37

jQuery Sürümü:

$("link[rel='shortcut icon']").attr("href", "favicon.ico");

veya daha iyisi:

$("link[rel*='icon']").attr("href", "favicon.ico");

Vanilya JS sürümü:

document.querySelector("link[rel='shortcut icon']").href = "favicon.ico";

document.querySelector("link[rel*='icon']").href = "favicon.ico";

@pkExec Bunun ve yukarıdaki keparo cevabının bir kombinasyonu (seçilen cevap) benim için hem ff'de hem de kromda çalışmasını sağladı.
MrShmee

17

Daha modern bir yaklaşım:

const changeFavicon = link => {
  let $favicon = document.querySelector('link[rel="icon"]')
  // If a <link rel="icon"> element already exists,
  // change its href to the given link.
  if ($favicon !== null) {
    $favicon.href = link
  // Otherwise, create a new element and append it to <head>.
  } else {
    $favicon = document.createElement("link")
    $favicon.rel = "icon"
    $favicon.href = link
    document.head.appendChild($favicon)
  }
}

Daha sonra şu şekilde kullanabilirsiniz:

changeFavicon("http://www.stackoverflow.com/favicon.ico")

11

Favicon kafa etiketinde şöyle bir şeyle bildirilir:

<link rel="shortcut icon" type="image/ico" href="favicon.ico">

Görünüm verilerinde istediğiniz simgenin adını aktarabilmeniz ve baş etiketine atabilmeniz gerekir.


1
IIRC, ancak, bazı tarayıcılar (senin yönüne bakıyorum, IE) bazen buna gerçekten saygı duymuyor.
Matthew Schinckel

(Ben simge dosyası açık bağlantı yerine, doğru yerde olması daha iyi sonuçlar buldum).
Matthew Schinckel

9

Opera, Firefox ve Chrome'a ​​dinamik favicon desteği eklemek için kullandığım bazı kodlar. IE veya Safari olsa çalışma alamadım. Temel olarak Chrome dinamik favorilere izin verir, ancak bunları yalnızca sayfanın konumu (veya içindeki bir iframevb.) Söyleyebildiğim kadar değiştiğinde günceller:

var IE = navigator.userAgent.indexOf("MSIE")!=-1
var favicon = {
    change: function(iconURL) {
        if (arguments.length == 2) {
            document.title = optionalDocTitle}
        this.addLink(iconURL, "icon")
        this.addLink(iconURL, "shortcut icon")

        // Google Chrome HACK - whenever an IFrame changes location 
        // (even to about:blank), it updates the favicon for some reason
        // It doesn't work on Safari at all though :-(
        if (!IE) { // Disable the IE "click" sound
            if (!window.__IFrame) {
                __IFrame = document.createElement('iframe')
                var s = __IFrame.style
                s.height = s.width = s.left = s.top = s.border = 0
                s.position = 'absolute'
                s.visibility = 'hidden'
                document.body.appendChild(__IFrame)}
            __IFrame.src = 'about:blank'}},

    addLink: function(iconURL, relValue) {
        var link = document.createElement("link")
        link.type = "image/x-icon"
        link.rel = relValue
        link.href = iconURL
        this.removeLinkIfExists(relValue)
        this.docHead.appendChild(link)},

    removeLinkIfExists: function(relValue) {
        var links = this.docHead.getElementsByTagName("link");
        for (var i=0; i<links.length; i++) {
            var link = links[i]
            if (link.type == "image/x-icon" && link.rel == relValue) {
                this.docHead.removeChild(link)
                return}}}, // Assuming only one match at most.

    docHead: document.getElementsByTagName("head")[0]}

Favicons'ları değiştirmek favicon.change("ICON URL")için yukarıdakileri kullanın.

( buna dayandığım kod için http://softwareas.com/dynamic-favicons'a verilen krediler .)


Krom böcek ileriye düğmeye kırar çünkü aslında, şiddetle kullanılmasını önermiyoruz ediyorum - Krom kesmek artık gerçekten gerekli değildir bu yüzden, Chrome 6 (serbest 10 Eylül) giderilmiştir.
josh3736

Chrome, belirtilen hatadan biraz farklı koşullarda da olsa aynı hataya sahip. code.google.com/p/chromium/issues/detail?id=99549
danorton

4

Greg'in yaklaşımını kullanır ve favicon.ico için özel bir işleyici yapardım İşte çalışan (basitleştirilmiş) bir işleyici:

using System;
using System.IO;
using System.Web;

namespace FaviconOverrider
{
    public class IcoHandler : IHttpHandler
    {
    public void ProcessRequest(HttpContext context)
    {
        context.Response.ContentType = "image/x-icon";
        byte[] imageData = imageToByteArray(context.Server.MapPath("/ear.ico"));
        context.Response.BinaryWrite(imageData);
    }

    public bool IsReusable
    {
        get { return true; }
    }

    public byte[] imageToByteArray(string imagePath)
    {
        byte[] imageByteArray;
        using (FileStream fs = new FileStream(imagePath, FileMode.Open, FileAccess.Read))
        {
        imageByteArray = new byte[fs.Length];
        fs.Read(imageByteArray, 0, imageByteArray.Length);
        }

        return imageByteArray;
    }
    }
}

Ardından, bu işleyiciyi IIS6'daki web yapılandırmasının httpHandlers bölümünde kullanabilir veya IIS7'deki 'İşleyici Eşlemeleri' özelliğini kullanabilirsiniz.


1
Aslında bunun neden reddedildiğini merak ediyorum? Bu aslında diğerlerinin de mevcut olan veya olmayan komut dosyalarına bağlı olduğu göz önüne alındığında en iyi cevaptır.
etermal

1
@ethermal Çünkü sunucu tarafında dinamik gibi görünüyor. OP müşterinin yanında dinamizm istiyordu.
Alexis Wilke

3

IE için bu işi yapmanın tek yolu, web sunucunuzu sunucu tarafı komut dosyası dilinizi (PHP, .NET vb.) Çağırmak için * .ico isteklerini tedavi edecek şekilde ayarlamaktır. Ayrıca tek bir komut dosyasına yönlendirmek ve bu komut dosyasının doğru favicon dosyasını teslim etmesini sağlamak için * .ico ayarlarını yapın. Farklı tarayıcılar arasında aynı tarayıcıda ileri geri sıçramak istiyorsanız, önbellekle ilgili bazı ilginç sorunlar olacağından eminim.


3

JQuery kullananlar için tek satırlık bir çözüm var:

$("link[rel*='icon']").prop("href",'https://www.stackoverflow.com/favicon.ico');

3

Veya bir ifade istiyorsanız :)

var canvas = document.createElement("canvas");
canvas.height = 64;
canvas.width = 64;

var ctx = canvas.getContext("2d");
ctx.font = "64px serif";
ctx.fillText("☠️", 0, 64); 

$("link[rel*='icon']").prop("href", canvas.toDataURL());

Dikmeler https://koddsson.com/posts/emoji-favicon/


2

WikiPedia'ya göre link, headbölümdeki etiketi kullanarak hangi favicon dosyasının yükleneceğini ,rel="icon" .

Örneğin:

 <link rel="icon" type="image/png" href="/path/image.png">

Bu çağrı için bazı dinamik içerik yazmak isterseniz, oturum bilgilerinizi bu şekilde alabilmeniz ve uygun içerikleri sunabilmeniz için çerezlere erişebildiğinizi hayal ediyorum.

Hem tarayıcıda hem de proxy'lerde dosya biçimlerinin (IE'nin yalnızca .ICO biçimini desteklediği, diğerlerinin çoğu PNG ve GIF görüntülerini desteklediği halde) ve büyük olasılıkla önbellekleme sorunlarına düştüğünüz olabilir. Bunun nedeni, özellikle bir yer işaretini bir sitenin mini logosuyla işaretlemek için favicon'un orijinal itirazı olabilir.


bundan çok daha fazlası. stackoverflow.com/a/45301651/661584 jeneratör sitesindeki SSS / bilgi sizi şaşırtacak - bu konuda çok şey var.
MemeDeveloper

3
Web 9 yılda çok değişiyor.
staticsan

2

Evet tamamen mümkün

  • Favicon.ico'dan (ve diğer dosya bağlantılarından) sonra bir sorgu dizesi kullanın - aşağıdaki yanıt bağlantısına bakın)
  • Sunucunun "someUserId" öğesine doğru görüntü dosyasıyla ( statik yönlendirme kuralları veya dinamik sunucu tarafı kodu olabilir) yanıt verdiğinden emin olun .

Örneğin

<link rel="shortcut icon" href="/favicon.ico?userId=someUserId">

Daha sonra, kullandığınız sunucu tarafı dili / çerçevesi ne olursa olsun , dosyayı userId'ye göre kolayca bulabilmeli ve bu isteğe yanıt olarak sunabilmelidir .

Ancak uygun şekilde favicons yapmak için (aslında gerçekten karmaşık bir konu ) lütfen buradaki cevaba bakın https://stackoverflow.com/a/45301651/661584

Tüm detayları kendiniz çalışmaktan çok daha kolay .

Zevk almak.


Evet, bağlantı iyi. Bu cevapların IE'de çalışmamasının ana nedeninin, bu varsayılan simgeyi kullanmadığı <link>, ancak bunun yerine apple-touch-iconveya başka bir varyantı aradığıdır.
Alexis Wilke

1

Projelerimde favico.js kullanıyorum .

Favicon'u önceden tanımlanmış şekillere ve ayrıca özel şekillere değiştirmeye izin verir.

Dahili olarak simge kodlama canvasiçin oluşturma ve base64veri URL'si için kullanır .

Kütüphane ayrıca güzel özelliklere sahiptir: simge rozetleri ve animasyonlar; iddiaya göre, hatta web kamerası video simgesi haline akışı :)


Bağlantı ve kütüphane çok faydalıdır, lütfen bunun nasıl çalıştığına dair bir açıklama sağlayın, böylece bunun da belirtildiği gibi soruya geçerli bir cevap haline gelecektir.
Dima Tisnek

1
Teşekkürler @ DimaTisnek. Cevabımı yükselttim.
Oscar Nevarez

0

Siteleri geliştirirken bu özelliği her zaman kullanıyorum ... böylece hangi sekmenin içinde yerel, geliştirici veya ürün çalıştığını bir bakışta görebiliyorum.

Chrome, SVG favicons'u desteklediğine göre artık çok daha kolay.

Tampermonkey Komut Dosyası

Bir kaz https://gist.github.com/elliz/bb7661d8ed1535c93d03afcd0609360f Bir demo sitesine noktaları Ben kadar indiren bir tampermonkey komut dosyası için https://elliz.github.io/svg-favicon/

Temel kod

Bunu başka bir cevaptan uyarladık ... geliştirilebilir ama ihtiyaçlarım için yeterince iyi olabilir.

(function() {
    'use strict';

    // play with https://codepen.io/elliz/full/ygvgay for getting it right
    // viewBox is required but does not need to be 16x16
    const svg = `
    <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">
      <circle cx="8" cy="8" r="7.2" fill="gold" stroke="#000" stroke-width="1" />
      <circle cx="8" cy="8" r="3.1" fill="#fff" stroke="#000" stroke-width="1" />
    </svg>
    `;

    var favicon_link_html = document.createElement('link');
    favicon_link_html.rel = 'icon';
    favicon_link_html.href = svgToDataUri(svg);
    favicon_link_html.type = 'image/svg+xml';

    try {
        let favicons = document.querySelectorAll('link[rel~="icon"]');
        favicons.forEach(function(favicon) {
            favicon.parentNode.removeChild(favicon);
        });

        const head = document.getElementsByTagName('head')[0];
        head.insertBefore( favicon_link_html, head.firstChild );
    }
    catch(e) { }

    // functions -------------------------------
    function escapeRegExp(str) {
        return str.replace(/([.*+?^=!:${}()|\[\]\/\\])/g, "\\$1");
    }

    function replaceAll(str, find, replace) {
        return str.replace(new RegExp(escapeRegExp(find), 'g'), replace);
    }

    function svgToDataUri(svg) {
        // these may not all be needed - used to be for uri-encoded svg in old browsers
        var encoded = svg.replace(/\s+/g, " ")
        encoded = replaceAll(encoded, "%", "%25");
        encoded = replaceAll(encoded, "> <", "><"); // normalise spaces elements
        encoded = replaceAll(encoded, "; }", ";}"); // normalise spaces css
        encoded = replaceAll(encoded, "<", "%3c");
        encoded = replaceAll(encoded, ">", "%3e");
        encoded = replaceAll(encoded, "\"", "'"); // normalise quotes ... possible issues with quotes in <text>
        encoded = replaceAll(encoded, "#", "%23"); // needed for ie and firefox
        encoded = replaceAll(encoded, "{", "%7b");
        encoded = replaceAll(encoded, "}", "%7d");
        encoded = replaceAll(encoded, "|", "%7c");
        encoded = replaceAll(encoded, "^", "%5e");
        encoded = replaceAll(encoded, "`", "%60");
        encoded = replaceAll(encoded, "@", "%40");
        var dataUri = 'data:image/svg+xml;charset=UTF-8,' + encoded.trim();
        return dataUri;
    }

})();

Sadece kendi SVG'nizi (belki bir araç kullanıyorsanız Jake Archibald'ın SVGOMG'si ile temizlenir) üstteki sabitin içine yerleştirin. Kare olduğundan (viewBox özniteliğini kullanarak) ve gitmeye hazır olduğunuzdan emin olun.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.