|
|
|
@ -7,15 +7,27 @@ let xScale, yScale;
|
|
|
|
const parseTime = d3.timeParse("%B %e, %Y");
|
|
|
|
const parseTime = d3.timeParse("%B %e, %Y");
|
|
|
|
const formatTime = d3.timeFormat("%B %e, %Y");
|
|
|
|
const formatTime = d3.timeFormat("%B %e, %Y");
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
const renderTable = () => {
|
|
|
|
|
|
|
|
d3.select('tbody').html('');
|
|
|
|
|
|
|
|
const trs = d3.select('tbody')
|
|
|
|
|
|
|
|
.selectAll('tr')
|
|
|
|
|
|
|
|
.data(instances.filter(d => d.highlighted))
|
|
|
|
|
|
|
|
.enter()
|
|
|
|
|
|
|
|
.append('tr')
|
|
|
|
|
|
|
|
.selectAll('td')
|
|
|
|
|
|
|
|
.data(d => [d.instance_id, d.course, d.graduation_date, d.total_students, d.dropped, d.graduates, d.ninety_day_outcomes])
|
|
|
|
|
|
|
|
.enter()
|
|
|
|
|
|
|
|
.append('td')
|
|
|
|
|
|
|
|
.text(value => value)
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
const renderPoints = () => {
|
|
|
|
const renderPoints = () => {
|
|
|
|
d3.select('#points').html('');
|
|
|
|
d3.select('#points').html('');
|
|
|
|
const circles = d3.select('#points')
|
|
|
|
const circles = d3.select('#points')
|
|
|
|
.selectAll('circle')
|
|
|
|
.selectAll('circle')
|
|
|
|
.data(instances, (datum) => {
|
|
|
|
.data(instances)
|
|
|
|
return datum.id
|
|
|
|
.enter()
|
|
|
|
});
|
|
|
|
.append('circle');
|
|
|
|
circles.enter().append('circle');
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
d3.selectAll('circle')
|
|
|
|
d3.selectAll('circle')
|
|
|
|
.attr('cy', (datum, index) => {
|
|
|
|
.attr('cy', (datum, index) => {
|
|
|
|
@ -33,7 +45,9 @@ const renderPoints = () => {
|
|
|
|
})
|
|
|
|
})
|
|
|
|
|
|
|
|
|
|
|
|
d3.selectAll('circle').on('click', (event, datum) => {
|
|
|
|
d3.selectAll('circle').on('click', (event, datum) => {
|
|
|
|
highlightInstance(datum.instance_id);
|
|
|
|
datum.highlighted = true;
|
|
|
|
|
|
|
|
renderPoints()
|
|
|
|
|
|
|
|
renderTable()
|
|
|
|
});
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
@ -74,32 +88,14 @@ const createAxes = () => {
|
|
|
|
.call(leftAxis);
|
|
|
|
.call(leftAxis);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
const highlightInstance = (instanceID) => {
|
|
|
|
|
|
|
|
selectedInstances.push(instanceID);
|
|
|
|
|
|
|
|
for(instance of instances){
|
|
|
|
|
|
|
|
if(instance.instance_id == instanceID){
|
|
|
|
|
|
|
|
if(!instance.highlighted){
|
|
|
|
|
|
|
|
instance.highlighted = true
|
|
|
|
|
|
|
|
const tbody = d3.select('tbody');
|
|
|
|
|
|
|
|
const tr = tbody.append('tr');
|
|
|
|
|
|
|
|
tr.append('td').html(instance.instance_id);
|
|
|
|
|
|
|
|
tr.append('td').html(instance.course);
|
|
|
|
|
|
|
|
tr.append('td').html(instance.graduation_date);
|
|
|
|
|
|
|
|
tr.append('td').html(instance.total_students);
|
|
|
|
|
|
|
|
tr.append('td').html(`${instance.dropped} (${Math.floor(instance.dropped/instance.total_students*100)}%)`);
|
|
|
|
|
|
|
|
tr.append('td').html(instance.graduates);
|
|
|
|
|
|
|
|
tr.append('td').html(`${instance.ninety_day_outcomes} (${Math.floor(instance.ninety_day_outcomes/instance.graduates*100)}%)`)
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
renderPoints()
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
const createFormSubmissionHandler = () => {
|
|
|
|
const createFormSubmissionHandler = () => {
|
|
|
|
d3.select('form').on('submit', (event)=>{
|
|
|
|
d3.select('form').on('submit', (event)=>{
|
|
|
|
event.preventDefault();
|
|
|
|
event.preventDefault();
|
|
|
|
const instanceID = parseInt(d3.select('input[type="text"]').property('value'))
|
|
|
|
const instanceID = parseInt(d3.select('input[type="text"]').property('value'))
|
|
|
|
highlightInstance(instanceID);
|
|
|
|
const found = instances.find(i => i.instance_id === instanceID)
|
|
|
|
|
|
|
|
found.highlighted = true;
|
|
|
|
|
|
|
|
renderTable();
|
|
|
|
|
|
|
|
renderPoints();
|
|
|
|
});
|
|
|
|
});
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|