PageRenderTime 43ms CodeModel.GetById 13ms RepoModel.GetById 1ms app.codeStats 0ms

/extensions/Survey/specials/SpecialSurvey.php

https://github.com/ChuguluGames/mediawiki-svn
PHP | 372 lines | 246 code | 58 blank | 68 comment | 20 complexity | 9e5543093e28c5de6b7458e4a0b27a0c MD5 | raw file
  1. <?php
  2. /**
  3. * Administration interface for a survey.
  4. *
  5. * @since 0.1
  6. *
  7. * @file SpecialSurvey.php
  8. * @ingroup Survey
  9. *
  10. * @licence GNU GPL v3 or later
  11. * @author Jeroen De Dauw < jeroendedauw@gmail.com >
  12. */
  13. class SpecialSurvey extends SpecialSurveyPage {
  14. /**
  15. * Constructor.
  16. *
  17. * @since 0.1
  18. */
  19. public function __construct() {
  20. parent::__construct( 'EditSurvey', 'surveyadmin', false );
  21. }
  22. /**
  23. * Main method.
  24. *
  25. * @since 0.1
  26. *
  27. * @param string $arg
  28. */
  29. public function execute( $subPage ) {
  30. if ( !parent::execute( $subPage ) ) {
  31. return;
  32. }
  33. global $wgRequest, $wgUser;
  34. if ( $wgRequest->wasPosted() && $wgUser->matchEditToken( $wgRequest->getVal( 'wpEditToken' ) ) ) {
  35. $this->handleSubmission();
  36. } else {
  37. if ( is_null( $subPage ) || trim( $subPage ) === '' ) {
  38. $this->getOutput()->redirect( SpecialPage::getTitleFor( 'Surveys' )->getLocalURL() );
  39. } else {
  40. $subPage = trim( $subPage );
  41. $survey = Survey::newFromName( $subPage, null, true );
  42. if ( $survey === false ) {
  43. $survey = new Survey( array( 'name' => $subPage ), true );
  44. }
  45. else {
  46. $this->displayNavigation( array(
  47. wfMsgExt( 'survey-navigation-take', 'parseinline', $subPage ),
  48. wfMsgExt( 'survey-navigation-stats', 'parseinline', $subPage ),
  49. wfMsgExt( 'survey-navigation-list', 'parseinline' )
  50. ) );
  51. }
  52. $this->showSurvey( $survey );
  53. $this->addModules( 'ext.survey.special.survey' );
  54. }
  55. }
  56. }
  57. /**
  58. * Handle submission of a survey.
  59. * This conists of finding the posted survey data, constructing the
  60. * corresponding objects, writing these to the db and then redirecting
  61. * the user back to the surveys list.
  62. *
  63. * @since 0.1
  64. */
  65. protected function handleSubmission() {
  66. global $wgRequest;
  67. $values = $wgRequest->getValues();
  68. if ( $wgRequest->getInt( 'survey-id' ) == 0 ) {
  69. $survey = new Survey( null );
  70. } else {
  71. $survey = Survey::newFromId( $wgRequest->getInt( 'survey-id' ), null, false );
  72. }
  73. foreach ( array( 'name', 'title', 'header', 'footer', 'thanks' ) as $field ) {
  74. $survey->setField( $field, $wgRequest->getText( 'survey-' . $field ) );
  75. }
  76. $survey->setField( 'enabled', $wgRequest->getCheck( 'survey-enabled' ) );
  77. foreach ( array( 'user_type', 'ratio', 'min_pages', 'expiry' ) as $field ) {
  78. $survey->setField( $field, $wgRequest->getInt( 'survey-' . $field ) );
  79. }
  80. $survey->setField( 'namespaces', array() );
  81. $survey->setQuestions( $this->getSubmittedQuestions() );
  82. $survey->writeToDB();
  83. $this->getOutput()->redirect( SpecialPage::getTitleFor( 'Surveys' )->getLocalURL() );
  84. }
  85. /**
  86. * Gets a list of submitted surveys.
  87. *
  88. * @return array of SurveyQuestion
  89. */
  90. protected function getSubmittedQuestions() {
  91. $questions = array();
  92. foreach ( $GLOBALS['wgRequest']->getValues() as $name => $value ) {
  93. $matches = array();
  94. if ( preg_match( '/survey-question-text-(\d+)/', $name, $matches ) ) {
  95. $questions[] = $this->getSubmittedQuestion( $matches[1] );
  96. } elseif ( preg_match( '/survey-question-text-new-(\d+)/', $name, $matches ) ) {
  97. $questions[] = $this->getSubmittedQuestion( $matches[1], true );
  98. }
  99. }
  100. return $questions;
  101. }
  102. /**
  103. * Create and return a survey question object from the submitted data.
  104. *
  105. * @since 0.1
  106. *
  107. * @param integer|null $questionId
  108. *
  109. * @return SurveyQuestion
  110. */
  111. protected function getSubmittedQuestion( $questionId, $isNewQuestion = false ) {
  112. global $wgRequest;
  113. if ( $isNewQuestion ) {
  114. $questionDbId = null;
  115. $questionId = "new-$questionId";
  116. } else {
  117. $questionDbId = $questionId;
  118. }
  119. $answers = array_filter(
  120. explode( "\n", $wgRequest->getText( "survey-question-answers-$questionId" ) ),
  121. function( $line ) {
  122. return trim( $line ) != '';
  123. }
  124. );
  125. $question = new SurveyQuestion( array(
  126. 'id' => $questionDbId,
  127. 'removed' => 0,
  128. 'text' => $wgRequest->getText( "survey-question-text-$questionId" ),
  129. 'type' => $wgRequest->getInt( "survey-question-type-$questionId" ),
  130. 'required' => 0, // $wgRequest->getCheck( "survey-question-required-$questionId" ),
  131. 'answers' => $answers
  132. ) );
  133. return $question;
  134. }
  135. /**
  136. * Show error when requesting a non-existing survey.
  137. *
  138. * @since 0.1
  139. */
  140. protected function showNameError() {
  141. $this->getOutput()->addHTML(
  142. '<p class="errorbox">' . wfMsgHtml( 'surveys-special-unknown-name' ) . '</p>'
  143. );
  144. }
  145. /**
  146. * Get an array of numbers with as keys the formatted version of the values.
  147. *
  148. * @since 0.1
  149. *
  150. * @param array $numbers
  151. *
  152. * @return array
  153. */
  154. protected function getNumericalOptions( array $numbers ) {
  155. $lang = $this->getLang();
  156. return array_flip( array_map(
  157. function( $n ) use( $lang ) { return $lang->formatNum( $n ); },
  158. array_combine( $numbers, $numbers )
  159. ) );
  160. }
  161. /**
  162. * Show the survey.
  163. *
  164. * @since 0.1
  165. *
  166. * @param Survey $survey
  167. */
  168. protected function showSurvey( Survey $survey ) {
  169. $fields = array();
  170. $fields[] = array(
  171. 'type' => 'hidden',
  172. 'default' => $survey->getId(),
  173. 'name' => 'survey-id',
  174. 'id' => 'survey-id',
  175. );
  176. $fields[] = array(
  177. 'type' => 'hidden',
  178. 'default' => $survey->getField( 'name' ),
  179. 'name' => 'survey-name',
  180. 'id' => 'survey-name',
  181. );
  182. $fields[] = array(
  183. 'type' => 'hidden',
  184. 'default' => $survey->getField( 'expiry' ),
  185. 'name' => 'survey-expiry',
  186. 'id' => 'survey-expiry',
  187. );
  188. $fields[] = array(
  189. 'class' => 'SurveyNameField',
  190. 'default' => $survey->getField( 'name' ),
  191. 'label-message' => 'survey-special-label-name',
  192. 'style' => 'font-weight: bold;'
  193. );
  194. $fields[] = array(
  195. 'type' => 'text',
  196. 'default' => $survey->getField( 'title' ),
  197. 'label-message' => 'survey-special-label-title',
  198. 'id' => 'survey-title',
  199. 'name' => 'survey-title',
  200. );
  201. $fields[] = array(
  202. 'type' => 'check',
  203. 'default' => $survey->getField( 'enabled' ) ? '1' : '0',
  204. 'label-message' => 'survey-special-label-enabled',
  205. 'id' => 'survey-enabled',
  206. 'name' => 'survey-enabled',
  207. );
  208. $fields[] = array(
  209. 'type' => 'radio',
  210. 'default' => $survey->getField( 'user_type' ),
  211. 'label-message' => 'survey-special-label-usertype',
  212. 'id' => 'survey-user_type',
  213. 'name' => 'survey-user_type',
  214. 'options' => array(
  215. wfMsg( 'survey-user-type-all' ) => Survey::$USER_ALL,
  216. wfMsg( 'survey-user-type-loggedin' ) => Survey::$USER_LOGGEDIN,
  217. wfMsg( 'survey-user-type-confirmed' ) => Survey::$USER_CONFIRMED,
  218. wfMsg( 'survey-user-type-editor' ) => Survey::$USER_EDITOR,
  219. wfMsg( 'survey-user-type-anon' ) => Survey::$USER_ANON,
  220. ),
  221. );
  222. $fields[] = array(
  223. 'type' => 'select',
  224. 'default' => $survey->getField( 'ratio' ),
  225. 'label-message' => 'survey-special-label-ratio',
  226. 'id' => 'survey-ratio',
  227. 'name' => 'survey-ratio',
  228. 'options' => $this->getNumericalOptions( array_merge( array( 0.01, 0.1 ), range( 1, 100 ) ) ),
  229. );
  230. $fields[] = array(
  231. 'type' => 'select',
  232. 'default' => $survey->getField( 'min_pages' ),
  233. 'label-message' => 'survey-special-label-minpages',
  234. 'id' => 'survey-min_pages',
  235. 'name' => 'survey-min_pages',
  236. 'options' => $this->getNumericalOptions( range( 0, 250 ) ),
  237. );
  238. $fields[] = array(
  239. 'type' => 'text',
  240. 'default' => $survey->getField( 'header' ),
  241. 'label-message' => 'survey-special-label-header',
  242. 'id' => 'survey-header',
  243. 'name' => 'survey-header',
  244. );
  245. $fields[] = array(
  246. 'type' => 'text',
  247. 'default' => $survey->getField( 'footer' ),
  248. 'label-message' => 'survey-special-label-footer',
  249. 'id' => 'survey-footer',
  250. 'name' => 'survey-footer',
  251. );
  252. $fields[] = array(
  253. 'type' => 'text',
  254. 'default' => $survey->getField( 'thanks' ),
  255. 'label-message' => 'survey-special-label-thanks',
  256. 'id' => 'survey-thanks',
  257. 'name' => 'survey-thanks',
  258. );
  259. foreach ( $survey->getQuestions() as /* SurveyQuestion */ $question ) {
  260. $fields[] = array(
  261. 'class' => 'SurveyQuestionField',
  262. 'options' => $question->toArray()
  263. );
  264. }
  265. // getContext was added in 1.18 and since that version is
  266. // the second argument for the HTMLForm constructor.
  267. if ( version_compare( $GLOBALS['wgVersion'], '1.18', '>=' ) ) {
  268. $form = new HTMLForm( $fields, $this->getContext() );
  269. } else {
  270. $form = new HTMLForm( $fields );
  271. $form->setTitle( $this->getTitle() );
  272. }
  273. $form->setSubmitText( wfMsg( 'surveys-special-save' ) );
  274. $form->addButton(
  275. 'cancelEdit',
  276. wfMsg( 'cancel' ),
  277. 'cancelEdit',
  278. array(
  279. 'onclick' => 'window.location="' . SpecialPage::getTitleFor( 'Surveys' )->getFullURL() . '";return false;'
  280. )
  281. );
  282. $form->show();
  283. }
  284. }
  285. class SurveyQuestionField extends HTMLFormField {
  286. public function getInputHTML( $value ) {
  287. $attribs = array(
  288. 'class' => 'survey-question-data'
  289. );
  290. foreach ( $this->mParams['options'] as $name => $value ) {
  291. if ( is_bool( $value ) ) {
  292. $value = $value ? '1' : '0';
  293. } elseif( is_object( $value ) || is_array( $value ) ) {
  294. $value = FormatJson::encode( $value );
  295. }
  296. $attribs['data-' . $name] = $value;
  297. }
  298. return Html::element(
  299. 'div',
  300. $attribs
  301. );
  302. }
  303. }
  304. class SurveyNameField extends HTMLFormField {
  305. public function getInputHTML( $value ) {
  306. return Html::element(
  307. 'span',
  308. array(
  309. 'style' => $this->mParams['style']
  310. ),
  311. $value
  312. );
  313. }
  314. }