2012-04-24 13 views
19

Sto cercando un modo semplice per aggiungere una riga di codice a un mio plug-in, per convertire un paio di valori di pixel in valori em, perché il layout del mio il progetto deve essere in ems. C'è un modo semplice per farlo, perché non voglio aggiungere un plug-in di terze parti al sito.jQuery/JavaScript: convertire i pixel in em in modo semplice

Non invierà il codice qui, in quanto non ha nulla a che fare con il plug-in stesso.

Grazie.

Esempio: 13px -> ?? em

+3

questo potrebbe aiutare http://pxtoem.com/ controllare la scheda "learn" – chepe263

risposta

3

pixel e lo SME sono fondamentalmente diversi tipi di unità. Non puoi semplicemente convertire tra di loro.

Ad esempio, un utente con una dimensione di carattere predefinita di 16px in un sito in cui le intestazioni di livello superiore sono in stile con una dimensione del carattere del 200%, 1em può essere uguale a 32px. Sposta il titolo altrove nel documento, potrebbe essere 64px o 16px. Dare lo stesso documento a un utente diverso, potrebbe essere 30/60/15px. Inizia a parlare di un elemento diverso e può cambiare di nuovo.

Il più vicino possibile a ciò che si desidera è convertire da pixel a ems + documento + contesto + impostazioni. Ma se qualcuno ti ha chiesto di organizzare il tuo progetto con gli em, probabilmente non sarà contento che tu stia cercando di farlo in pixel e poi di "convertirlo".

+5

ci sono casi validi quando si ha accesso solo al valore del pixel. Per esempio quando trascini un div intorno alla pagina, potresti voler ottenere il valore em prima di mantenere la posizione del div. Penso che la domanda sia perfettamente valida ed è possibile convertire i pixel in em se lo si fa all'interno del browser. Dopo che tutto il browser stesso ha convertito i valori em in pixel prima del rendering. – Aras

0

Ems non uguagliano pixel in alcun modo. Sono una misura relativa.

<span style="font-size: 1em;">This is 1em font size, which means the text is the same size as the parent</span> 

<span style="font-size: 1.5em;">This is 1.5em font size, which means the text is 150% the size as the parent</span> 

La dimensione di base è determinata dall'agente utente (browser).

+0

Le dimensioni di base sono determinate dalla dimensione del carattere stesso o dalla dimensione del carattere dei genitori. Se qualcuno ha definito la dimensione del carattere, quindi user-agent. – joseantgv

+0

@joseantgv Sì, d'accordo. Sto cercando di dire che la dimensione alla base di tutto è a livello di user-agent. – Brad

15

Quanto segue sembra di fare come volete, anche se si basa sulla font-size del genitore, e dell'elemento stesso, di essere restituiti nel px:

function px2em(elem) { 
    var W = window, 
     D = document; 
    if (!elem || elem.parentNode.tagName.toLowerCase() == 'body') { 
     return false; 
    } 
    else { 
     var parentFontSize = parseInt(W.getComputedStyle(elem.parentNode, null).fontSize, 10), 
      elemFontSize = parseInt(W.getComputedStyle(elem, null).fontSize, 10); 

     var pxInEms = Math.floor((elemFontSize/parentFontSize) * 100)/100; 
     elem.style.fontSize = pxInEms + 'em'; 
    } 
} 

JS Fiddle proof of concept.

Note:

  • La funzione restituisce false, se l'elemento si sta cercando di convertire in em è il body, anche se questo è perché non riuscivo a capire se era ragionevole per impostare il valore a 1em o semplicemente lasciarlo da solo.

  • Utilizza window.getComputedStyle(), quindi non funzionerà con IE, senza alcune regolazioni.

Riferimenti:

+3

+1, per riferimenti MDN. – saji89

17

Penso che la tua domanda sia molto importante. Poiché le classi di risoluzione dello schermo sono in rapido aumento, l'utilizzo del posizionamento di em per supportare un'ampia gamma di risoluzioni dello schermo è un approccio davvero allettante. Ma non importa quanto duramente si tenti di tenere tutto in em - a volte si ottiene un valore in pixel forse da trascinamento della selezione JQuery o da un'altra libreria, e si vorrebbe convertire questo valore in em prima di inviarlo di nuovo al server per la persistenza. In questo modo la prossima volta che l'utente guarda la pagina, l'elemento si troverà nella posizione corretta, indipendentemente dalla risoluzione dello schermo del dispositivo che sta utilizzando.

I plug-in JQuery non sono molto spaventosi quando è possibile rivedere il codice, specialmente se sono corti e dolci come this plugin to convert pixel values to em come si desidera. In effetti è così breve che incollo l'intera cosa qui. Per informazioni sul copyright, consultare il link.

$.fn.toEm = function(settings){ 
    settings = jQuery.extend({ 
     scope: 'body' 
    }, settings); 
    var that = parseInt(this[0],10), 
     scopeTest = jQuery('<div style="display: none; font-size: 1em; margin: 0; padding:0; height: auto; line-height: 1; border:0;">&nbsp;</div>').appendTo(settings.scope), 
     scopeVal = scopeTest.height(); 
    scopeTest.remove(); 
    return (that/scopeVal).toFixed(8) + 'em'; 
}; 


$.fn.toPx = function(settings){ 
    settings = jQuery.extend({ 
     scope: 'body' 
    }, settings); 
    var that = parseFloat(this[0]), 
     scopeTest = jQuery('<div style="display: none; font-size: 1em; margin: 0; padding:0; height: auto; line-height: 1; border:0;">&nbsp;</div>').appendTo(settings.scope), 
     scopeVal = scopeTest.height(); 
    scopeTest.remove(); 
    return Math.round(that * scopeVal) + 'px'; 
}; 

