In order to be able to use this awesome plugin: Jquery iphone contacts
i need to update my existing markup (normal list):
<div id="iphone-scrollcontainer">
<ul id="iphone-search">
<li><a href="#A" title="A">A</a></li>
<li><a href="#B" title="B">B</a></li>
<li><a href="#C" title="C">C</a></li>
<li><a href="#D" title="D">D</a></li>
<li><a href="#E" title="E">E</a></li>
<!-- More characters here -->
</ul>
<ul id="iphone-scroll">
<li><a href="http://en.wikipedia.org/wiki/Amsterdam" title="Amsterdam"><strong>Amsterdam</strong>747,290</a></li>
<li><a href="http://en.wikipedia.org/wiki/Amsterdam" title="Barcelona"><strong>Barcelona</strong>747,290</a></li>
<li><a href="http://en.wikipedia.org/wiki/Amsterdam" title="Sevilla"><strong>Sevilla</strong>747,290</a></li>
<li><a href="http://en.wikipedia.org/wiki/Amsterdam" title="Cadiz"><strong>Cadiz</strong>747,290</a></li>
</ul>
</div>
Into (Add Navigation indicators):
<div id="iphone-scrollcontainer">
<ul id="iphone-search">
<li><a href="#A" title="A">A</a></li>
<li><a href="#B" title="B">B</a></li>
<li><a href="#C" title="C">C</a></li>
<li><a href="#D" title="D">D</a></li>
<li><a href="#E" title="E">E</a></li>
<!-- More characters here -->
</ul>
<ul id="iphone-scroll">
<li>
<div id="nav-indicator-fixed"></div>
<a name="A"></a>
<div class="nav-indicator" id="nav-a">A</div>
<ul>
<li><a href="http://en.wikipedia.org/wiki/Amsterdam" title="Amsterdam"><strong>Amsterdam</strong>747,290</a></li>
<li><a href="http://en.wikipedia.org/wiki/Arnhem" title="Arnhem"><strong>Arnhem</strong>144,101</a></li>
<!-- More info here -->
</ul>
</li>
<li>
<a name="B"></a>
<div class="nav-indicator" id="nav-b">B</div>
<ul>
<li><a href="http://en.wikipedia.org/wiki/Bolsward" title="Bolsward"><strong>Bolsward</strong>9,607</a></li>
<li><a href="http://en.wikipedia.org/wiki/Buren" title="Buren"><strong>Buren</strong>25,644</a></li>
<!-- More info here -->
</ul>
</li>
</ul>
</div>
So i have to
add:
<div id="nav-indicator-fixed"></div>
<a name="A"></a>
<div class="nav-indicator" id="nav-a">A</div>
<ul>
Before A items and
</li></ul>
after A items, (and same with each existing first letter), am i right?
Now is when i don't know to do it in front end using jquery or if i can do it in the server using php
i generate my markup with a simple query: 'select name from citys order by name desc'
how and where would you do it?
(shouln't actually the plugin have the feature¿)
-EDIT-
php code was requested:
function nube_ingredientes($limit = 50){
$query = "SELECT count(*) as num, nombre FROM ciudades WHERE GROUP BY nombre ORDER BY num DESC LIMIT $limit";
$result = mysql_query($query);
$html .= '<div class="content">';
$html .= '<ul>';
while($taginfo = mysql_fetch_row($result)){
$numtags = $taginfo[0];
$tagname = $taginfo[1];
$tagurl = urlencode($tagname);
$tagsize = 9 + intval($numtags)*2;
$bla = 'get_items("'.str_replace(' ','-',$tagname).'")';
$tagname = str_replace('-', ' ', $tagname);
$html.= "<li><a href='#router' onclick='$bla' c='$numtags'>$tagname</a></li> "."
";
}
$html .= '</ul>
</div>';
echo $html;
}
I haven't tested this, so consider it psuedo-code, however it should give you a good starting point. The idea is to check the first letter of each row, and if it's different than the first letter of the previous row, emit the new HTML code. It is always best to emit the HTML code as close to final as possible. So this solution has no complicated changes required to the front end.
function nube_ingredientes($limit = 50){
$query = "SELECT count(*) as num, nombre FROM ciudades WHERE GROUP BY nombre ORDER BY num DESC LIMIT $limit";
$result = mysql_query($query);
$html .= '<div class="content">';
$html .= '<ul>';
while($taginfo = mysql_fetch_row($result)){
$numtags = $taginfo[0];
$tagname = $taginfo[1];
$tagurl = urlencode($tagname);
$tagsize = 9 + intval($numtags)*2;
$bla = 'get_items("'.str_replace(' ','-',$tagname).'")';
$tagname = str_replace('-', ' ', $tagname);
$thisChar = strtoupper(substr($tagname, 0, 1)); //Added by msigman
if($lastChar != $thisChar);//Added by msigman
{
$html .= "<li><div id='nav-indicator-fixed'></div>
<a name='$thisChar'></a>
<div class='nav-indicator' id='nav-$thisChar'>$thisChar</div>
<ul>"; //Added by msigman
}
$html.= "<li><a href='#router' onclick='$bla' c='$numtags'>$tagname</a></li> "."
";
if($lastChar != $thisChar); //Added by msigman
{
$lastChar = $thisChar; //Added by msigman
$html .= "</li></ul>"; //Added by msigman
}
}
$html .= '</ul></div>';
echo $html;
}
Assuming you might want to pass the basic data to the client without generating the markup in php, you can do it like this:
encode_json($results)
in PHP which will deliver something like this:// title, wiki-link, x-coord, y-coord
var data =
[["Amsterdam", "Amsterdam", 747, 290],
["Barcelona", "Barcelona", 747, 290],
...
]
I've added the wiki-link just in case it's not the title ;)
Now using jQuery and underscore.js you can generate your content with a few lines of code:
// group your data by the first letter of the title
var grouped = _.groupBy(data, function(row) {
// row[0] is the title
return row[0].substring(0, 1)
})
// generate the header
var letters = _.keys(grouped)
var header = $('<ul>', { id: 'iphone-search' })
_.each(letters, function(letter) {
$('<a>', { href: '#' + letter, title: letter }).html(letter).appendTo(header)
})
// the scroll body
var scrollBody = $('<ul>', { id: 'iphone-scroll' })
_.each(letters, function(letter) {
var li = $('<li>')
// create the navigational anchor
$('<a>', { name: letter }).appendTo(li)
// create the div to put the ul/li... on
var div = $('<div>', {
'class': 'nav-indicator',
'id': 'nav-' + letter.toLowerCase()
}).appendTo(li)
var ul = $('<ul>').appendTo(div)
_.each(grouped[letter], function(group) {
// now, for each element within the group
// create the <li><a>...</a></li> content
$('<li>').append(
$('<a>', {
title: group[0],
href: 'http://en.wikipedia.org/wiki/' + group[1] // the wiki-link
}).append(
$('<strong>').html(group[0])
).append(
$('<span>').html(group[2] + ', ' + group[3])
)
).appendTo(ul)
})
})
// now you can join them in the container
var container =
$('<div>', { id: 'iphone-scrollcontainer'}).append(header).append(scrollBody)
That should yield just the html you wanted ;) The last part appears a little messy, but at least its the same style as all elements are only generated by jQuery.