tripal.terms.api.inc

Provides an application programming interface (API) for working with controlled vocaublary terms.

File

tripal/api/tripal.terms.api.inc
View source
  1. <?php
  2. /**
  3. * @file
  4. * Provides an application programming interface (API) for working with
  5. * controlled vocaublary terms.
  6. */
  7. /**
  8. * @defgroup tripal_terms_api CV Terms
  9. * @ingroup tripal_api
  10. * @{
  11. * Tripal provides an application programming interface (API) for working with
  12. * controlled vocaublary terms. Tripal v3 is highly dependent on controlled
  13. * vocabularies for identifying all content types and fields attached to those
  14. * content types. However, Tripal v3 is also database agnostic. Therefore,
  15. * controlled vocabularies can be stored in any database back-end. By default
  16. * the tripal_chado module is used for storing controlled vocabularies. However,
  17. * if someone wanted to store controlled vocabularies in a database other than
  18. * Chado they can do so. These API functions provide a convenient wrapper for
  19. * accession controlled vocabularies no matter where they are stored.
  20. *
  21. * @}
  22. */
  23. /**
  24. * @section
  25. * Vocabulary Hooks.
  26. */
  27. /**
  28. * A hook for specifying information about the data store for vocabularies.
  29. *
  30. * The storage backend for controlled vocabularies has traditionally been
  31. * the Chado CV term tables. However, Tripal v3.0 introduces APIs for supporting
  32. * other backends. Therefore, this function indicates to Tripal which
  33. * data stores are capable of providing support for terms.
  34. *
  35. * @return
  36. * An array describing the storage backends implemented by the module. The
  37. * keys are storage backend names. To avoid name clashes, storage
  38. * backend names should be prefixed with the name of the module that
  39. * exposes them. The values are arrays describing the storage backend,
  40. * with the following key/value pairs:
  41. *
  42. * label: The human-readable name of the storage backend.
  43. * module: The name of the module providing the support for this backend.
  44. * description: A short description for the storage backend.
  45. * settings: An array whose keys are the names of the settings available for
  46. * the storage backend, and whose values are the default values for
  47. * those settings.
  48. *
  49. * @ingroup tripal_terms_api
  50. */
  51. function hook_vocab_storage_info() {
  52. return array(
  53. 'term_chado_storage' => array(
  54. 'label' => t('Chado'),
  55. 'description' => t('Integrates terms stored in the local Chado database with Tripal entities.'),
  56. 'settings' => array(),
  57. ),
  58. );
  59. }
  60. /**
  61. * Creates a form for specifying a term for TripalEntity creation.
  62. *
  63. * This hook allows the module that implements a vocabulary storage backend
  64. * to provide the form necessary to select a term that will then be used for
  65. * creating a new TripalEntity type. Tripal will expect that a 'vocabulary' and
  66. * 'accession' are in the $form_state['storage'] array. The 'vocabulary' and
  67. * must be the abbreviated uppercase vocabulary for the vocabulary (e.g. 'RO',
  68. * 'SO', 'PATO', etc.). The 'accession' must be the unique term ID (or
  69. * accession) for the term in the vocabulary.
  70. *
  71. * @param $form
  72. * @param $form_state
  73. *
  74. * @return
  75. * A form object.
  76. *
  77. * @ingroup tripal_terms_api
  78. */
  79. function hook_vocab_select_term_form(&$form, &$form_state) {
  80. return $form;
  81. }
  82. /**
  83. * Validates the hook_vocab_select_term_form().
  84. *
  85. * @param $form
  86. * @param $form_state
  87. *
  88. * @ingroup tripal_terms_api
  89. */
  90. function hook_vocab_select_term_form_validate($form, &$form_state) {
  91. }
  92. /**
  93. * Provides a form for importing vocabularies and their terms.
  94. *
  95. * Tripal allows for vocabularies to be stored separately from the biological
  96. * data. This hook allows the default term storage backend to provide an
  97. * approprite form for importing ontologies (either in OBO or OWL format).
  98. *
  99. * @param $form
  100. * @param $form_state
  101. *
  102. * @ingroup tripal_terms_api
  103. *
  104. */
  105. function hook_vocab_import_form($form, &$form_state) {
  106. return $form;
  107. }
  108. /**
  109. * Validates the hook_vocab_import_form().
  110. *
  111. * @param $form
  112. * @param $form_state
  113. *
  114. * @ingroup tripal_terms_api
  115. */
  116. function hook_vocab_import_form_validate($form, &$form_state) {
  117. }
  118. /**
  119. * Submits the hook_vocab_import_form().
  120. *
  121. * @param $form
  122. * @param $form_state
  123. *
  124. * @ingroup tripal_terms_api
  125. */
  126. function hook_vocab_import_form_submit($form, &$form_state) {
  127. }
  128. /**
  129. * Hook used by the default term storage backend to provide details for a term.
  130. *
  131. * This hook is called by the tripal_entity module to retrieve information
  132. * about the term from the storage backend. It must return an array with
  133. * a set of keys.
  134. *
  135. * @param $vocabulary
  136. * The vocabulary of the vocabulary in which the term is found.
  137. * @param $accession
  138. * The unique identifier (accession) for this term.
  139. *
  140. * @return
  141. * An array with at least the following keys:
  142. * -vocabulary : An associative array with the following keys:
  143. * -name: The short name for the vocabulary (e.g. SO, PATO, etc).
  144. * -description: The description of this vocabulary.
  145. * -url: The URL for the vocabulary.
  146. * -urlprefix : (optional) A URL to which the short_name and term
  147. * accession can be appended to form a complete URL for a term. If the
  148. * prefix does not support appending then the exact location for the
  149. * position of the short_name and the term accession will be
  150. * specified with the {db} and {accession} tags respectively.
  151. * -accession : The name unique ID of the term.
  152. * -url : The URL for the term.
  153. * -name : The name of the term.
  154. * -definition : The term's description.
  155. * any other keys may be added as desired. Returns NULL if the term
  156. * cannot be found.
  157. *
  158. * @ingroup tripal_terms_api
  159. */
  160. function hook_vocab_get_term($vocabulary, $accession) {
  161. // See the tripal_chado_vocab_get_term() function for an example.
  162. }
  163. /**
  164. * Retrieves a paged list of terms from a vocabulary.
  165. *
  166. * @param $vocabulary
  167. * The short name of the vocabulary.
  168. * @param $limit
  169. * The number of results to return.
  170. * @param $element
  171. * The pager element. This is equivalent to the element from the
  172. * pager_default_initialize() function of Drupal.
  173. *
  174. * @ingroup tripal_terms_api
  175. */
  176. function hook_vocab_get_terms($vocabulary, $limit = 25, $element = 0) {
  177. // See the tripal_chado_vocab_get_terms() function for an example.
  178. }
  179. /**
  180. * Hook used by the default term storage backend to provide children for a term.
  181. *
  182. * This hook is called by the tripal_entity module to retrieve a list of
  183. * children for a term from the storage backend. It must return an array
  184. * of terms where each term contains the same structure as that of the
  185. * hook_vocab_get_term().
  186. *
  187. * @param $vocabulary
  188. * The vocabulary of the vocabulary in which the term is found.
  189. * @param $accession
  190. * The unique identifier (accession) for this term.
  191. *
  192. * @return
  193. * An array of terms where each term contains the same structure as that of
  194. * the hook_vocab_get_term(), or an empty array if no children are present.
  195. *
  196. * @ingroup tripal_terms_api
  197. */
  198. function hook_vocab_get_term_children($vocabulary, $accession) {
  199. // See the tripal_chado_vocab_get_term_children() function for an example.
  200. }
  201. /**
  202. * Hook used by the default term storage backend to provide root terms.
  203. *
  204. * This hook is called by the tripal_entity module to retrieve a list of
  205. * root terms for a given vocabulary from the storage backend. It must return
  206. * an array of terms where each term contains the same structure as that of the
  207. * hook_vocab_get_term().
  208. *
  209. * @param $vocabulary
  210. * The vocabulary of the vocabulary in which the term is found.
  211. *
  212. * @return
  213. * An array of root terms where each term contains the same structure as that
  214. * of the hook_vocab_get_term(), or an empty array if no children are present.
  215. *
  216. * @ingroup tripal_terms_api
  217. */
  218. function hook_vocab_get_root_terms($vocabulary) {
  219. // See the tripal_chado_vocab_get_root_terms() function for an example.
  220. }
  221. /**
  222. * Hook used by the default term storage backend to provide details for a vocab.
  223. *
  224. * This hook is called by the tripal_entity module to retrieve information
  225. * about the vocabulary from the storage backend. It must return an array with
  226. * a set of keys.
  227. *
  228. * @param $vocabulary
  229. * The vocabulary of the vocabulary in which the term is found.
  230. *
  231. * @return
  232. * An array with at least the following keys:
  233. * - name : The full name of the vocabulary.
  234. * - short_name : The short name abbreviation for the vocabulary.
  235. * - description : A brief description of the vocabulary.
  236. * - url : (optional) A URL for the online resources for the vocabulary.
  237. * - urlprefix : (optional) A URL to which the short_name and term
  238. * accession can be appended to form a complete URL for a term. If the
  239. * prefix does not support appending then the exact location for the
  240. * position of the short_name and the term accession will be
  241. * specified with the {db} and {accession} tags respectively.
  242. *
  243. * @ingroup tripal_terms_api
  244. */
  245. function hook_vocab_get_vocabulary($vocabulary) {
  246. // See the tripal_chado_vocab_get_vocabulary() function for an example.
  247. }
  248. /**
  249. * Retrieves the list of vocabularies that are available on the site.
  250. *
  251. * @return
  252. * An array of vocabularies where each entry in the array is compatible
  253. * with the array returned by the tripal_get_vocabulary_details()
  254. * function.
  255. *
  256. * @ingroup tripal_terms_api
  257. */
  258. function hook_vocab_get_vocabularies() {
  259. // See the tripal_chado_vocab_get_vocabularies() function for an example.
  260. }
  261. /**
  262. * Hook used by the default term storage backend to add new terms.
  263. *
  264. * @param $details
  265. * An array with at least the following keys:
  266. * -vocabulary : An associative array with the following keys:
  267. * -name: The short name for the vocabulary (e.g. SO, PATO, etc).
  268. * -description: The description of this vocabulary.
  269. * -url: The URL for the vocabulary.
  270. * -urlprefix: (optional) A URL to which the short_name and term
  271. * accession can be appended to form a complete URL for a term. If the
  272. * prefix does not support appending then the exact location for the
  273. * position of the short_name and the term accession will be
  274. * specified with the {db} and {accession} tags respectively.
  275. * -accession : The name unique ID of the term.
  276. * -url : The URL for the term.
  277. * -name : The name of the term.
  278. * -definition : The term's description.
  279. * @return
  280. * TRUE if the term was added, FALSE otherwise. If the term already exists
  281. * it will be updated and the return value will be TRUE.
  282. *
  283. * @ingroup tripal_terms_api
  284. */
  285. function hook_vocab_add_term($details) {
  286. // See the tripal_chado_vocab_set_term() function for an example.
  287. }
  288. /**
  289. * Adds a term to the vocabulary storage backend.
  290. *
  291. * Use this function to add new terms dynamically to the vocabulary storage
  292. * backend. If the term already exists no new term is added.
  293. *
  294. * @param $details
  295. * An array with at least the following keys:
  296. * -vocabulary : An associative array with the following keys
  297. * -name: The short name for the vocabulary (e.g. SO, PATO, etc).
  298. * -description: The description of this vocabulary.
  299. * -url: The URL for the vocabulary.
  300. * -accession : The name unique ID of the term.
  301. * -url : The URL for the term.
  302. * -name : The name of the term.
  303. * -definition : The term's description.
  304. * @return
  305. * TRUE if the term was added, FALSE otherwise. If the term already exists
  306. * it will be updated and the return value will be TRUE.
  307. *
  308. * @ingroup tripal_terms_api
  309. */
  310. function tripal_add_term($details) {
  311. // TODO: we need some sort of administrative interface that lets the user
  312. // switch to the desired vocabulary type. For now, we'll just use the
  313. // first one in the list.
  314. $stores = module_invoke_all('vocab_storage_info');
  315. if (is_array($stores) and count($stores) > 0) {
  316. $keys = array_keys($stores);
  317. $module = $stores[$keys[0]]['module'];
  318. $function = $module . '_vocab_add_term';
  319. if (function_exists($function)) {
  320. return $function($details);
  321. }
  322. }
  323. }
  324. /**
  325. * Retrieves full information about a vocabulary term.
  326. *
  327. * @param $vocabulary
  328. * The vocabulary of the vocabulary in which the term is found.
  329. * @param $accession
  330. * The unique identifier (accession) for this term.
  331. *
  332. * @return
  333. * An array with at least the following keys:
  334. * - vocabulary : An array containing the following keys:
  335. * - name : The full name of the vocabulary.
  336. * - short_name : The short name abbreviation for the vocabulary.
  337. * - description : A brief description of the vocabulary.
  338. * - url : (optional) A URL for the online resources for the vocabulary.
  339. * - urlprefix : (optional) A URL to which the short_name and term
  340. * accession can be appended to form a complete URL for a term. If the
  341. * prefix does not support appending then the exact location for the
  342. * position of the short_name and the term accession will be
  343. * specified with the {db} and {accession} tags respectively.
  344. * - accession : The name unique ID of the term.
  345. * - url : The URL for the term.
  346. * - name : The name of the term.
  347. * - definition : The term's description.
  348. * any other keys may be added as desired. Returns NULL if the term
  349. * cannot be found.
  350. *
  351. * @ingroup tripal_terms_api
  352. */
  353. function tripal_get_term_details($vocabulary, $accession) {
  354. if (empty($vocabulary) OR empty($accession)) {
  355. tripal_report_error('tripal_term', TRIPAL_ERROR, "Unable to retrieve details for term due to missing vocabulary and/or accession");
  356. }
  357. // TODO: we need some sort of administrative interface that lets the user
  358. // switch to the desired vocabulary type. For now, we'll just use the
  359. // first one in the list.
  360. $stores = module_invoke_all('vocab_storage_info');
  361. if (is_array($stores) and count($stores) > 0) {
  362. $keys = array_keys($stores);
  363. $module = $stores[$keys[0]]['module'];
  364. $function = $module . '_vocab_get_term';
  365. if (function_exists($function)) {
  366. return $function($vocabulary, $accession);
  367. }
  368. }
  369. }
  370. /**
  371. * Retrieves the immediate children of the given term.
  372. *
  373. * @param $vocabulary
  374. * The vocabulary of the vocabulary in which the term is found.
  375. * @param $accession
  376. * The unique identifier (accession) for this term.
  377. *
  378. * @return
  379. * Returns an array of terms where each term is compatible with the
  380. * array returned by the tripal_get_term_details() function.
  381. *
  382. * @ingroup tripal_terms_api
  383. */
  384. function tripal_get_vocabulary_root_terms($vocabulary) {
  385. if (empty($vocabulary)) {
  386. tripal_report_error('tripal_term', TRIPAL_ERROR, 'Unable to retrieve details for term due to missing vocabulary.');
  387. }
  388. // TODO: we need some sort of administrative interface that lets the user
  389. // switch to the desired vocabulary type. For now, we'll just use the
  390. // first one in the list.
  391. $stores = module_invoke_all('vocab_storage_info');
  392. if (is_array($stores) and count($stores) > 0) {
  393. $keys = array_keys($stores);
  394. $module = $stores[$keys[0]]['module'];
  395. $function = $module . '_vocab_get_root_terms';
  396. if (function_exists($function)) {
  397. return $function($vocabulary);
  398. }
  399. }
  400. }
  401. /**
  402. * Retrieves the immediate children of the given term.
  403. *
  404. * @param $vocabulary
  405. * The vocabulary of the vocabulary in which the term is found.
  406. * @param $accession
  407. * The unique identifier (accession) for this term.
  408. *
  409. * @return
  410. * Returns an array of terms where each term is compatible with the
  411. * array returned by the tripal_get_term_details() function.
  412. *
  413. * @ingroup tripal_terms_api
  414. */
  415. function tripal_get_term_children($vocabulary, $accession) {
  416. if (empty($vocabulary) OR empty($accession)) {
  417. tripal_report_error('tripal_term', TRIPAL_ERROR, 'Unable to retrieve details for term due to missing vocabulary and/or accession.');
  418. }
  419. $stores = module_invoke_all('vocab_storage_info');
  420. if (is_array($stores) and count($stores) > 0) {
  421. $keys = array_keys($stores);
  422. $module = $stores[$keys[0]]['module'];
  423. $function = $module . '_vocab_get_term_children';
  424. if (function_exists($function)) {
  425. return $function($vocabulary, $accession);
  426. }
  427. }
  428. }
  429. /**
  430. * Retrieves full information about a vocabulary.
  431. *
  432. * Vocabularies are stored in a database backend. Tripal has no requirements
  433. * for how terms are stored. By default, the tripal_chado modules provides
  434. * storage for vocabularies and terms. This function will call the
  435. * hook_vocab_get_term() function for the database backend that is housing the
  436. * vocabularies and allow it to return the details about the term.
  437. *
  438. * @param $vocabulary
  439. * The vocabulary of the vocabulary in which the term is found.
  440. *
  441. * @return
  442. * An array with at least the following keys:
  443. * - name: The full name of the vocabulary.
  444. * - short_name: The short name abbreviation for the vocabulary.
  445. * - description: A brief description of the vocabulary.
  446. * - url: A URL for the online resources for the vocabulary.
  447. * - urlprefix: A URL to which the short_name and term
  448. * accession can be appended to form a complete URL for a term. If the
  449. * prefix does not support appending then the exact location for the
  450. * position of the short_name and the term accession will be
  451. * specified with the {db} and {accession} tags respectively.
  452. * - sw_url: The URL for mapping terms via the semantic web.
  453. * - num_terms: The number of terms loaded in the vocabulary.
  454. *
  455. * @ingroup tripal_terms_api
  456. */
  457. function tripal_get_vocabulary_details($vocabulary) {
  458. // TODO: we need some sort of administrative interface that lets the user
  459. // switch to the desired vocabulary type. For now, we'll just use the
  460. // first one in the list.
  461. $stores = module_invoke_all('vocab_storage_info');
  462. if (is_array($stores) and count($stores) > 0) {
  463. $keys = array_keys($stores);
  464. $module = $stores[$keys[0]]['module'];
  465. $function = $module . '_vocab_get_vocabulary';
  466. if (function_exists($function)) {
  467. return $function($vocabulary);
  468. }
  469. }
  470. }
  471. /**
  472. * Retrieves a paged list of terms from a vocabulary.
  473. *
  474. * @param $vocabulary
  475. * The short name of the vocabulary.
  476. * @param $limit
  477. * The number of results to return.
  478. * @param $element
  479. * The pager element. This is equivalent to the element from the
  480. * pager_default_initialize() function of Drupal.
  481. *
  482. * @ingroup tripal_terms_api
  483. */
  484. function tripal_get_vocabulary_terms($vocabulary, $limit = 25, $element = 0) {
  485. $stores = module_invoke_all('vocab_storage_info');
  486. if (is_array($stores) and count($stores) > 0) {
  487. $keys = array_keys($stores);
  488. $module = $stores[$keys[0]]['module'];
  489. $function = $module . '_vocab_get_terms';
  490. if (function_exists($function)) {
  491. return $function($vocabulary, $limit, $element);
  492. }
  493. }
  494. }
  495. /**
  496. * Retrieves the list of vocabularies that are available on the site.
  497. *
  498. * @return
  499. * An array of vocabularies where each entry in the array is compatible
  500. * with the array returned by the tripal_get_vocabulary_details()
  501. * function.
  502. *
  503. * @ingroup tripal_terms_api
  504. */
  505. function tripal_get_vocabularies() {
  506. $stores = module_invoke_all('vocab_storage_info');
  507. if (is_array($stores) and count($stores) > 0) {
  508. $keys = array_keys($stores);
  509. $module = $stores[$keys[0]]['module'];
  510. $function = $module . '_vocab_get_vocabularies';
  511. if (function_exists($function)) {
  512. return $function();
  513. }
  514. }
  515. }
  516. /**
  517. * Provides a term lookup form.
  518. *
  519. * It may be necessary at times for a form to provide to the user the ability
  520. * to lookup and use a controlled vocabulary term. However, a simple text box
  521. * or auto-lookup is not sufficient because a term name may be identical in
  522. * multiple vocabularies and the user would need to select the proper term.
  523. *
  524. * This function will add the form elements necessary to provide a lookup form.
  525. * The form elements should work with a flat form (no #tree set for the form)
  526. * or with a form in a TripalField.
  527. *
  528. * Use the tripal_get_term_lookup_form_result() function to retreive the
  529. * result in a form submit or validate.
  530. *
  531. * @param $form
  532. * The form (or $widget form).
  533. * @param $form_state
  534. * The form state.
  535. * @param $title
  536. * The title to give to the field set.
  537. * @param $description
  538. * A description for the lookup field element.
  539. * @param $is_required
  540. * Indicates if this form element is required.
  541. * @param $field_name
  542. * The name of the field, if this form is being added to a field widget.
  543. * @param $delta
  544. * The delta value for the field if this form is being added to a field
  545. * widget.
  546. *
  547. * @ingroup tripal_terms_api
  548. */
  549. function tripal_get_term_lookup_form(&$form, &$form_state, $default_name = '',
  550. $title = 'Vocabulary Term', $description = '', $is_required,
  551. $field_name = '', $delta = 0 ) {
  552. $term_name = $default_name;
  553. if (array_key_exists('values', $form_state)) {
  554. $term_name = $form_state['values']['term_name'];
  555. }
  556. if ($field_name and array_key_exists('input', $form_state) and array_key_exists($field_name, $form_state['input'])) {
  557. $term_name = $form_state['input'][$field_name]['und'][$delta]['term_match']['term_name'];
  558. }
  559. if (!$description) {
  560. $description = t('Enter the name of the term that specifies the type. ' .
  561. 'The type must be the name of a term in a controlled vocabulary and ' .
  562. 'the controlled vocabulary should already be loaded into this site.');
  563. }
  564. $form_state['storage']['term_match_field'] = $field_name;
  565. $form_state['storage']['term_match_delta'] = $delta;
  566. $form['term_match'] = array(
  567. '#type' => 'fieldset',
  568. '#collapsible' => FALSE,
  569. '#collapsed' => FALSE,
  570. '#title' => t($title),
  571. '#prefix' => '<div id = "tripal-vocab-select-form">',
  572. '#suffix' => '</div>',
  573. );
  574. $form['term_match']['term_name'] = array(
  575. '#title' => t('Type'),
  576. '#type' => 'textfield',
  577. '#description' => $description,
  578. '#required' => $is_required,
  579. '#default_value' => $term_name,
  580. '#autocomplete_path' => "admin/tripal/storage/chado/auto_name/cvterm/",
  581. );
  582. $form['term_match']['select_button'] = array(
  583. '#type' => 'button',
  584. '#value' => t('Lookup Term'),
  585. '#name' => 'select_cvterm',
  586. '#validate' => array(),
  587. '#limit_validation_errors' => array(),
  588. '#ajax' => array(
  589. 'callback' => "tripal_get_term_lookup_form_ajax_callback",
  590. 'wrapper' => "tripal-vocab-select-form",
  591. 'effect' => 'fade',
  592. 'method' => 'replace'
  593. ),
  594. );
  595. // If the term has been provided by the user then we want to search for
  596. // matching terms in the database and let them select among any matches.
  597. if ($term_name) {
  598. $submit_disabled = TRUE;
  599. $form['term_match']['terms_list'] = array(
  600. '#type' => 'fieldset',
  601. '#title' => t('Matching Terms'),
  602. '#description' => t('Please select the term the best matches the
  603. content type you want to create. If the same term exists in
  604. multiple vocabularies you will see more than one option below.')
  605. );
  606. $match = array(
  607. 'name' => $term_name,
  608. );
  609. // TODO: this should not call the chado functions because we're in the
  610. // tripal module.
  611. $terms = chado_generate_var('cvterm', $match, array('return_array' => TRUE));
  612. $terms = chado_expand_var($terms, 'field', 'cvterm.definition');
  613. $num_terms = 0;
  614. $selected_term = '';
  615. // Let the user select from any matching terms. Sometimes there may be
  616. // more than one that match.
  617. foreach ($terms as $term) {
  618. // Save the user a click by setting the default value as 1 if there's
  619. // only one matching term.
  620. $default = FALSE;
  621. $attrs = array();
  622. if ($num_terms == 0 and count($terms) == 1) {
  623. $default = TRUE;
  624. $attrs = array('checked' => 'checked');
  625. }
  626. $term_element_name = 'term-' . $term->cvterm_id;
  627. $form['term_match']['terms_list'][$term_element_name] = array(
  628. '#type' => 'checkbox',
  629. '#title' => $term->name,
  630. '#default_value' => $default,
  631. '#attributes' => $attrs,
  632. '#description' => '<b>Vocabulary:</b> ' . $term->cv_id->name . ' (' . $term->dbxref_id->db_id->name . ') ' . $term->cv_id->definition .
  633. '<br><b>Term: </b> ' . $term->dbxref_id->db_id->name . ':' . $term->dbxref_id->accession . '. ' .
  634. '<br><b>Definition:</b> ' . $term->definition,
  635. '#ajax' => array(
  636. 'callback' => "tripal_get_term_lookup_form_ajax_callback",
  637. 'wrapper' => "tripal-vocab-select-form",
  638. 'effect' => 'fade',
  639. 'method' => 'replace'
  640. ),
  641. );
  642. if (array_key_exists('values', $form_state) and array_key_exists($term_element_name, $form_state['values']) and
  643. $form_state['values'][$term_element_name] == 1) {
  644. $selected_term = $term;
  645. }
  646. $num_terms++;
  647. }
  648. if ($num_terms == 0) {
  649. $form['term_match']['terms_list']['none'] = array(
  650. '#type' => 'item',
  651. '#markup' => '<i>' . t('There is no term that matches the entered text.') . '</i>'
  652. );
  653. }
  654. }
  655. }
  656. /**
  657. * Returns the terms selected from the tripal_get_term_lookup_form.
  658. *
  659. * @param $form
  660. * The form (or $widget form).
  661. * @param $form_state
  662. * The form state.
  663. * @param $field_name
  664. * The name of the field, if this form is being added to a field widget.
  665. * @param $delta
  666. * The delta value for the field if this form is being added to a field
  667. * widget.
  668. *
  669. * @return
  670. * An array of term objects for each of the user selected terms.
  671. *
  672. * @ingroup tripal_terms_api
  673. */
  674. function tripal_get_term_lookup_form_result($form, $form_state, $field_name = '', $delta = 0) {
  675. $values = array();
  676. $selected = array();
  677. if ($field_name) {
  678. if (array_key_exists('term_match', $form_state['values'][$field_name]['und'][$delta])) {
  679. $values = $form_state['values'][$field_name]['und'][$delta]['term_match']['terms_list'];
  680. }
  681. }
  682. else {
  683. $values = $form_state['values'];
  684. }
  685. foreach ($values as $key => $value) {
  686. $matches = array();
  687. if (preg_match("/^term-(\d+)$/", $key, $matches) and $values['term-' . $matches[1]]) {
  688. $cvterm_id = $matches[1];
  689. $selected[] = chado_generate_var('cvterm', array('cvterm_id' => $cvterm_id));
  690. }
  691. }
  692. return $selected;
  693. }
  694. /**
  695. * Implements an AJAX callback for the tripal_chado_vocab_select_term_form.
  696. *
  697. * @ingroup tripal_terms_api
  698. */
  699. function tripal_get_term_lookup_form_ajax_callback($form, $form_state) {
  700. $field_name = $form_state['storage']['term_match_field'];
  701. $delta = $form_state['storage']['term_match_delta'];
  702. // If this form is in a field then we need to dig a bit deeper to return
  703. // the form elements.
  704. if ($field_name) {
  705. return $form[$field_name]['und'][$delta]['term_match'];
  706. }
  707. else {
  708. return $form['term_match'];
  709. }
  710. }