This question already has answers here:
Replace the directory of an image src, using Javascript
(2 answers)
Replace images source for all images
(3 answers)
Closed 5 years ago.
I am trying to make a custom style for the stylish plugin to use for the Eve Online forums. I am attempting to resize the avatar image because it was too small for my liking. However it's using a low-quality image and it looks too grainy when resized, so I am trying to figure out how to use the larger image by replacing part of the text, or replacing the url (whatever is easier). In the image, the only difference a piece of text that shows the size.
See:
meta.eveonline.com/erika_mizune/45/2168_1.png
meta.eveonline.com/erika_mizune/90/2168_1.png
So essentially the 45 (original) needs to be replaced with the 90 in order to look less grainy.
URL to Post: https://meta.eveonline.com/t/avatar-size-category-adjustment/9032
Stylish Plugin: https://userstyles.org/styles/144974/avatar-category-adjustment
My code to resize the image is this:
.topic-avatar img.avatar
{
height: 75px;
width: 75px;
border-radius: 0;
}
.topic-avatar
{
width: 75px !important;
}
I tried to search before posting but I'm not finding anything that will work for what I need.
Thanks!
Edit 1: I attempted to switch to tampermonkey to use JS as suggested but is not working. Below is the origional code:
<div class="topic-avatar">
<a class="trigger-user-card main-avatar" href="/u/Erika_Mizune"
data-user-card="Erika_Mizune"> <img alt="" width="45" height="45"
src="https://cdn-enterprise.discourse.org/eveonline/user_avatar/meta.eveonline.com/erika_mizune/45/2168_1.png"
title="Erika_Mizune" class="avatar"></a>
<div class="poster-avatar-extra"></div>
</div>
And the script I have in tampermonkey:
var imagelist = document.getElementsByClassName("avatar");
imagelist.foreach(function(element) {
element.src = element.src.replace("/45/", "/90/");
});
Edit 2: After trying to use debugging in the console I got the error that .foreach is not a function and attempted to try the following as well:
Try 1:
var imagelist = document.getElementsByTagName("img");
imagelist.foreach(function(element) {
element.src = element.src.replace("/45/", "/90/");
});
Try 2:
var imagelist = Array.from(document.getElementsByClassName('avatar'));
imagelist.foreach(function(element) {
element.src = element.src.replace("/45/", "/90/");
});
Try 3:
var imagelist = Array.from(document.getElementsByTagName('img'));
imagelist.foreach(function(element) {
element.src = element.src.replace("/45/", "/90/");
});
All of these attempts have returned the same error in console that .foreach is not a function.
I think the javascript solution is the right way to go.
It's really hard to say what's wrong with just a few lines of js from tampermonkey. Is it possible to show the complete files? Or post an example on jsfiddle or something?
It's easy to debug this kind of issue yourself in Chrome Inspector, by typing "debugger" in your code and opening the Source tab in Chrome Inspector (F12 button in Chrome). The inspector will stop at that line and you can see the values of different variables. For example:
First, open Chrome Inspector in Chrome browser. Then load the page with the debugger line:
var imagelist = document.getElementsByClassName("forum_image_class");
debugger;
imagelist.foreach(function(element){
element.src = element.src.replace("/45/", "/90/");
}
The browser will stop on the debugger line. Type 'imagelist' into the console and hit enter to see its current value. It might be empty, in which case the getElementsByClassName isnt retrieving anything. Which might be happening for a few different reasons. Or the imagelist array might get populated but the replace() isnt working as expected. Is it possible for you to figure out which is happenng and report it here?
ALSO: be careful with .replace(). You have to escape certain characters with a backslash and you should know what those special characters are. In this case you may or may not need to escape the forward slashes.
Try this? Add background: url(meta.eveonline.com/erika_mizune/90/2168_1.png) no-repeat !important; to your img CSS.
.topic-avatar img.avatar {
height: 75px;
width: 75px;
border-radius: 0;
background: url(meta.eveonline.com/erika_mizune/90/2168_1.png) no-repeat !important;
}
.topic-avatar {
width: 75px !important;
}
It isn't possible to change html content with CSS in the way you're describing. I'd recommend using Javascript to change the src of the <img> tag. Do something like
var imagelist = document.getElementsByClassName("forum_image_class");
imagelist.foreach(function(element){
element.src = element.src.replace("/45/", "/90/");
}
Related
I'm writing some automation for a website of ours in Internet Explorer (it has to be IE :< ) and I ran into some issues with execute_script. I need to move a vertical splitbar over 200px so it doesn't move certain elements off the page, making them unclickable. To do this I figured I would use the Watir::Browser#execute_script functionality. The idea would be to change the style tag to the correct coordinates. Unfortunately I haven't been able to get it to work due to "Element is no longer valid" errors. Here are the two cases I tried and their respective errors.
First, I tried just getting the style attribute (the one I need to change) via a javascript script.
script = <<-JS
return arguments[0].style
JS
browser.execute_script(script, aw.watir.div(class: 'x-vsplitbar'))
This gives me Uncaught exception: Element is no longer valid
I also tried changing the element's tag as well.
element = aw.watir.div(class: 'x-vsplitbar')
style = element.style.gsub('200', '400')
script = "return arguments[0].style = '#{style}'"
browser.execute_script(script, element)
This just gave me a sweet error JavaScript error (Selenium::WebDriver::Error::JavascriptError)
The script in this example comes out to:
return arguments[0].style = 'HEIGHT: 897px; WIDTH: 5px; POSITION: absolute; LEFT: 400px; TOP: 50px'
Not sure what I'm doing wrong here, I followed this guide.
Another solution would be to use Watir to simulate the dragging action needed but I couldn't figure out how to drag the bar to the right.
I'm building a website that contains divs with background images. I'm very new to JavaScript. I want to preload the images so when you go to the site you don't have to wait and view a blank box when the image is loading. I'm using this preload code, but when I go to the site the images are still loading slowly. Is there a way to make this faster?
<script>
$(document).ready( function() {
var c = new Image();
c.onload = function(){
$("#contenthome").css("background-image", "url(../Images/Homepage.png)");
}
c.src = "url(../Images/Homepage.png)";
});
</script>
This is not directly approachable but has two solutions.
This question's solution needs some understanding about server side request headers specifying caching information. I am used to appengine so I set expiry to about a month or so. Caching is all about suggesting a browser to "keep the following images with you for a while, don't take from me each time you need them". according to your server side language, it is worth spending so that you will master this important thing in browser environment.
And, you must play some trick if your user should not see a set of blank boxes while the images load. in fact, you style them invisible, and once loaded, you make them visible. since you are using jquery, you can use something like
$(window).load(
function(){ $('#showAfterLoadingComplete').show("slow").fadeIn(); }
A page of example is here
Try this:
<script>
$(function() {
var c = new Image();
$(c).load(function(){
$("#contenthome").css("background-image", "url(../Images/Homepage.png)");
$(this).attr('src','../Images/Homepage.png').show();
}).hide();
});
</script>
I would suggest employing a different method. Javascript has to wait for the page to load in order to work right, which inherently will introduce a delay.
Why not base 64 encode all your images into css classes in a dedicated css document.
You can use a site like this to convert your images:
http://webcodertools.com/imagetobase64converter
Then paste the Data URI into the background-image property in your css class.
Your eventual markup could look something like this:
<div id="contenthome">[some content]</div>
And your CSS would look something like this:
#contenthome {
background: [DATA URI] /*I didn't paste the actual URI here, as it would be quite long and unruly */
no-repeat
50% 50%;
background-size: contain;
display: inline-block;
height: auto;
width: auto;
}
You may have to play around with the height, width, background-size, and display properties to get it to show just right.
You could even take a further step and use a cache manifest to explicitly cache your css files so the load times are even faster.
How to calculate the width of an input HTML element so that it matches the size of its content ?
I already update an input on the fly as the user types :
<input type='text' onkeydown='this.size=this.value.length' />
However, this does not seem completely correct because it does not take into account the fact that some characters are longer than others :
I will get more and more whitespace if I type only some "l" characters
the size will be insufficient if I type only some "w" characters
How to proceed?
PS: Why I want to do this (already answered this in a answer that was deleted)?
I have sentences in which I have to replace the bracket content by inputs (ex: [user] is [years] old). I have no idea what the sentence can be, so I do not know an adequate length for the inputs, and I would like to keep it readable on one line (avoiding too much whitespace).
You could use a (hidden) canvas and the measureText() method of the context to get your string's width.
EDIT:
Looks fast enough.
First, define some CSS...
input,
#input-helper {
display: inline;
font-size: 14px;
font-family: serif;
line-height: 16px;
}
#input-helper {
position: absolute;
top: -10000px;
}
...then use some JavaScript...
var div = document.createElement("div");
div.id = "input-helper";
document.body.appendChild(div);
var input = document.querySelector("input");
input.addEventListener("keyup", function() {
div.textContent = this.value;
input.style.width = div.offsetWidth + "px";
});
jsFiddle.
You will want to choose a reasonable start width for your input element too.
If using jQuery is not a problem, here is a demo I put together on jsFiddle. It uses an Autoexpand.js file that does what you want. Check out the last example in the fiddle.
Some specifics:
It's based on .keyup and .keypress for the fastest response possible.
It takes into account the HTML markup that's pasted into the box. Things like linebreaks are dealt with.
The source file shows smart processing by taking everything about the font into consideration.
Also included in the jsFiddle are links to download a pastebin version of the fiddle since jsFiddle Sandbox breaks in IE8. That said, it also works in IE7 too!
First : Add this div where you want
<div id="calcsize" style="display:none;"></div>
Second : Use this function
function getWidthof(txt)
{
$('#calcsize').empty().append(txt);
return $('#calcsize').width();
}
EDIT: In response to many comments I do know that there is no sure fire way to fully protect an image from being downloaded. This method is to prevent the casual user from downloading by simple right click. The best way probably would be simply copyrighting your images and if you are very concerned would be using a service like Digimarc to digitally watermark your image. Now to the question:
I came across a site that is using a GIF overlay over their actual image so it protects the image from users right clicking and downloading the image (though you can still grab the actual image from within the code). The code they use to do this is:
<div><img src="-Transparent GIF File-" alt="" width="530" height="558"
border="0" original="-Actual Image Displayed-" /></div>
My question is the original tag is not a real tag and is used and translated by Javascript of some sort. I would like to replicate this on my site. Can someone help me find this script?
This is pointless. If a browser displays an image, it can be taken. Any attempt to prevent that is merely site overhead that can very easily be circumvented.
You're best protection is to put a copyright notice on the images themselves.
In any event, if you really want to swap the original attribute you can...
$(function() {
var o = $('img').attr('original');
$('img').attr('src', o);
});
Demo here
but... that doesn't do anything to prevent the user selecting and saving the image tied tot eh original attribute.
A simpler solution for what you're trying to accomplish is to add all of these attributes to the img tag:
ondrag="return false"
ondragstart="return false"
oncontextmenu="return false"
galleryimg="no"
onmousedown="return false"
Also, to optionally make the image print smaller, add this to the img tag:
class="imgPrint"
And include this related CSS:
#media print
{
.imgPrint
{
width: 40%;
}
}
You can do this without original tag also :
http://rainbow.arch.scriptmania.com/scripts/no_right_click.html
see this link.
I think this is what u want, this link may help you.
This is my implementation for a light protection of images.
It will create a transparent cover DOM element over the image (or text). If you disable javascript the image will be hidden and if you remove the cover the image will be hidden on mouse over. Also right click on images is disabled.
You can always printscreen, grab from the downloaded resources, etc, etc. This will only filter the most basic ways of download. But for a more convenient protection you have to hide the image path and render to a canvas object.
You can improve this, but there is always a method to get the image.
Tested on major browsers and working!
HTML
<div class="covered">
<img src="image.jpg" alt="" />
</div>
JAVASCRIPT + JQUERY
$('.covered').each( function () {
$(this).append('<cover></cover>');
$(this).mousedown(function(e){
if( e.button == 2 ) {
e.preventDefault();
return false;
}
return true;
});
$('img', this).css('display', 'block');
$(this).hover(function(){
var el = $('cover', this);
if (el.length <= 0) {
$(this).html('');
}
});
});
CSS
cover
{
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
}
.covered
{
position: relative;
}
.covered img
{
display: none;
}
I have some simple javascript that I'm using to auto-adjust the width of elements on pages and to vertically center the text on these pages.
My script works, but in IE9 and a little in Safari there is a distinct moment where the elements are not resized and they jump across the page. It's just a momentary flash, but it bugs me as I'm generally not a "good enough" kind of person. Here is my own script:
$(document).ready(function() {
var containerwidth = $("#main_content").css("width");
var picwidth = $(".picture").css("width");
$(".picture").parent().css("width", picwidth);
var correctwidth = parseInt(containerwidth) - parseInt(picwidth);
$(".main-text").css("width",correctwidth-25);
if( $(".margins").css("width") ) {
$(".title").css("width", parseInt($(".width-set").css("width"))+10);
} else {
$(".title").css("width", parseInt($(".title").parent().css("width"))-10);
}
var container_height = $(".main-text").height();
var text_height = $(".vert-align").height();
var offset = (container_height - text_height) / 2;
$(".vert-align").css("margin-top", offset);
[...]
});
I realize the use of explicit offsets and whatnot is hackish, but I'm in a hurry and will correct it later. And yes, I am using jQuery.
This is stored in a file, and I've tried both calling it in the head, and also directly after the elements it affects, but the result is the same. Is this jitter just a fact of life for using element manipulation with javascript, or is there some solution I've missed on the forums?
Thanks!
I suspect the reason is because you are calling this in the $(document).ready(), which runs after the DOM is loaded (i.e. your elements are already displayed).
If you absolutely have to resize elements after they've loaded, the only thing I can think of that might help is having an overlay that covers the entire window, maybe something like:
#overlay{
position: fixed;
width: 100%; height: 100%;
background: #fff;
z-index: 9001;
}
And then hiding the overlay via $("#overlay").hide() after the resizing in your $(document).ready() function. I haven't tested this so I don't know if it works. You might have to add a short setTimeOut as well.
To be honest, though, this solution feels very dirty. Hopefully someone else can think of something more elegant.
#ZDYN is correct. The "flicker" happens when the page is displayed but the jQuery code has not been executed.
You can try to set in the css your elements to "visibility: hidden" so they will have their dimensions for the calculations, then change the visibility to "visible" after the resizing.