1<?php 2/** 3 * webtrees: online genealogy 4 * Copyright (C) 2018 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\FlashMessages; 20use Fisharebest\Webtrees\I18N; 21use Fisharebest\Webtrees\Individual; 22use Fisharebest\Webtrees\Menu; 23use Fisharebest\Webtrees\Tree; 24use Symfony\Component\HttpFoundation\RedirectResponse; 25use Symfony\Component\HttpFoundation\Request; 26use Symfony\Component\HttpFoundation\Response; 27 28/** 29 * Class RelationshipsChartModule 30 */ 31class RelationshipsChartModule extends AbstractModule implements ModuleConfigInterface, ModuleChartInterface 32{ 33 /** It would be more correct to use PHP_INT_MAX, but this isn't friendly in URLs */ 34 const UNLIMITED_RECURSION = 99; 35 36 /** By default new trees allow unlimited recursion */ 37 const DEFAULT_RECURSION = self::UNLIMITED_RECURSION; 38 39 /** By default new trees search for all relationships (not via ancestors) */ 40 const DEFAULT_ANCESTORS = 0; 41 42 /** 43 * How should this module be labelled on tabs, menus, etc.? 44 * 45 * @return string 46 */ 47 public function getTitle() 48 { 49 /* I18N: Name of a module/chart */ 50 return I18N::translate('Relationships'); 51 } 52 53 /** 54 * A sentence describing what this module does. 55 * 56 * @return string 57 */ 58 public function getDescription() 59 { 60 /* I18N: Description of the “RelationshipsChart” module */ 61 return I18N::translate('A chart displaying relationships between two individuals.'); 62 } 63 64 /** 65 * What is the default access level for this module? 66 * 67 * Some modules are aimed at admins or managers, and are not generally shown to users. 68 * 69 * @return int 70 */ 71 public function defaultAccessLevel() 72 { 73 return Auth::PRIV_PRIVATE; 74 } 75 76 /** 77 * Return a menu item for this chart. 78 * 79 * @param Individual $individual 80 * 81 * @return Menu|null 82 */ 83 public function getChartMenu(Individual $individual) 84 { 85 $tree = $individual->getTree(); 86 $gedcomid = $tree->getUserPreference(Auth::user(), 'gedcomid'); 87 88 if ($gedcomid !== '') { 89 return new Menu( 90 I18N::translate('Relationship to me'), 91 route('relationships', [ 92 'xref1' => $gedcomid, 93 'xref2' => $individual->getXref(), 94 'ged' => $individual->getTree()->getName(), 95 ]), 96 'menu-chart-relationship', 97 ['rel' => 'nofollow'] 98 ); 99 } else { 100 return new Menu( 101 I18N::translate('Relationships'), 102 route('relationships', [ 103 'xref1' => $individual->getXref(), 104 'ged' => $individual->getTree()->getName(), 105 ]), 106 'menu-chart-relationship', 107 ['rel' => 'nofollow'] 108 ); 109 } 110 } 111 112 /** 113 * Return a menu item for this chart - for use in individual boxes. 114 * 115 * @param Individual $individual 116 * 117 * @return Menu|null 118 */ 119 public function getBoxChartMenu(Individual $individual) 120 { 121 return $this->getChartMenu($individual); 122 } 123 124 125 /** 126 * The URL to a page where the user can modify the configuration of this module. 127 * 128 * @return string 129 */ 130 public function getConfigLink() 131 { 132 return route('module', [ 133 'module' => $this->getName(), 134 'action' => 'Admin', 135 ]); 136 } 137 138 /** 139 * @param Request $request 140 * 141 * @return Response 142 */ 143 public function getAdminAction(Request $request): Response 144 { 145 $this->layout = 'layouts/administration'; 146 147 return $this->viewResponse('modules/relationships_chart/config', [ 148 'all_trees' => Tree::getAll(), 149 'ancestors_options' => $this->ancestorsOptions(), 150 'default_ancestors' => self::DEFAULT_ANCESTORS, 151 'default_recursion' => self::DEFAULT_RECURSION, 152 'recursion_options' => $this->recursionOptions(), 153 'title' => I18N::translate('Chart preferences') . ' — ' . $this->getTitle(), 154 ]); 155 } 156 157 /** 158 * @param Request $request 159 * 160 * @return RedirectResponse 161 */ 162 public function postAdminAction(Request $request): RedirectResponse 163 { 164 foreach (Tree::getAll() as $tree) { 165 $tree->setPreference('RELATIONSHIP_RECURSION', $request->get('relationship-recursion-' . $tree->getTreeId())); 166 $tree->setPreference('RELATIONSHIP_ANCESTORS', $request->get('relationship-ancestors-' . $tree->getTreeId())); 167 } 168 169 FlashMessages::addMessage(I18N::translate('The preferences for the module “%s” have been updated.', $this->getTitle()), 'success'); 170 171 return new RedirectResponse($this->getConfigLink()); 172 } 173 174 /** 175 * Possible options for the ancestors option 176 */ 177 private function ancestorsOptions() 178 { 179 return [ 180 0 => I18N::translate('Find any relationship'), 181 1 => I18N::translate('Find relationships via ancestors'), 182 ]; 183 } 184 185 /** 186 * Possible options for the recursion option 187 */ 188 private function recursionOptions() 189 { 190 return [ 191 0 => I18N::translate('none'), 192 1 => I18N::number(1), 193 2 => I18N::number(2), 194 3 => I18N::number(3), 195 self::UNLIMITED_RECURSION => I18N::translate('unlimited'), 196 ]; 197 } 198} 199