Index: trunk/extensions/PlayerStatsGrabber/SpecialPlayerStatsPage.php |
— | — | @@ -1,7 +0,0 @@ |
2 | | -<?php |
3 | | -/* hanndles acutal output of special stats page */ |
4 | | - |
5 | | -class SpecialPlayerStatsPage extends SpecialPage { |
6 | | - |
7 | | -} |
8 | | -?> |
\ No newline at end of file |
Index: trunk/extensions/PlayerStatsGrabber/PlayerStatsGrabber_body.php |
— | — | @@ -0,0 +1,97 @@ |
| 2 | +<?php |
| 3 | +/* hanndles acutal output of special stats page */ |
| 4 | +if ( !defined( 'MEDIAWIKI' ) ) die(); |
| 5 | + |
| 6 | +class SpecialPlayerStatsGrabber extends SpecialPage { |
| 7 | + var $action=''; |
| 8 | + function SpecialPlayerStatsGrabber() { |
| 9 | + SpecialPage::SpecialPage("PlayerStatsGrabber"); |
| 10 | + wfLoadExtensionMessages('PlayerStatsGrabber'); |
| 11 | + } |
| 12 | + //used for page title |
| 13 | + function getDescription(){ |
| 14 | + switch($this->req_param){ |
| 15 | + case 'Survey': |
| 16 | + return wfMsg('ps_take_video_survey'); |
| 17 | + break; |
| 18 | + case '': |
| 19 | + default: |
| 20 | + return wfMsg('playerstatsgrabber'); |
| 21 | + break; |
| 22 | + } |
| 23 | + } |
| 24 | + function execute( $par ) { |
| 25 | + global $wgRequest, $wgOut; |
| 26 | + $this->req_param = $par; |
| 27 | + print $wgRequest->getText('param'); |
| 28 | + //set the header: |
| 29 | + $this->setHeaders(); |
| 30 | + |
| 31 | + //do the page: |
| 32 | + switch($this->req_param){ |
| 33 | + case 'Survey': |
| 34 | + //check if |
| 35 | + $this->do_survey_forum(); |
| 36 | + break; |
| 37 | + case '':default: |
| 38 | + $this->do_stats_page(); |
| 39 | + break; |
| 40 | + } |
| 41 | + } |
| 42 | + function do_stats_page(){ |
| 43 | + global $wgOut, $wgRequest; |
| 44 | + $wgOut->addHTML( " $this->req_param stats output will go here, with a link to a full report once its available"); |
| 45 | + } |
| 46 | + function do_survey_forum(){ |
| 47 | + global $wgOut, $psEmbedAry, $wgTitle; |
| 48 | + $wgOut->addHTML ( wfMsg('ps_survey_description')); |
| 49 | + |
| 50 | + //select the embed ary element: |
| 51 | + $tw=0; |
| 52 | + foreach($psEmbedAry as $embed){ |
| 53 | + $tw+=$embed['weight']; |
| 54 | + } |
| 55 | + $selected_val = rand(0, $tw); |
| 56 | + foreach($psEmbedAry as $embed){ |
| 57 | + $tw+=$embed['weight']; |
| 58 | + if($tw>=$selected_val){ |
| 59 | + break; |
| 60 | + } |
| 61 | + } |
| 62 | + $embed_code=''; |
| 63 | + if(isset($embed['html_code'])){ |
| 64 | + $embed_code=$embed['html_code']; |
| 65 | + }else if(isset($embed['wiki_code'])){ |
| 66 | + $embed_code=$embed['wiki_code']; |
| 67 | + } |
| 68 | + //$q = 'action='.$this->action; |
| 69 | + #if ( "no" == $redirect ) { $q .= "&redirect=no"; } |
| 70 | + $action = $wgTitle->escapeLocalURL( $q ); |
| 71 | + //work with "embed" |
| 72 | + //output table with flash and or video embed: |
| 73 | + $wgOut->addHTML( <<<EOT |
| 74 | +<table> |
| 75 | +<tr> |
| 76 | + <td> |
| 77 | + </td> |
| 78 | + <td> |
| 79 | + <form id="editform" name="editform" method="post" action="$action" enctype="multipart/form-data"> |
| 80 | + form goes here |
| 81 | + </form> |
| 82 | + </td> |
| 83 | +</tr> |
| 84 | +</table> |
| 85 | + |
| 86 | +EOT |
| 87 | + ); |
| 88 | + $o=''; |
| 89 | + $o.='<td>'.$embed_code.'</td>'; |
| 90 | + $o.='<td>'; |
| 91 | + |
| 92 | + $o.='</td>'; |
| 93 | + $o.='</tr></table>'; |
| 94 | + } |
| 95 | +} |
| 96 | + |
| 97 | + |
| 98 | +?> |
\ No newline at end of file |
Index: trunk/extensions/PlayerStatsGrabber/PlayerStatsGrabber.i18n.php |
— | — | @@ -1,3 +1,23 @@ |
2 | 2 | <?php |
| 3 | +$messages = array(); |
3 | 4 | |
| 5 | +$messages['en'] = array( |
| 6 | + 'playerstatsgrabber' => 'Player Stats Survey', |
| 7 | + 'ps_take_video_survey'=> 'Video Playback Survey', |
| 8 | + 'ps_survey_description'=> |
| 9 | + 'This Survey will help wikipedia improve support for rich media. Please follow the on-screen instructions:', |
| 10 | + 'ps_could_play'=>'When you clicked "play", did the video playback?', |
| 11 | + 'ps_sound'=>'Did you have your volume up, and did you hear sound? ', |
| 12 | + 'ps_problems_desc'=>'If you experienced any problems playing the video, mark what applies. |
| 13 | + If you need more space use the other text field.', |
| 14 | + 'ps_problem_jumpy_playback'=>' Jumping playback (the video played then paused then played)', |
| 15 | + 'ps_problem_bad_sync' => 'audio was out of sync with the video', |
| 16 | + 'ps_would_install' =>'As a Wikipedia user, would you install an additional plug-in to view |
| 17 | +video on Wikipedia?', |
| 18 | + 'ps_would_switch' =>'As a Wikipedia user, would you consider installing a different browser to improve your experience on Wikipedia?', |
| 19 | + 'ps_your_email' =>'your email address (optional) ', |
| 20 | + 'ps_submit_survey' =>'Submit Survey', |
| 21 | + 'ps_privacy' =>'Privacy note goes here' |
| 22 | +); |
| 23 | + |
4 | 24 | ?> |
\ No newline at end of file |
Index: trunk/extensions/PlayerStatsGrabber/PlayerStatsGrabber.php |
— | — | @@ -1,15 +1,47 @@ |
2 | 2 | <?php |
3 | 3 | /* |
4 | 4 | * simple stats output and gather for oggPlay and a "sample page" |
| 5 | + */ |
| 6 | + |
| 7 | +# Alert the user that this is not a valid entry point to MediaWiki if they try to access the special pages file directly. |
| 8 | +if (!defined('MEDIAWIKI')) { |
| 9 | + echo <<<EOT |
| 10 | +To install my extension, put the following line in LocalSettings.php: |
| 11 | +require_once( "\$IP/extensions/MyExtension/MyExtension.php" ); |
| 12 | +EOT; |
| 13 | + exit( 1 ); |
| 14 | +} |
| 15 | +/* |
| 16 | + * config values |
5 | 17 | */ |
6 | 18 | |
7 | | -//add SpecialPlayerStats Output page: |
8 | | -$wgSpecialPages['PlayerStats'] = array('SpecialPlayerStatsPage', |
9 | | - 'PlayerStats', |
10 | | - 'mwExecutePlayerStats', |
11 | | - dirname( __FILE__ ) . '/specials/Statistics/SMW_SpecialStatistics.php', true, ''); |
12 | | -$wgSpecialPageGroups['PlayerStats'] = 'wiki'; // like Special:Statistics |
| 19 | +//embed code and "weight" (ie weight of 3 is 3x more likely than weight of 1) |
| 20 | +//flash embed coode (the raw html that gets outputed to the browers) |
| 21 | +$psEmbedAry = array( |
| 22 | + array( 'embed_type'=>'flash', |
| 23 | + 'source_type'=>'youtube', |
| 24 | + 'name'=>'Sample Youtube Embed', |
| 25 | + 'weight'=>1, |
| 26 | + 'code'=>'<object width="425" height="344"><param name="movie" value="http://www.youtube.com/v/eaADQTeZRCY&hl=en&fs=1"></param><param name="allowFullScreen" value="true"></param><embed src="http://www.youtube.com/v/eaADQTeZRCY&hl=en&fs=1" type="application/x-shockwave-flash" allowfullscreen="true" width="425" height="344"></embed></object>' |
| 27 | + ), |
| 28 | + array( 'embed_type' =>'local', |
| 29 | + 'weight'=>1, |
| 30 | + 'wiki_code' =>'[[Image:Sample_fish.ogg]]' |
| 31 | + ) |
| 32 | +); |
13 | 33 | |
| 34 | + |
| 35 | + |
| 36 | +/* |
| 37 | + * end config |
| 38 | + */ |
| 39 | + |
| 40 | +$wgExtensionMessagesFiles['PlayerStatsGrabber'] = dirname( __FILE__ ) . '/PlayerStatsGrabber.i18n.php'; |
| 41 | +$wgAutoloadClasses['SpecialPlayerStatsGrabber'] = dirname( __FILE__ ) . '/PlayerStatsGrabber_body.php'; |
| 42 | +$wgSpecialPages['PlayerStatsGrabber'] = array( 'SpecialPlayerStatsGrabber' ); |
| 43 | + |
| 44 | +$wgSpecialPageGroups['PlayerStatsGrabber'] = 'wiki'; // like Special:Statistics |
| 45 | + |
14 | 46 | //add ajax hook to accept the status input: |
15 | 47 | $wgAjaxExportList[] = 'mw_push_player_stats'; |
16 | 48 | |
— | — | @@ -30,10 +62,114 @@ |
31 | 63 | * (ties survay page data to detection) |
32 | 64 | */ |
33 | 65 | function mw_push_player_stats(){ |
34 | | - global $wgRequest; |
| 66 | + global $wgRequest; |
35 | 67 | //do the insert into the userPlayerStats table: |
36 | | - $dbw =& wfGetDB( DB_WRITE ); |
37 | | - //print_r($wgRequest); |
38 | | - |
| 68 | + $dbr =& wfGetDB( DB_READ ); |
| 69 | + if( $wgRequest->getVal('cb')=='' |
| 70 | + || $wgRequest->getVal('cb_inx')=='' |
| 71 | + || $wgRequest->getVal('uh')==''){ |
| 72 | + //output error: |
| 73 | + return 'error: missing param for json callback'; |
| 74 | + } |
| 75 | + if(!isset($wgRequest->data['cs'])|| !is_array($wgRequest->data['cs'])){ |
| 76 | + $wgRequest->data['cs']=array(); |
| 77 | + } |
| 78 | + //set up insert array: |
| 79 | + $insAry = array( |
| 80 | + 'user_hash' => $wgRequest->getVal('uh'), |
| 81 | + 'b_user_agent' => $wgRequest->getVal('b_user_agent'), |
| 82 | + 'b_name' => $wgRequest->getVal('b_name'), |
| 83 | + 'b_version' => $wgRequest->getVal('b_version'), |
| 84 | + 'b_os' => $wgRequest->getVal('b_os'), |
| 85 | + 'flash_version' => $wgRequest->getVal('fv'), |
| 86 | + 'java_version' => $wgRequest->getVal('jv'), |
| 87 | + 'html5_video_enabled'=>(in_array('videoElement', $wgRequest->data['cs'] ))?true:false, |
| 88 | + 'java_enabled' => ( in_array('cortado', $wgRequest->data['cs'] ) )?true:false, |
| 89 | + 'totem_enabled' => ( in_array('totem', $wgRequest->data['cs'] ) )?true:false, |
| 90 | + 'flash_enabled' =>( in_array('flash', $wgRequest->data['cs'] ) )?true:false, |
| 91 | + 'quicktime_enabled' =>( in_array( array('quicktime-mozilla','quicktime-activex'), |
| 92 | + $wgRequest->data['cs'] ) |
| 93 | + )?true:false, |
| 94 | + 'vlc_enabled' =>( in_array( array('vlc-mozilla', 'vlc-activex'), |
| 95 | + $wgRequest->data['cs'] ) |
| 96 | + )?true:false, |
| 97 | + 'mplayer_enabled' =>( in_array( 'mplayerplug-in', |
| 98 | + $wgRequest->data['cs'] ) |
| 99 | + )?true:false |
| 100 | + ); |
| 101 | + //check for user hash (don't collect multiple times for the same user) |
| 102 | + //$user_hash = |
| 103 | + $insert_id = $dbr->selectField('player_stats_log', 'id', |
| 104 | + array( 'user_hash'=>$wgRequest->getVal('uh') ), |
| 105 | + 'mw_push_player_stats::Select User Hash'); |
| 106 | + //last_insert_id |
| 107 | + if( $insert_id ){ |
| 108 | + //for now don't insert repeates |
| 109 | + }else{ |
| 110 | + $dbw =& wfGetDB( DB_WRITE ); |
| 111 | + $dbw->insert( 'player_stats_log', $insAry, 'mw_push_player_stats:Insert'); |
| 112 | + $insert_id = $dbw->insertId(); |
| 113 | + $dbw->commit(); |
| 114 | + } |
| 115 | + header( 'Content-Type: text/javascript' ); |
| 116 | + return htmlspecialchars( $wgRequest->getVal('cb') ). '(' .PhpArrayToJsObject_Recurse( |
| 117 | + array( |
| 118 | + 'cb_inx' => htmlspecialchars( $wgRequest->getVal('cb_inx') ), |
| 119 | + 'id' => $insert_id |
| 120 | + ) |
| 121 | + ) . ');'; |
39 | 122 | } |
| 123 | + |
| 124 | +/* |
| 125 | + * @@todo should use API json output wrappers |
| 126 | + */ |
| 127 | +if( ! function_exists('php2jsObj') ){ |
| 128 | + function php2jsObj( $array, $objName = 'mv_result' ) |
| 129 | + { |
| 130 | + return $objName . ' = ' . phpArrayToJsObject_Recurse( $array ) . ";\n"; |
| 131 | + } |
| 132 | +} |
| 133 | +if( ! function_exists('PhpArrayToJsObject_Recurse') ){ |
| 134 | + function PhpArrayToJsObject_Recurse( $array ) { |
| 135 | + // Base case of recursion: when the passed value is not a PHP array, just output it (in quotes). |
| 136 | + if ( ! is_array( $array ) && !is_object( $array ) ) { |
| 137 | + // Handle null specially: otherwise it becomes "". |
| 138 | + if ( $array === null ) |
| 139 | + { |
| 140 | + return 'null'; |
| 141 | + } |
| 142 | + return '"' . javascript_escape( $array ) . '"'; |
| 143 | + } |
| 144 | + // Open this JS object. |
| 145 | + $retVal = "{"; |
| 146 | + // Output all key/value pairs as "$key" : $value |
| 147 | + // * Output a JS object (using recursion), if $value is a PHP array. |
| 148 | + // * Output the value in quotes, if $value is not an array (see above). |
| 149 | + $first = true; |
| 150 | + foreach ( $array as $key => $value ) { |
| 151 | + // Add a comma before all but the first pair. |
| 152 | + if ( ! $first ) { |
| 153 | + $retVal .= ', '; |
| 154 | + } |
| 155 | + $first = false; |
| 156 | + // Quote $key if it's a string. |
| 157 | + if ( is_string( $key ) ) { |
| 158 | + $key = '"' . $key . '"'; |
| 159 | + } |
| 160 | + $retVal .= $key . ' : ' . PhpArrayToJsObject_Recurse( $value ); |
| 161 | + } |
| 162 | + // Close and return the JS object. |
| 163 | + return $retVal . "}"; |
| 164 | + } |
| 165 | +} |
| 166 | +if( ! function_exists('javascript_escape')){ |
| 167 | + function javascript_escape( $val ) { |
| 168 | + // first strip /r |
| 169 | + $val = str_replace( "\r", '', $val ); |
| 170 | + return str_replace( array( '"', "\n", '{', '}' ), |
| 171 | + array( '\"', '"' . "+\n" . '"', '\{', '\}' ), |
| 172 | + $val ); |
| 173 | + } |
| 174 | +} |
| 175 | + |
40 | 176 | ?> |
\ No newline at end of file |
Index: trunk/extensions/PlayerStatsGrabber/playerStats.js |
— | — | @@ -27,21 +27,32 @@ |
28 | 28 | //@@todo research if we can detect if MS video support a given codec |
29 | 29 | |
30 | 30 | //detect flash support |
31 | | - if(FlashDetect.installed) |
32 | | - this.clientSupports['flash']; |
| 31 | + if( FlashDetect.installed ) |
| 32 | + this.clientSupports['flash']=true; |
33 | 33 | |
34 | | - for(i in this.clientSupports){ |
35 | | - url+='&cs='+encodeURIComponent(i); |
| 34 | + var j=0; |
| 35 | + for(var i in this.clientSupports){ |
| 36 | + url+='&cs[]='+encodeURIComponent(i); |
| 37 | + j++; |
36 | 38 | } |
| 39 | + |
37 | 40 | //get the flash version: |
38 | 41 | url+='&fv='+ encodeURIComponent( FlashDetect.raw ); |
39 | 42 | |
| 43 | + |
| 44 | + //detect java version if possible: (ie not IE with default security) |
| 45 | + if( javaDetect.version ){ |
| 46 | + url+= '&jv='+ encodeURIComponent ( javaDetect.version ); |
| 47 | + } |
| 48 | + |
40 | 49 | //add some additional params seperated out to enum keys: |
41 | 50 | url+= '&b_user_agent=' +encodeURIComponent( navigator.userAgent ); |
42 | 51 | url+= '&b_name=' + encodeURIComponent( BrowserDetect.browser ) ; |
43 | 52 | url+= '&b_version=' + encodeURIComponent( BrowserDetect.version ); |
44 | 53 | url+= '&b_os=' + encodeURIComponent( BrowserDetect.OS ) ; |
45 | 54 | |
| 55 | + //and finaly add the user hash: |
| 56 | + url+='&uh=' + encodeURIComponent ( wgOggPlayer.userHash ); |
46 | 57 | |
47 | 58 | //now send out our stats update (run via javascript include to support remote servers: |
48 | 59 | do_request ( url, function( responseObj ){ |
— | — | @@ -82,11 +93,7 @@ |
83 | 94 | js_log('missing req cb index'); |
84 | 95 | return false; |
85 | 96 | } |
86 | | - if(!response['pay_load']){ |
87 | | - js_log("missing pay load"); |
88 | | - return false; |
89 | | - } |
90 | | - global_req_cb[response['cb_inx']](response['pay_load']); |
| 97 | + global_req_cb[response['cb_inx']](response); |
91 | 98 | } |
92 | 99 | function js_log(string){ |
93 | 100 | if( window.console ){ |
— | — | @@ -108,6 +115,43 @@ |
109 | 116 | return false; |
110 | 117 | } |
111 | 118 | |
| 119 | +//checks for java support records java version if possible |
| 120 | +var javaDetect = { |
| 121 | + javaEnabled: false, |
| 122 | + version: false, |
| 123 | + init:function(){ |
| 124 | + if (typeof navigator != 'undefined' && typeof navigator.javaEnabled != 'undefined'){ |
| 125 | + this.javaEnabled = navigator.javaEnabled(); |
| 126 | + }else{ |
| 127 | + this.javaEnabled = 'unknown'; |
| 128 | + } |
| 129 | + if (navigator.javaEnabled() && typeof java != 'undefined') |
| 130 | + this.version = java.lang.System.getProperty("java.version"); |
| 131 | + //try to get the IE version of java (not likely to work with default security setting) |
| 132 | + if( wgOggPlayer.msie ){ |
| 133 | + var shell; |
| 134 | + try { |
| 135 | + // Create WSH(WindowsScriptHost) shell, available on Windows only |
| 136 | + shell = new ActiveXObject("WScript.Shell"); |
| 137 | + |
| 138 | + if (shell != null) { |
| 139 | + // Read JRE version from Window Registry |
| 140 | + try { |
| 141 | + this.version = shell.regRead("HKEY_LOCAL_MACHINE\\Software\\JavaSoft\\Java Runtime Environment\\CurrentVersion"); |
| 142 | + } catch(e) { |
| 143 | + // handle exceptions raised by 'shell.regRead(...)' here |
| 144 | + // so that the outer try-catch block would receive only |
| 145 | + // exceptions raised by 'shell = new ActiveXObject(...)' |
| 146 | + } |
| 147 | + } |
| 148 | + } catch(e) { |
| 149 | + //could not get it |
| 150 | + } |
| 151 | + } |
| 152 | + } |
| 153 | +} |
| 154 | +javaDetect.init(); |
| 155 | + |
112 | 156 | //http://www.featureblend.com/license.txt |
113 | 157 | var FlashDetect=new function(){var self=this;self.installed=false;self.raw="";self.major=-1;self.minor=-1;self.revision=-1;self.revisionStr="";var activeXDetectRules=[{"name":"ShockwaveFlash.ShockwaveFlash.7","version":function(obj){return getActiveXVersion(obj);}},{"name":"ShockwaveFlash.ShockwaveFlash.6","version":function(obj){var version="6,0,21";try{obj.AllowScriptAccess="always";version=getActiveXVersion(obj);}catch(err){} |
114 | 158 | return version;}},{"name":"ShockwaveFlash.ShockwaveFlash","version":function(obj){return getActiveXVersion(obj);}}];var getActiveXVersion=function(activeXObj){var version=-1;try{version=activeXObj.GetVariable("$version");}catch(err){} |
Index: trunk/extensions/PlayerStatsGrabber/playerStats.sql |
— | — | @@ -0,0 +1,20 @@ |
| 2 | +CREATE TABLE IF NOT EXISTS `player_stats_log` ( |
| 3 | + `id` int(11) unsigned NOT NULL auto_increment, |
| 4 | + `time_stamp` timestamp NOT NULL default CURRENT_TIMESTAMP, |
| 5 | + `user_hash` char(40) character set utf8 collate utf8_bin NOT NULL, |
| 6 | + `html5_video_enabled` tinyint(1) default NULL, |
| 7 | + `java_enabled` tinyint(1) default NULL, |
| 8 | + `flash_enabled` tinyint(1) default NULL, |
| 9 | + `quicktime_enabled` tinyint(1) default NULL, |
| 10 | + `vlc_enabled` tinyint(1) default NULL, |
| 11 | + `mplayer_enabled` tinyint(1) default NULL, |
| 12 | + `totem_enabled` tinyint(1) default NULL, |
| 13 | + `b_user_agent` varchar(254) character set utf8 collate utf8_bin NOT NULL, |
| 14 | + `b_name` enum('Chrome','OmniWeb','Safari','Opera','iCab','Konqueror','Mozilla','Firefox','Camino','Netscape','Explorer') character set utf8 collate utf8_bin NOT NULL, |
| 15 | + `b_version` varchar(20) character set utf8 collate utf8_bin NOT NULL, |
| 16 | + `b_os` enum('Linux','Windows','Mac') character set utf8 collate utf8_bin NOT NULL, |
| 17 | + `flash_version` varchar(128) character set utf8 collate utf8_bin default NULL, |
| 18 | + `java_version` varchar(128) character set utf8 collate utf8_bin default NULL, |
| 19 | + PRIMARY KEY (`id`), |
| 20 | + KEY `user_hash` (`user_hash`) |
| 21 | +) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=1 ; |