Passed
Push — master ( 290708...134887 )
by Greg
06:31
created

AbstractCensusColumn   A

Complexity

Total Complexity 21

Size/Duplication

Total Lines 181
Duplicated Lines 0 %

Importance

Changes 0
Metric Value
eloc 41
dl 0
loc 181
rs 10
c 0
b 0
f 0
wmc 21

11 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 5 1
A father() 0 9 2
A abbreviation() 0 3 1
A mother() 0 9 2
A spouseFamily() 0 9 1
A place() 0 3 1
A title() 0 3 1
A lastPartOfPlace() 0 5 1
B nameAtCensusDate() 0 22 8
A notCountry() 0 9 2
A date() 0 3 1
1
<?php
2
3
/**
4
 * webtrees: online genealogy
5
 * Copyright (C) 2019 webtrees development team
6
 * This program is free software: you can redistribute it and/or modify
7
 * it under the terms of the GNU General Public License as published by
8
 * the Free Software Foundation, either version 3 of the License, or
9
 * (at your option) any later version.
10
 * This program is distributed in the hope that it will be useful,
11
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
 * GNU General Public License for more details.
14
 * You should have received a copy of the GNU General Public License
15
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
16
 */
17
18
declare(strict_types=1);
19
20
namespace Fisharebest\Webtrees\Census;
21
22
use Fisharebest\Webtrees\Date;
23
use Fisharebest\Webtrees\Family;
24
use Fisharebest\Webtrees\Individual;
25
26
use function array_slice;
27
use function explode;
28
use function implode;
29
30
/**
31
 * Definitions for a census column
32
 */
33
class AbstractCensusColumn
34
{
35
    /** @var CensusInterface */
36
    private $census;
37
38
    /** @var string */
39
    private $abbr;
40
41
    /** @var string */
42
    private $title;
43
44
    /**
45
     * Create a column for a census
46
     *
47
     * @param CensusInterface $census - The census to which this column forms part.
48
     * @param string          $abbr   - The abbreviated on-screen name "BiC"
49
     * @param string          $title  - The full column heading "Born in the county"
50
     */
51
    public function __construct(CensusInterface $census, string $abbr, string $title)
52
    {
53
        $this->census = $census;
54
        $this->abbr   = $abbr;
55
        $this->title  = $title;
56
    }
57
58
    /**
59
     * A short version of the column's name.
60
     *
61
     * @return string
62
     */
63
    public function abbreviation(): string
64
    {
65
        return $this->abbr;
66
    }
67
68
    /**
69
     * Find the father of an individual
70
     *
71
     * @param Individual $individual
72
     *
73
     * @return Individual|null
74
     */
75
    public function father(Individual $individual): ?Individual
76
    {
77
        $family = $individual->childFamilies()->first();
78
79
        if ($family instanceof Family) {
80
            return $family->husband();
81
        }
82
83
        return null;
84
    }
85
86
    /**
87
     * Find the mother of an individual
88
     *
89
     * @param Individual $individual
90
     *
91
     * @return Individual|null
92
     */
93
    public function mother(Individual $individual): ?Individual
94
    {
95
        $family = $individual->childFamilies()->first();
96
97
        if ($family instanceof Family) {
98
            return $family->wife();
99
        }
100
101
        return null;
102
    }
103
104
    /**
105
     * Find the current spouse family of an individual
106
     *
107
     * @param Individual $individual
108
     *
109
     * @return Family|null
110
     */
111
    public function spouseFamily(Individual $individual): ?Family
112
    {
113
        return $individual->spouseFamilies()
114
            ->filter(function (Family $family): bool {
115
                // Exclude families that were created after this census date
116
                return Date::compare($family->getMarriageDate(), $this->date()) <= 0;
117
            })
118
            ->sort(Family::marriageDateComparator())
119
            ->last();
120
    }
121
122
    /**
123
     * What was an individual's likely name on a given date, allowing
124
     * for marriages and married names.
125
     *
126
     * @param Individual $individual
127
     *
128
     * @return string[]
129
     */
130
    protected function nameAtCensusDate(Individual $individual): array
131
    {
132
        $names  = $individual->getAllNames();
133
        $name   = $names[0];
134
        $family = $this->spouseFamily($individual);
135
136
        if ($family instanceof Family) {
137
            foreach ($family->facts(['MARR']) as $marriage) {
138
                if ($marriage->date()->isOK()) {
139
                    $spouse = $family->spouse($individual);
140
                    foreach ($names as $individual_name) {
141
                        foreach ($spouse->getAllNames() as $spouse_name) {
142
                            if ($individual_name['type'] === '_MARNM' && $individual_name['surn'] === $spouse_name['surn']) {
143
                                return $individual_name;
144
                            }
145
                        }
146
                    }
147
                }
148
            }
149
        }
150
151
        return $name;
152
    }
153
154
    /**
155
     * When did this census occur
156
     *
157
     * @return Date
158
     */
159
    public function date(): Date
160
    {
161
        return new Date($this->census->censusDate());
162
    }
163
164
    /**
165
     * The full version of the column's name.
166
     *
167
     * @return string
168
     */
169
    public function title(): string
170
    {
171
        return $this->title;
172
    }
173
174
    /**
175
     * Extract the country (last part) of a place name.
176
     *
177
     * @param string $place - e.g. "London, England"
178
     *
179
     * @return string - e.g. "England"
180
     */
181
    protected function lastPartOfPlace(string $place): string
182
    {
183
        $parts = explode(', ', $place);
184
185
        return end($parts);
186
    }
187
188
    /**
189
     * Remove the country of a place name, where it is the same as the census place
190
     *
191
     * @param string $place - e.g. "London, England"
192
     *
193
     * @return string - e.g. "London" (for census of England) and "London, England" elsewhere
194
     */
195
    protected function notCountry(string $place): string
196
    {
197
        $parts = explode(', ', $place);
198
199
        if (end($parts) === $this->place()) {
200
            return implode(', ', array_slice($parts, 0, -1));
201
        }
202
203
        return $place;
204
    }
205
206
    /**
207
     * Where did this census occur
208
     *
209
     * @return string
210
     */
211
    public function place(): string
212
    {
213
        return $this->census->censusPlace();
214
    }
215
}
216