Forum How do I...?

Making <br> space the same as </p>

ibk
I need to make <br> within a paragraph give the same vertical space as a </p>, but not affect <br>s that appear elsewhere in the document. (this is because some HTML editors insert </p><p> when you press Enter, and some insert <br>)

That is, have
<p>This is a paragraph.</p><p>And this is another.</p>

end up with the same look as
<p>This is a paragraph.<br>And this is another.</p>



The stylesheet inlcudes
p { padding-bottom: 0.5em}
to give a bit of space between paragraphs.

I tried
br { display: block; padding-bottom: 0.5em}
which sort of worked, but had consequences to other <br>s elsewhere.

I tried
p br { padding-bottom: 0.5em}
but that didn't seem to work at all.

Any thoughts?

[/code]
mikeday
This worked for me:
p { margin: 0; padding-bottom: 0.5em }
br { display: block; padding-bottom: 0.5em }

Do you have any other style rules that could be interfering with it?
ibk
Thanks.
Isn't it funny the way problems magically disappear over the weekend? I'm sure I was using CSS equivalent to yours, and it wasn't working... and yet now it is. :oops:

However, I want to prevent the extra spacing inside tables, and also where I have used <br> to split an image from its caption. On top of that, I can foresee a problem where the HTML does not have a <p> at all - just text within a <body>.

So far I've come up with
p { margin: 0; padding-bottom: 3em }
br { display: block; padding-bottom: 3em }
table br {display: inline; padding: 0; }
img + br {display: inline; padding: 0; }

which is getting close (I've increased the padding to 3em to make it more obvious during these tests).

Is there some way I can use the not: pseudo-selector to achieve this? I tried
br:not(table br) { display: block; padding-bottom: 3em }

but that didn't work. I'm sure the syntax is obvious once you know...

What I want to say is "every br that is not within a table, and not immediately after an img".
mikeday
The :not selector won't work, as it can only match down the tree, not up the tree, you can't check parents that way. Your two rules look good though:
table br {display: inline; padding: 0; }
img + br {display: inline; padding: 0; } 

What's wrong with using these?
ibk
I'm happy enough with my rules, and they do the trick.

I suppose my desire to use not() is because I am taking the default stylesheet's rules and modifying the bits that don't quite work. Not being able to use not() means having to explicitly specify more attributes on more elements. In this case, I need sets of rules (one for the included case, one for the excluded case). If I could use not() I would have one rule, plus a "meta rule" that says when to apply the rule.
Perhaps this amount of abstraction just doesn't reside within CSS. Which is fine; I'm don't really want to change the world.

Thanks for your help (although it still remains a mystery to me why what I tried on Thursday didn't work until Monday morning...)
mikeday
You're right, it would be nice to be able to express it using one single rule. Negated rules can be a bit fiddly though. I think it can be expressed in XPath, but it's not exactly trivial to write though:
br[not(ancestor::table)][not(preceding-sibling::*[1]/self::img)]

The simplest solution would be if CSS selectors supported true negation and intersection operators, which would allow your three selectors to be combined into one (note, this is hypothetical unsupported syntax):
br /\ ~(table br) /\ ~(img + br)

This would select elements that match all three selectors, being br elements that are not descendants of tables and don't immediately follow images. Now that I look at it, that's really quite cool. :D