I am trying to implement accessibility option on my page that would change CSS to different file when accessibility button would be clicked.
For now, all my templates extends base_generic.html, where style.css is loaded. When accessibility button would be clicked, I wish for it to change to use style_access.css for that user. How can I accomplish that?
I think a way could be, to refer in the HTML template to both CSS files, and use an onclick function with javascript, and jquery to change the id or class of the specific elements of the template.
So for example,
let's say I wanted onclick to change the CSS of an element, I could make a counter and toggle between two ids that I will have referenced in my CSS file or files.
<body>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js">
</script>
<button>This is a div</button>
<h1 class="potatoe" id="hello">HELLO THIS IS TEXT</h1>
<style>
#hello { color: red; }
#bye { color: blue; }
</style>
<script>
var clickCount = 0;
$("button").on("click", function() {
clickCount++;
$(".potatoe").attr("id", clickCount % 2 === 0 ? "bye" : "hello");
});
</script>
</body>
As you'll see everytime you click the button the CSS of the element will change
This is not exactly changing between CSS files but it ultimately changes the CSS of the elements you want to select.
You can implement by using JavaScript more easily:
const toggleButton = document.getElementById('button');
const workContainer = document.getElementById('work');
toggleButton.addEventListener('click', () => {
document.body.classList.toggle('blue');
toggleButton.classList.toggle('active');
workContainer.classList.toggle('blue');
if(document.body.classList.contains('blue')){
localStorage.setItem('blue', 'enabled');
}else{
localStorage.setItem('blue', 'disabled');
}
});
if(localStorage.getItem('blue') == 'enabled'){
document.body.classList.toggle('blue');
toggleButton.classList.toggle('active');
workContainer.classList.toggle('blue');
}
I have a Html page which has anchor tag, I Need to remove certain style applied already in html page for anchor tag while the html page is opened throw Iframe.
HTML Content as below:
<html>
<body>
<div>some content<a href="http://www.website.com" name="test1"/> some content </div>
</body>
</html>
I tried as below:
a[name^="test1"]:before{
content:"[prefix text]";
display:inline;
color:red;
}
a[name^="test1"]:after{
content:"suffix text";
display:inline;
color:green;
}
iframe a[name^="test1"]:before{
display:none;
}
iframe a[name^="test1"]:after{
display:none;
}
But inside "iframe" also these styles has been applying.
You have to first detect if your page is rendered inside an iframe and in that case apply an alternative CSS. It' can't be done with vanilla CSS then it has to be done with some JavaScript:
<script type="text/javascript">
function getTopWindow() {
try {
return window.top;
} catch {
// If we can't access window.top then browser is restricting
// us because of same origin policy.
return true;
}
}
function isRendererdInFrame() {
// If top window is null we may safely assume we're in iframe
return window.self !== getTopWindow();
}
function loadCss(location) {
if(document.createStyleSheet) {
document.createStyleSheet('http://server/stylesheet.css');
} else {
var styles = "#import url('" + location + "');";
var newSS=document.createElement('link');
newSS.rel='stylesheet';
newSS.href='data:text/css,'+escape(styles);
document.getElementsByTagName("head")[0].appendChild(newSS);
}
}
</script>
Code to load CSS from JavaScript is from How to load up CSS files using Javascript?.
With all that code you may simply write (even just after that inside <script> block):
var cssToLoad = isRendererdInFrame() ? "iframe.css" : "not-iframe.css";
loadCss("http://server/" + cssToLoad);
Of course same technique can be applied to patch CSS with iframe specific styles:
if (isRenderedInFrame())
loadCss("http://server/iframe-patch.css");
i dont know how to detect if page is opened in iframe or not, but there is one possible(not very nice) workaround, you can set iframe to width which is not commonly used by devices (example 463px) and then set media query for this resolution which apply when content is shown in this iframe. This is really nasty way since its not 100% and i would not recommending that.
Below code is for navigating to the Google Webpage when the element <li> is clicked.
<li onclick="window.location='http://www.google.com';" style="cursor:pointer;">Google</li>
Now I have another <li> which goes to different websites depending on a parameter. I tried this
<script>
document.write('<li onclick="window.location='http://www.google.com/mmm/yyy/' + random_variable + 'ddd/eee';" style="cursor:pointer;">Google</li>');
</script>
This isn't working fine. What am I doing wrong?
You don't want to use document.write. Instead you can change the attributes of the tags themselves. onClick is just javascript inside your code so you can replace variables
<li onclick="location.href='http://www.google.com/mmm/yyy/' + random_variable + 'ddd/eee';">Google</li>
It's a little messy. I'd personally do it with jQuery and a regular <a> tag
Javascript/jQuery
$(document).ready(function() {
$('#someid').click(function(e) {
e.preventDefault()
location.href= 'http://google.com/' + random_variable;
});
});
Or if your random variable is available onload you could just replace the href attribute
$(document).ready(function() {
$('#someid').attr('href','http://google.com/' + random_variable);
});
HTML
<li>Google</li>
var targetElement = document.getElementById("id");
targetElement.appendChild('<li>...</li>';
The first line find the existing element, where you want to insert the <li>.
The second line insert it.
When you have a url like this www.example.com/#signup, what the browser does is just to focus it's view on the HTML element with id signup, is that right?
Is it possible to change the element's CSS style if it's focused in that way?
E.g. let's say I have a div element, with the id signup, then if I enter www.example.com, the div's background is white and if I enter www.example.com/#signup it's yellow. Like "emphasizing" the sign up form. Is this at all possible?
:target { background-color: yellow; }
The :target psuedo-class does exactly this.
You can read the window.location.hash property when the page loads and apply the corresponding css classs. Something like:
<script type='text/javascript>
function init(){
var hash = window.location.hash.substr(1);
var element = document.getElementById(hash);
if(element){
element.className += " emphasize";
}
}
</script>
<body onload="init()">
...
</body>
When I use the HTML <base> tag to define a base URL for all relative links on a page, anchor links also refer directly to the base URL. Is there a way to set the base URL that would still allow anchor links to refer to the currently open page?
For example, if I have a page at http://example.com/foo/:
Current behaviour:
<base href="http://example.com/" />
bar <!-- Links to "http://example.com/bar/" -->
baz <!-- Links to "http://example.com/#baz" -->
Desired behaviour:
<base href="http://example.com/" />
bar <!-- Links to "http://example.com/bar/" -->
baz <!-- Links to "http://example.com/foo/#baz" -->
I found a solution on this site: using-base-href-with-anchors that doesn't require jQuery, and here is a working snippet:
<base href="https://example.com/">
/test
Anchor
Or without inline JavaScript, something like this:
document.addEventListener('DOMContentLoaded', function(){
var es = document.getElementsByTagName('a')
for(var i=0; i<es.length; i++){
es[i].addEventListener('click', function(e) {
e.preventDefault()
document.location.hash = e.target.getAttribute('href')
})
}
})
Building upon James Tomasino's answer, this one is slightly more efficient, solves a bug with double hashes in the URL and a syntax error.
$(document).ready(function() {
var pathname = window.location.href.split('#')[0];
$('a[href^="#"]').each(function() {
var $this = $(this),
link = $this.attr('href');
$this.attr('href', pathname + link);
});
});
A little bit of jQuery could probably help you with that. Although base href is working as desired, if you want your links beginning with an anchor (#) to be totally relative, you could hijack all links, check the href property for those starting with #, and rebuild them using the current URL.
$(document).ready(function () {
var pathname = window.location.href;
$('a').each(function () {
var link = $(this).attr('href');
if (link.substr(0,1) == "#") {
$(this).attr('href', pathname + link);
}
});
}
Here's an even shorter, jQuery based version I use in a production environment, and it works well for me.
$().ready(function() {
$("a[href^='\#']").each(function() {
this.href = location.href.split("#")[0] + '#' + this.href.substr(this.href.indexOf('#')+1);
});
});
You could also provide an absolute URL:
<base href="https://example.com/">
test
Rather than this
test
I'm afraid there is no way to solve this without any server-side or browser-side script. You can try the following plain JavaScript (without jQuery) implementation:
document.addEventListener("click", function(event) {
var element = event.target;
if (element.tagName.toLowerCase() == "a" &&
element.getAttribute("href").indexOf("#") === 0) {
element.href = location.href + element.getAttribute("href");
}
});
<base href="https://example.com/">
/test
#test
It also works (unlike the other answers) for dynamically generated (i.e. created with JavaScript) a elements.
If you use PHP, you can use following function to generate anchor links:
function generateAnchorLink($anchor) {
$currentURL = "//{$_SERVER['HTTP_HOST']}{$_SERVER['REQUEST_URI']}";
$escaped = htmlspecialchars($currentURL, ENT_QUOTES, 'UTF-8');
return $escaped . '#' . $anchor;
}
Use it in the code like that:
baz
To prevent multiple #s in a URL:
document.addEventListener("click", function(event) {
var element = event.target;
if (element.tagName.toLowerCase() == "a" &&
element.getAttribute("href").indexOf("#") === 0) {
my_href = location.href + element.getAttribute("href");
my_href = my_href.replace(/#+/g, '#');
element.href = my_href;
}
});
My approach is to search for all links to an anchor, and prefix them with the document URL.
This only requires JavaScript on the initial page load and preserves browser features like opening links in a new tab. It also and doesn't depend on jQuery, etc.
document.addEventListener('DOMContentLoaded', function() {
// Get the current URL, removing any fragment
var documentUrl = document.location.href.replace(/#.*$/, '')
// Iterate through all links
var linkEls = document.getElementsByTagName('A')
for (var linkIndex = 0; linkIndex < linkEls.length; linkIndex++) {
var linkEl = linkEls[linkIndex]
// Ignore links that don't begin with #
if (!linkEl.getAttribute('href').match(/^#/)) {
continue;
}
// Convert to an absolute URL
linkEl.setAttribute('href', documentUrl + linkEl.getAttribute('href'))
}
})
You can use some JavaScript code inside the tag that links.
<span onclick="javascript:var mytarget=((document.location.href.indexOf('#')==-1)? document.location.href + '#destination_anchor' : document.location.href);document.location.href=mytarget;return false;" style="display:inline-block;border:1px solid;border-radius:0.3rem"
>Text of link</span>
How does it work when the user clicks?
First it checks if the anchor (#) is already present in the URL. The condition is tested before the "?" sign. This is to avoid the anchor being added twice in the URL if the user clicks again the same link, since the redirection then wouldn't work.
If there is sharp sign (#) in the existing URL, the anchor is appended to it and the result is saved in the mytarget variable. Else, keep the page URL unchanged.
Lastly, go to the (modified or unchanged) URL stored by the mytarget variable.
Instead of <span>, you can also use <div> or even <a> tags.
I would suggest avoiding <a> in order to avoid any unwanted redirection if JavaScript is disabled or not working, and emulate the look of your <a> tag with some CSS styling.
If, despite this, you want to use the <a> tag, don't forget adding return false; at the end of the JavaScript code and set the href attribute like this <a onclick="here the JavaScript code;return false;" href="javascript:return false;">...</a>.
From the example given in the question. To achieve the desired behavior, I do not see the need of using a "base" tag at all.
The page is at http://example.com/foo/
The below code will give the desired behaviour:
bar <!-- Links to "http://example.com/bar/" -->
baz <!-- Links to "http://example.com/foo/#baz" -->
The trick is to use "/" at the beginning of string href="/bar/".
If you're using Angular 2 or later (and just targeting the web), you can do this:
File component.ts
document = document; // Make document available in template
File component.html
<a [href]="document.location.pathname + '#' + anchorName">Click Here</a>