Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Start addressing https://github.com/OneZoom/OZtree/issues/183 #185

Open
wants to merge 1 commit into
base: 3.4
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion OZprivate/rawJS/OZTreeModule/src/factory/data_repo.js
Original file line number Diff line number Diff line change
Expand Up @@ -257,6 +257,7 @@ function parse_ordered_leaves(data_repo, leaves, node_details) {
leaf_meta_entry[data_repo.mc_key_l["OTTid"]] = ott;
leaf_meta_entry[data_repo.mc_key_l["scientificName"]] =leaves[i][node_details.leaf_cols["name"]];
leaf_meta_entry[data_repo.mc_key_l["popularity"]] = leaves[i][node_details.leaf_cols["popularity"]];
leaf_meta_entry[data_repo.mc_key_l["extinction_date"]] = leaves[i][node_details.leaf_cols["extinction_date"]];
}
}

Expand All @@ -269,7 +270,7 @@ function parse_ordered_nodes(data_repo, nodes, node_details) {
node_meta_entry[data_repo.mc_key_n["OTTid"]] = ott;
node_meta_entry[data_repo.mc_key_n["scientificName"]] = nodes[i][node_details.node_cols["name"]];
node_meta_entry[data_repo.mc_key_n["popularity"]] = nodes[i][node_details.node_cols["popularity"]];
node_meta_entry[data_repo.mc_key_n["lengthbr"]] = Math.abs(nodes[i][node_details.node_cols["age"]]);
node_meta_entry[data_repo.mc_key_n["age_Ma"]] = Math.abs(nodes[i][node_details.node_cols["age"]]);

node_meta_entry[data_repo.mc_key_n["sp1"]] = nodes[i][node_details.node_cols["{pic}1"]];
node_meta_entry[data_repo.mc_key_n["sp2"]] = nodes[i][node_details.node_cols["{pic}2"]];
Expand Down
38 changes: 26 additions & 12 deletions OZprivate/rawJS/OZTreeModule/src/factory/midnode.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,13 +25,13 @@ class Midnode {
this._sponsor_name = null;
this._sponsor_kind = null;
this._sponsor_extra = null;
this._age = null;
this._age = undefined;
this._spec_num_full = null;
this._picset_len = null;
this._picset_codes = null;
this._signpost_common = false;
this._threatened_branch = null;
this._redlist = null;
this._redlist = undefined;
this._pic_filename = null;
this._picID_credit = null;
this._picID_src = null;
Expand Down Expand Up @@ -90,13 +90,13 @@ class Midnode {
this._sponsor_name = null;
this._sponsor_kind = null;
this._sponsor_extra = null;
this._age = null;
this._age = undefined;
this._spec_num_full = null;
this._picset_len = null;
this._picset_codes = null;
this._signpost_common = false;
this._threatened_branch = null;
this._redlist = null;
this._redlist = undefined;
this._pic_filename = null;
this._picID_credit = null;
this._picID_src = null;
Expand Down Expand Up @@ -239,7 +239,7 @@ class Midnode {


/**
* Get attribute of node by key name. Use this function to fetch metadata of node only.
* Get attribute of node or leaf by key name from the data_repo store.
*/
get_attribute(key_name) {
if (this.detail_fetched && this.is_leaf) {
Expand Down Expand Up @@ -327,14 +327,28 @@ class Midnode {
}
return _sponsor_extra;
}
get lengthbr() {
if (this._age !== null) return this._age;
let age = this.get_attribute("lengthbr");
age = isNaN(age) ? 0 : age;
get age_Ma() {
/* used for internal node dates - if 0 or null, this is unknown */
if (this._age !== undefined) return this._age;
let _age_Ma = this.get_attribute("age_Ma");
_age_Ma = isNaN(_age_Ma) ? 0 : _age_Ma;
if (this.detail_fetched) {
this._age = age;
this._age = _age_Ma;
}
return age;
return _age_Ma;
}
get extinction_Ma() {
/* used for leaf dates. Extant are null, unknown is marked by a large negative value
(-1e4: more Mya than the age of the planet). In this case we simply return `true`.
Zero might mark something very recently extinct, e.g. marked as extinct by IUCN
*/
if (this._age !== undefined) return this._age;
let _extinction_Ma = this.get_attribute("extinction_date");
_extinction_Ma = (_extinction_Ma < -5e3)?true:_extinction_Ma
if (this.detail_fetched) {
this._age = _extinction_Ma;
}
return _extinction_Ma;
}
get spec_num_full() {
if (this._spec_num_full !== null) return this._spec_num_full;
Expand Down Expand Up @@ -396,7 +410,7 @@ class Midnode {
return num_threatened > this.richness_val * 0.5;
}
get redlist() {
if (this._redlist !== null) return this._redlist;
if (this._redlist !== undefined) return this._redlist;
let _redlist = this.get_attribute("IUCN");
if (this.detail_fetched) {
this._redlist = _redlist;
Expand Down
23 changes: 17 additions & 6 deletions OZprivate/rawJS/OZTreeModule/src/factory/utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -58,15 +58,26 @@ export function gpmapper(datein, full) {
}


export function ageAsText(Ma) {
//return e.g. 100 thousand years ago
export function ageAsText(Ma, leaf) {
//return e.g. "100 thousand years ago", or a similar string
let subs_strs = leaf?OZstrings['leaf_date']:OZstrings['node_date'];
if (Ma >10) {
return OZstrings['Mya'].replace(/\{(\w+)\}/g, function (m, c) {return({'mya':(Math.round(Ma*10)/10.0).toString()}[c])});
return subs_strs['Mya'].replace(
/\{(\w+)\}/g,
function (m, c) {return({'mya':(Math.round(Ma*10)/10.0).toString()}[c])});
} else {
if (Ma >1) {
return OZstrings['Mya'].replace(/\{(\w+)\}/g, function (m, c) {return({'mya':(Math.round(Ma*100)/100.0).toString()}[c])});
if (Ma > 1) {
return subs_strs['Mya'].replace(
/\{(\w+)\}/g,
function (m, c) {return({'mya':(Math.round(Ma*100)/100.0).toString()}[c])});
} else if (Ma > 0.001) {
return subs_strs['tya'].replace(
/\{(\w+)\}/g,
function (m, c) {return({'tya':(Math.round(Ma*10000)/10.0).toString()}[c])});
} else {
return OZstrings['tya'].replace(/\{(\w+)\}/g, function (m, c) {return({'tya':(Math.round(Ma*10000)/10.0).toString()}[c])});
return subs_strs['ya'].replace(
/\{(\w+)\}/g,
function (m, c) {return({'ya':(Math.round(Ma*1000000)).toString()}[c])});
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,16 +58,16 @@ class ATNodeLayout extends NodeLayoutBase {
function get_concestor_interior_header(node) {
let textonly_header;
let concestor_append = "Concestor " + node.concestor + ",";
if (node.lengthbr && node.lengthbr>0) {
if (node.age_Ma && node.age_Ma>0) {
//This is a dated node
if (is_primary_or_secondary_name(node)) {
textonly_header = (["", "", "the most recent common ancestor to today’s",
"the " + gpmapper(node.lengthbr) + " period, lived " + concestor_append,
ageAsText(node.lengthbr) + ", during"]);
"the " + gpmapper(node.age_Ma) + " period, lived " + concestor_append,
ageAsText(node.age_Ma) + ", during"]);
} else {
textonly_header = (["", "common ancestor to species including", "lived " + concestor_append + " the most recent",
"during the " + gpmapper(node.lengthbr) + " period,",
ageAsText(node.lengthbr)])
"during the " + gpmapper(node.age_Ma) + " period,",
ageAsText(node.age_Ma)])
}
} else {
//This is an undated node (shouldn't happen)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import {global_button_action} from '../../button_manager';
import {live_area_config} from '../live_area_config';
import {add_mr} from '../move_restriction';
import {get_image, image_ready} from '../../image_cache';
import {extxt, spec_num_full} from '../../factory/utils';
import {extxt, spec_num_full, ageAsText} from '../../factory/utils';
import config from '../../global_config';

class LeafLayoutBase {
Expand Down Expand Up @@ -156,16 +156,24 @@ class LeafLayoutBase {
}

get_conservation_text(node) {
if (node.redlist === "EX"
||node.redlist === "EW"
||node.redlist === "CR"
||node.redlist === "EN"
||node.redlist === "VU"
||node.redlist === "NT"
||node.redlist === "LC") {
return [OZstrings["Conservation"], OZstrings["IUCN Red List status:"], extxt(node)]
if (node.extinction_Ma !== null) {
if (node.extinction_Ma !== true) {
return ageAsText(node.extinction_Ma, true).split("\n");
} else {
return OZstrings["Fossil species"].split("\n");
};
} else {
return [];
if (node.redlist === "EX"
||node.redlist === "EW"
||node.redlist === "CR"
||node.redlist === "EN"
||node.redlist === "VU"
||node.redlist === "NT"
||node.redlist === "LC") {
return [OZstrings["Conservation"], OZstrings["IUCN Red List status:"], extxt(node)]
} else {
return [];
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -601,12 +601,12 @@ class NodeLayoutBase {

get_date_str(node) {
let date_str;
if (node.lengthbr > 10) {
date_str = (Math.round((node.lengthbr)*10)/10.0).toString() + " Ma";
} else if (node.lengthbr > 1) {
date_str = (Math.round((node.lengthbr)*100)/100.0).toString() + " Ma";
} else if (node.lengthbr > 0) {
date_str = (Math.round((node.lengthbr)*10000)/10.0).toString() + " Ka";
if (node.age_Ma > 10) {
date_str = (Math.round((node.age_Ma)*10)/10.0).toString() + " Ma";
} else if (node.age_Ma > 1) {
date_str = (Math.round((node.age_Ma)*100)/100.0).toString() + " Ma";
} else if (node.age_Ma > 0) {
date_str = (Math.round((node.age_Ma)*10000)/10.0).toString() + " Ka";
} else {
date_str = "";
}
Expand All @@ -616,8 +616,8 @@ class NodeLayoutBase {
get_textonly_header(node) {
let ntxt = OZstrings['node_labels']['text_only']
let textonly_header;
if (node.lengthbr && node.lengthbr>0) {
let vars = {'date_with_units':ageAsText(node.lengthbr), 'geo_time':gpmapper(node.lengthbr, true)};
if (node.age_Ma && node.age_Ma>0) {
let vars = {'date_with_units':ageAsText(node.age_Ma), 'geo_time':gpmapper(node.age_Ma, true)};
if (is_primary_or_secondary_name(node)) {
textonly_header = substitute_variables(ntxt['dated']['named'], vars).split("\n").reverse();
} else {
Expand All @@ -637,8 +637,8 @@ class NodeLayoutBase {
let ntxt = OZstrings['node_labels']['with_pic']
let pic_header_text;
//NB - these are in reverse order, as we often don't use the top two lines
if (node.lengthbr && (node.lengthbr>0)) {
let vars = {'date_with_units':ageAsText(node.lengthbr), 'geo_time':gpmapper(node.lengthbr, true)};
if (node.age_Ma && (node.age_Ma>0)) {
let vars = {'date_with_units':ageAsText(node.age_Ma), 'geo_time':gpmapper(node.age_Ma, true)};
if (is_primary_or_secondary_name(node)) {
pic_header_text = substitute_variables(ntxt['dated']['named'], vars).split("\n").reverse();
} else {
Expand Down
62 changes: 41 additions & 21 deletions OZprivate/rawJS/OZTreeModule/src/themes/natural_theme.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,13 @@ let iucnDD = green1;
let iucnNE = green1;
let iucnDefault = green1;

function is_fossil(leaf) {
// fossils have extinction_Ma > 0 (if known) or true
// extant (or recently extinct) leaves should all have extinction_Ma===null
// we use == not === to also treat undefined (data not yet filled out) as not fossil
return (leaf.extinction_Ma == null)?false:true;
}

function outline_highlight(node) {
if (node.richness_val > 1) {
return 'rgb(0,0,0)';
Expand All @@ -33,25 +40,29 @@ function outline_highlight(node) {
function leafcolor2b(node) {
switch(node.redlist) {
case "EX":
return ('rgb(50,50,50)');
return ('rgb(50,50,50)');
case "EW":
return ('rgb(50,50,50)');
return ('rgb(50,50,50)');
case "CR":
return ('rgb(80,00,00)');
return ('rgb(80,00,00)');
case "EN":
return ('rgb(80,00,00)');
return ('rgb(80,00,00)');
case "VU":
return ('rgb(80,00,00)');
return ('rgb(80,00,00)');
case "NT":
return ('rgb(20,80,00)');
return ('rgb(20,80,00)');
case "LC":
return ('rgb(20,80,00)');
return ('rgb(20,80,00)');
case "DD":
return ('rgb(20,80,00)');
return ('rgb(20,80,00)');
case "NE":
return ('rgb(20,80,00)');
return ('rgb(20,80,00)');
default:
return ('rgb(20,80,00)');
if (is_fossil(node)) {
return ('rgb(50,50,50)');
} else {
return ('rgb(20,80,00)');
}
}
}

Expand All @@ -69,42 +80,47 @@ function get_redlist_color(node) {
switch(node.redlist) {
case "EX":
//return ('rgb(150,175,215)'); // new blue
return iucnEX;
return iucnEX;
case "EW":
//return ('rgb(150,175,215)'); // new blue
return iucnEW;
return iucnEW;
//return ('rgb(80,80,80)');
case "CR":
return iucnCR;
return iucnCR;
//////////return (red1);
//'rgb(215,175,150)' = dinah pink
case "EN":
//return ('rgb(225,185,130)');
//return ('rgb(210,170,145)');
return iucnEN;
return iucnEN;
//////////return (red1);

case "VU":
return iucnVU;
return iucnVU;
//return (red1);
//return ('rgb(210,170,145)');
//return ('rgb(220,220,220)');
case "NT":
return iucnNT;
return iucnNT;
//return ('rgb(170,195,96)');
//return ('rgb(180,208,90)');
//return ('rgb(200,220,180)');
//return ('rgb(190,200,80)');
case "LC":
return iucnLC;
return iucnLC;
case "DD":
return iucnDD;
return iucnDD;
//return ('rgb(60,50,135)');
case "NE":
return iucnNE;
return iucnNE;
//return ('rgb(0,0,190)');
default:
return iucnDefault;
if (is_fossil(node)) {
return iucnEX;
} else {
// extant leaves should all have age==null or age==0
return iucnDefault;
}
}
}

Expand Down Expand Up @@ -146,7 +162,11 @@ function get_redlist_color2(node) {
return green2;
//return ('rgb(0,0,190)');
default:
return green2;
if (is_fossil(node)) {
return ('rgb(110,110,110)');
} else {
return green2;
}
}
}

Expand Down
13 changes: 11 additions & 2 deletions views/treeviewer/js_strings.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,17 @@ OZstrings = {
},
'sp': T("species## singular"),
'spp': T("species## plural"),
'Mya': T("{mya} million years ago"),
'tya': T("{tya} thousand years ago"),
'Fossil species':T("Fossil species"),
'leaf_date':{
'Mya':T("This fossil species\nwent extinct {mya}\nmillion years ago"),
'tya':T("This fossil species\nwent extinct {tya}\nthousand years ago"),
'ya':T("This fossil species\nwent extinct {ya}\nyears ago")
},
'node_date':{
'Mya': T("{mya} million years ago"),
'tya': T("{tya} thousand years ago"),
'ya': T("{ya} years ago")
},
'sciname': T("Scientific name: "),
'sponsor_text':{
'node':{
Expand Down