Published
Edited
Jul 12, 2022
Fork of base map
1 star
Insert cell
# base map - text
Insert cell
d3 = require("d3@7", "d3-geo-scale-bar@1.2", "d3-tile@1")
Insert cell
height = 900
Insert cell
width = 960
Insert cell
Insert cell
test = FileAttachment("test@2.json").json()
Insert cell
number = test.icon
Insert cell
chart = {
//const width = 960,
//height = 900;
//const svg = d3.select(DOM.svg(width, height));
const svg = d3.create("svg")
//.attr("viewBox", [-150, -25, width+270, height+100]);
.attr("viewBox", [-175, -25, width+270, height+100]);

// Use Mercator projection
var projection = d3
.geoMercator()
.fitSize([width - 50, height - 50], bbox);

var path1 = d3.geoPath().projection(projection);
var path2 = d3.geoPath().projection(projection);
var path3 = d3.geoPath().projection(projection);
var path4 = d3.geoPath().projection(projection);
var path5 = d3.geoPath().projection(projection);

var g = svg.append("g").attr("id", "paths");
//i'm not using the boundary lines, so I'm going to comment them out
/*
g.selectAll("path1") //d3 geopath
.data(boundary.features) //get data to define path
.enter() //there are more data than elements, this selects them
.append("path") //appends path to data
.attr('class','outlines')
.attr("d", path1) //The d attribute defines a path to be drawn, only applies to appended elements
.style("fill", "none")
.style('stroke-opacity','1')
.style("stroke-width", '.5')
.style("stroke", "rgb(0,0,0)")
*/

g.selectAll("path4") //d3 geopath
.data(parks.features) //get data to define path
.enter() //there are more data than elements, this selects them
.append("path") //appends path to data
.attr('class','outlines')
.attr("d", path4) //The d attribute defines a path to be drawn, only applies to appended elements
.style("fill", "green")
.style("fill-opacity", ".3")
.style('stroke-opacity','.4')
.style("stroke-width", '.5')
.style("stroke", "none")

g.selectAll("path2") //d3 geopath
.data(subLns.features) //get data to define path
.enter() //there are more data than elements, this selects them
.append("path") //appends path to data
.attr('class','outlines')
.attr("d", path2) //The d attribute defines a path to be drawn, only applies to appended elements
.style("fill", "none")
.style('stroke-opacity','.5')
.style("stroke-width", '.75')
.style("stroke", "rgb(0,0,0)")

g.selectAll("path3") //d3 geopath
.data(bldgs.features) //get data to define path
.enter() //there are more data than elements, this selects them
.append("path") //appends path to data
.attr('class','outlines')
.attr("d", path3) //The d attribute defines a path to be drawn, only applies to appended elements
.style("fill", "rgb(240,240,240)")
.style("fill-opacity", ".5")
.style('stroke-opacity','.4')
.style("stroke-width", '.5')
.style("stroke", "rgb(0,0,0)")


g.selectAll("path5") //d3 geopath
.data(site.features) //get data to define path
.enter() //there are more data than elements, this selects them
.append("path") //appends path to data
.attr('class','outlines')
.attr("d", path5) //The d attribute defines a path to be drawn, only applies to appended elements
.style("fill", "none")
//.style("fill-opacity", ".5")
.style('stroke-opacity','1')
.style("stroke-width", '2.5')
.style("stroke", "rgb(0,0,0)")
.attr('stroke-dasharray',"14 14")


var c = svg.selectAll("circle") //d3 geopath
.data(subSts.features)
.enter() //there are more data than elements, this selects them
.append("circle") //appends path to data
.attr("cx", function(d) {return path1.centroid(d)[0]})
.attr("cy", function(d) {return path1.centroid(d)[1]})
.attr('r',2)
.attr('fill','black')
.style('fill-opacity','1')


c.enter().append('circle')
.data(chargers)
.enter() //there are more data than elements, this selects them
.append("circle") //appends path to data
.attr("cx", function(d) {return projection([d.long,d.lat])[0]})
.attr("cy", function(d) {return projection([d.long,d.lat])[1]})
.attr('r',3)
.attr('fill','red')
.style('fill-opacity','1')

c.enter().append('circle')
.data(bikes)
.enter() //there are more data than elements, this selects them
.append("circle") //appends path to data
.attr("cx", function(d) {return projection([d.long,d.lat])[0]})
.attr("cy", function(d) {return projection([d.long,d.lat])[1]})
.attr('r',4)
.attr('fill','white')
.style('fill-opacity','1')
.style('stroke','rgb(0,0,0)')
.style('stroke-weight','.5')
.on("mouseover",addBikeText)
.on("mouseout",removeBikeText)


c.enter().append('circle')
.data(test.icon)
.enter() //there are more data than elements, this selects them
.append("circle") //appends path to data
.attr("cx", d => d.x)
.attr("cy", d => d.y)
//.attr("cx", function(d) {return x})
//.attr("cy", function(d) {return y})
//.attr("cx", 50)
//.attr("cy", 50)
.attr('r',1)
.attr('fill','blue')
.style('fill-opacity','1')
//}


//var ln = d3.line()
//.x(d => d.x)
//.y(d => d.y)
//.stroke('black')
svg.append("polyline")
.attr("points", test.icon);

//}
// svg
//.append("text") //appends path to data
var t = svg.selectAll('text')
.data(subSts.features)
.enter()
.append('text')
.attr('class','station')
.attr('x',function(d) {return path1.centroid(d)[0]})
.attr('y',function(d) {return path1.centroid(d)[1]-5})
.attr("font-family", "Helvetica")
.attr('font-size','.4em')
.attr('text-anchor','middle')
.style("font-weight","bold")
.style("fill","rgb(100,100,100)")
.text(function(d) {return d.properties.name})

t.enter().append('text')
.data(chargers)
.enter()
.append('text')
.attr('class','station')
.attr('x','-10')
.attr('y',function(d, i) { return i * 30 ;})
.attr("font-family", "Helvetica")
.attr('font-size','.55em')
.attr('text-anchor','end')
.style("font-weight","bold")
.style("fill","rgb(100,100,100)")
.text(function(d) {return d.name})

t.enter().append('text')
.data(chargers)
.enter()
.append('text')
.attr('class','station')
.attr('x','-10')
.attr('y',function(d, i) { return i * 30 + 8;})
.attr("font-family", "Helvetica")
.attr('font-size','.4em')
.attr('text-anchor','end')
.style("font-weight","normal")
.style("fill","rgb(100,100,100)")
.text(function(d) {return d.description})

svg
.append('text')
.attr('class','station')
.attr('x','450')
.attr('y','550')
.attr("font-family", "Helvetica")
.attr('font-size','1.25em')
//.attr('text-anchor','end')
.style("font-weight","bold")
.style("fill","rgb(0,0,0)")
.text('Times Square')

svg
.append('text')
.attr('class','station')
.attr('x','450')
.attr('y','565')
.attr("font-family", "Helvetica")
.attr('font-size','.75em')
.style("font-weight","200")
.style("fill","rgb(0,0,0)")
.text('The Future of Travel')

svg
.append('line')
.attr('class','sbLn')
.attr('x1',450)
.attr('y1',545)
.attr('x2',383)
.attr('y2',545)
.attr('stroke-width','1.5')
.attr('stroke-opacity','1')
.style('stroke','rgb(0,0,0)')

t.enter().append('line')
.data(chargers)
.enter()
.append('line')
.attr('class','annotation_line')
.attr('x1','-5')
.attr('y1',function(d, i) { return i * 30-3 ;})
.attr('x2',function(d) {return projection([d.long,d.lat])[0]})
.attr('y2',function(d, i) { return i * 30-3 ;})
.attr('stroke-width','1')
.attr('stroke-opacity','1')
.attr('stroke-dasharray',"4 4")
.style('stroke','rgb(100,100,100)')

t.enter().append('line')
.data(chargers)
.enter()
.append('line')
.attr('class','annotation_line')
.attr('x1',function(d) {return projection([d.long,d.lat])[0]})
.attr('y1',function(d, i) { return i * 30-3 ;})
.attr('x2',function(d) {return projection([d.long,d.lat])[0]})
.attr('y2',function(d) {return projection([d.long,d.lat])[1]})
.attr('stroke-width','1')
.attr('stroke-opacity','1')
.attr('stroke-dasharray',"4 4")
.style('stroke','rgb(100,100,100)')

//citi bikes



svg
.append('text')
.attr('class','station')
.attr('x','-40')
.attr('y','700')
.attr("font-family", "Helvetica")
.attr('font-size','.8em')
.attr('text-anchor','end')
.attr("font-weight","normal")
.attr('fill','rgb(0,0,0)')
.text('Citi Bike Station')

svg
.append('line')
.attr('class','sbLn')
.attr('x1',-160)
.attr('y1',710)
.attr('x2',-10)
.attr('y2',710)
.attr('stroke-width','1.8')
.attr('stroke-opacity','1')
.style('stroke','rgb(0,0,0)')

function addBikeText(event,d){

svg.append('text')
.attr('class','citiStation')
.attr('x','-82')
.attr('y','730')
.attr("font-family", "Helvetica")
.attr('font-size','.7em')
.attr('text-anchor','middle')
.style("font-weight","bold")
.style("fill","rgb(0,0,0)")
.text(d.name)

svg.append('text')
.attr('class','citiStation')
.attr('x','-82')
.attr('y','745')
.attr("font-family", "Helvetica")
.attr('font-size','.6em')
.attr('text-anchor','middle')
//.style("font-weight","bold")
.style("fill","rgb(0,0,0)")
.text(d.description)

svg
.append('line')
.attr('class','cbLn')
.attr('x1',-25)
.attr('y1',700)
.attr('x2',projection([d.long,d.lat])[0])
.attr('y2',700)
.attr('stroke-width','.4')
.attr('stroke-opacity','1')
.attr('stroke-dasharray',"4 4")
.style('stroke','rgb(0,0,0)')

svg
.append('line')
.attr('class','cbLn')
.attr('x1',projection([d.long,d.lat])[0])
.attr('y1',700)
.attr('x2',projection([d.long,d.lat])[0])
.attr('y2',projection([d.long,d.lat])[1])
.attr('stroke-width','.4')
.attr('stroke-opacity','1')
.attr('stroke-dasharray',"4 4")
.style('stroke','rgb(0,0,0)')

//console.log('hello')

}

function removeBikeText(event,d){
d3.selectAll("text.citiStation").remove()
d3.selectAll("line.cbLn").remove()
}

/*
t.enter().append('text')
.data(bikes)
.enter()
.append('text')
.attr('class','station')
.attr('x','940')
.attr('y',function(d, i) { return height-(i * 30)})
.attr("font-family", "Helvetica")
.attr('font-size','.55em')
.attr('text-anchor','start')
.style("font-weight","bold")
.style("fill","rgb(100,100,100)")
.text(function(d) {return d.name})

t.enter().append('text')
.data(bikes)
.enter()
.append('text')
.attr('class','station')
.attr('x','940')
.attr('y',function(d, i) { return height-(i * 30)+8})
.attr("font-family", "Helvetica")
.attr('font-size','.4em')
.attr('text-anchor','start')
.style("font-weight","normal")
.style("fill","rgb(100,100,100)")
.text(function(d) {return d.description})
.on('mouseover',makeBold)

function makeBold(d,i){
//var ln = d3.select(this).attr("fill", 'rgb(0,0,0)');

//data.features.indexOf(d)

}


t.enter().append('line')
.data(bikes)
.enter()
.append('line')
.attr('class','annotation_line')
.attr('x1','940')
.attr('y1',function(d, i) { return height-(i * 30)-3})
.attr('x2',function(d) {return projection([d.long,d.lat])[0]})
.attr('y2',function(d, i) { return height-(i * 30)-3})
.attr('stroke-width','1')
.attr('stroke-opacity','1')
.attr('stroke-dasharray',"4 4")
.style('stroke','rgb(100,100,100)')

t.enter().append('line')
.data(bikes)
.enter()
.append('line')
.attr('class','annotation_line')
.attr('x1',function(d) {return projection([d.long,d.lat])[0]})
.attr('y1',function(d, i) {return height-(i * 30)-3})
.attr('x2',function(d) {return projection([d.long,d.lat])[0]})
.attr('y2',function(d) {return projection([d.long,d.lat])[1]})
.attr('stroke-width','1')
.attr('stroke-opacity','1')
.attr('stroke-dasharray',"4 4")
.style('stroke','rgb(100,100,100)')

*/

//svg.append("g")
//.call(scaleBar);
scaleBar
.projection(projection)
.size([width, height/2]);

svg.append("g")
.call(scaleBar);

return svg.node();
}
Insert cell
parks = FileAttachment("parks.geojson").json()
Insert cell
subSts = FileAttachment("sub_stops.geojson").json()
Insert cell
bldgs = FileAttachment("bldgs.geojson").json()
Insert cell
bbox = FileAttachment("site_boundary.geojson").json()
Insert cell
subLns = FileAttachment("subway_lines.geojson").json()
Insert cell
boundary = FileAttachment("nyc_boundary.geojson").json()
Insert cell
Insert cell
chargers = d3.csv(link,d3.autoType)
Insert cell
bikes = d3.csv(bkLink,d3.autoType)
Insert cell
Insert cell
site = FileAttachment("site.geojson").json()
Insert cell
textTest = FileAttachment("text").json()
Insert cell
//txt1 = d3.autoType(textTest)
Insert cell
FileAttachment("test@3.json").json()
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more