![](/img/trans.png)
[英]How to use JavaScript's setattribute to affect multiple elements?
[英]Using Switch Statement to style/color multiple elements, through use of setAttribute() (Javascript)
我正在建立一個網頁,以檢測您當地的天氣預報。 但是,為了使其唯一,我正在嘗試使網頁在界面上更改其顏色。 它將根據天氣api中的天氣圖標更改顏色。 (即weath.weather [0] [“ icon”])。 我正在嘗試使其盡快運行,同時使其更易於理解。 所以我正在尋找一種替代方法。
我決定將顏色更改功能存儲在一個變量中,以便可以多次重用,因此可以縮短Switch語句。 它包含一個可以重復使用的CSS字符串變量。 字符串是setAttribute函數的樣式屬性:
var coloring = function(id, Text, Background) {
var colorChange = "color: " + Text + "; background: " + Background + ";";
document.getElementById(id).setAttribute("style", colorChange);
};
這將用於通過參考ID來更改Dom的各個元素/部分的顏色。 這是Dom:
<body id="background"> <div id="header"> <h1>Local Weather Detector</h1> </div> <div id="location"> <h5 id="locIntro">Today's weather from Location...</h5> </div> <div id="box"> <div id="temperature"> <p><strong>Today, </strong>The temperature in your area is... <button id="tempSwap"> </button></p> </div> <div id="weather"> <p>- and the general forecast is...</p> </div> </div> <div id="copywrite"><h6> Ⓒ Thomas Jackson</h6> <h6>(Project for Free Code Camp, Full Stack course)</h6></div> </body>
我將從api獲取圖標數據,然后switch語句將根據其圖標確定需要更改的顏色。 每個使用coloring()函數的Switch Case都會將Dom的顏色更改為其自己的設置顏色:
$.getJSON(api, function(weath) {
switch (weath.weather[0]["icon"]) {
case "01d": //clear
coloring("background", "#f1c40f", "#3498db");
coloring("box", "#2980b9", "#ecf0f1");
coloring("temp", "#c0392b", "");
break;
case "01d":
case "03d":
case "04d":
case "50d": //cloud
coloring("background", "#3498db", "#ecf0f1");
coloring("header", "#f1c40f", "");
coloring("box", "", "#2980b9");
coloring("temp", "", "#3498db");
break;
case "02d": //cloudClear
coloring("background", "c0392b", "#2980b9");
coloring("header", "#f1c40f", "");
coloring("box", "", "#ecf0f1");
coloring("temp", "", "#2980b9");
break;
case "11d": //thunder
coloring("background", "#c0392b", "#2980b9");
coloring("header", "#f1c40f", "");
coloring("box", "", "#f1c40f");
coloring("temp", "", "#c0392b");
break;
case "13d": //snow
coloring("background", "#ecf0f1", "#2980b9");
coloring("header", "#34495e", "");
coloring("box", "", "#a5f2f3");
coloring("temp", "", "#34495e");
break;
case "03n":
case "04n":
case "50n": //cloudNight
coloring("background", "#ecf0f1", "#7f8c8d");
coloring("header", "#e74c3c", "");
coloring("box", "#f1c40f", "#34495e");
coloring("temp", "", "#2c3e50");
break;
case "09n":
case "10n": //rainNight
coloring("background", "#3498db", "#2c3e50");
coloring("header", "#f1c40f", "");
coloring("box", "#2980b9", "#95a5a6");
coloring("temp", "#3498db", "#2980b9");
break;
case "11n": //thunderNight
coloring("background", "#f1c40f", "#2c3e50");
coloring("header", "#e74c3c", "");
coloring("box", "#c0392b", "#f1c40f");
coloring("temp", "", "#c0392b");
break;
case "13n": //snowNight
coloring("background", "#f1c40f", "#2c3e50");
coloring("header", "#a5f2f3", "");
coloring("box", "#34495e", "#a5f2f3");
coloring("temp", "#2c3e50", "#f1c40f");
break;}
}
如果我要以錯誤的方式進行操作,那么最好知道。 我在這里的主要目標是使它對於其他開發人員而言更加高效和清晰。
解決這個問題的方法與我所說的“正確”方法(通常有不止一種)並沒有太大的距離–盡管有一些微優化和清晰度增強器的空間。
首先,如果您想提高其他維護者的可讀性,建議您將圖標代碼存儲在命名常量中。 一個case: "01d"
不告訴我的圖標是什么東西,但是這並不:
var ICON_STORMY = "01d";
switch (weath.weather[0].icon) {
case ICON_STORMY:
...
break;
...
}
其次,您的着色函數使用率很高,因此我也會對此加以加強-不會太多,但是也許這樣,它可以被調用一次,而不是為每個id
調用一次。
例如,您可以這樣編寫:
function colorAll(elems) {
elems.forEach(function (elem) {
var colorChange = "color: " + elem.text + "; background: " + elem.background + ";";
document.getElementById(elem.id).setAttribute("style", colorChange);
});
}
...然后使用該函數,如下所示:
colorAll([{ id: 'background', text: 'blah blah', background: '#666666' }, { ... }]);
...這樣的想法是,如果您傳遞完成一個完整開關案例所需的所有信息,則只需要調用一次即可。
功能思維
switch
語句很有用,但是它不適合您編寫的其他功能代碼,它具有副作用,發生狀態突變的可能性,副作用,並且主要不能與其他函數組成
在switch語句中幾乎總是應該有一個默認情況。我假設。如果在weath.weather[0]["icon"]
情況下未找到相關值,則不注冊該情況。 讓我們看一下我們正在處理的開關盒
$.getJSON(api, function(weath) {
switch (weath.weather[0]["icon"]) {
case "01d": //clear
coloring("background", "#f1c40f", "#3498db");
coloring("box", "#2980b9", "#ecf0f1");
coloring("temp", "#c0392b", "");
break;
case "01d":
case "03d":
case "04d":
case "50d": //cloud
coloring("background", "#3498db", "#ecf0f1");
coloring("header", "#f1c40f", "");
coloring("box", "", "#2980b9");
coloring("temp", "", "#3498db");
break;
default:
console.log(`case is not registered`);
break;
}
}
如果我們將其轉換為三進制,則代碼如下所示。 我正在使用ES6箭頭功能以提高可讀性
$.getJSON(api,(weath) => {
const icon = weath.weather[0].icon;
// try to convert switch to if/else or ternary
icon === '01d' ? coloring() : //coloring methods of 01d
icon === '02d' ? coloring() //coloring methods of 02d
: console.log('no case matched');
});
可以使用以下功能優化此重復代碼
const switchcase = (cases, defaultCase, key) => {
if (key in cases) {
return cases[key]
} else {
return defaultCase
}
}
應用鑽營技術上面的方法,並使用三元取代傳統if else
const switchcase = cases => defaultCase => key =>
key in cases ? cases[key] : defaultCase
現在可以像下面這樣優化代碼
$.getJSON(api, switchcase({
'01d' : coloring1(),
'02d' : coloring2()
})(console.log('no case matched'))(weath.weather[0].icon)
);
早期版本的switchcase
有一個問題,因為在傳遞給switchcase
函數之前先評估整個對象常量。 這意味着coloring1()
和coloring2()
均被評估。 這可能非常危險。
如果對象文字中的值是函數,則只有在匹配情況下才可以執行它們。
代碼將更改為
$.getJSON(api, switchcase({
'01d':() => { coloring('x');coloring('...');},
'02d':() => { coloring('y');coloring('...');}
})(() => console.log('no cases matched'))(weath.weather[0].icon)
);
優化代碼
$.getJSON(api, switchcase({
01d:() => coloringClear(),
03d:() => coloringCloud(),
04d:() => coloringCloud(),
50d:() => coloringCloud(),
02d:() => coloringCloudClear(),
11d:() => coloringThunder(),
13d:() => coloringSnow(),
03n:() => coloringCloudNight(),
04n:() => coloringCloudNight(),
50n:() => coloringCloudNight(),
09n:() => coloringRainNight(),
10n:() => coloringRainNight(),
11n:() => coloringThunderNight(),
13n:() => coloringSnowNight()
})('Unknown')(weath.weather[0]["icon"])
);
將對象保留在單獨的變量中,以實現更好的可維護性。 將所有着色方法移至上述一種方法中。 將它們寫為單獨的函數
希望可以通過以上代碼優化性能
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.