Javascript 基于数组返回DOM元素
作为一项挑战,我正在尝试创建一个JavaScript选择引擎,即一个JavaScript函数,该函数将在给定CSS选择器的情况下返回DOM元素 我无法使用document.querySelector/document.querySelector all 我目前正在创建参数的对象,但现在被卡住了。我现在需要遍历页面上的每个元素,如果它与我的标记或class/id匹配,则将该元素推送到一个数组中Javascript 基于数组返回DOM元素,javascript,html,arrays,object,dom,Javascript,Html,Arrays,Object,Dom,作为一项挑战,我正在尝试创建一个JavaScript选择引擎,即一个JavaScript函数,该函数将在给定CSS选择器的情况下返回DOM元素 我无法使用document.querySelector/document.querySelector all 我目前正在创建参数的对象,但现在被卡住了。我现在需要遍历页面上的每个元素,如果它与我的标记或class/id匹配,则将该元素推送到一个数组中 $("div") //Should return 2 DIVs $("img.some_class")
$("div") //Should return 2 DIVs
$("img.some_class") //Should return 1 IMG
$("#some_id") //Should return 1 DIV
$(".some_class") //Should return 1 DIV and 1 IMG
函数$(选择器){
var元素=[];
var pageTags=[];
var all=document.getElementsByTagName(“*”);
//拆分选择器
var arg=parse(选择器);
函数解析(子选择器){
var obj={tags:[],classes:[],id:[],attrs:[]};
子选择器.split(/(?=\)|(?=\)|(?=\[)/).forEach(函数(令牌){
交换机(令牌[0]){
案例“#”:
obj.ids.push(token.slice(1));
打破
案例“”:
obj.classes.push(token.slice(1));
打破
案例“[”:
对象属性推(token.slice(1,-1).split('=');
打破
违约:
对象标签推送(令牌);
打破
}
});
返回obj;
}
控制台日志(arg);
对于(所有的var项目){
//获取所有页面元素的标记名
var元素=item.tagName.toLowerCase();
控制台日志(元素);
//if参数包含DOM元素
if(参数索引of(元素)!=-1){
var x=document.getElementsByTagName(元素);
对于(x的var测试){
元素。推(测试);
}
}
}
返回元素;
}
检查此项。
当然会有更多的组合
我将测试用例限制为您提供的html示例
function _select(attrValues, tagFilter, cssSel) {
var results = [];
//var value = selector.slice(1);
var all = document.getElementsByTagName(tagFilter);
//look for an id attribute
if (cssSel === '#') {
for (var i = 0; i < all.length; i++) {
if (all[i].id === attrValues) {
results.push(all[i]);
}
}
} else {
if (typeof attrValues === 'string') {
for (var i = 0; i < all.length; i++) {
if (all[i].classList.contains(attrValues)) {
results.push(all[i]);
}
}
} else {
//multiple selector classes
var found = 0;
for (var i = 0; i < all.length; i++) {
for (var j = 0; j < attrValues.length; j++) {
if (all[i].classList.contains(attrValues[j])) {
found += 1;
if (found === attrValues.length) {
results.push(all[i]);
}
}
}
}
}
}
return results;
}
function $(selector) {
var cssSel = selector.charAt(0);
var cssSelectors = ['.', '#'];
if (cssSel === cssSelectors[0] || cssSel === cssSelectors[1]) {
//direct selector
var attrValue = selector.slice(1),
tagFilter = '*';
return _select(attrValue, tagFilter, cssSel)
} else {
for (var i = 0; i < cssSelectors.length; i++) {
var tokens = selector.split(cssSelectors[i]);
if (tokens.length > 1 && tokens[0] !== "") {
//nested selector
var tagFilter = tokens[0], //the first of the array should be the tagname ,because the case of the cssSelector at charAt(0) should have been caught in the if at the beginning.
attrValue = tokens.slice(1); //the rest of the array are selector values
return _select(attrValue, tagFilter, cssSel)
}
}
}
return document.getElementsByTagName(selector);
}
//TEST cases
var results = $("div")
console.log('Should return 2 DIVs')
for ( var e of results){
console.log(e)
}
var results = $(".some_class")
console.log('Should return 1 DIV and 1 IMG')
for ( var e of results){
console.log(e)
}
var results = $("#some_id")
console.log('Should return 1 DIV ')
for ( var e of results){
console.log(e)
}
var results = $("img.some_class")
console.log('Should return 1 IMG')
for ( var e of results){
console.log(e)
}
var results = $("div.some_class.some_other_class")
console.log('Should return 1 div')
for ( var e of results){
console.log(e)
}
函数\u选择(属性值、标记过滤器、cssSel){
var结果=[];
//var值=选择器。切片(1);
var all=document.getElementsByTagName(tagFilter);
//查找id属性
如果(cssSel=='#'){
对于(变量i=0;i1&&tokens[0]!=“”){
//嵌套选择器
var tagFilter=tokens[0],//数组的第一个应该是标记名,因为字符(0)处cssSelector的大小写应该在开始时被if捕获。
attrValue=tokens.slice(1);//数组的其余部分是选择器值
返回_选择(属性值、标记过滤器、cssSel)
}
}
}
返回文档.getElementsByTagName(选择器);
}
//测试用例
var结果=$(“div”)
console.log('应返回2个div')
对于(结果的var e){
控制台日志(e)
}
var结果=$(“.some_类”)
log('应返回1个DIV和1个IMG')
对于(结果的var e){
控制台日志(e)
}
var结果=$(“#某些#id”)
console.log('应返回1个DIV')
对于(结果的var e){
控制台日志(e)
}
var结果=$(“img.some_类”)
log('应返回1个IMG')
对于(结果的var e){
控制台日志(e)
}
var结果=$(“div.some\u class.some\u other\u class”)
console.log('应返回1个div')
对于(结果的var e){
控制台日志(e)
}
只有这一次我会说“使用jquery”的挑战是使用普通JavaScript:(你不知道或不想使用queryselectoral()
?这是挑战@Mamun,我不能使用它或jquery。这听起来像是家庭作业。这是家庭作业,不是吗?肯定是家庭作业。