gedcom = $gedcom; $this->parent = $parent; $this->fact_id = $fact_id; $this->tag = $match[1]; } else { // TODO need to rewrite code that passes dummy data to this function //throw new Exception('Invalid GEDCOM data passed to WT_Fact::_construct('.$gedcom.')'); } } // Get the value of level 1 data in the fact // Allow for multi-line values function getValue() { if (preg_match('/^1 (?:' . $this->tag . ') ?(.*(?:(?:\n2 CONT .*)*))/', $this->gedcom, $match)) { return str_replace("\n2 CONT ", "\n", $match[1]); } else { return null; } } // Get the record to which this fact links function getTarget() { $xref = trim($this->getValue(), '@'); switch ($this->tag) { case 'FAMC': case 'FAMS': return WT_Family::getInstance($xref); case 'HUSB': case 'WIFE': case 'CHIL': return WT_Individual::getInstance($xref); case 'SOUR': return WT_Source::getInstance($xref); case 'OBJE': return WT_Media::getInstance($xref); case 'REPO': return WT_Repository::getInstance($xref); case 'NOTE': return WT_Note::getInstance($xref); default: return WT_GedcomRecord::getInstance($xref); } } // Get the value of level 2 data in the fact function getAttribute($tag) { if (preg_match('/\n2 (?:' . $tag . ') ?(.*(?:(?:\n3 CONT .*)*)*)/', $this->gedcom, $match)) { return str_replace("\n2 CONT ", "\n", $match[1]); } else { return null; } } // Do the privacy rules allow us to display this fact to the current user function canShow($access_level=WT_USER_ACCESS_LEVEL) { // TODO - use the privacy settings for $this->gedcom_id, not the default gedcom. global $person_facts, $global_facts; // Does this record have an explicit RESN? if (strpos($this->gedcom, "\n2 RESN confidential")) { return WT_PRIV_NONE >= $access_level; } if (strpos($this->gedcom, "\n2 RESN privacy")) { return WT_PRIV_USER >= $access_level; } if (strpos($this->gedcom, "\n2 RESN none")) { return true; } // Does this record have a default RESN? if (!$this->parent) die($eek); $xref = $this->parent->getXref(); if (isset($person_facts[$xref][$this->tag])) { return $person_facts[$xref][$this->tag] >= $access_level; } if (isset($global_facts[$this->tag])) { return $global_facts[$this->tag] >= $access_level; } // No restrictions - it must be public return true; } // Check whether this fact is protected against edit public function canEdit() { // Managers can edit anything // Members cannot edit RESN, CHAN and locked records return $this->parent->canEdit() && !$this->isOld() && ( WT_USER_GEDCOM_ADMIN || WT_USER_CAN_EDIT && strpos($this->gedcom, "\n2 RESN locked")===false && $this->getTag()!='RESN' && $this->getTag()!='CHAN' ); } // The place where the event occured. function getPlace() { if ($this->place === null) { $this->place = $this->getAttribute('PLAC'); } return $this->place; } // We can call this function many times, especially when sorting, // so keep a copy of the date. function getDate() { if ($this->date === null) { $this->date = new WT_Date($this->getAttribute('DATE')); } return $this->date; } // The raw GEDCOM data for this fact function getGedcom() { return $this->gedcom; } // Unique identifier for the fact function getFactId() { return $this->fact_id; } // What sort of fact is this? function getTag() { return $this->tag; } // Used to convert a real fact (e.g. BIRT) into a close-relative’s fact (e.g. _BIRT_CHIL) function setTag($tag) { $this->tag = $tag; } // The Person/Family record where this WT_Fact came from function getParent() { return $this->parent; } function getLabel($abbreviate=false) { if ($abbreviate) { return WT_Gedcom_Tag::getAbbreviation($this->tag); } else { switch($this->tag) { case 'EVEN': case 'FACT': if ($this->getType()) { // Custom FACT/EVEN - with a TYPE return WT_I18N::translate(htmlspecialchars($this->type)); } // no break - drop into next case default: return WT_Gedcom_Tag::getLabel($this->tag, $this->parent); } } } // Is this a pending edit? public function setIsOld() { $this->is_old = true; $this->is_new = false; } public function isOld() { return $this->is_old; } public function setIsNew() { $this->is_new = true; $this->is_old = false; } public function isNew() { return $this->is_new; } // Print a simple fact version of this event function print_simple_fact($return=false, $anchor=false) { global $ABBREVIATE_CHART_LABELS; $value = $this->getValue(); $data = ''.$this->getLabel($ABBREVIATE_CHART_LABELS).''; // Don't display "yes", because format_fact_date() does this for us. (Should it?) if ($value && $value != 'Y') { $data .= ' ' . htmlspecialchars($value) . ''; } $data .= ' '.format_fact_date($this, $this->getParent(), $anchor, false); $data .= ' '.format_fact_place($this, $anchor, false, false); $data .= '
'; if ($return) { return $data; } else { echo $data; } } // Display an icon for this fact. // Icons are held in a theme subfolder. Not all themes provide icons. function Icon() { $dir=WT_THEME_DIR.'images/facts/'; $tag=$this->getTag(); $file=$tag.'.png'; if (file_exists($dir.$file)) { return ''; } elseif (file_exists($dir.'NULL.png')) { // Spacer image - for alignment - until we move to a sprite. return ''; } else { return ''; } } // Static Helper functions to sort events static function CompareDate($a, $b) { if ($a->getDate()->isOK() && $b->getDate()->isOK()) { // If both events have dates, compare by date $ret=WT_Date::Compare($a->getDate(), $b->getDate()); if ($ret==0) { // If dates are the same, compare by fact type $ret=self::CompareType($a, $b); // If the fact type is also the same, retain the initial order if ($ret==0) { $ret=$a->sortOrder - $b->sortOrder; } } return $ret; } else { // One or both events have no date - retain the initial orde return $a->sortOrder - $b->sortOrder; } } // Static method to Compare two events by their type static function CompareType($a, $b) { global $factsort; if (empty($factsort)) $factsort=array_flip(array( "BIRT", "_HNM", "ALIA", "_AKA", "_AKAN", "ADOP", "_ADPF", "_ADPF", "_BRTM", "CHR", "BAPM", "FCOM", "CONF", "BARM", "BASM", "EDUC", "GRAD", "_DEG", "EMIG", "IMMI", "NATU", "_MILI", "_MILT", "ENGA", "MARB", "MARC", "MARL", "_MARI", "_MBON", "MARR", "MARR_CIVIL", "MARR_RELIGIOUS", "MARR_PARTNERS", "MARR_UNKNOWN", "_COML", "_STAT", "_SEPR", "DIVF", "MARS", "_BIRT_CHIL", "DIV", "ANUL", "_BIRT_", "_MARR_", "_DEAT_","_BURI_", // other events of close relatives "CENS", "OCCU", "RESI", "PROP", "CHRA", "RETI", "FACT", "EVEN", "_NMR", "_NMAR", "NMR", "NCHI", "WILL", "_HOL", "_????_", "DEAT", "_FNRL", "BURI", "CREM", "_INTE", "_YART", "_NLIV", "PROB", "TITL", "COMM", "NATI", "CITN", "CAST", "RELI", "SSN", "IDNO", "TEMP", "SLGC", "BAPL", "CONL", "ENDL", "SLGS", "ADDR", "PHON", "EMAIL", "_EMAIL", "EMAL", "FAX", "WWW", "URL", "_URL", "AFN", "REFN", "_PRMN", "REF", "RIN", "_UID", "CHAN", "_TODO", "NOTE", "SOUR", "OBJE" )); // Facts from same families stay grouped together // Keep MARR and DIV from the same families from mixing with events from other FAMs // Use the original order in which the facts were added if ($a->parent instanceof WT_Family && $b->parent instanceof WT_Family && !$a->parent->equals($b->parent)) { return $a->sortOrder - $b->sortOrder; } $atag = $a->getTag(); $btag = $b->getTag(); // Events not in the above list get mapped onto one that is. if (!array_key_exists($atag, $factsort)) { if (preg_match('/^(_(BIRT|MARR|DEAT|BURI)_)/', $atag, $match)) { $atag=$match[1]; } else { $atag="_????_"; } } if (!array_key_exists($btag, $factsort)) { if (preg_match('/^(_(BIRT|MARR|DEAT|BURI)_)/', $btag, $match)) { $btag=$match[1]; } else { $btag="_????_"; } } //-- don't let dated after DEAT/BURI facts sort non-dated facts before DEAT/BURI //-- treat dated after BURI facts as BURI instead if ($a->getAttribute('DATE')!=NULL && $factsort[$atag]>$factsort['BURI'] && $factsort[$atag]<$factsort['CHAN']) $atag='BURI'; if ($b->getAttribute('DATE')!=NULL && $factsort[$btag]>$factsort['BURI'] && $factsort[$btag]<$factsort['CHAN']) $btag='BURI'; $ret = $factsort[$atag]-$factsort[$btag]; //-- if facts are the same then put dated facts before non-dated facts if ($ret==0) { if ($a->getAttribute('DATE')!=NULL && $b->getAttribute('DATE')==NULL) return -1; if ($b->getAttribute('DATE')!=NULL && $a->getAttribute('DATE')==NULL) return 1; //-- if no sorting preference, then keep original ordering $ret = $a->sortOrder - $b->sortOrder; } return $ret; } }