course_search.module

  1. 7.x modules/course_search/course_search.module
  2. 6.x modules/course_search/course_search.module
  3. 4.x modules/course_search/course_search.module
  4. 5.x modules/course_search/course_search.module

This module allows users to search for courses, descriptions, and, if supported, rotation schedules and sample syllabi.

File

modules/course_search/course_search.module
View source
  1. <?php
  2. /**
  3. * @file
  4. * This module allows users to search for courses, descriptions, and, if supported, rotation schedules
  5. * and sample syllabi.
  6. */
  7. function course_search_menu() {
  8. $items = array();
  9. $items["tools/course-search"] = array(
  10. "title" => "Course Search",
  11. "description" => "Use this tool to view course descriptions, sample syllabi, and projected course offering schedules.",
  12. "page_callback" => "course_search_display_search",
  13. "access_arguments" => array('access_course_search'),
  14. "page_settings" => array(
  15. "page_has_search" => FALSE,
  16. "page_banner_is_link" => TRUE,
  17. "page_hide_report_error" => TRUE,
  18. "target" => "_blank",
  19. "menu_icon" => fp_get_module_path('course_search') . "/icons/book_go.png",
  20. ),
  21. "type" => MENU_TYPE_NORMAL_ITEM,
  22. );
  23. $items["course-search/get-syllabus"] = array(
  24. "title" => "Course Search",
  25. "page_callback" => "course_search_download_syllabus",
  26. "access_arguments" => array('access_course_search'),
  27. "type" => MENU_TYPE_CALLBACK,
  28. );
  29. $items["admin/config/course-search"] = array(
  30. "title" => "Course Search Settings",
  31. "description" => "Administer the Course Search module's settings",
  32. "page_callback" => "fp_render_form",
  33. "page_arguments" => array("course_search_settings_form", "system_settings"),
  34. "access_arguments" => array("administer_course_search"),
  35. "page_settings" => array(
  36. "page_has_search" => FALSE,
  37. "page_banner_is_link" => TRUE,
  38. "page_hide_report_error" => TRUE,
  39. "menu_icon" => fp_get_module_path('course_search') . "/icons/book_go.png",
  40. "menu_links" => array(
  41. 0 => array(
  42. "text" => "Admin Console",
  43. "path" => "admin-tools/admin",
  44. "query" => "de_catalog_year=%DE_CATALOG_YEAR%",
  45. ),
  46. ),
  47. ),
  48. "type" => MENU_TYPE_NORMAL_ITEM,
  49. );
  50. $items["tools/course-search/courses"] = array(
  51. "title" => "Course Search",
  52. "page_callback" => "course_search_display_courses",
  53. "access_arguments" => array('access_course_search'),
  54. "page_settings" => array(
  55. "page_has_search" => FALSE,
  56. "page_banner_is_link" => TRUE,
  57. "page_hide_report_error" => TRUE,
  58. ),
  59. "type" => MENU_TYPE_CALLBACK,
  60. );
  61. $items["tools/course-search/edit-list"] = array(
  62. "title" => "Update Course Information",
  63. "page_callback" => "course_search_display_edit_courses",
  64. "access_arguments" => array("can_update_course_info_details"),
  65. "page_settings" => array(
  66. "page_has_search" => FALSE,
  67. "menu_links" => array(
  68. 0 => array(
  69. "text" => "Back to Course Search",
  70. "path" => "tools/course-search",
  71. ),
  72. ),
  73. ),
  74. "file" => menu_get_module_path("course_search") . "/course_search.edit.inc",
  75. "type" => MENU_TYPE_CALLBACK,
  76. );
  77. $items["tools/course-search/edit-info-details"] = array(
  78. "title" => "Edit Course Info Details",
  79. "page_callback" => "fp_render_form",
  80. "page_arguments" => array("course_search_edit_course_details_form"),
  81. "access_arguments" => array("can_update_course_info_details"),
  82. "page_settings" => array(
  83. "page_has_search" => FALSE,
  84. "page_banner_is_link" => TRUE,
  85. "menu_links" => array(
  86. 0 => array(
  87. "text" => "Back to Course Search",
  88. "path" => "tools/course-search",
  89. ),
  90. 1 => array(
  91. "text" => "Back to Course Edit List",
  92. "path" => "tools/course-search/edit-list",
  93. ),
  94. ),
  95. ),
  96. "file" => menu_get_module_path("course_search") . "/course_search.edit.inc",
  97. "type" => MENU_TYPE_CALLBACK,
  98. );
  99. $items["tools/course-search/view-reports"] = array(
  100. "title" => "View Reports",
  101. "page_callback" => "course_search_display_view_reports",
  102. "access_arguments" => array("can_update_course_info_details"),
  103. "page_settings" => array(
  104. "page_has_search" => FALSE,
  105. "menu_links" => array(
  106. 0 => array(
  107. "text" => "Back to Course Search",
  108. "path" => "tools/course-search",
  109. ),
  110. 1 => array(
  111. "text" => "Back to Course Edit List",
  112. "path" => "tools/course-search/edit-list",
  113. ),
  114. ),
  115. ),
  116. "file" => menu_get_module_path("course_search") . "/course_search.edit.inc",
  117. "type" => MENU_TYPE_CALLBACK,
  118. );
  119. // Simple callback to download CSV
  120. $items["tools/course-search/get-offering-csv"] = array(
  121. "page_callback" => "course_search_get_offering_csv",
  122. "access_arguments" => array("can_update_course_info_details"),
  123. "file" => menu_get_module_path("course_search") . "/course_search.edit.inc",
  124. "type" => MENU_TYPE_CALLBACK,
  125. );
  126. return $items;
  127. }
  128. function course_search_perm() {
  129. return array(
  130. "access_course_search" => array(
  131. 'title' => t('Access course search'),
  132. 'description' => t('Users with this setting are allowed to actually view the course search link,
  133. descriptions, syllabi, etc.'),
  134. ),
  135. "administer_course_search" => array(
  136. "title" => t("Administer course search"),
  137. "description" => t("Users with this setting will be able
  138. to modify settings for the Course Search module."),
  139. ),
  140. "can_update_course_info_details" => array(
  141. "title" => t("Can update course info details"),
  142. "description" => t("Allows users to update the 'course info' details,
  143. like the course's sample syllabus and rotation
  144. schedule."),
  145. ),
  146. );
  147. }
  148. /**
  149. * The system settins form for course_search settings.
  150. */
  151. function course_search_settings_form() {
  152. $form = array();
  153. $form["course_search_avail_term_id_suffix_order"] = array(
  154. "type" => "textfield",
  155. "label" => t("Available Term ID Suffixes & Order"),
  156. "value" => variable_get("course_search_avail_term_id_suffix_order", ""),
  157. "description" => t("Enter the order of term ID suffixes, so that they will display
  158. in the correct order in the table of available course
  159. offerings. Separate by comma.") . "
  160. <br>
  161. Ex: 60, 40, 41, 80, 81, mm",
  162. );
  163. $form["course_search_avail_term_headers"] = array(
  164. "type" => "textfield",
  165. "label" => t("Available Term Table Headers"),
  166. "value" => variable_get("course_search_avail_term_headers", ""),
  167. "description" => t("Enter the table headers for the available table, in the same
  168. order as the suffix order above.") . "
  169. <br>
  170. Ex: Spring, May, Summer 1, Summer 2, Fall, Winter",
  171. );
  172. $form["course_search_avail_term_mobile_headers"] = array(
  173. "type" => "textfield",
  174. "label" => t("Available Term Mobile Table Headers"),
  175. "value" => variable_get("course_search_avail_term_mobile_headers", ""),
  176. "description" => t("Enter the table headers for the available table, in the same
  177. order as the suffix order above, as it should be displayed on
  178. a mobile device (with a smaller screen).") . "
  179. <br>
  180. Ex: Spr, May, Sum1, Sum2, Fall, Win",
  181. );
  182. return $form;
  183. }
  184. /**
  185. * This function will actually deliver a syllabus to the user's browser
  186. * for download.
  187. *
  188. */
  189. function course_search_download_syllabus() {
  190. // Get our global variables...
  191. $c = trim($_REQUEST["c"]);
  192. $id = trim($_REQUEST["id"]);
  193. $db = get_global_database_handler();
  194. $temp = explode("_", $c);
  195. $subject_id = $temp[0];
  196. $course_num = $temp[1];
  197. // Get the filename in question...
  198. $query = "select * from course_syllabi
  199. where course_perm_id = '?' ";
  200. $params = array($subject_id . "_" . $course_num);
  201. if ($id != "") {
  202. $query = "select * from course_syllabi
  203. where course_id = '?' ";
  204. $params = array($id);
  205. }
  206. $res = db_query($query, $params);
  207. $cur = db_fetch_array($res);
  208. $filename = $cur["filename"];
  209. $course_id = $cur["course_id"];
  210. // Get the latest subject_id and course_num for this course!
  211. $new_course = new Course();
  212. $new_course->course_id = $course_id;
  213. $new_course->catalog_year = variable_get("current_catalog_year", 2006);
  214. $new_course->load_descriptive_data(false, false, true);
  215. $subject_id = $new_course->subject_id;
  216. $course_num = $new_course->course_num;
  217. $files_path = $GLOBALS["fp_system_settings"]["file_system_path"];
  218. if ($filename == "" || !file_exists("$files_path/custom/files/syllabi/$filename"))
  219. { // Check to make sure the src file actually exists.
  220. // Display a message, letting the user know it does not
  221. // exist.
  222. watchdog("syllabus", "fail,$c", array(), WATCHDOG_ERROR);
  223. fp_add_message(t("Sorry, the syllabus for @course could not be found.", array("@course" => "$subject_id $course_num")));
  224. // Just so admins can see:
  225. fpm("Admin: file path attempted: $files_path/custom/files/syllabi/$filename");
  226. return;
  227. }
  228. watchdog("syllabus", "get,$c", array(), WATCHDOG_DEBUG);
  229. $content_type = "application/plain"; // default, save as generic binary file.
  230. $temp = explode("\.", $filename);
  231. $ext = $temp[count($temp) - 1]; // get the original file extension.
  232. // attempt to match to the correct content_type...
  233. if ($ext == "pdf"){ $content_type = "application/pdf"; }
  234. if ($ext == "doc") { $content_type = "application/msword"; }
  235. if ($ext == "docx") { $content_type = "application/vnd.openxmlformats-officedocument.wordprocessingml.document"; }
  236. if ($ext == "txt") { $content_type = "text/plain"; }
  237. if ($ext == "pot") { $content_type = "application/mspowerpoint"; }
  238. if ($ext == "ppt") { $content_type = "application/powerpoint"; }
  239. if (strstr($ext,"xl")) { $content_type = "application/excel"; }
  240. $fn = urlencode($subject_id . "_" . $course_num . "_SAMPLE_SYLLABUS") .".$ext"; // make it a safe filename.
  241. $fn = str_replace("+"," ",$fn); // restore spaces from + symbols...
  242. // Give it to the browser!
  243. header('Content-type: ' . $content_type . '');
  244. header('Content-Disposition: attachment; filename="' . $fn . '"');
  245. readfile("$files_path/custom/files/syllabi/" . $filename . "");
  246. die;
  247. }
  248. /**
  249. * Show the user their select of courses.
  250. */
  251. function course_search_display_courses() {
  252. $rtn = "";
  253. fp_add_css(fp_get_module_path("course_search") . "/css/course_search_style.css");
  254. if (fp_screen_is_mobile()) {
  255. fp_add_css(fp_get_module_path("course_search") . "/css/course_search_mobile_style.css");
  256. }
  257. $mode = "";
  258. // We are going to be setting up a render array for this screen, so other modules can alter it later.
  259. $render = array();
  260. $render["#id"] = "course_search_display_courses";
  261. $rtn .= fp_render_curved_line(t("Course Search"));
  262. $settings = fp_get_system_settings();
  263. $current_catalog_year = $settings["current_catalog_year"];
  264. // catalog_year is always just whatever the current year is.
  265. $catalog_year = $current_catalog_year;
  266. $subject_id = $_REQUEST["subject_id"];
  267. $render["#catalog_year"] = array(
  268. "type" => "do_not_render",
  269. "value" => $catalog_year,
  270. );
  271. $render["#subject_id"] = array(
  272. "type" => "do_not_render",
  273. "value" => $subject_id,
  274. );
  275. $clean_urls = variable_get("clean_urls", FALSE);
  276. // Try to find out the title to this subject, if one exists
  277. // in our subjects table.
  278. $res = db_query("SELECT * FROM subjects
  279. WHERE subject_id ='?' ", $subject_id);
  280. $cur = db_fetch_array($res);
  281. $title = $cur["title"];
  282. if ($title == "") $title = $subject_id;
  283. //$rtn .= t("Current catalog year:") . " <b>$catalog_year-" . ($catalog_year +1) . "</b>
  284. // ";
  285. $render["current_cat_year"] = array(
  286. "value" => t("Current catalog year:") . " <b>$catalog_year-" . ($catalog_year +1) . "</b>",
  287. );
  288. $important_notice = "
  289. <div class='tenpt hypo' style='padding: 5px;'>
  290. <b>Important Notice:</b> <ul style='margin-top: 5px;'>
  291. <li>Course descriptions are intended for unofficial use only. Consult your catalog for the official listing.</li>
  292. <li>Anticipated course availability reflects current plans but actual offerings may change because of factors
  293. unknown at planning time. Consult the schedule of classes for final offerings.</li>
  294. <li>Sample syllabi are provided for planning purposes only. The syllabus used by an instructor may vary from this sample.</li>
  295. <li>Please ask your advisor if you have any questions about a course.</li>
  296. </ul>
  297. </div>
  298. ";
  299. if (fp_screen_is_mobile()) {
  300. // TODO: implement the fieldset thingy.
  301. //$pC .= $screen->draw_c_fieldset($important_notice, "View important notice", true);
  302. }
  303. else {
  304. //$rtn .= $important_notice;
  305. $render["important_notice"] = array(
  306. "value" => $important_notice,
  307. );
  308. }
  309. /*
  310. $rtn .= "
  311. <!-- <div> -->
  312. <div style='margin: 10px 0 20px 10px; border-bottom: 2px solid black;'>
  313. <span style='font-size: 14pt; font-weight:bold;'>$title</span>
  314. " . l("[change]", "tools/course-search", "", array("class" => "nounderline")) . "
  315. </div>
  316. ";
  317. */
  318. $render["subject_change"] = array(
  319. "value" => "<div style='margin: 10px 0 20px 10px; border-bottom: 2px solid black;'>
  320. <span style='font-size: 14pt; font-weight:bold;'>$title</span>
  321. " . l("[change]", "tools/course-search", "", array("class" => "nounderline")) . "
  322. </div>",
  323. );
  324. // Draw the term selector.
  325. $html = "";
  326. $only_term = @$_REQUEST["only_term"];
  327. $html .= "<form id='term_form' action='" . fp_url("tools/course-search/courses") . "' method='GET'>
  328. <input type='hidden' name='mode' value='$subject_id'>
  329. <input type='hidden' name='subject_id' value='$subject_id'>
  330. ";
  331. if (!$clean_urls) {
  332. // Hack for if clean URLs isn't enabled
  333. $html .= "<input type='hidden' name='q' value='tools/course-search/courses'>";
  334. }
  335. $html .= "
  336. View courses offered:
  337. <select name='only_term' onChange='document.getElementById(\"term_form\").submit();'>
  338. <option value=''>Any term</option>
  339. ";
  340. //$term_array = get_term_id_suffixes();
  341. $term_array = csv_to_array(variable_get("course_search_avail_term_id_suffix_order"));
  342. $schedule_text = "";
  343. for ($t = $catalog_year; $t <= $catalog_year + 4; $t++)
  344. {
  345. $html .= "<option value=''>---------------------</option>";
  346. foreach($term_array as $x)
  347. {
  348. $schedule_text .= "<td class='tenpt' align='center'>";
  349. $the_term_id = $t . $x;
  350. $temp_course = new Course();
  351. $temp_course->term_id = $the_term_id;
  352. $term_desc = $temp_course->get_term_description(false);
  353. $sel = "";
  354. if ($only_term != "" && $only_term == "$the_term_id") {
  355. $sel = " selected";
  356. }
  357. $html .= "<option value='$the_term_id' $sel>$term_desc</option> \n";
  358. }
  359. }
  360. $html .= "
  361. </select>
  362. </form>";
  363. $render["term_selector_form"] = array(
  364. "value" => $html,
  365. );
  366. if ($only_term != "") {
  367. $temp_course = new Course();
  368. $temp_course->term_id = $only_term;
  369. $term_desc = $temp_course->get_term_description(false);
  370. /*
  371. $rtn .= "<div style='font-weight: bold; padding-bottom: 20px;'>
  372. The following courses are currently scheduled to be offered during " . $term_desc . ".
  373. </div>";
  374. */
  375. $render["term_selected_only_term"] = array(
  376. "value" => "<div style='font-weight: bold; padding-bottom: 20px;'>
  377. " . t("The following courses are currently scheduled to be offered during") . $term_desc . "
  378. </div>",
  379. );
  380. }
  381. $term_structures = get_term_structures();
  382. $grad_notice_flag = false;
  383. $temp_course = new Course();
  384. // removed course_num < 500 and
  385. $result = db_query("SELECT * FROM courses
  386. WHERE `catalog_year`='?' AND
  387. `subject_id`='?' AND
  388. `exclude`='0' ORDER BY `course_num` ", $catalog_year, $subject_id);
  389. if ($result)
  390. {
  391. while ($cur = db_fetch_array($result))
  392. {
  393. $n_subject_id = trim($cur["subject_id"]);
  394. $n_course_num = trim($cur["course_num"]);
  395. $n_course_id = $cur["course_id"];
  396. $bool_hide = FALSE;
  397. $title = trim($cur["title"]);
  398. $title = $temp_course->fix_title($title);
  399. $description = trim($cur["description"]);
  400. if ($description == "")
  401. {
  402. $description = t("No description is available at this time. Consult
  403. the official course catalog for listings.");
  404. }
  405. $syllabus_text = "";
  406. $syllabus_array = course_search_get_course_syllabus_details("", "", $n_course_id);
  407. if ($syllabus_array["url"] != "")
  408. {
  409. $syllabus_text = "<div class='course-search-sample-syllabus'>
  410. <a href='{$syllabus_array["url"]}' class='nounderline'>
  411. <img src='" . fp_theme_location() . "/images/document_icon.gif' border='0' height='12'>
  412. " . t("Sample Syllabus") . "</a>
  413. </div>
  414. ";
  415. }
  416. // Look for all 5 years.
  417. $long_schedule_array = course_search_get_course_rotation_schedule($n_course_id, $catalog_year, 100, true);
  418. // Only grab next 2 years.
  419. $schedule_array = course_search_get_course_rotation_schedule($n_course_id, $catalog_year);
  420. $full_schedule_array = course_search_get_course_rotation_schedule($n_course_id);
  421. $schedule_text = "";
  422. if (count($long_schedule_array) > 0)
  423. {
  424. $schedule_text .= "
  425. <div>
  426. <b>" . t("Anticipated availability:") . "</b>
  427. ";
  428. $s_disp = "auto";
  429. if ($mode != "advanced")
  430. { // only show this in the basic mode, not advanced.
  431. foreach ($schedule_array as $term_id)
  432. {
  433. $temp_course = new Course();
  434. $temp_course->term_id = $term_id;
  435. $schedule_text .= " " . $temp_course->get_term_description(true) . ",";
  436. }
  437. $schedule_text = substr($schedule_text, 0, -1); // take off comma.
  438. $rnd_div_id = rand(1,999999);
  439. $schedule_text .= "
  440. &nbsp; | &nbsp;
  441. <a href='javascript: toggleHideDiv(\"$rnd_div_id\");' class='nounderline'>
  442. <span id='SPAN$rnd_div_id'>
  443. more&raquo;
  444. </span></a> ";
  445. $s_disp = "none";
  446. }
  447. // Consult our settings to find out what order our terms should be in.
  448. $term_array = csv_to_array(variable_get("course_search_avail_term_id_suffix_order"));
  449. // Get our table headers
  450. $avail_headers = variable_get("course_search_avail_term_headers");
  451. $avail_mobile_headers = variable_get("course_search_avail_term_mobile_headers");
  452. $th = explode(",", $avail_headers);
  453. $twidth = "90%";
  454. $mleft = "20px;";
  455. if (fp_screen_is_mobile()) {
  456. $th = explode(",", $avail_mobile_headers);
  457. $twidth = "100%";
  458. $mleft = "0";
  459. }
  460. $schedule_text .= "
  461. </div>
  462. <div id='$rnd_div_id' style='display: $s_disp; margin-left: $mleft;'>
  463. <table border='1' width='$twidth' class='fp-course-search-avail'>
  464. <tr>
  465. <td>" . t("Year") . "</td>
  466. ";
  467. foreach ($th as $header_text) {
  468. $schedule_text .= "<td>" . trim($header_text) . "</td>";
  469. }
  470. $schedule_text .= " </tr>";
  471. for ($t = $catalog_year; $t <= $catalog_year + 4; $t++)
  472. {
  473. $schedule_text .= "<tr>
  474. <td class='tenpt' align='center'>
  475. <b>$t</b>
  476. </td>";
  477. foreach($term_array as $x)
  478. {
  479. $schedule_text .= "<td class='tenpt' align='center'>";
  480. $the_term_id = $t . $x;
  481. // Does the term suffix ($x) call for the year to be
  482. // subtracted by 1, or modified at all? This is the case at ULM for fall.
  483. // Ex: 201340 is Fall of *2012*, not 2013.
  484. // We can tell this because the term structure (from admin settings)
  485. //fpm($term_structures);
  486. if (strtoupper($term_structures[$x]["disp_adjust"]) == "[Y-1]" || strtoupper($term_structures[$x]["disp_adjust"]) == "[Y4-1]") {
  487. // It is subtracted by one. So the year for "XYZ of 2016" is actually recorded as 2017xyz
  488. $the_term_id = ($t + 1) . $x;
  489. }
  490. if (strtoupper($term_structures[$x]["disp_adjust"]) == "[Y+1]" || strtoupper($term_structures[$x]["disp_adjust"]) == "[Y4+1]") {
  491. // It is added by one. So the year for "XYZ of 2016" is actually recorded as 2015xyz
  492. $the_term_id = ($t - 1) . $x;
  493. }
  494. if (in_array($the_term_id, $full_schedule_array))
  495. {
  496. $schedule_text .= "<img src='" . fp_theme_location() . "/images/small_check.gif'>";
  497. }
  498. else {
  499. if ($only_term != "" && $only_term == $the_term_id) {
  500. // Meaning, the term that the user selected is NOT in this
  501. // course's schedule. So, we should hide it.
  502. $bool_hide = TRUE;
  503. }
  504. }
  505. $schedule_text .= "&nbsp;</td>";
  506. }
  507. $schedule_text .= "</tr>";
  508. }
  509. $schedule_text .= "
  510. </table>
  511. </div>
  512. ";
  513. }
  514. else if ($only_term != "") {
  515. // This is if there are NO schedule offerings, yet the user
  516. // selected to view a particular term.
  517. $bool_hide = TRUE;
  518. }
  519. if (course_search_get_course_rotation_schedule_not_anticipated($n_course_id))
  520. {
  521. // This course has no anticipated offerings!
  522. $schedule_text = "<div><b>" . t("Anticipated availability:") . "</b>
  523. " . t("There are no anticipated course offerings
  524. at this time.") . "</div>";
  525. if ($only_term != "") $bool_hide = TRUE;
  526. }
  527. $min_hours = trim($cur["min_hours"]*1);
  528. $max_hours = trim($cur["max_hours"]*1);
  529. if ($min_hours == $max_hours)
  530. {
  531. $hours = $min_hours;
  532. } else {
  533. $hours = "$min_hours to $max_hours";
  534. }
  535. $repeat = "";
  536. if (trim($cur["repeat_hours"]*1) > $min_hours)
  537. {
  538. $repeat = "<div class='course-search-repeat'>" . t("May be repeated for up to @repeat hours of credit.", array("@repeat" => $cur["repeat_hours"]*1)) . "</div>";
  539. if (trim($cur["repeat_hours"]*1) > 20) {
  540. $repeat = "<div class='course-search-repeat'>" . t("May be repeated for credit.") . "</div>";
  541. }
  542. }
  543. // Draw it on screen...
  544. if ($bool_hide != true) {
  545. /*
  546. *
  547. * TODO: This section should really only be if the course is designated as a graduate course or not, not based on course_num.
  548. *
  549. if ($grad_notice_flag == false && $course_num > 4999)
  550. {
  551. $grad_notice_flag = true;
  552. $rtn .= "<div style='font-size: 10pt; font-weight: bold;
  553. border-bottom: 1px solid black;
  554. margin-left: 10px;
  555. margin-bottom: 20px;
  556. margin-top: 50px;'>
  557. " . t("The following courses are for Graduate Students only.") . "
  558. </div>";
  559. }
  560. * */
  561. $details = $schedule_text . $syllabus_text;
  562. $hyp1 = " - ";
  563. $on_click = "";
  564. if (fp_screen_is_mobile()) {
  565. $on_click = "onClick='toggleCourseExtra(this);'";
  566. $hyp1 = "";
  567. }
  568. $html = "";
  569. // Note, the HTML comments are so other modules, that wish to manipulate this block, have something easy to find/replace
  570. $html .= "<div class='course-search-course-block'>
  571. <!-- TITLE-ROW -->
  572. <div class='course-search-course-title-row'
  573. $on_click>
  574. <!-- COURSE-NAME -->
  575. <span class='course-search-course-name'>$n_subject_id $n_course_num</span>
  576. $hyp1
  577. <!-- END-COURSE-NAME ->
  578. <!-- COURSE-TITLE -->
  579. <span class='course-search-course-title'>$title</span> - $hours " . t("hrs.") . "$repeat
  580. <!-- END-COURSE-TITLE -->
  581. </div>
  582. <!-- END-TITLE-ROW -->
  583. <!-- COURSE-EXTRA -->
  584. <div class='course-search-course-extra'>
  585. <!-- DESC -->
  586. <div class='course-search-course-description'>$description</div>
  587. <!-- END-DESC -->
  588. <!-- DETAILS -->
  589. <div class='course-search-course-details'>$details</div>
  590. <!-- END-DETAILS -->
  591. ";
  592. if (user_has_permission("can_update_course_info_details") && !fp_screen_is_mobile()) {
  593. $html .= "<!-- ADMIN-OPTIONS -->
  594. <div class='course-search-admin-options'>
  595. " . t("Administrative options:") . "
  596. " . l(t("Edit syllabus and rotation schedule"), "tools/course-search/edit-info-details", "course_id=$n_course_id&subject_id=$n_subject_id&course_num=$n_course_num") . "
  597. </div>
  598. <!-- END-ADMIN-OPTIONS -->";
  599. }
  600. $html .= "</div>
  601. <!-- END-COURSE-EXTRA -->"; // div course-search-course-extra
  602. $html .= "</div>"; // div course-search-course-block
  603. $render["course_search_course_block__$n_course_id"] = array(
  604. "value" => $html,
  605. );
  606. }
  607. }
  608. }
  609. watchdog("course_search", "User viewed courses in subject: @subject", array("@subject" => $subject_id), WATCHDOG_DEBUG);
  610. //$pC .= $screen->get_java_script_code();
  611. $html = '
  612. <script type="text/javascript">
  613. function toggleHideDiv(rndDivID)
  614. {
  615. var d = document.getElementById(rndDivID);
  616. if (d.style.display == "none")
  617. {
  618. d.style.display = "";
  619. document.getElementById("SPAN" + rndDivID).innerHTML = "&laquo;less";
  620. } else {
  621. d.style.display = "none";
  622. document.getElementById("SPAN" + rndDivID).innerHTML = "more&raquo;";
  623. }
  624. }
  625. function toggleCourseExtra(e) {
  626. $(e).siblings(".course-search-course-extra").slideToggle("medium");
  627. }
  628. </script>
  629. ';
  630. $render["extra_javascript"] = array(
  631. "value" => $html,
  632. );
  633. $rtn .= fp_render_content($render);
  634. return $rtn;
  635. }
  636. function course_search_get_course_rotation_schedule_not_anticipated($course_id)
  637. {
  638. // Returns TRUE if not is NOT ANTICIPATED. False, if this
  639. // is a normal courses which has an offering, or a blank
  640. // offering. This will
  641. // only return true if NOTA is set as a term for this course.
  642. $res = db_query("SELECT * FROM course_rotation_schedule
  643. WHERE course_id = '?'
  644. AND term_id = 'NOTA'
  645. ", $course_id);
  646. if (db_num_rows($res) > 0) {
  647. return true;
  648. }
  649. return false;
  650. }
  651. function course_search_get_course_rotation_schedule($course_id, $year = "", $limit = 20, $bool_include_next_five_years = false)
  652. {
  653. // return an array containing the terms that this course
  654. // is going to be offered, if any.
  655. $rtn_array = array();
  656. $arr = array();
  657. $year_line = "";
  658. if ($year != "")
  659. { // if a year is entered, we will get the next few years, and the previous
  660. // one for good measure.
  661. $year_line = "and (`term_id` LIKE '$year%' or `term_id` LIKE '" . ($year+1) . "%') ";
  662. if ($bool_include_next_five_years)
  663. {
  664. $yearm1 = $year - 1;
  665. $year2 = $year + 1;
  666. $year3 = $year + 2;
  667. $year4 = $year + 3;
  668. $year5 = $year + 4;
  669. $year6 = $year + 5;
  670. $year_line = "and (`term_id` LIKE '$year%'
  671. or `term_id` LIKE '$yearm1%'
  672. or `term_id` LIKE '$year2%'
  673. or `term_id` LIKE '$year3%'
  674. or `term_id` LIKE '$year4%'
  675. or `term_id` LIKE '$year5%'
  676. or `term_id` LIKE '$year6%'
  677. ) ";
  678. }
  679. }
  680. $res = db_query("SELECT * FROM course_rotation_schedule
  681. WHERE `course_id`= ?
  682. $year_line
  683. ORDER BY term_id DESC
  684. LIMIT $limit", $course_id);
  685. while($cur = db_fetch_array($res))
  686. {
  687. $t = $cur["term_id"];
  688. // Get the term from the end.
  689. $ss = trim(substr($t,4,1));
  690. if ($ss == "m"){$ss = "1.5";}
  691. if (is_numeric($ss)) {
  692. $ss = $ss * 10;
  693. }
  694. $year = trim(substr($t,0,4));
  695. // We do all this so we can establish an order to the terms
  696. // by using a sort() command later.
  697. $arr[] = $year . "~" . $ss . "~" . $t;
  698. }
  699. sort($arr);
  700. // Now we want to get out JUST the terms...
  701. foreach($arr as $line)
  702. {
  703. $temp = explode("~",$line);
  704. $rtn_array[] = trim($temp[2]);
  705. }
  706. return $rtn_array;
  707. }
  708. function course_search_get_course_syllabus_details($subject_id = "", $course_num = "", $course_id = -1)
  709. {
  710. // This will return an array containing information
  711. // about a course's syllabus, if it exists.
  712. $rtn_array = FALSE;
  713. // Does this course have a syllabus?
  714. $query = "SELECT * FROM course_syllabi
  715. WHERE `course_perm_id`='$subject_id" . "_$course_num'";
  716. if ($course_id != -1) {
  717. $query = "SELECT * FROM course_syllabi
  718. WHERE `course_id`='$course_id' ";
  719. }
  720. $res = db_query($query);
  721. $cur = db_fetch_array($res);
  722. //$url = $GLOBALS["fp_system_settings"]["selfURL"] . "/" . get_module_path("course_search") . "/syllabus.php?id=" . $cur["course_id"];
  723. if ($cur["filename"] != "") {
  724. $rtn_array = array();
  725. $rtn_array["url"] = $GLOBALS["fp_system_settings"]["base_url"] . "/" . fp_url("course-search/get-syllabus", "id=" . $cur["course_id"], FALSE);
  726. $rtn_array["filename"] = $cur["filename"];
  727. $rtn_array["posted"] = $cur["posted"];
  728. }
  729. return $rtn_array;
  730. }
  731. /**
  732. * Displays the search pulldown for the user to use to find courses.
  733. */
  734. function course_search_display_search() {
  735. $rtn = "";
  736. $mode = "";
  737. fp_add_css(fp_get_module_path("course_search") . "/css/course_search_style.css");
  738. if (fp_screen_is_mobile()) {
  739. fp_add_css(fp_get_module_path("course_search") . "/css/course_search_mobile_style.css");
  740. }
  741. $rtn .= "";
  742. if (user_has_permission("can_update_course_info_details")) {
  743. $rtn .= "<div>" . t("Administrators:") . " " . l(t("Edit course schedules and syllabi"), "tools/course-search/edit-list") . "</div>";
  744. }
  745. $rtn .= fp_render_curved_line("Course Search");
  746. $settings = fp_get_system_settings();
  747. $current_catalog_year = $settings["current_catalog_year"];
  748. // catalog_year is always just whatever the current year is.
  749. $catalog_year = $current_catalog_year;
  750. $clean_urls = variable_get("clean_urls", FALSE); // are clean URLs enabled?
  751. if ($catalog_year == "")
  752. {
  753. $rtn .= "Please select an available catalog year from the
  754. list below.<br><br>
  755. <form action='" . fp_url("tools/course-search") . "' method='GET' name='mainform' id='myform'>
  756. <table align='center'>
  757. <td width='150' valign='bottom'>
  758. <select name='catalog_year'>";
  759. for ($t = $current_catalog_year; $t >= $GLOBALS["fp_system_settings"]["earliest_catalog_year"]; $t--)
  760. {
  761. $rtn .= "<option value='$t'>$t - " . ($t+1) . "</option> \n";
  762. }
  763. $rtn .= "</select>
  764. </td>
  765. <td valign='bottom'>
  766. <input type='submit' value='Select ->'>
  767. </td>
  768. </table>";
  769. if (!$clean_urls) {
  770. // Hack for if clean URLs isn't enabled
  771. $rtn .= "<input type='hidden' name='q' value='tools/course-search'>";
  772. }
  773. $rtn .= " </form>";
  774. }
  775. else {
  776. // Catalog year has been selected.
  777. $rtn .= "Current catalog year: <b>$catalog_year-" . ($catalog_year +1) . "</b>
  778. <br><br>
  779. Please select an available subject from the list below.<br>
  780. <br>
  781. <form action='" . fp_url("tools/course-search/courses") . "' method='GET' name='mainform' id='myform'>";
  782. if (!$clean_urls) {
  783. // Hack for if clean URLs isn't enabled
  784. $rtn .= "<input type='hidden' name='q' value='tools/course-search/courses'>";
  785. }
  786. if (!fp_screen_is_mobile()) {
  787. $rtn .= "
  788. <div align='center'>
  789. <select name='subject_id' style='width: 80%;'>
  790. ";
  791. }
  792. // We want to make a pull-down list of all available subjects.
  793. // Keep in mind with this join-- we may have courses who have
  794. // a subject_id, for which we don't have that subject in the subjects
  795. // table.
  796. $query = "SELECT DISTINCT b.subject_id, a.title FROM courses b LEFT JOIN subjects a
  797. ON (a.subject_id = b.subject_id)
  798. WHERE exclude = 0
  799. AND catalog_year = '?'
  800. ";
  801. $subjects = array();
  802. $result = db_query($query, $catalog_year);
  803. while ($cur = db_fetch_array($result))
  804. {
  805. //fpm($cur);
  806. $title = trim($cur["title"]);
  807. $subject_id = trim($cur["subject_id"]);
  808. if ($title == "") {
  809. $title = $subject_id;
  810. }
  811. $subjects[$subject_id] = $title;
  812. }
  813. asort($subjects);
  814. foreach ($subjects as $subject_id => $title) {
  815. if (!fp_screen_is_mobile()) {
  816. $rtn .= "<option value='$subject_id'>$title ($subject_id)</option>";
  817. }
  818. else {
  819. $rtn .= "<a class='course-search-subject-select-line'
  820. href='" . fp_url("tools/course-search/courses", "subject_id=$subject_id") . "'>
  821. <div class='course-search-dept-name'>$title ($subject_id)</div>
  822. </a>";
  823. }
  824. }
  825. if (!fp_screen_is_mobile()) {
  826. $rtn .= "
  827. </select>
  828. <input type='hidden' name='mode' value='$mode'>
  829. </div><br><br><br>
  830. <div align='right'>
  831. <input type='submit' value='Select ->'>
  832. </div>";
  833. }
  834. $rtn .= "</form>";
  835. }
  836. return $rtn;
  837. }

Functions

Namesort descending Description
course_search_display_courses Show the user their select of courses.
course_search_display_search Displays the search pulldown for the user to use to find courses.
course_search_download_syllabus This function will actually deliver a syllabus to the user's browser for download.
course_search_get_course_rotation_schedule
course_search_get_course_rotation_schedule_not_anticipated
course_search_get_course_syllabus_details
course_search_menu
course_search_perm
course_search_settings_form The system settins form for course_search settings.