Utilizzo Esempio: $(myPixelValue).toEm(); o $(myEmValue).toPx();.

Ho appena provato questo nella mia applicazione, funziona benissimo. Quindi pensavo di condividere.

+0

Non ho mai visto jQuery usato così. Suppongo che questo supporti i valori stringa ('" 3px "' o '" 3em "'), ma questo non richiede a jQuery di interrogare il documento per quei selettori, prima di arrivare al '.toPx() del plugin' o '.toEm()'? –

1

Vecchia domanda, ma per riferimento, ecco qualcosa che ho messo insieme, l'ambito e il suffisso sono facoltativi. Passalo come valore rem o em come stringa, ad es. '4em' [puoi usare spazi e maiuscole/minuscole] e restituirà il valore di px. A meno che non gli si fornisca un ambito, che sarebbe l'elemento obiettivo per trovare il valore EM locale, per impostazione predefinita verrà impostato il corpo, fornendo effettivamente il valore rem. Infine, il parametro suffisso opzionale [booleano] aggiungerà 'px' al valore restituito in modo tale che 48 diventi 48px per esempio.

es: emRemToPx('3em', '#content')

ritorno 48 su un font-size 16px/100% documento

/** 
* emRemToPx.js | @whatsnewsisyphus 
* To the extent possible under law, the author(s) have dedicated all copyright and related and neighboring rights to this software to the public domain worldwide. This software is distributed without any warranty. 
* see CC0 Public Domain Dedication <http://creativecommons.org/publicdomain/zero/1.0/>. 
*/ 
    var emRemToPx = function(value, scope, suffix) { 
    if (!scope || value.toLowerCase().indexOf("rem") >= 0) { 
     scope = 'body'; 
    } 
    if (suffix === true) { 
     suffix = 'px'; 
    } else { 
     suffix = null; 
    } 
    var multiplier = parseFloat(value); 
    var scopeTest = $('<div style="display: none; font-size: 1em; margin: 0; padding:0; height: auto; line-height: 1; border:0;">&nbsp;</div>').appendTo(scope); 
    var scopeVal = scopeTest.height(); 
    scopeTest.remove(); 
    return Math.round(multiplier * scopeVal) + suffix; 
    }; 
0

controllare questo piccolo script out: https://github.com/normanzb/size

ti aiuta a convertire le unità il più a lungo come si passa in un elemento dom di riferimento

0

Di solito quando si desidera convertire px a em, la conversione avviene sull'elemento stesso. getComputedStyle restituisce il valore in px che interrompe la loro reattività.Il seguente codice può essere utilizzato per aiutare con questo problema:

/** 
* Get the equivalent EM value on a given element with a given pixel value. 
* 
* Normally the number of pixel specified should come from the element itself (e.g. element.style.height) since EM is 
* relative. 
* 
* @param {Object} element - The HTML element. 
* @param {Number} pixelValue - The number of pixel to convert in EM on this specific element. 
* 
* @returns {Boolean|Number} The EM value, or false if unable to convert. 
*/ 
window.getEmValueFromElement = function (element, pixelValue) { 
    if (element.parentNode) { 
     var parentFontSize = parseFloat(window.getComputedStyle(element.parentNode).fontSize); 
     var elementFontSize = parseFloat(window.getComputedStyle(element).fontSize); 
     var pixelValueOfOneEm = (elementFontSize/parentFontSize) * elementFontSize; 
     return (pixelValue/pixelValueOfOneEm); 
    } 
    return false; 
}; 

Utilizzando sarebbe semplice come:

var element = document.getElementById('someDiv'); 
var computedHeightInEm = window.getEmValueFromElement(element, element.offsetHeight); 
0

Ho confezionato questa funzionalità in una libreria, completa di tipo di parametro di controllo: px-to-em

Dato questo HTML:

<p id="message" style="font-size: 16px;">Hello World!</p> 

ci si può aspettare questi outp UTS:

pxToEm(16, message) === 1 
pxToEm(24, message) === 1.5 
pxToEm(32, message) === 2 

Dal momento che l'OP ha richiesto un modo per fare questo senza una biblioteca, ho copiato il codice sorgente di px-to-em ad una demo live:

function pxToEm (px, element) { 
 
    element = element === null || element === undefined ? document.documentElement : element; 
 
    var temporaryElement = document.createElement('div'); 
 
    temporaryElement.style.setProperty('position', 'absolute', 'important'); 
 
    temporaryElement.style.setProperty('visibility', 'hidden', 'important'); 
 
    temporaryElement.style.setProperty('font-size', '1em', 'important'); 
 
    element.appendChild(temporaryElement); 
 
    var baseFontSize = parseFloat(getComputedStyle(temporaryElement).fontSize); 
 
    temporaryElement.parentNode.removeChild(temporaryElement); 
 
    return px/baseFontSize; 
 
} 
 

 
console.log(pxToEm(16, message), 'Should be 1'); 
 
console.log(pxToEm(24, message), 'Should be 1.5'); 
 
console.log(pxToEm(32, message), 'Should be 2');
<p id="message" style="font-size: 16px;">Hello World!</p>

I imparato da this answer che con getComputedStyle possiamo ottenere in modo affidabile il valore del divisore px con il punto decimale, che migliora la precisione del calcolo. Ho scoperto che la risposta di Aras potrebbe essere superiore a 0,5 px, il che ha causato errori di arrotondamento per noi.