/* Jappix - An open social platform These are the PEP JS scripts for Jappix ------------------------------------------------- License: AGPL Author: Vanaryon Last revision: 26/08/11 */ // Stores the PEP items function storePEP(xid, type, value1, value2, value3, value4) { // Handle the correct values if(!value1) value1 = ''; if(!value2) value2 = ''; if(!value3) value3 = ''; if(!value4) value4 = ''; // If one value if(value1 || value2 || value3 || value4) { // Define the XML variable var xml = ''; // Generate the correct XML if(type == 'tune') xml += '' + value1.htmlEnc() + '' + value2.htmlEnc() + '' + value3.htmlEnc() + '' + value4.htmlEnc() + ''; else if(type == 'geoloc') xml += '' + value1.htmlEnc() + '' + value2.htmlEnc() + '' + value3.htmlEnc() + ''; else xml += '' + value1.htmlEnc() + '' + value2.htmlEnc() + ''; // End the XML node xml += ''; // Update the input with the new value setDB('pep-' + type, xid, xml); } else removeDB('pep-' + type, xid); // Display the PEP event displayPEP(xid, type); } // Displays a PEP item function displayPEP(xid, type) { // Read the target input for values var value = $(XMLFromString(getDB('pep-' + type, xid))); var dText; var aLink = '' // If the PEP element exists if(type) { // Get the user hash var hash = hex_md5(xid); // Initialize var fText, fValue; var dText = ''; // Parse the XML for mood and activity if((type == 'mood') || (type == 'activity')) { if(value) { var pepValue = value.find('value').text(); var pepText = value.find('text').text(); // No value? if(!pepValue) pepValue = 'none'; // Apply the good values if(type == 'mood') fValue = moodIcon(pepValue); else if(type == 'activity') fValue = activityIcon(pepValue); if(!pepText) fText = _e("unknown"); else fText = pepText; } else { if(type == 'mood') fValue = moodIcon('undefined'); else if(type == 'activity') fValue = activityIcon('exercising'); fText = _e("unknown"); } dText = fText; fText = fText.htmlEnc(); } else if(type == 'tune') { fValue = 'tune-note'; if(value) { // Parse the tune XML var tArtist = value.find('artist').text(); var tTitle = value.find('title').text(); var tAlbum = value.find('album').text(); var tURI = value.find('uri').text(); var fArtist, fTitle, fAlbum, fURI; // Apply the good values if(!tArtist && !tAlbum && !tTitle) { fText = _e("unknown"); dText = fText; } else { // URI element if(!tURI) fURI = 'http://grooveshark.com/search?q=' + encodeURIComponent(tArtist + ' ' + tTitle + ' ' + tAlbum); else fURI = tURI; // Artist element if(!tArtist) fArtist = _e("unknown"); else fArtist = tArtist; // Title element if(!tTitle) fTitle = _e("unknown"); else fTitle = tTitle; // Album element if(!tAlbum) fAlbum = _e("unknown"); else fAlbum = tAlbum; // Generate the link to the title aLink = ' href="' + fURI + '" target="_blank"'; // Generate the text to be displayed dText = fArtist + ' - ' + fTitle + ' (' + fAlbum + ')'; fText = '' + dText + ''; } } else { fText = _e("unknown"); dText = fText; } } else if(type == 'geoloc') { fValue = 'location-world'; if(value) { // Parse the geoloc XML var tLat = value.find('lat').text(); var tLon = value.find('lon').text(); var tHuman = value.find('human').text(); var tReal = tHuman; // No human location? if(!tHuman) tHuman = _e("See his/her position on the globe"); // Generate the text to be displayed if(tLat && tLon) { aLink = ' href="http://maps.google.com/?q=' + encodeQuotes(tLat) + ',' + encodeQuotes(tLon) + '" target="_blank"'; fText = '' + tHuman.htmlEnc() + ''; if(tReal) dText = tReal; else dText = tLat + '; ' + tLon; } else { fText = _e("unknown"); dText = fText; } } else { fText = _e("unknown"); dText = fText; } } // Apply the text to the buddy infos var this_buddy = '#buddy-list .buddy[data-xid=' + escape(xid) + ']'; if(exists(this_buddy)) $(this_buddy + ' .bi-' + type).replaceWith('

' + fText + '

