1<?php 2/** 3 * webtrees: online genealogy 4 * Copyright (C) 2017 webtrees development team 5 * This program is free software: you can redistribute it and/or modify 6 * it under the terms of the GNU General Public License as published by 7 * the Free Software Foundation, either version 3 of the License, or 8 * (at your option) any later version. 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * You should have received a copy of the GNU General Public License 14 * along with this program. If not, see <http://www.gnu.org/licenses/>. 15 */ 16namespace Fisharebest\Webtrees\Module; 17 18use Fisharebest\Webtrees\Auth; 19use Fisharebest\Webtrees\Controller\PageController; 20use Fisharebest\Webtrees\Family; 21use Fisharebest\Webtrees\Filter; 22use Fisharebest\Webtrees\GedcomRecord; 23use Fisharebest\Webtrees\I18N; 24use Fisharebest\Webtrees\Individual; 25use Fisharebest\Webtrees\Menu; 26use Fisharebest\Webtrees\Module\ClippingsCart\ClippingsCartController; 27use Fisharebest\Webtrees\Session; 28 29/** 30 * Class ClippingsCartModule 31 */ 32class ClippingsCartModule extends AbstractModule implements ModuleMenuInterface, ModuleSidebarInterface { 33 /** {@inheritdoc} */ 34 public function getTitle() { 35 return /* I18N: Name of a module */ 36 I18N::translate('Clippings cart'); 37 } 38 39 /** {@inheritdoc} */ 40 public function getDescription() { 41 return /* I18N: Description of the “Clippings cart” module */ 42 I18N::translate('Select records from your family tree and save them as a GEDCOM file.'); 43 } 44 45 /** 46 * What is the default access level for this module? 47 * 48 * Some modules are aimed at admins or managers, and are not generally shown to users. 49 * 50 * @return int 51 */ 52 public function defaultAccessLevel() { 53 return Auth::PRIV_USER; 54 } 55 56 /** 57 * This is a general purpose hook, allowing modules to respond to routes 58 * of the form module.php?mod=FOO&mod_action=BAR 59 * 60 * @param string $mod_action 61 */ 62 public function modAction($mod_action) { 63 switch ($mod_action) { 64 case 'ajax': 65 $html = $this->getSidebarAjaxContent(); 66 header('Content-Type: text/html; charset=UTF-8'); 67 echo $html; 68 break; 69 case 'index': 70 global $controller, $WT_TREE; 71 72 $MAX_PEDIGREE_GENERATIONS = $WT_TREE->getPreference('MAX_PEDIGREE_GENERATIONS'); 73 74 $clip_ctrl = new ClippingsCartController; 75 $cart = Session::get('cart'); 76 77 $controller = new PageController; 78 $controller 79 ->setPageTitle($this->getTitle()) 80 ->pageHeader(); 81 82 echo '<script>'; 83 echo 'function radAncestors(elementid) {var radFamilies=document.getElementById(elementid);radFamilies.checked=true;}'; 84 echo '</script>'; 85 86 if (!$cart[$WT_TREE->getTreeId()]) { 87 echo '<h2>', I18N::translate('Family tree clippings cart'), '</h2>'; 88 } 89 90 if ($clip_ctrl->action == 'add') { 91 $record = GedcomRecord::getInstance($clip_ctrl->id, $WT_TREE); 92 if ($clip_ctrl->type === 'FAM') { ?> 93 <form action="module.php"> 94 <input type="hidden" name="mod" value="clippings"> 95 <input type="hidden" name="mod_action" value="index"> 96 <input type="hidden" name="id" value="<?= $clip_ctrl->id ?>"> 97 <input type="hidden" name="type" value="<?= $clip_ctrl->type ?>"> 98 <input type="hidden" name="action" value="add1"> 99 <table> 100 <thead> 101 <tr> 102 <td class="topbottombar"> 103 <?= I18N::translate('Add to the clippings cart') ?> 104 </td> 105 </tr> 106 </thead> 107 <tbody> 108 <tr> 109 <td class="optionbox"> 110 <input type="radio" name="others" value="parents"> 111 <?= $record->getFullName() ?> 112 </td> 113 </tr> 114 <tr> 115 <td class="optionbox"> 116 <input type="radio" name="others" value="members" checked> 117 <?= /* I18N: %s is a family (husband + wife) */ 118 I18N::translate('%s and their children', $record->getFullName()) ?> 119 </td> 120 </tr> 121 <tr> 122 <td class="optionbox"> 123 <input type="radio" name="others" value="descendants"> 124 <?= /* I18N: %s is a family (husband + wife) */ 125 I18N::translate('%s and their descendants', $record->getFullName()) ?> 126 </td> 127 </tr> 128 </tbody> 129 <tfoot> 130 <tr> 131 <td class="topbottombar"><input type="submit" value="<?= I18N::translate('continue') ?>"> 132 </td> 133 </tr> 134 </tfoot> 135 </table> 136 </form> 137 <?php } elseif ($clip_ctrl->type === 'INDI') { ?> 138 <form action="module.php"> 139 <input type="hidden" name="mod" value="clippings"> 140 <input type="hidden" name="mod_action" value="index"> 141 <input type="hidden" name="id" value="<?= $clip_ctrl->id ?>"> 142 <input type="hidden" name="type" value="<?= $clip_ctrl->type ?>"> 143 <input type="hidden" name="action" value="add1"> 144 <table> 145 <thead> 146 <tr> 147 <td class="topbottombar"> 148 <?= I18N::translate('Add to the clippings cart') ?> 149 </td> 150 </tr> 151 </thead> 152 <tbody> 153 <tr> 154 <td class="optionbox"> 155 <label> 156 <input type="radio" name="others" checked value="none"> 157 <?= $record->getFullName() ?> 158 </label> 159 </td> 160 </tr> 161 <tr> 162 <td class="optionbox"> 163 <label> 164 <input type="radio" name="others" value="parents"> 165 <?php 166 if ($record->getSex() === 'F') { 167 echo /* I18N: %s is a woman's name */ 168 I18N::translate('%s, her parents and siblings', $record->getFullName()); 169 } else { 170 echo /* I18N: %s is a man's name */ 171 I18N::translate('%s, his parents and siblings', $record->getFullName()); 172 } 173 ?> 174 </label> 175 </td> 176 </tr> 177 <tr> 178 <td class="optionbox"> 179 <label> 180 <input type="radio" name="others" value="members"> 181 <?php 182 if ($record->getSex() === 'F') { 183 echo /* I18N: %s is a woman's name */ 184 I18N::translate('%s, her spouses and children', $record->getFullName()); 185 } else { 186 echo /* I18N: %s is a man's name */ 187 I18N::translate('%s, his spouses and children', $record->getFullName()); 188 } 189 ?> 190 </label> 191 </td> 192 </tr> 193 <tr> 194 <td class="optionbox"> 195 <label> 196 <input type="radio" name="others" value="ancestors" id="ancestors"> 197 <?php 198 if ($record->getSex() === 'F') { 199 echo /* I18N: %s is a woman's name */ 200 I18N::translate('%s and her ancestors', $record->getFullName()); 201 } else { 202 echo /* I18N: %s is a man's name */ 203 I18N::translate('%s and his ancestors', $record->getFullName()); 204 } 205 ?> 206 </label> 207 <br> 208 <?= I18N::translate('Number of generations') ?> 209 <input type="text" size="5" name="level1" value="<?= $MAX_PEDIGREE_GENERATIONS ?>" onfocus="radAncestors('ancestors');"> 210 </td> 211 </tr> 212 <tr> 213 <td class="optionbox"> 214 <label> 215 <input type="radio" name="others" value="ancestorsfamilies" id="ancestorsfamilies"> 216 <?php 217 if ($record->getSex() === 'F') { 218 echo /* I18N: %s is a woman's name */ 219 I18N::translate('%s, her ancestors and their families', $record->getFullName()); 220 } else { 221 echo /* I18N: %s is a man's name */ 222 I18N::translate('%s, his ancestors and their families', $record->getFullName()); 223 } 224 ?> 225 </label> 226 <br> 227 <?= I18N::translate('Number of generations') ?> 228 <input type="text" size="5" name="level2" value="<?= $MAX_PEDIGREE_GENERATIONS ?>" onfocus="radAncestors('ancestorsfamilies');"> 229 </td> 230 </tr> 231 <tr> 232 <td class="optionbox"> 233 <label> 234 <input type="radio" name="others" value="descendants" id="descendants"> 235 <?php 236 if ($record->getSex() === 'F') { 237 echo /* I18N: %s is a woman's name */ 238 I18N::translate('%s, her spouses and descendants', $record->getFullName()); 239 } else { 240 echo /* I18N: %s is a man's name */ 241 I18N::translate('%s, his spouses and descendants', $record->getFullName()); 242 } 243 ?> 244 </label> 245 <br> 246 <?= I18N::translate('Number of generations') ?> 247 <input type="text" size="5" name="level3" value="<?= $MAX_PEDIGREE_GENERATIONS ?>" onfocus="radAncestors('descendants');"> 248 </td> 249 </tr> 250 </tbody> 251 <tfoot> 252 <tr> 253 <td class="topbottombar"> 254 <input type="submit" value="<?= I18N::translate('continue') ?>"> 255 </td> 256 </tr> 257 </tfoot> 258 </table> 259 </form> 260 <?php } elseif ($clip_ctrl->type === 'SOUR') { ?> 261 <form action="module.php"> 262 <input type="hidden" name="mod" value="clippings"> 263 <input type="hidden" name="mod_action" value="index"> 264 <input type="hidden" name="id" value="<?= $clip_ctrl->id ?>"> 265 <input type="hidden" name="type" value="<?= $clip_ctrl->type ?>"> 266 <input type="hidden" name="action" value="add1"> 267 <table> 268 <thead> 269 <tr> 270 <td class="topbottombar"> 271 <?= I18N::translate('Add to the clippings cart') ?> 272 </td> 273 </tr> 274 </thead> 275 <tbody> 276 <tr> 277 <td class="optionbox"> 278 <label> 279 <input type="radio" name="others" checked value="none"> 280 <?= $record->getFullName() ?> 281 </label> 282 </td> 283 </tr> 284 <tr> 285 <td class="optionbox"> 286 <label> 287 <input type="radio" name="others" value="linked"> 288 <?= /* I18N: %s is the name of a source */ 289 I18N::translate('%s and the individuals that reference it.', $record->getFullName()) ?> 290 </label> 291 </td> 292 </tr> 293 </tbody> 294 <tfoot> 295 <tr> 296 <td class="topbottombar"> 297 <input type="submit" value="<?= I18N::translate('continue') ?>"> 298 </td> 299 </tr> 300 </tfoot> 301 </table> 302 </form> 303 <?php } 304 } 305 306 if (!$cart[$WT_TREE->getTreeId()]) { 307 if ($clip_ctrl->action != 'add') { 308 echo I18N::translate('The clippings cart allows you to take extracts from this family tree and download them as a GEDCOM file.'); 309 ?> 310 <form name="addin" action="module.php"> 311 <input type="hidden" name="mod" value="clippings"> 312 <input type="hidden" name="mod_action" value="index"> 313 <table> 314 <thead> 315 <tr> 316 <td colspan="2" class="topbottombar"> 317 <?= I18N::translate('Add to the clippings cart') ?> 318 </td> 319 </tr> 320 </thead> 321 <tbody> 322 <tr> 323 <td class="optionbox"> 324 <input type="hidden" name="action" value="add"> 325 <input type="text" data-autocomplete-type="IFSRO" name="id" id="cart_item_id" size="5"> 326 </td> 327 <td class="optionbox"> 328 <input type="submit" value="<?= /* I18N: A button label. */ I18N::translate('add') ?>"> 329 </td> 330 </tr> 331 </tbody> 332 </table> 333 </form> 334 <?php 335 } 336 337 // -- end new lines 338 echo I18N::translate('Your clippings cart is empty.'); 339 } else { 340 // Keep track of the INDI from the parent page, otherwise it will 341 // get lost after ajax updates 342 $pid = Filter::get('pid', WT_REGEX_XREF); 343 344 if ($clip_ctrl->action !== 'download' && $clip_ctrl->action !== 'add') { ?> 345 <form action="module.php"> 346 <input type="hidden" name="mod" value="clippings"> 347 <input type="hidden" name="mod_action" value="index"> 348 <input type="hidden" name="action" value="download"> 349 <input type="hidden" name="pid" value="<?= $pid ?>"> 350 <table> 351 <tr> 352 <td colspan="2" class="topbottombar"> 353 <h2><?= I18N::translate('Download') ?></h2> 354 </td> 355 </tr> 356 <tr> 357 <td class="descriptionbox width50 wrap"> 358 <?= I18N::translate('To reduce the size of the download, you can compress the data into a .ZIP file. You will need to uncompress the .ZIP file before you can use it.') ?> 359 </td> 360 <td class="optionbox wrap"> 361 <input type="checkbox" name="Zip" value="yes"> 362 <?= I18N::translate('Zip file(s)') ?> 363 </td> 364 </tr> 365 <tr> 366 <td class="descriptionbox width50 wrap"> 367 <?= I18N::translate('Include media (automatically zips files)') ?> 368 </td> 369 <td class="optionbox"> 370 <input type="checkbox" name="IncludeMedia" value="yes"> 371 </td> 372 </tr> 373 374 <?php if (Auth::isManager($WT_TREE)) { ?> 375 <tr> 376 <td class="descriptionbox width50 wrap"> 377 <?= I18N::translate('Apply privacy settings') ?> 378 </td> 379 <td class="optionbox"> 380 <input type="radio" name="privatize_export" value="none" checked> 381 <?= I18N::translate('None') ?> 382 <br> 383 <input type="radio" name="privatize_export" value="gedadmin"> 384 <?= I18N::translate('Manager') ?> 385 <br> 386 <input type="radio" name="privatize_export" value="user"> 387 <?= I18N::translate('Member') ?> 388 <br> 389 <input type="radio" name="privatize_export" value="visitor"> 390 <?= I18N::translate('Visitor') ?> 391 </td> 392 </tr> 393 <?php } elseif (Auth::isMember($WT_TREE)) { ?> 394 <tr> 395 <td class="descriptionbox width50 wrap"> 396 <?= I18N::translate('Apply privacy settings') ?> 397 </td> 398 <td class="optionbox"> 399 <input type="radio" name="privatize_export" value="user" checked> <?= I18N::translate('Member') ?><br> 400 <input type="radio" name="privatize_export" value="visitor"> <?= I18N::translate('Visitor') ?> 401 </td> 402 </tr> 403 <?php } ?> 404 405 <tr> 406 <td class="descriptionbox width50 wrap"> 407 <?= I18N::translate('Convert from UTF-8 to ISO-8859-1') ?> 408 </td> 409 <td class="optionbox"> 410 <input type="checkbox" name="convert" value="yes"> 411 </td> 412 </tr> 413 414 <tr> 415 <td class="descriptionbox width50 wrap"> 416 <?= I18N::translate('Add the GEDCOM media path to filenames') ?> 417 </td> 418 <td class="optionbox"> 419 <input type="checkbox" name="conv_path" value="<?= Html::escape($WT_TREE->getPreference('GEDCOM_MEDIA_PATH')) ?>"> 420 <span dir="auto"><?= Html::escape($WT_TREE->getPreference('GEDCOM_MEDIA_PATH')) ?></span> 421 </td> 422 </tr> 423 424 <tr> 425 <td class="topbottombar" colspan="2"> 426 <input type="submit" value="<?= /* I18N: A button label. */ I18N::translate('download') ?>"> 427 </td> 428 </tr> 429 </table> 430 </form> 431 <br> 432 433 <form name="addin" action="module.php"> 434 <input type="hidden" name="mod" value="clippings"> 435 <input type="hidden" name="mod_action" value="index"> 436 <table> 437 <thead> 438 <tr> 439 <td colspan="2" class="topbottombar" style="text-align:center; "> 440 <?= I18N::translate('Add to the clippings cart') ?> 441 </td> 442 </tr> 443 </thead> 444 <tbody> 445 <tr> 446 <td class="optionbox"> 447 <input type="hidden" name="action" value="add"> 448 <input type="text" data-autocomplete-type="IFSRO" name="id" id="cart_item_id" size="8"> 449 </td> 450 <td class="optionbox"> 451 <input type="submit" value="<?= /* I18N: A button label. */ I18N::translate('add') ?>"> 452 </td> 453 </tr> 454 </tbody> 455 <tfoot> 456 <tr> 457 <th colspan="2"> 458 <a href="module.php?mod=clippings&mod_action=index&action=empty"> 459 <?= I18N::translate('Empty the clippings cart') ?> 460 </a> 461 </th> 462 </tr> 463 </tfoot> 464 </table> 465 </form> 466 467 <?php } ?> 468 469 <h2> 470 <?= I18N::translate('Family tree clippings cart') ?> 471 </h2> 472 <table id="mycart" class="sortable list_table width100"> 473 <thead> 474 <tr> 475 <th class="list_label"><?= I18N::translate('Record') ?></th> 476 <th class="list_label"><?= I18N::translate('Remove') ?></th> 477 </tr> 478 </thead> 479 <tbody> 480 <?php 481 foreach (array_keys($cart[$WT_TREE->getTreeId()]) as $xref) { 482 $record = GedcomRecord::getInstance($xref, $WT_TREE); 483 if ($record) { 484 switch ($record::RECORD_TYPE) { 485 case 'INDI': 486 $icon = 'icon-indis'; 487 break; 488 case 'FAM': 489 $icon = 'icon-sfamily'; 490 break; 491 case 'SOUR': 492 $icon = 'icon-source'; 493 break; 494 case 'REPO': 495 $icon = 'icon-repository'; 496 break; 497 case 'NOTE': 498 $icon = 'icon-note'; 499 break; 500 case 'OBJE': 501 $icon = 'icon-media'; 502 break; 503 default: 504 $icon = 'icon-clippings'; 505 break; 506 } 507 ?> 508 <tr> 509 <td class="list_value"> 510 <i class="<?= $icon ?>"></i> 511 <?php 512 echo '<a href="', $record->getHtmlUrl(), '">', $record->getFullName(), '</a>'; 513 ?> 514 </td> 515 <td class="list_value center vmiddle"><a href="module.php?mod=clippings&mod_action=index&action=remove&id=<?= $xref ?>" class="icon-remove" title="<?= I18N::translate('Remove') ?>"></a></td> 516 </tr> 517 <?php 518 } 519 } 520 ?> 521 </table> 522 <?php 523 } 524 break; 525 default: 526 http_response_code(404); 527 break; 528 } 529 } 530 531 /** 532 * The user can re-order menus. Until they do, they are shown in this order. 533 * 534 * @return int 535 */ 536 public function defaultMenuOrder() { 537 return 20; 538 } 539 540 /** 541 * A menu, to be added to the main application menu. 542 * 543 * @return Menu|null 544 */ 545 public function getMenu() { 546 global $controller, $WT_TREE; 547 548 $submenus = []; 549 if (isset($controller->record)) { 550 $submenus[] = new Menu($this->getTitle(), 'module.php?mod=clippings&mod_action=index&ged=' . $WT_TREE->getNameUrl(), 'menu-clippings-cart', ['rel' => 'nofollow']); 551 } 552 if (!empty($controller->record) && $controller->record->canShow()) { 553 $submenus[] = new Menu(I18N::translate('Add to the clippings cart'), 'module.php?mod=clippings&mod_action=index&action=add&id=' . $controller->record->getXref(), 'menu-clippings-add', ['rel' => 'nofollow']); 554 } 555 556 if ($submenus) { 557 return new Menu($this->getTitle(), '#', 'menu-clippings', ['rel' => 'nofollow'], $submenus); 558 } else { 559 return new Menu($this->getTitle(), 'module.php?mod=clippings&mod_action=index&ged=' . $WT_TREE->getNameUrl(), 'menu-clippings', ['rel' => 'nofollow']); 560 } 561 } 562 563 /** {@inheritdoc} */ 564 public function defaultSidebarOrder() { 565 return 60; 566 } 567 568 /** {@inheritdoc} */ 569 public function hasSidebarContent() { 570 // Creating a controller has the side effect of initialising the cart 571 new ClippingsCartController; 572 573 return true; 574 } 575 576 /** 577 * Load this sidebar synchronously. 578 * 579 * @return string 580 */ 581 public function getSidebarContent() { 582 global $controller; 583 584 $controller->addInlineJavascript(' 585 $("#sb_clippings_content").on("click", ".add_cart, .remove_cart", function() { 586 $("#sb_clippings_content").load(this.href); 587 return false; 588 }); 589 '); 590 591 return '<div id="sb_clippings_content">' . $this->getCartList() . '</div>'; 592 } 593 594 /** {@inheritdoc} */ 595 public function getSidebarAjaxContent() { 596 global $WT_TREE; 597 598 $cart = Session::get('cart'); 599 600 $clip_ctrl = new ClippingsCartController; 601 $add = Filter::get('add', WT_REGEX_XREF); 602 $add1 = Filter::get('add1', WT_REGEX_XREF); 603 $remove = Filter::get('remove', WT_REGEX_XREF); 604 $others = Filter::get('others'); 605 $clip_ctrl->level1 = Filter::getInteger('level1'); 606 $clip_ctrl->level2 = Filter::getInteger('level2'); 607 $clip_ctrl->level3 = Filter::getInteger('level3'); 608 if ($add) { 609 $record = GedcomRecord::getInstance($add, $WT_TREE); 610 if ($record) { 611 $clip_ctrl->id = $record->getXref(); 612 $clip_ctrl->type = $record::RECORD_TYPE; 613 $clip_ctrl->addClipping($record); 614 } 615 } elseif ($add1) { 616 $record = Individual::getInstance($add1, $WT_TREE); 617 if ($record) { 618 $clip_ctrl->id = $record->getXref(); 619 $clip_ctrl->type = $record::RECORD_TYPE; 620 if ($others == 'parents') { 621 foreach ($record->getChildFamilies() as $family) { 622 $clip_ctrl->addClipping($family); 623 $clip_ctrl->addFamilyMembers($family); 624 } 625 } elseif ($others == 'ancestors') { 626 $clip_ctrl->addAncestorsToCart($record, $clip_ctrl->level1); 627 } elseif ($others == 'ancestorsfamilies') { 628 $clip_ctrl->addAncestorsToCartFamilies($record, $clip_ctrl->level2); 629 } elseif ($others == 'members') { 630 foreach ($record->getSpouseFamilies() as $family) { 631 $clip_ctrl->addClipping($family); 632 $clip_ctrl->addFamilyMembers($family); 633 } 634 } elseif ($others == 'descendants') { 635 foreach ($record->getSpouseFamilies() as $family) { 636 $clip_ctrl->addClipping($family); 637 $clip_ctrl->addFamilyDescendancy($family, $clip_ctrl->level3); 638 } 639 } 640 } 641 } elseif ($remove) { 642 unset($cart[$WT_TREE->getTreeId()][$remove]); 643 Session::put('cart', $cart); 644 } elseif (isset($_REQUEST['empty'])) { 645 $cart[$WT_TREE->getTreeId()] = []; 646 Session::put('cart', $cart); 647 } elseif (isset($_REQUEST['download'])) { 648 return $this->downloadForm($clip_ctrl); 649 } 650 651 return $this->getCartList(); 652 } 653 654 /** 655 * A list for the side bar. 656 * 657 * @return string 658 */ 659 public function getCartList() { 660 global $WT_TREE; 661 662 $cart = Session::get('cart', []); 663 if (!array_key_exists($WT_TREE->getTreeId(), $cart)) { 664 $cart[$WT_TREE->getTreeId()] = []; 665 } 666 $pid = Filter::get('pid', WT_REGEX_XREF); 667 668 if (!$cart[$WT_TREE->getTreeId()]) { 669 $out = I18N::translate('Your clippings cart is empty.'); 670 } else { 671 $out = '<ul>'; 672 foreach (array_keys($cart[$WT_TREE->getTreeId()]) as $xref) { 673 $record = GedcomRecord::getInstance($xref, $WT_TREE); 674 if ($record instanceof Individual || $record instanceof Family) { 675 switch ($record::RECORD_TYPE) { 676 case 'INDI': 677 $icon = 'icon-indis'; 678 break; 679 case 'FAM': 680 $icon = 'icon-sfamily'; 681 break; 682 } 683 $out .= '<li>'; 684 if (!empty($icon)) { 685 $out .= '<i class="' . $icon . '"></i>'; 686 } 687 $out .= '<a href="' . $record->getHtmlUrl() . '">'; 688 if ($record instanceof Individual) { 689 $out .= $record->getSexImage(); 690 } 691 $out .= ' ' . $record->getFullName() . ' '; 692 if ($record instanceof Individual && $record->canShow()) { 693 $out .= ' (' . $record->getLifeSpan() . ')'; 694 } 695 $out .= '</a>'; 696 $out .= '<a class="icon-remove remove_cart" href="module.php?mod=' . $this->getName() . '&mod_action=ajax&remove=' . $xref . '&pid=' . $pid . '" title="' . I18N::translate('Remove') . '"></a>'; 697 $out .= '</li>'; 698 } 699 } 700 $out .= '</ul>'; 701 } 702 703 if ($cart[$WT_TREE->getTreeId()]) { 704 $out .= 705 '<br><a href="module.php?mod=' . $this->getName() . '&mod_action=ajax&empty=true&pid=' . $pid . '" class="remove_cart">' . 706 I18N::translate('Empty the clippings cart') . 707 '</a>' . 708 '<br>' . 709 '<a href="module.php?mod=' . $this->getName() . '&mod_action=ajax&download=true&pid=' . $pid . '" class="add_cart">' . 710 I18N::translate('Download') . 711 '</a>'; 712 } 713 $record = Individual::getInstance($pid, $WT_TREE); 714 if ($record && !array_key_exists($record->getXref(), $cart[$WT_TREE->getTreeId()])) { 715 $out .= '<br><a href="module.php?mod=' . $this->getName() . '&mod_action=ajax&action=add1&type=INDI&id=' . $pid . '&pid=' . $pid . '" class="add_cart"><i class="icon-clippings"></i> ' . I18N::translate('Add %s to the clippings cart', $record->getFullName()) . '</a>'; 716 } 717 718 return $out; 719 } 720 721 /** 722 * A form to choose the download options. 723 * 724 * @param ClippingsCartController $clip_ctrl 725 * 726 * @return string 727 */ 728 public function downloadForm(ClippingsCartController $clip_ctrl) { 729 global $WT_TREE; 730 731 $pid = Filter::get('pid', WT_REGEX_XREF); 732 733 $out = '<script>'; 734 $out .= 'function cancelDownload() { 735 var link = "module.php?mod=' . $this->getName() . '&mod_action=ajax&pid=' . $pid . '"; 736 $("#sb_clippings_content").load(link); 737 }'; 738 $out .= '</script>'; 739 $out .= '<form action="module.php"> 740 <input type="hidden" name="mod" value="clippings"> 741 <input type="hidden" name="mod_action" value="index"> 742 <input type="hidden" name="pid" value="' . $pid . '"> 743 <input type="hidden" name="action" value="download"> 744 <table> 745 <tr><td colspan="2" class="topbottombar"><h2>' . I18N::translate('Download') . '</h2></td></tr> 746 <tr><td class="descriptionbox width50 wrap">' . I18N::translate('Zip file(s)') . '</td> 747 <td class="optionbox"><input type="checkbox" name="Zip" value="yes" checked></td></tr> 748 749 <tr><td class="descriptionbox width50 wrap">' . I18N::translate('Include media (automatically zips files)') . '</td> 750 <td class="optionbox"><input type="checkbox" name="IncludeMedia" value="yes" checked></td></tr> 751 '; 752 753 if (Auth::isManager($WT_TREE)) { 754 $out .= 755 '<tr><td class="descriptionbox width50 wrap">' . I18N::translate('Apply privacy settings') . '</td>' . 756 '<td class="optionbox">' . 757 '<input type="radio" name="privatize_export" value="none" checked> ' . I18N::translate('None') . '<br>' . 758 '<input type="radio" name="privatize_export" value="gedadmin"> ' . I18N::translate('Manager') . '<br>' . 759 '<input type="radio" name="privatize_export" value="user"> ' . I18N::translate('Member') . '<br>' . 760 '<input type="radio" name="privatize_export" value="visitor"> ' . I18N::translate('Visitor') . 761 '</td></tr>'; 762 } elseif (Auth::isMember($WT_TREE)) { 763 $out .= 764 '<tr><td class="descriptionbox width50 wrap">' . I18N::translate('Apply privacy settings') . '</td>' . 765 '<td class="list_value">' . 766 '<input type="radio" name="privatize_export" value="user" checked> ' . I18N::translate('Member') . '<br>' . 767 '<input type="radio" name="privatize_export" value="visitor"> ' . I18N::translate('Visitor') . 768 '</td></tr>'; 769 } 770 771 $out .= ' 772 <tr><td class="descriptionbox width50 wrap">' . I18N::translate('Convert from UTF-8 to ISO-8859-1') . '</td> 773 <td class="optionbox"><input type="checkbox" name="convert" value="yes"></td></tr> 774 775 <tr> 776 <td class="descriptionbox width50 wrap">' . I18N::translate('Add the GEDCOM media path to filenames') . '</td> 777 <td class="optionbox"> 778 <input type="checkbox" name="conv_path" value="' . Html::escape($WT_TREE->getPreference('GEDCOM_MEDIA_PATH')) . '"> 779 <span dir="auto">' . Html::escape($WT_TREE->getPreference('GEDCOM_MEDIA_PATH')) . '</span></td> 780 </tr> 781 782 <input type="hidden" name="conv_path" value="' . $clip_ctrl->conv_path . '"> 783 784 </td></tr> 785 786 <tr><td class="topbottombar" colspan="2"> 787 <input type="button" value="' . /* I18N: A button label. */ I18N::translate('cancel') . '" onclick="cancelDownload();"> 788 <input type="submit" value="' . /* I18N: A button label. */ I18N::translate('download') . '"> 789 </form>'; 790 791 return $out; 792 } 793} 794