Need help with this script please..

J

Johnny Knoxville

I've added a favicon to my site (http://lazyape.filetap.com/) which works
fine if you add the site to favourites the normal way, but I have some
JavaScript code on a couple of pages with a link, which when you click it
bookmarks the site (much easier). The favicon is never saved if the site
is bookmarked this way. Does anyone have any ideas how to fix this??

This is the code:

<script language="JavaScript">

<!-- Begin
if ((navigator.appName == "Microsoft Internet Explorer") && (parseInt
(navigator.appVersion) >= 4)) {

var url="http://www.YOURSITE.com";
var title="YOURSITE";

document.write('<A HREF="java script:window.ext');
document.write('ernal.AddFavorite(url,title);" ');
document.write('onMouseOver=" window.status=');
document.write("'Add YOURSITE to your favorites!'; return true ");
document.write('"onMouseOut=" window.status=');
document.write("' '; return true ");
document.write('"><font size="2" face="Arial, Helvetica, sans-serif">
Bookmark our Site!</a></font>');
}
else {
var msg = "Bookmark our site!";
if(navigator.appName == "Netscape") msg += " Press CTRL+D keys";
document.write(msg);
}

// End -->

</script>

Thanks for your help.
 
R

Richard Cornford

Johnny Knoxville said:
I've added a favicon to my site (http://lazyape.filetap.com/) which
works fine if you add the site to favourites the normal way, but I
have some JavaScript code on a couple of pages with a link, which
when you click it bookmarks the site (much easier). The favicon is
never saved if the site is bookmarked this way. Does anyone have any
ideas how to fix this??

Attempting to reproduce normal browser behaviour within a web page falls
into the category of "reinventing the wheal" and even expertly
implemented the result is often square.
This is the code:

<script language="JavaScript">

The language attribute is deprecated in HTML 4+ while the type attribute
is required.

<!-- Begin

This wrapping script element contents in HTML comments to "hide them
from older browsers" is no longer needed as the "older browsers" that it
defended against have long since gone out of use.
if ((navigator.appName == "Microsoft Internet Explorer") &&
(parseInt(navigator.appVersion) >= 4)) {

Browser detecting based on the properties of the navigator object is
utterly meaningless. The code above might send at least the vast
majority of IE browsers into this branch of the code but it will also
pass a significant number of other browsers spoofing IE but still
incapable of the task the resulting HTML will imply is possible.

Examining the navigator object properties (apart from being next to
useless for the task) is also an unnecessary process as the output HTML
event handler is going to attempt to execute the AddFavorite method of
the external object. So the test logic for this branch should be testing
for the existence of those to objects:-

if(window.external)&(external.addFavorite)){

-which matches the decision to write the A element into the page with
the browsers ability to execute the code it contains with the greatest
precision posible.
var url="http://www.YOURSITE.com";
var title="YOURSITE";

document.write('<A HREF="java script:window.ext');

The space between "java" and "script" in the above javascript: pseudo
protocol URL will prevent it form working, but it is unwise to use
javascript pseudo protocol URLs in HREF attributes to execute
side-effect code as some browsers (including versions of IE) take
activation of the HREF as navigation and put the current page into a
waiting state in which various resource hungry tasks are shut down
pending the arrival of the result of the navigation (which will never
arrive)).

For an A element the JavaScript code should probably be executed in an
onclick event handler (which has to return false to prevent the
navigation specified in the HREF, which could itself be empty or "#" in
this case as JavaScritp support is implied by the fact that the link has
been written into the page).

However, from the usability point of view, an A element may not be the
best choice for this functionality as users have experienced A elements
as a vehicle for navigation and are used to them performing that role.
An <input type="button"> or <button type="button"> element might be
better suited to the task (though Netscape 4 does not recognise the
latter and would require the former to be placed in a form (not that
important in this branch of the code as only IE supports the external
object)).
document.write('ernal.AddFavorite(url,title);" ');
document.write('onMouseOver=" window.status=');
document.write("'Add YOURSITE to your favorites!'; return true ");
document.write('"onMouseOut=" window.status=');
document.write("' '; return true ");
document.write('"><font size="2" face="Arial, Helvetica, sans-serif">

Font tags are deprecated in HTML 4 (and invalid in strict HTML 4), CSS
styling would be more appropriate in this context (as IE 4+ would have
no problems applying font face and size to this element).
Bookmark our Site!</a></font>');

The sequence of HTML output by this script has gone: opening A tag,
opening FONT tag, closing A tag, closing FONT tag. That is the sort of
nonsense HTML that Microsoft Word outputs and is totally wrong. HTML
elements may not overlap each other in that way they may only contain
each other, FONT should be entirely within A or A should be entirely
within FONT.

That is such a rudimentary mistake that I would take it a grounds to
identify whichever site you found this script on and never visit it
again as its author clearly has not even grasped the fundamentals.
}
else {
var msg = "Bookmark our site!";
if(navigator.appName == "Netscape") msg += " Press CTRL+D keys";

This navigator.appName test is just as meaningless as the first and
there is no relationship between "Netscape" appearing in the appName
property and the use of the key sequence CTRL+D to bookmark a site.
Unfortunately, there is no mechanism by which JavaScript can determine
the bookmaking keyboard shortcut on a browser that does not have an
external.AddFavorite function so writing anything at this point stands a
realistic chance of being misguiding to the reader. It would probably be
best to abandon this - else - branch of the code and rely on the user
having enough nouce to know how to bookmark a page on their own browser
(they don’t all have air between their ears).
document.write(msg);
}

// End -->

</script>

Thanks for your help.

I doubt that this was much help (apart from the advice to give wherever
you fond this script a wide berth in future). If the perceived need to
use this script arises from the use of window.open to attempt to deny
the user the use of their browser menus, or from the use of framesets,
then the best solution would be to stop doing that. If it is just a
bells and whistles extra then trim it down to only act on an
external.AddFavorite supporting browser, or don't bother at all.

Richard.
 
R

Richard Cornford

Doesn't fly in my IE6. Adding the missing ( from the if test
still doesn't let it work.
Adding the second & to it still doesn't let it pass:

Opps! I really messed that up. I do have an excuse but it is not at all
good so I won’t bother explaining.
if((window.external)&&(external.addFavorite)){
alert('I support it')
}
still gives no alert in IE6.

if (window.external){
alert('I support window.external')
}
else{
alert('I dont support window.external')
}

Adding a test for window.external.addFavorite utterly
breaks it:
if (window.external.addFavorite){
alert('I support window.external.addFavorite')
}
else{
alert('I dont support window.externaladdFavorite')
}

IE6 will give me no alert at all.

I had a look at the listings from my DOM scanning script before posting
and confirmed my recollection that a typeof test on any of the function
properties of the external object throws an "Object doesn't support this
property or method" exception, but I assumed that my script would not
have listed the properties if they did not type-convert to true. But
apparently they don’t and my script is listing them precisely because
they did throw the exception when tested with typeof (where undefined
properties of the external object don’t).

Obviously testing for the existence of AddFavourite by executing a
typeof test within a try-catch block and then calling the function only
if the browser throws an "Object doesn't support this property or
method" exception isn’t a viable strategy for determining if the
function exists.
To make it even more confusing, addfavorite seems to be case
insensitive:

That seems to be true of all of the external object’s function
properties, probably a VBScript compatibility thing.
http://tinyurl.com/t9dx
Is a c.l.j article covering a lot of this. I still can't find
a valid test that will test for the existence of .addfavorite
in window.external :-(

I notice that the external object has a - QueryInterface – function, but
even if applicable to the problem of checking AddFavourite its existence
doesn’t move the problem forward as it suffers from exactly the same
unusual behaviour as the AddFavourite function.

Oh well, it looks like there is no test (at least not a sane one) and:-

if(window.external){
// so infer the expected
// properties of the external object
}

-is as good as it gets. Which is not quite good enough. But then I think
that an Add Favourite button is a bad idea to start with. My 5 year old
niece can add a URL to the favourites, and she is only just starting to
be able to read, so I think most users will have figured out how to do
it for themselves.

Richard.
 
J

Johnny Knoxville

Thanks for your replies. I can't believe I didn't even see the <font>/
<a> error in there. I did some more reading up on javascript (rather than
just finding a code, trusting in and copy/pasting it in).

I'd like to put an "Add Bookmark" link onto my site, just to prompt
people to do it, in case it doesn't come to mind! But I didn't want to
use a button - a link would fit much better with the look of the site.

Would something like this be more like it:

<html>
<head>

<script type="text/javascript">
function bookmark()
{
window.external.AddFavorite("http://www.mywebsite.com","My Site")
}
</script>

</head>

<body>

<a href="javascript:bookmark()" onmouseover=" window.status='Add :: My
Site :: to favorites!'; return true" onmouseout=" window.status='';
return true">Bookmark This Site</a>

</body>
</html>

Thanks again.
 
J

Johnny Knoxville

Still, why should the favicon only work when the site is added to favorites
the normal way?
 
R

Richard Cornford

I'd like to put an "Add Bookmark" link onto my site, just to
prompt people to do it, in case it doesn't come to mind! But
I didn't want to use a button - a link would fit much better
with the look of the site.

Presentation, if that is your only reason for insisting on using a link,
is best addressed with CSS. However, what makes you think that people
who you will not credit with enough common sense to realise that they
can bookmark a web site if they want to will interpret a hyperlink with
the text "Bookmark This Site" as a control for bookmaking your site
instead of maybe a recommendation to visit and bookmark some 3rd party
site?
Would something like this be more like it:

No, this is worse. You have failed to grasp the point of Randy and I
discussing the practicalities of techniques for verifying the browser's
support for external.AddFavorite.

Your code faces three realistic possibilities; 1. Encountering a browser
that does not support JavaScript or has had JavaScript disabled. 2.
Encountering a JavaScript capable browser that does not implement the
window.external object or implements but without the AddFavourite
method. 3. Being loaded into a browser that is willing to execute
JavaScript and implements a window.external object with an AddFavourite
method (apparently only true for a subset of Microsoft IE browsers,
excluding, at least, the AOL branded version). No script that attempts
to automate part of the bookmaking of the site will work on any but the
final possibility, and it would be a very bad idea to present a user
(assuming that they did understand its purpose) with a link that claims
to automate the bookmaking of a site under circumstances where it will
not.

By using a document.write statement to add the link to the HTML the
original script successfully addressed the possibility of the browser
not supporting JavaScript because in that case the link would never be
added to the page so the user could not be mislead by the inclusion of a
non functional link in the page. However, the original script failed to
distinguish between browsers that were capable of executing the
external.AddFavourite statement and those that could not because it
based the decision on the unrelated properties of the navigator object.
Randy and I are proposing basing that decision on the existence of the
window.external object, because the existence of that object has a
direct baring on the existence of the window.external object. It would
be nice to also be able to confirm the existence of the AddFavourite
method but that appears to be impractical, meaning that the script
cannot distinguish between a browser that has an external object but
does not implement the AddFavourite method and a browser that fully
reproduces an IE style external object.

<a href="javascript:bookmark()" ...
<snip>

To save yourself unnecessary future grief, never use a javascript:
pseudo-protocol HREF to execute a function as a side-effect. Instead use
the onclick attribute (possibly returning false to cancel the navigation
specified in the HREF) to execute JavaScript functions.

Richard.
 
J

Johnny Knoxville

OK, sorry I thought you were recommending I didn't bother testing for
browser compatibility earlier.

Reading over what you suggested, I need something along these lines...

<html>
<body>

<script type="text/javascript">
function bookmark()
{
window.external.AddFavorite("http://www.mywebsite.com","My Site")
}

if (window.external) {
document.write('<a href="home.html" onclick="bookmark(); return false"
onmouseover="

window.status='Add :: My Site :: to favorites!'; return true"
onmouseout=" window.status=''; return

true">Bookmark This Site</a>');
}

</script>

</body>
</html>

Forgive me for being new to javascript. I know this doesn't work, but I
don't know why. I tried to get the browser test in there, and also put
in an on-click command instead. Am I getting closer? Why doesn't this
work?

Thanks.
 
R

Richard Cornford

<html>
<body>

<script type="text/javascript">
function bookmark()
{
window.external.AddFavorite("http://www.mywebsite.com","My Site")
}

if (window.external) {
document.write('<a href="home.html" onclick="bookmark();
return false" onmouseover="window.status='Add ::
My Site :: to favorites!'; return true"
onmouseout=" window.status=''; return
true">Bookmark This Site</a>');
}

</script>

</body>
</html>
Why doesn't this work?

Quote nesting in your string literal. JavaScript allows strings literals
to be defined with either single or double quotes. If double quotes are
used then single quotes may appear within the string and be treated as
literal characters. If single quotes define a string then double quotes
within the string will be treated as literal characters. However, the
string that you pass to the document.write function is defined with
single quotes, it contains double quotes, which will be treated as
literal characters, but it also contains single quote characters, the
first of which will be treated as terminating the string literal,
rendering the rest of the string a syntax error.

To avoid the problem quote characters that are needed within a string
that is defined using the same type of quote character must be escaped
by preceding them with the - \ - (escape) character.

Fix that and the code works, at least as well as it is ever going to.

Richard.
 

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

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,582
Members
45,062
Latest member
OrderKetozenseACV

Latest Threads

Top