'); // Apply the text to the buddy chat if(exists('#' + hash)) { // Selector var bc_pep = $('#' + hash + ' .bc-pep'); // We remove the old PEP item bc_pep.find('a.bi-' + type).remove(); // If the new PEP item is not null, create a new one if(fText != _e("unknown")) bc_pep.prepend( '' ); // Process the new status position adaptChatPresence(hash); } // If this is the PEP values of the logged in user if(xid == getXID()) { // Change the icon/value of the target element if((type == 'mood') || (type == 'activity')) { // Change the input value var dVal = ''; var dAttr = pepValue; // Must apply default values? if(pepValue == 'none') { if(type == 'mood') dAttr = 'happy'; else dAttr = 'exercising'; } // No text? if(dText != _e("unknown")) dVal = dText; // Store this user event in our database setDB(type + '-value', 1, dAttr); setDB(type + '-text', 1, dVal); // Apply this PEP event $('#my-infos .f-' + type + ' a.picker').attr('data-value', dAttr); $('#my-infos .f-' + type + ' input').val(dVal); $('#my-infos .f-' + type + ' input').placeholder(); } else if((type == 'tune') || (type == 'geoloc')) { // Reset the values $('#my-infos .f-others a.' + type).remove(); // Not empty? if(dText != _e("unknown")) { // Specific stuffs var href, title, icon_class; if(type == 'tune') { href = fURI; title = dText; icon_class = 'tune-note'; } else { href = 'http://maps.google.com/?q=' + encodeQuotes(tLat) + ',' + encodeQuotes(tLon); title = _e("Where are you?") + ' (' + dText + ')'; icon_class = 'location-world'; } // Must create the container? if(!exists('#my-infos .f-others')) $('#my-infos .content').append('
'); // Create the element $('#my-infos .f-others').prepend( '' + '' + '' ); } // Empty? else if(!exists('#my-infos .f-others a.icon')) $('#my-infos .f-others').remove(); // Process the buddy-list height again adaptRoster(); } } } } // Changes the mood icon function moodIcon(value) { // The main var var icon; // Switch the values switch(value) { case 'angry': case 'cranky': case 'hot': case 'invincible': case 'mean': case 'restless': case 'serious': case 'strong': icon = 'mood-one'; break; case 'contemplative': case 'happy': case 'playful': icon = 'mood-two'; break; case 'aroused': case 'envious': case 'excited': case 'interested': case 'lucky': case 'proud': case 'relieved': case 'satisfied': case 'shy': icon = 'mood-three'; break; case 'calm': case 'cautious': case 'contented': case 'creative': case 'humbled': case 'lonely': case 'undefined': case 'none': icon = 'mood-four'; break; case 'afraid': case 'amazed': case 'confused': case 'dismayed': case 'hungry': case 'in_awe': case 'indignant': case 'jealous': case 'lost': case 'offended': case 'outraged': case 'shocked': case 'surprised': case 'embarrassed': case 'impressed': icon = 'mood-five'; break; case 'crazy': case 'distracted': case 'neutral': case 'relaxed': case 'thirsty': icon = 'mood-six'; break; case 'amorous': case 'curious': case 'in_love': case 'nervous': case 'sarcastic': icon = 'mood-eight'; break; case 'brave': case 'confident': case 'hopeful': case 'grateful': case 'spontaneous': case 'thankful': icon = 'mood-nine'; break; default: icon = 'mood-seven'; break; } // Return the good icon name return icon; } // Changes the activity icon function activityIcon(value) { // The main var var icon; // Switch the values switch(value) { case 'doing_chores': icon = 'activity-doing_chores'; break; case 'drinking': icon = 'activity-drinking'; break; case 'eating': icon = 'activity-eating'; break; case 'grooming': icon = 'activity-grooming'; break; case 'having_appointment': icon = 'activity-having_appointment'; break; case 'inactive': icon = 'activity-inactive'; break; case 'relaxing': icon = 'activity-relaxing'; break; case 'talking': icon = 'activity-talking'; break; case 'traveling': icon = 'activity-traveling'; break; case 'working': icon = 'activity-working'; break; default: icon = 'activity-exercising'; break; } // Return the good icon name return icon; } // Sends the user's mood function sendMood(value, text) { /* REF: http://xmpp.org/extensions/xep-0107.html */ // We propagate the mood on the xmpp network var iq = new JSJaCIQ(); iq.setType('set'); // We create the XML document var pubsub = iq.appendNode('pubsub', {'xmlns': NS_PUBSUB}); var publish = pubsub.appendChild(iq.buildNode('publish', {'node': NS_MOOD, 'xmlns': NS_PUBSUB})); var item = publish.appendChild(iq.buildNode('item', {'xmlns': NS_PUBSUB})); var mood = item.appendChild(iq.buildNode('mood', {'xmlns': NS_MOOD})); if(value != 'none') { mood.appendChild(iq.buildNode(value, {'xmlns': NS_MOOD})); mood.appendChild(iq.buildNode('text', {'xmlns': NS_MOOD}, text)); } // And finally we send the mood that is set con.send(iq); logThis('New mood sent: ' + value + ' (' + text + ')', 3); } // Sends the user's activity function sendActivity(main, sub, text) { // We propagate the mood on the xmpp network var iq = new JSJaCIQ(); iq.setType('set'); // We create the XML document var pubsub = iq.appendNode('pubsub', {'xmlns': NS_PUBSUB}); var publish = pubsub.appendChild(iq.buildNode('publish', {'node': NS_ACTIVITY, 'xmlns': NS_PUBSUB})); var item = publish.appendChild(iq.buildNode('item', {'xmlns': NS_PUBSUB})); var activity = item.appendChild(iq.buildNode('activity', {'xmlns': NS_ACTIVITY})); if(main != 'none') { var mainType = activity.appendChild(iq.buildNode(main, {'xmlns': NS_ACTIVITY})); // Child nodes if(sub) mainType.appendChild(iq.buildNode(sub, {'xmlns': NS_ACTIVITY})); if(text) activity.appendChild(iq.buildNode('text', {'xmlns': NS_ACTIVITY}, text)); } // And finally we send the mood that is set con.send(iq); logThis('New activity sent: ' + main + ' (' + text + ')', 3); } // Sends the user's geographic position function sendPosition(vLat, vLon, vAlt, vCountry, vCountrycode, vRegion, vPostalcode, vLocality, vStreet, vBuilding, vText, vURI) { /* REF: http://xmpp.org/extensions/xep-0080.html */ // We propagate the position on pubsub var iq = new JSJaCIQ(); iq.setType('set'); // We create the XML document var pubsub = iq.appendNode('pubsub', {'xmlns': NS_PUBSUB}); var publish = pubsub.appendChild(iq.buildNode('publish', {'node': NS_GEOLOC, 'xmlns': NS_PUBSUB})); var item = publish.appendChild(iq.buildNode('item', {'xmlns': NS_PUBSUB})); var geoloc = item.appendChild(iq.buildNode('geoloc', {'xmlns': NS_GEOLOC})); // Create two position arrays var pos_names = ['lat', 'lon', 'alt', 'country', 'countrycode', 'region', 'postalcode', 'locality', 'street', 'building', 'text', 'uri', 'timestamp']; var pos_values = [ vLat, vLon, vAlt, vCountry, vCountrycode, vRegion, vPostalcode, vLocality, vStreet, vBuilding, vText, vURI, getXMPPTime('utc')]; for(var i = 0; i < pos_names.length; i++) { if(pos_names[i] && pos_values[i]) geoloc.appendChild(iq.buildNode(pos_names[i], {'xmlns': NS_GEOLOC}, pos_values[i])); } // And finally we send the XML con.send(iq); // For logger if(vLat && vLon) logThis('Geolocated.', 3); else logThis('Not geolocated.', 2); } // Parses the user's geographic position function parsePosition(data) { var result = $(data).find('result:first'); // Get latitude and longitude var lat = result.find('geometry:first location:first lat').text(); var lng = result.find('geometry:first location:first lng').text(); var array = [ lat, lng, result.find('address_component:has(type:contains("country")):first long_name').text(), result.find('address_component:has(type:contains("country")):first short_name').text(), result.find('address_component:has(type:contains("administrative_area_level_1")):first long_name').text(), result.find('address_component:has(type:contains("postal_code")):first long_name').text(), result.find('address_component:has(type:contains("locality")):first long_name').text(), result.find('address_component:has(type:contains("route")):first long_name').text(), result.find('address_component:has(type:contains("street_number")):first long_name').text(), result.find('formatted_address:first').text(), 'http://maps.google.com/?q=' + encodeQuotes(lat) + ',' + encodeQuotes(lng) ]; return array; } // Converts a position into an human-readable one function humanPosition(tLocality, tRegion, tCountry) { var tHuman = ''; // Any locality? if(tLocality) { tHuman += tLocality; if(tRegion) tHuman += ', ' + tRegion; if(tCountry) tHuman += ', ' + tCountry; } // Any region? else if(tRegion) { tHuman += tRegion; if(tCountry) tHuman += ', ' + tCountry; } // Any country? else if(tCountry) tHuman += tCountry; return tHuman; } // Gets the user's geographic position function getPosition(position) { // Convert integers to strings var vLat = '' + position.coords.latitude; var vLon = '' + position.coords.longitude; var vAlt = '' + position.coords.altitude; // Get full position (from Google Maps API) $.get('./php/geolocation.php', {latitude: vLat, longitude: vLon, language: XML_LANG}, function(data) { // Parse data! var results = parsePosition(data); // Handled! sendPosition( vLat, vLon, vAlt, results[2], results[3], results[4], results[5], results[6], results[7], results[8], results[9], results[10] ); // Store data setDB('geolocation', 'now', xmlToString(data)); logThis('Position details got from Google Maps API.'); }); logThis('Position got: latitude > ' + vLat + ' / longitude > ' + vLon + ' / altitude > ' + vAlt); } // Geolocates the user function geolocate() { // Don't fire it until options & features are not retrieved! if(!getDB('options', 'geolocation') || (getDB('options', 'geolocation') == '0') || !enabledPEP()) return; // We publish the user location if allowed if(navigator.geolocation) { // Wait a bit... (to fix a bug) $('#my-infos').stopTime().oneTime('1s', function() { navigator.geolocation.getCurrentPosition(getPosition); }); logThis('Geolocating...', 3); } // Any error? else logThis('Not geolocated: browser does not support it.', 1); } // Displays all the supported PEP events for a given XID function displayAllPEP(xid) { displayPEP(xid, 'mood'); displayPEP(xid, 'activity'); displayPEP(xid, 'tune'); displayPEP(xid, 'geoloc'); } // Addon launcher function launchPEP() { // Apply empty values to the PEP database setDB('mood-value', 1, ''); setDB('mood-text', 1, ''); setDB('activity-value', 1, ''); setDB('activity-text', 1, ''); // Click event for user mood $('#my-infos .f-mood a.picker').click(function() { // Initialize some vars var path = '#my-infos .f-mood div.bubble'; var mood_id = ['crazy', 'excited', 'playful', 'happy', 'shocked', 'hot', 'sad', 'amorous', 'confident']; var mood_lang = [_e("Crazy"), _e("Excited"), _e("Playful"), _e("Happy"), _e("Shocked"), _e("Hot"), _e("Sad"), _e("Amorous"), _e("Confident")]; var mood_val = $('#my-infos .f-mood a.picker').attr('data-value'); // Yet displayed? var can_append = true; if(exists(path)) can_append = false; // Add this bubble! showBubble(path); if(!can_append) return false; // Generate the HTML code var html = '
'; for(i in mood_id) { // Yet in use: no need to display it! if(mood_id[i] == mood_val) continue; html += ''; } html += '
'; // Append the HTML code $('#my-infos .f-mood').append(html); // Click event $(path + ' a').click(function() { // Update the mood marker $('#my-infos .f-mood a.picker').attr('data-value', $(this).attr('data-value')); // Close the bubble closeBubbles(); // Focus on the status input $(document).oneTime(10, function() { $('#mood-text').focus(); }); return false; }); return false; }); // Click event for user activity $('#my-infos .f-activity a.picker').click(function() { // Initialize some vars var path = '#my-infos .f-activity div.bubble'; var activity_id = ['doing_chores', 'drinking', 'eating', 'exercising', 'grooming', 'having_appointment', 'inactive', 'relaxing', 'talking', 'traveling', 'working']; var activity_lang = [_e("Chores"), _e("Drinking"), _e("Eating"), _e("Exercising"), _e("Grooming"), _e("Appointment"), _e("Inactive"), _e("Relaxing"), _e("Talking"), _e("Traveling"), _e("Working")]; var activity_val = $('#my-infos .f-activity a.picker').attr('data-value'); // Yet displayed? var can_append = true; if(exists(path)) can_append = false; // Add this bubble! showBubble(path); if(!can_append) return false; // Generate the HTML code var html = '
'; for(i in activity_id) { // Yet in use: no need to display it! if(activity_id[i] == activity_val) continue; html += ''; } html += '
'; // Append the HTML code $('#my-infos .f-activity').append(html); // Click event $(path + ' a').click(function() { // Update the activity marker $('#my-infos .f-activity a.picker').attr('data-value', $(this).attr('data-value')); // Close the bubble closeBubbles(); // Focus on the status input $(document).oneTime(10, function() { $('#activity-text').focus(); }); return false; }); return false; }); // Submit events for PEP inputs $('#mood-text, #activity-text').placeholder() .keyup(function(e) { if(e.keyCode == 13) { $(this).blur(); return false; } }); // Input blur handler $('#mood-text').blur(function() { // Read the parameters var value = $('#my-infos .f-mood a.picker').attr('data-value'); var text = $(this).val(); // Must send the mood? if((value != getDB('mood-value', 1)) || (text != getDB('mood-text', 1))) { // Update the local stored values setDB('mood-value', 1, value); setDB('mood-text', 1, text); // Send it! sendMood(value, text); } }) // Input focus handler .focus(function() { closeBubbles(); }); // Input blur handler $('#activity-text').blur(function() { // Read the parameters var value = $('#my-infos .f-activity a.picker').attr('data-value'); var text = $(this).val(); // Must send the activity? if((value != getDB('activity-value', 1)) || (text != getDB('activity-text', 1))) { // Update the local stored values setDB('activity-value', 1, value); setDB('activity-text', 1, text); // Send it! sendActivity(value, '', text); } }) // Input focus handler .focus(function() { closeBubbles(); }); }