{
const points = vl
.markArc({ innerRadius: 5, cornerRadius: 20, padAngle: 0.01 })
.data(ds3)
.encode(
vl.order().fieldQ('monthnum'),
vl.theta().fieldQ('sunshine').stack(true).scale({range: [0.75 * Math.PI, 2.75 * Math.PI]}),
vl.radius().fieldQ('sunshine').scale({ rangeMin: 10, rangeMax: 50 }),
vl.tooltip([vl.fieldN('month'), vl.fieldQ('sunshine')]),
vl.color({ value: "yellow" }),
vl.latitude().fieldQ('lat'),
vl.longitude().fieldQ('lon')
);
const textConfig = { dy: 4, dx: 2 };
const textName = points
.markText(textConfig)
.transform(vl.filter('datum["sunshine"] === datum["minSun"] || datum["sunshine"] === datum["maxSun"]'))
.encode(
vl.text().fieldQ('sunshine'),
vl.color().value("black")
);
const borderColors = {
domain: ['Summer', 'Fall', 'Winter', 'Spring'],
range: ['rgba(83, 157, 235, 1)', 'rgba(238, 248, 253, 1)', 'rgba(235, 141, 83, 1)', 'rgba(91, 226, 98, 1)']
};
const cityLabels = vl
.markText({ size: 11, dy: -60, font: "Roboto", fontSize: 16, fontWeight: 100 })
.data(ds3)
.encode(
vl.latitude().fieldQ('lat'),
vl.longitude().fieldQ('lon'),
vl.text().fieldN('city')
);
const map = vl
.markGeoshape({ fill: 'rgba(255, 246, 224, 1)', stroke: "rgba(211, 71, 246, 0.5)", strokeWidth: 0.5 })
.data(vl.topojson(usa).feature('states'))
.height(620);
const seasonsBorder = vl
.markArc({ radius: 50, radius2: 52, padAngle: 0.04, cornerRadius: 7, thetaOffset: 2.2 })
.data(ds3)
.encode(
vl.color().fieldN('season').scale(borderColors).legend(null),
vl.theta().fieldN('season'),
vl.latitude().fieldQ('lat'),
vl.longitude().fieldQ('lon')
);
const pointsBackground = vl
.markCircle({ size: 10000, color: "rgb(0, 140, 233, 0.8)" })
.data(summed)
.encode(
vl.latitude().fieldQ('lat'),
vl.longitude().fieldQ('lon')
);
return vl.layer(map, pointsBackground, points, seasonsBorder, cityLabels, textName)
.project(vl.projection('albersUsa'))
.view({ fill: 'rgba(167, 226, 251, 1)' })
.width(900)
.height(500)
.render();
}