2010-03-29 12 views
9

Diciamo che sto sviluppando un'applicazione per iPhone che è un catalogo di automobili. L'utente sceglierà una macchina da una lista e presenterò una vista dettagliata per l'auto, che descriverà cose come la velocità massima. La vista di dettaglio sarà essenzialmente un UIWebView che sta caricando un file HTML esistente.Modifica CSS al volo in una UIWebView su iPhone

Diversi utenti vivranno in diverse parti del mondo, quindi gradiranno vedere la velocità massima per l'auto in qualsiasi unità sia appropriata per la loro posizione. Diciamo che ci sono due di queste unità: SI (km/h) e convenzionale (mph). Diciamo anche che l'utente sarà in grado di cambiare le unità di visualizzazione premendo un pulsante sullo schermo; quando ciò accade, la schermata dei dettagli dovrebbe cambiare per mostrare le unità rilevanti.

Finora, ecco cosa ho fatto per cercare di risolverlo.

Il codice HTML potrebbe essere simile a questo:

 
<?xml version="1.0" encoding="UTF-8"?> 
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en-US" lang="en-US"> 
<head> 
<title>Some Car</title> 
<link rel="stylesheet" media="screen" type="text/css" href="persistent.css" /> 
<link rel="alternate stylesheet" media="screen" type="text/css" href="si.css" title="si" /> 
<link rel="alternate stylesheet" media="screen" type="text/css" href="conventional.css" title="conventional" /> 
<script type="text/javascript" src="switch.js"></script> 
</head> 
<body> 
<h1>Some Car</h1> 
<div id="si"> 
<h2>Top Speed: 160 km/h</h2> 
</div> 
<div id="conventional"> 
<h2>Top Speed: 100 mph</h2> 
</div> 
</body> 

Il foglio di stile peristent, persistent.css:

#si 
{ 
    display:none; 
} 

#conventional 
{ 
    display:none; 
} 

Il primo foglio di stile alternativo, si.css:

#si 
{ 
    display:inline; 
} 

#conventional 
{ 
    display:none; 
} 

E il secondo foglio di stile alternativo, convenzionale.css:

#si 
{ 
    display:none; 
} 

#conventional 
{ 
    display:inline; 
} 

Basato su un tutorial in A List Apart, i miei switch.js sembra qualcosa di simile:

function disableStyleSheet(title) 
{ 
    var i, a; 
    for (i = 0; (a = document.getElementsByTagName("link")[i]); i++) 
    { 
     if ((a.getAttribute("rel").indexOf("alt") != -1) && (a.getAttribute("title") == title)) 
     { 
      a.disabled = true; 
     } 
    } 
} 

function enableStyleSheet(title) 
{ 
    var i, a; 
    for (i = 0; (a = document.getElementsByTagName("link")[i]); i++) 
    { 
     if ((a.getAttribute("rel").indexOf("alt") != -1) && (a.getAttribute("title") == title)) 
     { 
      a.disabled = false; 
     } 
    } 
} 

function switchToSiStyleSheet() 
{ 
    disableStyleSheet("conventional"); 
    enableStyleSheet("si"); 
} 

function switchToConventionalStyleSheet() 
{ 
    disableStyleSheet("si"); 
    enableStyleSheet("conventional"); 
} 

mio gestore di azione pulsante sembra qualcosa di simile:

- (void)notesButtonAction:(id)sender 
{ 
    static BOOL isUsingSi = YES; 
    if (isUsingSi) 
    { 
     NSString* command = [[NSString alloc] initWithString:@"switchToSiStyleSheet();"]; 
     [self.webView stringByEvaluatingJavaScriptFromString:command]; 
     [command release]; 
    } 
    else 
    { 
     NSString* command = [[NSString alloc] initWithFormat:@"switchToConventionalStyleSheet();"]; 
     [self.webView stringByEvaluatingJavaScriptFromString:command]; 
     [command release]; 
    } 
    isUsingSi = !isUsingSi; 
} 

Ecco il primo problema La prima volta che si preme il pulsante, lo UIWebView non cambia. La seconda volta che viene colpito, sembra che il foglio di stile convenzionale sia caricato. La terza volta, passa al foglio di stile SI; la quarta volta, torna al convenzionale e così via. Quindi, fondamentalmente, solo la prima pressione di un pulsante non sembra fare nulla.

Ecco il secondo problema. Non sono sicuro di come passare al foglio di stile corretto al caricamento iniziale di UIWebView. Ho provato questo:

- (void)webViewDidFinishLoad:(UIWebView *)webView 
{ 
    NSString* command = [[NSString alloc] initWithString:@"switchToSiStyleSheet();"]; 
    [self.webView stringByEvaluatingJavaScriptFromString:command]; 
    [command release]; 
} 

Ma, come il primo colpo tasto, non sembra di fare nulla.

Qualcuno può aiutarmi con questi due problemi?

+0

Irrilevante, ma è possibile semplicemente le 3 istruzioni ObjC in una sola: '[auto.webView stringByEvaluatingJavaScriptFromString: @ "switchToSiStyleSheet();"]; ' – kennytm

risposta

2

Probabilmente lo avete capito tempo fa, ma poiché questa è la pagina migliore su questo argomento sul web, risponderò per completezza.

Eri molto vicino. Tutto quello che devi fare è aggiungere una chiamata iniziale alla tua funzione nel tuo HTML head.

<head> 
<title>Some Car</title> 
<link rel="stylesheet" media="screen" type="text/css" href="persistent.css" /> 
<link rel="alternate stylesheet" media="screen" type="text/css" href="si.css" title="si" /> 
<link rel="alternate stylesheet" media="screen" type="text/css" href="conventional.css" title="conventional" /> 
<script type="text/javascript" src="switch.js"></script> 
<script type="text/javascript">switchToSiStyleSheet();</script> 
</head> 
Problemi correlati