inheritance problem

0

0m4r

Hello,
I'm quite new with Javascript and so actually I'm trying to learn
something about it.
I want to "extend" the Image DOM element, so I wrote this Javascript
code:

=== MyImg.js ===
function MyImg(imgsrc){
this.src = imgsrc;
}
MyImg.prototype = new Image();
=== /MyImg.js ===

Then I put this code int an HTML page:

=== index.html ==
[...some HTML header stuff...]
<script language=..... >
function load(){

var container = document.getElementById("test1");
var container1 = document.getElementById("test2");

var gImg = new MyImg("Image1.jpg");
var gImg1 = new MyImg("Image2.jpg");

container.appendChild(gImg);
container.appendChild(gImg1);

container1.innerHTML = gImg.src + "<br>" + gImg1.src;
</script>
</head>
<body onload="load">
<div id="test1"/>
<div id="test2"/>
</body>
</html>
=== /index.html ===

and here is the result I have back:

=== generated HTML code ===
<div id="test1">
<img src="Image2.jpg"/>
</div>
<div id="test2">
Image2.jpg<br/>Image2.jpg
</div>
=== /generated HTML code ===

Instead of what I expect:

=== expected HTML code ===
<div id="test1">
<img src="Image1.jpg"/>
<img src="Image2.jpg"/>
</div>
<div id="test2">
Image1.jpg<br/>Image2.jpg
</div>
=== /expected HTML code ===


Where I'm wrong? Could anybody help me?

Thanks a lot,
Omar
 
R

RobG

Hello,
I'm quite new with Javascript and so actually I'm trying to learn
something about it.
I want to "extend" the Image DOM element, so I wrote this Javascript
code:

=== MyImg.js ===
function MyImg(imgsrc){
this.src = imgsrc;}

MyImg.prototype = new Image();
=== /MyImg.js ===

Then I put this code int an HTML page:

=== index.html ==
[...some HTML header stuff...]
<script language=..... >

The language attribute is deprecated, type is required.

function load(){

var container = document.getElementById("test1");
var container1 = document.getElementById("test2");

var gImg = new MyImg("Image1.jpg");
var gImg1 = new MyImg("Image2.jpg");

container.appendChild(gImg);
container.appendChild(gImg1);

appendChild expects its argument to be a HTML element that implements
the Node interface. For some browsers, your use of new Image() on the
prototype chain fits the bill, in others, not. It is a risky strategy
that is bound to fail a good percentage of the time.

container1.innerHTML = gImg.src + "<br>" + gImg1.src;
</script>
</head>
<body onload="load">

In order to execute the function referenced by 'load', you need to add
the call operator:

<div id="test1"/>

That is invalid HTML. For div elements, the closing tag is required.

<div id="test2"/>
</body>
</html>
=== /index.html ===

and here is the result I have back:

In some browsers you will get a syntax error due to the previously
mentioned issue with appendChild.

=== generated HTML code ===
<div id="test1">
<img src="Image2.jpg"/>

I'll bet there isn't a browser out there that returns that as HTML.
Firefox returns:

<div id="test1">
<div id="test2">file:///Users/rogreen/Desktop/Image2.jpg<br>file:///
Users/rob/Desktop/Image2.jpg said:
</div>
<div id="test2">
Image2.jpg<br/>Image2.jpg
</div> [...]

Where I'm wrong? Could anybody help me?

Use valid HTML. If you want to build DOM Image elements, then do
that.


<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<head>
<title>foo</title>
<script type="text/javascript">

function load(){

var container = document.getElementById("test1");
var container1 = document.getElementById("test2");

var gImg = new Image();
gImg.src = "Image1.jpg";
var gImg1 = new Image();
gImg1.src = "Image2.jpg";

container.appendChild(gImg);
container.appendChild(gImg1);
container1.innerHTML = gImg.src + "<br>" + gImg1.src;
}
</script>
</head>
<body onload="load()">
<div id="test1"></div>
<div id="test2"></div>
</body>
 
M

Marcos Toledo

Hi Omar, Rob,

This question actually got me thinking a lot. Although I agree with
Rob in the details about your HTML (div closing, languague, etc), and
all the discouraging about extending the "Image" DOM Object, I think
the question has bigger merits, even if theoretically, which got me
thinking as well.

Your actual result contain only a single element inside the test div,
instead of the expected 2. And it is, apparently, only the second
element, but I noticed something:

When you define "Image" as your prototype, by the time you instantiate
the first Image, all of the attributes your object has are the
attributes found in the Image prototype. This means that, by the time
you are assining this.src the value in the parameter, this is an
actual image.

When you create your second instance, with "Image2.jpg", due to the
prototype chain, you also have all of the attributes found in the
Image prototype assined the this. Though, the weird part is:

*The src attribute found when creating the second image, is
"Image1.jpg"*

This means that, internally, the 1st object and the 2nd object created
through your constructors are actually the same. The src in the 1st is
overriden with the 2nd, and the appendChild fails, because the object
has already been appended.

This wouldn't happen if you mimicked all of the DOM Image object's
attributes and assigned it to another non-dom object, say, Image2
{src:''};, and added that new object to the prototype instead of
Image.

This has led me to the conclusion that the prototype chain works in a
different way when you have DOM Objects in it, than when you have
actual objects.

Am I missing something?

Anyway, good question.

[]s
Toledo
 
0

0m4r

function load(){
appendChild expects its argument to be a HTML element that implements
the Node interface. For some browsers, your use of new Image() on the
prototype chain fits the bill, in others, not. It is a risky strategy
that is bound to fail a good percentage of the time.

Mmmmh... So which would be a good solution to prevent this?

Use valid HTML. If you want to build DOM Image elements, then do
that.

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<head>
<title>foo</title>
<script type="text/javascript">

function load(){

var container = document.getElementById("test1");
var container1 = document.getElementById("test2");

var gImg = new Image();
gImg.src = "Image1.jpg";
var gImg1 = new Image();
gImg1.src = "Image2.jpg";

container.appendChild(gImg);
container.appendChild(gImg1);
container1.innerHTML = gImg.src + "<br>" + gImg1.src;
}
</script>
</head>
<body onload="load()">
<div id="test1"></div>
<div id="test2"></div>
</body>

I fix the <div> issue, but It still doesn't work... I don't want to
use the Image element but a sort of "extension" of the Image DOM
element....

Thanks for your answer!
 
0

0m4r

Hi Omar, Rob,

This question actually got me thinking a lot. Although I agree with
Rob in the details about your HTML (div closing, languague, etc), and
all the discouraging about extending the "Image" DOM Object, I think
the question has bigger merits, even if theoretically, which got me
thinking as well.

Your actual result contain only a single element inside the test div,
instead of the expected 2. And it is, apparently, only the second
element, but I noticed something:

When you define "Image" as your prototype, by the time you instantiate
the first Image, all of the attributes your object has are the
attributes found in the Image prototype. This means that, by the time
you are assining this.src the value in the parameter, this is an
actual image.

When you create your second instance, with "Image2.jpg", due to the
prototype chain, you also have all of the attributes found in the
Image prototype assined the this. Though, the weird part is:

*The src attribute found when creating the second image, is
"Image1.jpg"*

This means that, internally, the 1st object and the 2nd object created
through your constructors are actually the same. The src in the 1st is
overriden with the 2nd, and the appendChild fails, because the object
has already been appended.

This is what I was supposing too... You are confirming my thoughts!
This wouldn't happen if you mimicked all of the DOM Image object's
attributes and assigned it to another non-dom object, say, Image2
{src:''};, and added that new object to the prototype instead of
Image.

How can I do this? I can't figure out how to reproduce the behavior
you are talcking about.
could you pleas wrote me a simple snippet?

anyway, thanks for your answer!

Omar
 
A

Apekatthjerne

This is what I was supposing too... You are confirming my thoughts!


How can I do this? I can't figure out how to reproduce the behavior
you are talcking about.
could you pleas wrote me a simple snippet?

anyway, thanks for your answer!

Omar


I just use this function:

//START
function downloadImage()
{
for(var i = 0, argumentsLength = arguments.length, newImages = []; i
< argumentsLength; i++)
{
newImages = new Image;
newImages.src = arguments;
}
}
//END

So you can call as many as you wish. For example:
//START
downloadImage('logo.gif'); // just one
downloadImage('logo.gif', 'example.jpg', 'footer.png'); // let's have
a few
//END

Apekatthjerne
 
0

0m4r

I just use this function:

//START
function downloadImage()
{
for(var i = 0, argumentsLength = arguments.length, newImages = []; i
< argumentsLength; i++)
{
newImages = new Image;
newImages.src = arguments;
}}

//END

So you can call as many as you wish. For example:
//START
downloadImage('logo.gif'); // just one
downloadImage('logo.gif', 'example.jpg', 'footer.png'); // let's have
a few
//END

Apekatthjerne





Your solution is not the one I was, and I'm actually, looking for...
I need to "extend" a standard DOM object and, as it looks, is ont
possible!
 
D

David Mark

Mmmmh... So which would be a good solution to prevent this?











I fix the <div> issue, but It still doesn't work... I don't want to
use the Image element but a sort of "extension" of the Image DOM
element....

An Image object is not necessarily an image element. Forget the Image
constructor and use createElement to create image elements. Then set
their src properties. No "extensions" necessary.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,777
Messages
2,569,604
Members
45,234
Latest member
SkyeWeems

Latest Threads

Top