The issue I am facing now happens in an automated form generated by JS, which is using controls trimmed in DIVs. The resulting HTML is given here:
<div id="E0" style="width:200px;" class="FLD">
<div style="flex: initial;">Val A:</div>
<input type="text" style="flex: 1 1 auto;">
</div>
<div id="E1" style="width: 600px;" class="FLD" lf="1">
<div style="flex: initial;">Val B:</div>
<input type="text" style="flex: 1 1 auto;">
</div>
<div id="E2" style="width: 400px;" class="FLD">
<div style="flex: 1 1 auto;">Val C:</div>
<input style="width:60px; flex:initial;" type="text">
</div>
The associated CSS:
.FLD{ display:inline-flex; flex-direction:row; }
.FLD[lf]::after{ /* The issue described below*/ }
Note that the "inputs" above may be different elements and the above is just "private case".
The issue:
As from the above structure, I expect the DIV "E0" and DIV "E1" to be in the same line, while "E2" in a separate line below (assuming the parent container wide enough, at least).
The DIVs will appear all inline (because by default I want them to be like this). However, the attribute "lf" if set (can also be set by JS internal property), shall virtually add <br> element after the DIV.
If I create <br> element after the DIV, it will make a problem if I want to remove the DIV in one command also its "<br>" - as they become 2 separated elements - and as this appears in SPA, I want to have a clean removing function or hidding function to handle that element only, without considering "trailings".
If I use "display:flex;" instead of "display:inline-flex" for just that one particular element, the situation will become all DIVs in separate lines (not inline element which happen to be the middle one, will cause the previous to be on top and the next below it).
The last approach I thought to use, is .FLD[lf]::after{ content:'' } selector - but then, my question is comming:
Is there such possibility in CSS to somehow add line feed (something like "<br>") after DOM element? I have tried "content", but it seems working on text-string only, so even "\n" is not doing what I want. I believe that is not possible, but maybe I am wrong and there is another way...
I don't think that what you re asking is possible. But...
You can use float and clear css properties combined:
#E0, #E1, #E2{
float: left;
}
#E2{
clear: left
}
This will arrange your divs in a similar way
Related
I'm dynamically creating jQuery UI sliders, using the following code in a forEach loop:
// Sets an id for the slider handles, gives them a custom class (makes them appear as circles, centers them)
$("#slideRange" + i).find(".ui-slider-handle").attr("id","slideHandle" + i).addClass("customSliderHandle");
// These two lines set the times below the slider handles.
$("#timeSlider" + i).find(".slideStartLabel").text(startTime);
$("#timeSlider" + i).find(".slideEndLabel").text(endTime);
This successfully makes the following slider, with variable times, for every iteration:
What I'd like to do, instead of showing the times below the circular handles, is have the times appear in the middle of the handles. The end result would look like this (photoshopped):
The times will then update, according to the slider values, within the "slide" event callback.
My question is: how do I assign unique id's to the two slider handles, so that I can then set their text independently in the "slide" callback? The code I wrote above gives both handles the same id. Using this id to set text to a handle will only apply to the first handle, leaving me no way to change the text of the second. Using find(), get(), or just $(".ui-slider-handle") are all ways of getting an array of the slider handles, but when I try attr("id","uniqueId") on one of the elements of that array, I get "(...).method(...) is not a method".
Or is assigning unique id's the wrong approach, here? Is there a jQuery or vanilla Js way of setting attributes of one element at a time, when searching by class and getting potentially multiple results?
Also, for context: I'm using find() because I'm using clone() on a markup shell, then appending it to a central div. Here's the shell:
<!-- This hidden div will be cloned, customized, and appended onto .modal-body -->
<div id="timeslotShell" class="timeslot row" style="display:none">
<div class="container-fluid slotContents" id="slotContents">
<span class="col-md-4"> Listing <div class="slotNumber listNum">*Listing No.*</div>: From <div class="slotNumber startNumber slotStartShell"> *Start Time* </div> until
<div class="slotNumber endNumber slotEndShell"> *End Time* </div> </span>
<div class="col-md-8">
<button type="button" class="btn btn-md btn-info slotButton">
Choose A Time From Within These Hours
</button>
</div>
<div id="timeSliderShell" class="collapse timeSlider">
<br><br>
<div id="slider-range" class="slideRange row"></div>
<div id="slideLabels" class="slideLabels slideRange row">
<div class="slideStartLabel"></div><div class="slideEndLabel"></div>
</div>
</div>
</div>
<br><br>
</div>
Cool -- as luck with have it, I found the answer shortly after posting this. Check this post if you're dealing with a similar issue:
Slider Value Display with jQuery UI - 2 handles
All that's needed, in the .find() calls, is
.find(".ui-slider-handle:first").text(value1);
for the first handle and then
.find(".ui-slider-handle:last").text(value2);
for the second.
This question already has answers here:
Are (non-void) self-closing tags valid in HTML5?
(8 answers)
Closed 7 years ago.
It's working this way on all the browsers I can see the page from. I swear to you that this is the exact code from the html:
<td class="bardisplay">
<div class="bar hot" />
<div class="bar cool" />
</td>
But yet in the debugger of every single browser I've brought this up in, the DOM inspector shows something like this: (Chrome, here)
There is no difference between Mozilla, IE, and Chrome. I about freaked out when I saw it in the Chrome debugger.
Here is all the pertinent CSS:
td.bardisplay {
height : 66px;
padding : 8px 0px;
margin-left : 5pt;
}
.bar { height : 50px; }
.hot {
float : left;
background-color : red;
}
.cool {
float : left;
background-color : green;
}
Now, the really weird thing: I did not have this problem, with the same html when I put all my bar displays into a main table (3 levels up).
I had a six-column table, one with a label, one with a display, and one with a ratio, and the next three repeating, but I did not like how the second set of columns would "wag" back and forth as the table was updated. So I set the master table to a single row of two tds with three-column tables inside them. The display is now rock-solid, except that the DOM wants to put one div inside the other.
I googled this about every way I could think before posting here.
<div>'s cannot self-close, so the browser assumes the second one is the child of the first one:
<td class="bardisplay">
<div class="bar hot"></div>
<div class="bar cool"></div>
</td>
In HTML 5, <foo /> means <foo>, the start tag. It is not a "self-closing tag". Instead, certain elements are designated as having no end tag, for example <br>. These are collectively called void elements. The slash is just syntactic sugar for people who are addicted to XML. Using the slash in a non-void element tag is invalid, but browsers parse it as the start tag anyway, leading to a mismatch in end tags.
Source
How about this?
<td class="bardisplay">
<div class="bar hot"> </div>
<div class="bar cool"> </div>
</td>
I'm using the following HTML structure:
<div id="clock">5:30 AM
<div id="day">Wednesday
</div>
<div id="date">14 December
</div>
</div>
I update the contents of these elements using Javascript. For "day" and "date" I use $("#day").text(day) and $("#date").text(date). Because "clock" is a parent element I had to use $("#clock").prepend(clock) to succesfully add the text.
The problem with the latter function, is that new text is prepended every time the clock is refreshed, i.e. it builds up a list of clock times. For the first two functions the text is just replaced, like it should. Is there a way to make this happen for the "clock" function as well?
EDIT: Sorry, should have been a bit more clear about the clock. Have edited the code, so you understand. BTW, the reason the clock is parent element is that could make the other two elements depend on the clock's position and styling.
I also created a jsFiddle: https://jsfiddle.net/daanodinot/NZtFA/
I left the list building thing (annoyingly) in!
BTW, I'm not too sure if function(); setInterval('function()', 1000) is the best way to refresh, so if you something better I'd be happy to know :)
What you need to do is change the structure of your html to this.
<div id="wrapper">
<div id="clock"></div>
<div id="day"></div>
<div id="date"></div>
</div>
Then for the javascript
$('#clock').text('12:45');
$('#day').text('Wednesday');
$('#date').text('12/14/2011');
This way you can just change/refresh the text of clock instead of prepending values to it.
Another approach, with your current html, which i do not recommend.
<div id="clock">
<div id="day">
</div>
<div id="date">
</div>
</div>
The js
$('#clock').contents().get(0).nodeValue = '12:45';
$('#day').text('Wednesday');
$('#date').text('12/14/2011');
If you have HTML
<div id="clock">
<div id="day"></div>
<div id="date"></div>
</div>
Then you don't have to modify #clock at all. By doing $("#day").text(day) and $("#date").text(date) content of those divs is changed and you don't have to touch #clock.
But in case you want to replace a content of a element then use .html(newContent). See documentation.
You should first add a new element with prepend and then replace it's content, now you just constantly keep prepending new elements instead of working on the same element again.
What do you mean by
Because "clock" is a parent element I had to use
$("#clock").prepend(clock) to succesfully add the text.
?
It seems redundant. Since $('#day') and $('#date') uniquely address your targeted elements.
My tip:
Do not use clock. $("#day").text(day) and $("#date").text(date) already update the numbers inside your #clock element.
Hy,
my consideration for your problem is, IF you choose to manipulate the Content of the #clock div you could simply do this:
var newContent="";//in here comes whatever you want to add to your clock div
$('#clock').html($('#clock').html()+newContent);
That's the way I use it most of the time but you could also do this:
var curContent=$('#clock').html();
curContent+="<>put in your code to add</>";
$('#clock').html(curContent);
This is I guess a bit slower than the first one, but it works.
I have this code : http://jsfiddle.net/Qchmqs/BSKrG/
<div class="step"><-- this is darned wrong
<div id="step2"><a>Darn</a></div>
<div id="step2"><a>Darn</a></div>
<div id="step2"><a>Darn</a></div>
</div>
<div class="step"><-- this works fine
<div id="step2"><a>Darn</a>
<a>Darn</a>
<a>Darn</a></div>
</div>
The first block is three links inside three separate divs inside a surrounding div
The bottom block has the links inside one parent div
I am trying to change the background of an active link, but it won't turn off in the upper block.
The script works well with the bottom links but not working as expected with the upper ones
PS : The active class should be toggled only from the Links i have a lot of other scripts in the page that uses the .active links from this list.
For starters, do what JamesJohnson said and remove the multiple IDs. They can only cause you problems down the road.
In the upper links, the a tags aren't siblings because you put each one in its own div. So you need to do this to remove classes from the other as:
$(this).parent().siblings('div').children('a').removeClass('active');
http://jsfiddle.net/mblase75/BSKrG/1/
Unfortunately, that breaks the functionality on the lower links. You can achieve success in both places by adding andSelf to the parent siblings:
$(this).parent().siblings('div').andSelf().children('a').removeClass('active');
http://jsfiddle.net/mblase75/BSKrG/2/
It's not working on the upper ones because you're assigning the same id to the divs. You should probably use the class attribute instead:
<div class="step2"><a>Damn</a></div>
<div class="step2"><a>Damn</a></div>
<div class="step2"><a>Damn</a></div>
After making the above changes, you should be able to do this:
$(".step2 a").text("Hello World!");
maybe this:
<div class="step">
<div id="step2"><a>Damn</a>
<a>Damn</a>
<a>Damn</a></div>
</div>
<div class="step">
<div id="step2"><a>Damn</a>
<a>Damn</a>
<a>Damn</a></div>
</div>
Using radio inputs you can create this effect without any JS at all, which degrades gracefully from its intended appearance (a red backgrounded "damn") to damn with radios next to it (sending the same information).
ironically, this example at JSfiddle: http://jsfiddle.net/YvQdj/
My memory is a bit fuzzy, but I'm pretty sure this doesn't work in older versions of IE without some finagling.
Is it possible to wrap an <a> tag around <div>s like so:
<a href=etc etc>
<div class="layout">
<div class="title">
Video Type
<div class="description">Video description</div>
</div>
</div>
</a>
Eclipse is telling me the div's are in the wrong place?
If this is not allowed. How can I make the entire 'layout' class become a link?
That structure would be valid in HTML5 since in HTML5 anchors can wrap almost any element except for other anchors and form controls. Most browsers nowadays have support for this and will parse the code in the question as valid HTML. The answer below was written in 2011, and may be useful if you're supporting legacy browsers (*cough* Internet Explorer *cough*).
Older browsers without HTML5 parsers (like, say, Firefox 3.6) will still get confused over that, and possibly mess up the DOM structure.
Three options for HTML4 - use all inline elements:
<a href=etc etc>
<span class="layout">
<span class="title">
Video Type
<span class="description">Video description</span>
</span>
</span>
</a>
Then style with display: block
Use JavaScript and :hover:
<div class="layout">
<div class="title">
Video Type
<div class="description">Video description</div>
</div>
</div>
And (assuming jQuery)
$('.layout').click(function(){
// Do something
}):
And
.layout:hover {
// Hover effect
}
Or lastly use absolute positioning to place an a anchor with CSS to cover the whole of .layout
<div class="layout">
<div class="title">
Video Type
<div class="description">Video description</div>
</div>
<a class="more_link" href="somewhere">More information</a>
</div>
And CSS:
.layout {
position: relative;
}
.layout .more_link {
position: absolute;
display: block;
top: 0;
bottom: 0;
left: 0;
right: 0;
text-indent: -9999px;
z-index: 1000;
}
This won't work with older versions of IE, of course.
While the <a> tag is not allowed to contain <div> element, it is allowed to contain other inline elements such as <span>.
When I encountered the problem i swapped the div tag with a <span>. Since the span tag is an inline element, you need to apply a display:block to the css of your <span> element, in order to make it behave like the <div> block element.
This should be valid xhtml and does not require any javascript.
Here's an example:
<a href="#">
<span style="display:block">
Some content. Maybe some other span elements, or images.
</span>
</a>
Another simple solution - just add an onclick event handler to the div thusly:
<div class="layout" onclick="location.href='somewhere'">
<div class="title">
Video Type
<div class="description">Video description</div>
</div>
</div>
This works great for me but there is one small gotcha. I'm not sure how search engine friendly this is. I fear that google's web crawlers might not find this link so I also tend to include a traditional A HREF link somewhere in the block like this:
<div class="layout" onclick="location.href='destination_url'">
<div class="title">
Video Type
<div class="description">Video description</div>
</div>
This is a link
</div>
Timothy's solution is correct ... instead of wrapping an anchor around a div ... you simply give layout to the anchor element with display:block and add the size and width of the anchor ...
.div_class { width: 100px; height: 100px; }
.div_class a { width: 100px; height: 100px; display: block; }
<div class='div_class'></div>
HTML provides two general elements, where div is a natural block element, and span is a natural inline element. All other elements are similarly assigned to be a natural block or inline.
Now, while both can be made by css display to be any of inline, inline-block or block, they are still treated for enclosure purposes as their natural selves, hence the warning messages. Leopards and spots sort of thing.
However, css is only meant to be for making what an element looks like (presentation), but not actually be like (functionality), so it doesn't change an element's basic nature, though that gets very fuzzy in practice. A span made block becomes a bully that kicks everything else off the line, which is very un-inline sort of behaviour.
So, to mitigate against possible conflicts between their natural and css-induced behaviours, it is better to allow:
div or any natural block tag to only ever be block or inline-block.
span or any natural inline tag to only ever be inline or inline-block.
This will also mitigate against tending to build page structures that will likely end up churning out error and warning messages.
Basically, NEVER embed a natural block tag inside a natural inline tag, at any depth.
Why there is a really a distinction is perhaps due to a simplistic idea of what HTML was going to be used for when it was first dreamed up.
Certainly, framework makers got around a lot of these what-to-embed-where problems by just using myriads of divs everywhere, and 'divitis' was born, and still alive and well in every framework. Just have to press F12 in a browser on almost any commercial web page and drill down through a dozen divs. This very page has 15 unbroken levels of divs.
It is not hard to see why just settling on divs made sense. For example, a p tag may have a bunch of links to various sites, and that is ok because inline links are allowed in a block p. However, if not wanting to have query variables visible in those urls, then buttons are required. If only one, then the p can be put inside a form, as a p cannot contain a form.
The formaction attribute on a button can be used to target a url other than the form default, but it still does not allow independent forms, each with their own set of hidden inputs. A button can use the form attribute to use it with a form that isn't an ancestor, but it can get messy to keep track of.
For multiple links to different sites to appear as part of one paragraph though, the only way is to use a div instead of the p and then wrap each button in its own form set to inline. Most frameworks have to cope with so much more complex scenarios that nested divs are the only way to go.
It meant that they really only had to manage one tag per purpose and manage it as if it was an isolated environment. So what was meant to be an occasionally-used functional grouping tag became the web's Lego block. And none of them are going to risk breaking their frameworks by converting to HTML5 semantic tags in a hurry. In the end, semantic tags only really work for fairly static content rather than rich interactive sites.
I had tried to create custom solution using jQuery, which would imitate same behavior as a tag does, for parent DIV.
DEMO:
https://jsfiddle.net/kutec/m9vxhcke/
As per W3C standard, you cannot do this:
<div class="boxes">
<a href="http://link1.com" target="_blank">
<div class="box">
<h3>Link with _blank attr</h3>
</div>
</a>
</div>
You must follow this:
<div class="boxes">
<div class="box">
<h3>
Link with _blank attr
</h3>
</div>
</div>
But by following above code, you wouldn't get the whole DIV clickable :).
Correct structure should be something like this, which also allows you to click over the DIV to redirect on the given href value:
<div class="boxes" data-href="http://link1.com" data-target="_blank">
<div class="box">
<h3>
Link with _blank attr
</h3>
</div>
</div>
Simple Solution:
$(function() {
$('.boxes a').each(function(){
var aTag = $(this).attr('href');
$(this).parent().attr('data-href',aTag);
$("[data-href]").click(function() {
window.location.href = $(this).attr("data-href");
return false;
});
})
}(jQuery));
Dynamic Solution:
(function ( $ ) {
$.fn.dataURL = function() {
// variables
var el = $(this);
var aTag = el.find('a');
var aHref;
var aTarget;
// get & set attributes
aTag.each(function() {
var aHref = $(this).attr('href');
$(this).parent().attr('data-href',this);
aTarget = $(this).attr('target');
$(this).parent().attr('data-target',aTarget);
});
// imitation - default attributes' behavior on "data-" attributes
$(el).delegate('[data-href]','click', function() {
var loc = window.location.href;
loc = $(this).attr("data-href");
aTarget = $(this).attr('data-target');
if(aTarget == "_blank"){
window.open(loc);
} else {
window.location = loc;
}
return false;
});
//removing attributes from selector itself
el.removeAttr('data-href');
el.removeAttr('data-target');
// css
$('[data-href]').css('cursor','pointer');
};
}( jQuery ));
Final call:
<script>
$('.boxes').dataURL();
</script>
Hope this would be helpful :)
You would just want to style the "a" tag as display: block;
Eclipse is appropriately telling you that your HTML is not to spec (as a div tag is not allowed in an anchor tag).
But, since you seem to want to be visually making the anchor look like a big-ol-box, then simply style it as such :)
One easy way to make the div a link/clickable is by using html javascript onclick attribute:
<div class="clickable-div" onclick="location.href='#';"><div> ... </div></div>