Author Topic: Javascript Question This Time  (Read 12703 times)

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« on: March 04, 2012, 05:55:29 PM »
Keep trying to use google to answer this, but can't find an actual answer >.<

I've decided to try keeping my site up to date again because it's a great tool for showing off what I can do and have done.

One of my current hold ups is how I want to redo my about page.  I want to have different sections (history of the site, a "faq" without being asked any qustions, etc.) without having them all displayed simultaneously or having to completely reload the page to display them.  I know that this is possible via javascript as I did it for an expandable menu when I was working for the college IT department.  However, I have no idea if I can create a javascript function outside of the header, especially within a php file (php and javascript, I have learned, don't always play well together).

So, does anyone know if I can create a function in the middle of a php file?
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline TH300

  • Hero Member
  • *****
  • Posts: 1404
    • http://op3game.net
Javascript Question This Time
« Reply #1 on: March 04, 2012, 09:20:19 PM »
Without fully understanding what you want to do:

Why can't you just put the java script function into the header? You can use php to generate the header, including the js function. But I don't see why you'd have to do that. So, maybe you explain a bit more?

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #2 on: March 05, 2012, 12:49:52 AM »
My current navigation system works like this:

The top links send a value to the index.php site which is used by a switch to select which page to include.  In order to save some time and space, the index page require()-integrates a header and a footer file.  My past experiments with using javascript with this system indicates that any functios included in the header will not work within the code of the included pages.

What I want to do is this:

page option 1
page option 2
page option 3

[page text 1]
[page text 2]
[page text 3]

when option 1 is selected, I want text 1 to show and all other texts to hide, same with option and text 2, same with option and text 3 ad infinitum.

I know this can be done with a function that looks for a specific tag (most common one to use being <div>), but I don't know all the limitations in the interaction of php and javascript
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline Hooman

  • Administrator
  • Hero Member
  • *****
  • Posts: 4955
Javascript Question This Time
« Reply #3 on: March 05, 2012, 03:48:15 AM »
This is perfectly feasible to do. Occasionally, when you embed one language within another, you may have to add extra escapes around special characters, but otherwise, there should be no problem.

However, there is probably a better way to do it.

It's generally considered good practice to keep your JavaScript code separate from the HTML (or PHP) code, and just link to it. You can link to the JavaScript from the header, or anywhere in the body. The header and the very end of the body tend to be the most popular places to link in JavaScript.

I can maybe dig up some links for you giving the details of how. I believe they also did a reasonable job explaining the why aspect as well.


If you insist on going the JavaScript embedded in PHP route, then just remember that PHP is processed on the server, and the JavaScript is run on the client. The server uses PHP to generate output, which gets sent to the client as a file, which is parsed by the web browser, and then JavaScript is executed there. There should be no interaction between JavaScript and PHP (other than possibly encoding specially interpreted characters when you embed one in the other). The JavaScript is just along for the ride from source file to server output. It doesn't gain any meaning until the client web browser processes it.


I have most of the relevant JavaScript links saved on my work computer so I'll have to get back to you with those. But meanwhile, I found this site very useful for web development reference:
http://www.tizag.com/
I find they have a very clean design, it's not loaded with ads, good technical content which isn't too superficial or dumbed down. I can't remember now, but it might have treated certain web technologies a little more in depth than others. (Perhaps more details on JavaScript than HTML?)

Also, after poking around a bit with Google, I think "Unobtrusive JavaScript", or "Separating Behavior From Structure" may be relevant search terms for articles of interest.




As for your specific problem, do you plan to have all data already loaded on the page, but some of it invisible? Or do you plan to load some of it on demand? For small sections, it's probably faster to use the first method, but for large sections, or a large number of sections, the second method may be better.
 

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #4 on: March 05, 2012, 11:03:45 AM »
I loved tizag when learning php for those very same reasons and that they didn't keep reitterating the same point over and over.

If there is another way to do it without javascript, I'm willing to consider it.  I just don't want a full page reload to swith between text sections.

My plan was to have everything fully loaded but hidden.  That's what I worked with before and I liked the results.

When I was doing a little forum building project, I was working with an auto-redirect script that was supposed to work similarly to how this forum redirects after posting, logging in, and logging out.  However, when I tested it, it didn't work and there were no error indications.  I have a feeling that the php end of things might have interrupted the script with a change that I didn't notice.
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline TH300

  • Hero Member
  • *****
  • Posts: 1404
    • http://op3game.net
Javascript Question This Time
« Reply #5 on: March 05, 2012, 01:57:40 PM »
If you don't want to reload pages, I see no other option than Javascript. I made a small example. Please tell us if that's what you need.

Code: [Select]
<html>
  <head>
    <title>Test</title>
    <script type="text/javascript">
      function showPage(number) {
        for (var i = 0; i < 2; i++)
        {
          if (i == number) document.getElementsByName('page')[i].style.display="block";
          else document.getElementsByName('page')[i].style.display="none";
        }
      }
    </script>
  </head>
  <body>
    <p><a href="javascript:showPage(0)">show page 0</a></p>
    <p><a href="javascript:showPage(1)">show page 1</a></p>
    <p name="page" style="display:block">this is page 0</p>
    <p name="page" style="display:none">this is page 1</p>
  </body>
</html>

Note: All pages have the same name "page". Selection of a page is done by its number. Numbering goes from 0 to <number of pages - 1>. Visibility is controlled with the "display" css property which will make the object completely invisible if set to "none".
 

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #6 on: March 05, 2012, 02:45:28 PM »
That's the same basic function I remember.  I'm still concerned with it, however, because putting javascript in the header.html file then using require(header.html); or include(header.html); in the index.php has not worked for me in the past.  Granted, I've had other issues in the past that NO ONE could explain.  The most notable was a class file that wasn't working when everyone I talked to at phpfreaks (I think it was that forum anyway) said that everything was correct and it should be working.
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline TH300

  • Hero Member
  • *****
  • Posts: 1404
    • http://op3game.net
Javascript Question This Time
« Reply #7 on: March 05, 2012, 03:01:03 PM »
Somewhere I read that one can put javascript anywhere in the html file. Did you try that?

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #8 on: March 05, 2012, 03:33:02 PM »
I know you can, but I don't think I can close one upon opening another without a function.  At least not without an overkill of code...
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline TH300

  • Hero Member
  • *****
  • Posts: 1404
    • http://op3game.net
Javascript Question This Time
« Reply #9 on: March 05, 2012, 06:35:40 PM »
Quote
I know you can, but I don't think I can close one upon opening another without a function.  At least not without an overkill of code...
close one what? Sorry, I'm not good in guessing.

Did you ever look at the php file after the server processed it, i.e. the thing that gets delivered to your browser? For the browser its supposed to look like any regular html file, just with the ending php. You could save that file, change the extension to html, upload that to your webspace and test that. If it still doesn't work, you know at least, that its not a php related problem (bt rather a problem with the html that gets generated by the php).

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #10 on: March 05, 2012, 06:39:06 PM »
It's very difficult to hold conversations with different thought pathways sometimes, lol

When one text section opens, it closes the others.  The only way I know of to do that efficiently is to use a function.

I had not thought about trying that...
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline TH300

  • Hero Member
  • *****
  • Posts: 1404
    • http://op3game.net
Javascript Question This Time
« Reply #11 on: March 05, 2012, 06:47:34 PM »
Quote
When one text section opens, it closes the others.  The only way I know of to do that efficiently is to use a function.
Thats what I think. But whats wrong with that? You have javascript and hence you have functions. I tried the piece of html that I posted above. It works. If yours doesn't work, you should search for differences.

It may also be a good idea to check browser options. If javascript is disabled in your browser, the thing won't work.

Btw. above I wanted to say that you can place the "script" tag anywhere inside the head OR body. That way you can still declare a function once and use it several times.
« Last Edit: March 05, 2012, 06:54:04 PM by TH300 »

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #12 on: March 06, 2012, 01:01:02 AM »
I must have screwed something up with the delayed auto-redirect function then...I'm not sure, but I *might* have used a php if to only include it in the header if specific pages were chosen, so that was probably the error.

At first I didn't want the function in the header partially because it seemed useless to have it there in a system that used a single header for all pages when only one used it.  Since the php end of my concerns with it are gone, I think it might be useful for other pages as well.
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline Hooman

  • Administrator
  • Hero Member
  • *****
  • Posts: 4955
Javascript Question This Time
« Reply #13 on: March 06, 2012, 03:42:05 AM »
You generally need JavaScript to handle dynamic behaviour, so I would expect a solution to a problem like this requires JavaScript. As far as I can tell, the only action HTML supports, is following links, and the only action CSS supports, is things like underlining or highlighting links on mouseover. There might be a few more CSS effects, but I'm not aware of them.


I poked around a few links I had stored on my work computer. I was trying to find stuff on keeping JavaScript and HTML separate, like I mentioned before. I haven't re-read them to check, but I think these were some good ones:
http://www.digital-web.com/articles/separa...nd_structure_2/
http://www.quirksmode.org/js/introevents.html

There's also a Wiki article I found along the same lines:
http://en.wikipedia.org/wiki/Unobtrusive_JavaScript
Also, to make better use of those schemes, it helps to know a little more about DOM (Document Object Model). Here's a reference (which I had to use to write my example):
http://www.w3.org/TR/REC-DOM-Level-1/level...l#ID-1451460987


Now on to my code sample. Keep in mind that I don't do a whole lot of web programming, so you'll probably find better or shorter ways. I attempted to keep the HTML plain and simple, and usable even if JavaScript is disabled. I also attempted to keep the JavaScript somewhat general (although, that probably added to it's length and complexity). Note the absence of JavaScript code in the HTML file (other than the link in the header).


ShowHide.html:
Code: [Select]
<html>
<head>
  <title>Show/Hide Test</title>
  <script src="ShowHide.js"></script>
</head>
<body>

  Some random page text to help add context.

  <div id="container">
   <h1>Section 1</h1>
   <div>
    This is some text in the first container.
   </div>
   <h1>Section 2</h1>
   <div>
    This is some text in the second container.
   </div>
   <h1>Section 3</h1>
   <div>
    This is some text in the third container.
   </div>
  </div>

  More random text just to see how things fit.

</body>
</html>

ShowHide.js:
Code: [Select]

window.onload = function() {
// Initialize container with show/hide behavior
initShowHide(document.getElementById('container'));
}


function initShowHide(container) {
// Analyse structure of container
var nodeDivPairList = findNodeDivPair(container);
// Setup hide/show handlers for each pair, and hide div tags initially
for (var i = 0; i < nodeDivPairList.length; i++) {
  // Install click handler to header tag (whatever tag comes before a div section)
  nodeDivPairList[i][0].onclick = function() {
   // Hide all paired div tags except one for current header tag
   for (var i = 0; i < nodeDivPairList.length; i++) {
    if (nodeDivPairList[i][0] != this) {
     nodeDivPairList[i][1].style.display = 'none';   // Hide other div
    } else {
     nodeDivPairList[i][1].style.display = 'block';  // Show current div
    }
   }
  }
  // Hide div tag
  nodeDivPairList[i][1].style.display = 'none';
}
}

// Finds an array of (tag, divTag) pairs within a given container
function findNodeDivPair(container) {
array = [];
var headerNode;
// Iterate over all child nodes
for (var node = container.firstChild; node != null; node = node.nextSibling) {
  // Check if the child node is an element node (HTML tag)
  if (node.nodeType == 1) {
   // Check for end of pair
   if (headerNode != null && node.nodeName == 'DIV') {
    array.push([headerNode, node]);
    headerNode = null;  // Reset headerNode so it doesn't interfere with next pair match
   } else {
    headerNode = node;
   }
  }
}
return array;
}


Explanation of the JavaScript:
When you reference the file from the HTML header, it defines a few functions, and sets a window.onload handler. No code runs other than the simple assignment of an anonymous function to the onload event property.

When the page completely loads, including all resources, it triggers the onload event, which looks for the tag with the "container" id, and modifies it to have the show/hide behavior using the initShowHide function.

The findNodeDivPair function is used to scan a container for tag pairs, where the first tag can be of any type (including a div), and the second tag is a div. It skips over non tag nodes, such as text (including spaces and tabs from tag indentation). It was written to skip over pairs of tags that can't be properly matched (such as two successive span tags, or a header tag followed by a span tag). Basically, a missing div tag, or badly formed HTML section shouldn't mess things up much. The scan results are returned as an array of pairs.

The initShowHide function uses the findNodeDivPair function to understand the structure of the container it runs on. The initShowHide function will setup onclick handler functions for the first tag of each pair (the header element), which is responsible for hiding all section divs (the second tag of each pair), and then showing it's own associated div tag.


I had to scratch my head a bit about the closure part. I figured I'd either need to scan the DOM structure for every click, or I'd have to use a global variable or a closure to store cached references to the divs. The nesting of the handler function in the initShowHide function creates a closure, which gives the handler access to the array of tag pairs. The handler function can use "this" to refer to the node being clicked on, which is compared against the first element (the header) of each pair to know if it's associated div should be shown or hidden.


Also, if JavaScript is disabled, you'll just get a regular document with all sections visible. There is one downside to the example I've given though. If the page has lots of external resources to load, it may be some time before the JavaScript runs (since onload doesn't fire until everything is loaded), and so all sections may be initially visible until that happens. In practice, for small pages, you can probably ignore this, as you'll never notice this effect. If you're concerned about it though, it can be solved.

To deal with the initial visibility, should you need to, you can set a CSS rule to hide the div tags in the container element. The rule would be something along the lines of "#container div { display: none; }". I would suggest setting this from JavaScript though, right when you setup the onload event handler. If you set this rule in a simple CSS file, and JavaScript is disabled, all the div tags will be permanently hidden. If you do it from JavaScript, then they're only hidden when JavaScript is running and can reveal them as the headers are clicked. Basically, you have a nice fallback in that case.
« Last Edit: March 06, 2012, 03:44:33 AM by Hooman »

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #14 on: March 06, 2012, 04:10:50 AM »
(note: this post was made before checking the links and reading the example thuroughly because you reminded me of something else)

If I remember correctly, there is a way to check if javascript is enabled or disabled...just don't know if it is though meta tags or if php has a way...if php, I could have it revert to page anchors...which I don't like using but are, admittedly, a much simpler way of providing a form of intra-page navagation.

I'm going to go through everything over the week before I decide if javascript is the way to go or not.

anything after the following line is edits after reading through this some more.
-----------------------------------------------
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline TH300

  • Hero Member
  • *****
  • Posts: 1404
    • http://op3game.net
Javascript Question This Time
« Reply #15 on: March 06, 2012, 06:15:29 AM »
Quote
If I remember correctly, there is a way to check if javascript is enabled or disabled...just don't know if it is though meta tags or if php has a way...
In Html you can use "<noscript>".

Considering that php gets executed on the webserver I find it unlikely that php knows whether javascript is enabled. (unles,, of course you add a GET-variable for it. But that doesn't work when a visitor first enters your page)
« Last Edit: March 06, 2012, 06:17:26 AM by TH300 »

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #16 on: March 06, 2012, 11:17:28 AM »
Very true.  Unless I were to separate the disclaimer page (used to warn that I don't censor myself) and the navigation system it would work, but that's not really what I want to do.

That gave me another thought..is it possible to set up a call to a javascript function within the <a> tag in such a way that, if the function fails, it will revert to an anchor?  I think that this would be an interesting way to detect and compensate for javascript beig disabled...
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline Hooman

  • Administrator
  • Hero Member
  • *****
  • Posts: 4955
Javascript Question This Time
« Reply #17 on: March 07, 2012, 03:33:54 AM »
PHP can't detect JavaScript, since it's run on the server, and JavaScript is a client side thing. You could potentially modify PHP output if the server was told by the client it doesn't support JavaScript, but that can only work on the second and subsequent pages. If you had a login screen, you might use JavaScript to set a hidden form element to true, that normally defaults to false, and the server could use that to make assumptions about JavaScript. But, other than these custom coded solutions, PHP won't know in general if a client supports JavaScript.


You can have an anchor with a regular HTML href link, and an onclick event handler. If the event handler returns false, it will cancel navigation to the href link. Hence, you can use the href as a fallback, while "upgrading" your links with an onclick handler.


You can modify the code I posted to give it a try. Change the header tags (the h1 tags) to anchors, add a suitable href, and ensure the handler function returns false at the end.

Modification to JavaScript:
Code: [Select]
  nodeDivPairList[i][0].onclick = function() {
   // Hide all paired div tags except one for current header tag
   for (var i = 0; i < nodeDivPairList.length; i++) {
    if (nodeDivPairList[i][0] != this) {
     nodeDivPairList[i][1].style.display = 'none';   // Hide other div
    } else {
     nodeDivPairList[i][1].style.display = 'block';  // Show current div
    }
   }
   return false;  // <-- Modification
  }

Mind you, the example starts to look a bit ugly due to the default inline styling for links. When you click one to expand it's text, the other anchors suddenly move off the end of the line to appear below the new expanded text. I find the effect looks much nicer when the clickable elements are always on separate lines. You can try adding the following CSS style to keep the anchors on separate lines:
Code: [Select]
  <style>
   #container a { display: block; }
  </style>

Of course keeping the CSS in a separate linked file is usually nicer. But for my one line example I just couldn't bring myself to bother.
 

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #18 on: March 07, 2012, 07:47:28 PM »
Well, after reading through everything, it seems that it would be better to just used anchored text blocks rather than using the show/hide that I originally wanted to.  Overall, trying to compensate for disabled javascript involves a lot more code than I really want to use for this simple of a page.  However, when I re-start my forum build project, all of this will definately help me out :D
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline Hooman

  • Administrator
  • Hero Member
  • *****
  • Posts: 4955
Javascript Question This Time
« Reply #19 on: March 08, 2012, 12:12:37 AM »
A lot of people these days don't worry about compensating for disabled JavaScript. They just plain let the site not work. Occasionally, if they're polite, they may tell you the site requires JavaScript, possibly on some kind of home page, perhaps using a simple <noscript> tag.

In practice, almost everyone has JavaScript enabled these days. If you feel you need it, then use it. If you feel like adding some polish, then maybe add some proper fallbacks afterwards. That's sometimes a little easier to do if you understand how you would have done it when designing things from the start, but perhaps it's not worth your time at that point.

On the other hand, simpler methods are often better. It's valuable to consider whether or not you actually need JavaScript. In either case, I find at least thinking about how you'd do it with and without JavaScript may lead to a better overall design. At the very least it gets you thinking about the nature of the problem you are trying to solve.


Best of luck with your project.
 

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #20 on: March 08, 2012, 01:04:14 AM »
Thanks hooman.  I'd be grateful for any feedback on how it's looking so far.  I currently have the homepage finished and the structure of the About page in place.  Still need to finish with the content there before I work on the other sections.  It's a bit slow because I'm stealing time between stuff for classes.  I once again let myself fall into the trap of someone telling me that something was easier, lol
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #21 on: March 08, 2012, 11:49:37 AM »
(double-post, arrrg!  lol.  Only way to bring attention to the new question)

In preparation for the next section rebuild, I was playing around with what you gave me hooman, and there is just one thing I don't like about it:  you have to click the headers to hide/show the sections.

Is there a way to make it formatted more like this:

Code: [Select]
<table width='100%'>
 <tr>
  <td width='10%'>
   //intra-page navagation, triggers sectional show/hide
  </td>
  <td>
   //sections that are shown/hidden
  </td>
 <tr>
</table>

I know with php, I accomplished this with a switch:

Code: [Select]
<?php
 if(empty($_GET['pg']))
  {
    $p = '0';
  }
 else
  {
   $p = $_GET['pg'];
  }
 echo "<table width='100%'>\n <tr>\n  <td width='10%'>\n";
 require('nav.html');
 echo "\n  </td>\n  <td>\n";
 switch($p)
  {
    case 0:
     //either use an echo or include, depending on content
     break;
    //repeat for all sections
  }
 echo "\n  </td>\n <tr>\n</table>"
?>

I use "\n" of course in order to preserve the formatting (more for my own sanity than anything else)
« Last Edit: March 08, 2012, 11:50:36 AM by CK9 »
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline Hooman

  • Administrator
  • Hero Member
  • *****
  • Posts: 4955
Javascript Question This Time
« Reply #22 on: March 08, 2012, 11:54:12 PM »
Quote
I'd be grateful for any feedback on how it's looking so far.
How is it looking? I didn't notice a link anywhere?


Ahh, sounds like you want a tab control, rather than an accordion. Rather than show/hide, you want section replacement, right? What about initial load. Should one of the options display by default?


I've written some tab code before, but since I did it for work, I can't exactly just paste it here. Mind you, there is plenty of code for that on the net. Actually, one particularly memorable source I came across on JavaScript tab controls was: http://www.barelyfitz.com/projects/tabber/

I rather enjoyed the appearance of the tab control on that site. I also found how they linked the JavaScript code to the tab controls to be quite fascinating. They set a CSS class on a div to identify it as a tab control. Then, when the page loads, the JavaScript runs, and looks for all tags with that class and modifies them to have tab like behavior.

Note that not all tag elements need to be created in the source HTML. Instead, the JavaScript can scan a section of the document, and insert additional tag elements to function as the tabs. This might even be preferable, since then you don't need to worry about linking the control with the content as you build the HTML. Instead, the JavaScript can link the controls to the content when it scans the contents to generate the controls. Most tab control code I've seen though requires tabs to be pre-existing and needs some kind of explicit linking between the tab and the content. Usually it involves setting an id for each content section, and referencing that from a tab control element.

You can also mark the active tab, by setting or removing a CSS style on the tab. In the example I linked to, the bottom border is removed on the selected tab, and it's background color is changed to match the content section. This gives the appearance that the tab flows into the content section below. The other tabs are marked with a different background color, and have a separating line along the bottom. There is also some nice mouse-over effects which helps indicate that the tabs are clickable. All of this styling can be done with CSS, and only requires JavaScript to swap class tags around when changing which tab is active.


The code I used to do my tab stuff for work was probably about on par with what I posted above (the accordion like behavior) for size and complexity. The link I just posted for the tab control is a little more extensive, and seems to support a few additional features. You can probably get by with something simpler if one of your objectives is to learn how to do all this from scratch. If instead, you just want something to work, or if you want to save time, then the code they give away there probably isn't too bad. You might also want to consider looking into libraries like jQuery. In particular, there is a jQuery UI Tab Widget, with basically all of the same graphical effects listed above:
http://jqueryui.com/demos/tabs/
 

Offline CK9

  • Administrator
  • Hero Member
  • *****
  • Posts: 6226
    • http://www.outpost2.net/~ck9
Javascript Question This Time
« Reply #23 on: March 09, 2012, 01:04:01 AM »
Is the website button not on the bottom of your post with the forum skin you use?  Then again...I don't think many other people look there...

http://ck9.outpost2.net

I use a "disclaimer" as the default page.

I'm not a big fan of the file-cabinet look to the example, but it is the same core idea.  Do you know if it can work as side-tabs instead of top-tabs?
CK9 in outpost
Iamck in runescape (yes, I still play...sometimes...)
srentiln in minecraft (I like legos, and I like computer games...it was only a matter of time...) and youtube...
xdarkinsidex on deviantart

yup, I have too many screen names

Offline Hooman

  • Administrator
  • Hero Member
  • *****
  • Posts: 4955
Javascript Question This Time
« Reply #24 on: March 09, 2012, 02:18:04 AM »
Sure, that should be a reasonably simple CSS change to move the tabs to the side. It's been a while since I've used it though, so I'm hesitant to make a recommendation. I suppose "float" comes to mind, when you want to tag elements out of the normal flow. That combined with margin perhaps. There may be better alternatives though.


I saw no website link anywhere before. Didn't even think of skin settings.

I see a typo in your disclaimer: "anouther"

When you click on the navigation links, the visited color doesn't have a lot of contrast with the background. Maybe using a CSS rule along the lines of "a:visited { color: <whatever>; }" would be helpful.

Are you planning to update the page links at the top with this tab-like idea? I can see how the usual tab look might not work well for that. But that's just a CSS difference. The behavior, and hence the JavaScript code to handle it, will be the same.