民進黨團提案刪除核四101年度預算投票結果:
出席 93 贊成 45 反對 47 棄權 1
提案不通過。
立委投票結果產生器
幫你把立委在國會表決的結果畫成一目了然的圖表! Generated with http://bl.ocks.org/4248542
幫你把立委在國會表決的結果畫成一目了然的圖表! Generated with http://bl.ocks.org/4248542
html, body { | |
width: 100%; | |
height:100% | |
} | |
.mly-seat { | |
/*stroke: #f00*/ | |
cursor: pointer; | |
} | |
.mly-vote { | |
font-family: arial; | |
} | |
.mly-name { | |
font-size: 15px; | |
cursor: pointer; | |
} |
<!DOCTYPE html> | |
<html lang="en"> | |
<head> | |
<meta charset="utf-8"> | |
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"> | |
<meta name="viewport" content="width=device-width"> | |
<title>立法委員投票結果</title> | |
<link rel="shortcut icon" href="favicon.ico"> | |
<script type="text/javascript" src="http://crypto-js.googlecode.com/svn/tags/3.0.2/build/rollups/md5.js"></script> | |
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script> | |
<script type="text/javascript" src="http://d3js.org/d3.v3.min.js"></script> | |
<link rel="stylesheet" type="text/css" href="index.css"> | |
<script type="text/javascript" src="lyvote.js"></script> | |
<script type="text/javascript" src="index.js"></script> | |
</head> | |
<body> | |
<div id="nuke" class="twlyvote ad-8 session-2 sitting-13"><span class="approval">許忠信 蔡煌瑯 李俊俋 葉宜津 鄭麗君 林岱樺 黃文玲 薛凌 蔡其昌 張曉風 許智傑 吳秉叡 陳唐山 林世嘉 黃偉哲 柯建銘 陳其邁 高志鵬 林淑芬 陳亭妃 何欣純 潘孟安 魏明谷 趙天麟 劉櫂豪 林佳龍 楊曜 姚文智 李應元 劉建國 李昆澤 陳歐珀 邱志偉 管碧玲 陳節如 蘇震清 蕭美琴 段宜康 陳明文 吳宜臻 丁守中 許添財 邱議瑩 尤美女 田秋堇</span><span class="veto">曾巨威 林德福 王進士 李鴻鈞 賴士葆 蔡正元 黃昭順 鄭汝芬 江惠貞 蔡錦隆 陳碧涵 楊玉欣 吳育昇 楊瓊瓔 盧嘉辰 江啟臣 徐欣瑩 林國正 徐少萍 孫大千 林鴻池 翁重鈞 廖國棟 林滄敏 蘇清泉 李貴敏 費鴻泰 林明溱 謝國樑 陳超明 潘維剛 楊應雄 楊麗環 紀國棟 陳根德 陳鎮湘 詹凱臣 王廷升 盧秀燕 徐耀昌 孔文吉 王育敏 簡東明 陳淑慧 吳育仁 林郁方 張慶忠</span><span class="abstention">邱文彥</span></div> | |
</body> | |
</html> |
!!! 5 | |
html(lang="en") | |
head | |
meta(charset='utf-8') | |
meta(http-equiv="X-UA-Compatible", content="IE=edge,chrome=1") | |
meta(name='viewport', content='width=device-width') | |
title 立法委員投票結果 | |
link(rel="shortcut icon",href="favicon.ico") | |
script(type="text/javascript",src="http://crypto-js.googlecode.com/svn/tags/3.0.2/build/rollups/md5.js") | |
script(type="text/javascript",src="http://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js") | |
script(type="text/javascript",src="http://d3js.org/d3.v3.min.js") | |
link(rel="stylesheet",type="text/css",href="index.css") | |
script(type="text/javascript",src="lyvote.js") | |
script(type="text/javascript",src="index.js") | |
body | |
#nuke.twlyvote.ad-8.session-2.sitting-13 | |
span.approval 許忠信 蔡煌瑯 李俊俋 葉宜津 鄭麗君 林岱樺 黃文玲 薛凌 蔡其昌 張曉風 許智傑 吳秉叡 陳唐山 林世嘉 黃偉哲 柯建銘 陳其邁 高志鵬 林淑芬 陳亭妃 何欣純 潘孟安 魏明谷 趙天麟 劉櫂豪 林佳龍 楊曜 姚文智 李應元 劉建國 李昆澤 陳歐珀 邱志偉 管碧玲 陳節如 蘇震清 蕭美琴 段宜康 陳明文 吳宜臻 丁守中 許添財 邱議瑩 尤美女 田秋堇 | |
span.veto 曾巨威 林德福 王進士 李鴻鈞 賴士葆 蔡正元 黃昭順 鄭汝芬 江惠貞 蔡錦隆 陳碧涵 楊玉欣 吳育昇 楊瓊瓔 盧嘉辰 江啟臣 徐欣瑩 林國正 徐少萍 孫大千 林鴻池 翁重鈞 廖國棟 林滄敏 蘇清泉 李貴敏 費鴻泰 林明溱 謝國樑 陳超明 潘維剛 楊應雄 楊麗環 紀國棟 陳根德 陳鎮湘 詹凱臣 王廷升 盧秀燕 徐耀昌 孔文吉 王育敏 簡東明 陳淑慧 吳育仁 林郁方 張慶忠 | |
span.abstention 邱文彥 |
(function(){ | |
$(function(){ | |
return lyvote.render({ | |
/* optional argument */ | |
cx: 600, | |
cy: 500, | |
transform: "scale(0.8)", | |
seatMapping: lyvote.map.linear | |
/* required argument */, | |
namelist: "voter.json", | |
node: '#nuke' | |
}); | |
}); | |
}).call(this); |
<- $ | |
lyvote.render do | |
/* optional argument */ | |
cx: 600 | |
cy: 500 # chart center coordinate | |
transform: "scale(0.8)" # chart transformation | |
#seat-count: [12 16 18 22 24 21] # seat count in each row, totally 6 rows. auto-gen if not provided | |
seat-mapping: lyvote.map.linear | |
/* required argument */ | |
namelist: "voter.json" # e.g., mly-8.json | |
node: \#nuke # tag selector in string | |
(function(){ | |
var slice$ = [].slice, split$ = ''.split; | |
this.lyvote = { | |
svg: null, | |
config: { | |
cx: 500, | |
cy: 500, | |
transform: "", | |
node: 'body' | |
}, | |
colors: { | |
"KMT": '#55f', | |
"DPP": '#090', | |
"NSU": '#fbb', | |
"TSU": '#b26', | |
"PFP": '#f90', | |
"N/A": '#bbb', | |
'null': '#bbb' | |
}, | |
map: { | |
qsort: { | |
idx: 0, | |
map: {}, | |
order: null, | |
limit: 0, | |
init: function(r){ | |
var len, res$, i$, it, ref$, len$, t, i, results$ = []; | |
len = r.config.seatCount.reduce(curry$(function(x$, y$){ | |
return x$ + y$; | |
})); | |
this.limit = 0; | |
res$ = []; | |
for (i$ = 0; i$ < len; ++i$) { | |
it = i$; | |
res$.push(it); | |
} | |
this.order = res$; | |
res$ = []; | |
for (i$ = 0, len$ = (ref$ = this.order).length; i$ < len$; ++i$) { | |
it = ref$[i$]; | |
res$.push([it, r.seatPosition(it)[0]]); | |
} | |
this.order = res$; | |
for (i$ = 0; i$ < len; ++i$) { | |
it = i$; | |
ref$ = [this.order[it], it + parseInt(Math.random() * (len - it))], t = ref$[0], i = ref$[1]; | |
this.order[it] = this.order[i]; | |
results$.push(this.order[i] = t); | |
} | |
return results$; | |
}, | |
_sort: function(r, limit, level, L, R){ | |
var pi, t, p, i, j; | |
if (level > limit) { | |
return; | |
} | |
if (L >= R) { | |
return; | |
} | |
pi = L + parseInt(Math.random() * (R - L + 1)); | |
t = this.order[L]; | |
this.order[L] = this.order[pi]; | |
this.order[pi] = t; | |
p = this.order[L][1]; | |
i = L + 1; | |
j = R; | |
while (i < j) { | |
while (this.order[i][1] <= p && i < j) { | |
i++; | |
} | |
while (this.order[j][1] > p) { | |
j--; | |
} | |
if (i >= j) { | |
break; | |
} | |
t = this.order[i]; | |
this.order[i] = this.order[j]; | |
this.order[j] = t; | |
} | |
t = this.order[L]; | |
this.order[L] = this.order[j]; | |
this.order[j] = t; | |
this._sort(r, limit, level + 1, L, j - 1); | |
return this._sort(r, limit, level + 1, j + 1, R); | |
}, | |
sort: function(r){ | |
return this._sort(r, this.limit++, 0, 0, this.order.length - 1); | |
}, | |
indexOf: function(r, name){ | |
var ref$, ref1$; | |
return this.order[(ref1$ = (ref$ = this.map)[name]) != null | |
? ref1$ | |
: ref$[name] = this.idx++][0]; | |
} | |
}, | |
xorder: { | |
idx: 0, | |
map: {}, | |
order: null, | |
indexOf: function(r, name){ | |
var it, ref$, ref1$; | |
if (!this.order) { | |
this.order = (function(){ | |
var i$, to$, fn$ = curry$(function(x$, y$){ | |
return x$ + y$; | |
}), results$ = []; | |
for (i$ = 0, to$ = r.config.seatCount.reduce(fn$); i$ < to$; ++i$) { | |
it = i$; | |
results$.push([it, r.seatPosition(it)[0]]); | |
} | |
return results$; | |
}()).sort(function(a, b){ | |
return a[1] - b[1]; | |
}); | |
} | |
return this.order[(ref1$ = (ref$ = this.map)[name]) != null | |
? ref1$ | |
: ref$[name] = this.idx++][0]; | |
} | |
}, | |
strip: { | |
idx: 0, | |
map: {}, | |
order: null, | |
indexOf: function(r, name){ | |
var len, ref$, ref1$; | |
if (!this.order) { | |
len = r.config.seatCount.reduce(curry$(function(x$, y$){ | |
return x$ + y$; | |
})); | |
this.order = (function(){ | |
var i$, to$, results$ = []; | |
for (i$ = 0, to$ = len; i$ <= to$; i$ += 2) { | |
results$.push(i$); | |
} | |
return results$; | |
}()).concat((function(){ | |
var i$, to$, results$ = []; | |
for (i$ = 1, to$ = len; i$ <= to$; i$ += 2) { | |
results$.push(i$); | |
} | |
return results$; | |
}())); | |
} | |
return this.order[(ref1$ = (ref$ = this.map)[name]) != null | |
? ref1$ | |
: ref$[name] = this.idx++]; | |
} | |
}, | |
circular: { | |
idx: 0, | |
map: {}, | |
order: null, | |
indexOf: function(r, name){ | |
var it, ref$, ref1$; | |
if (!this.order) { | |
this.order = (function(){ | |
var i$, to$, fn$ = curry$(function(x$, y$){ | |
return x$ + y$; | |
}), results$ = []; | |
for (i$ = 0, to$ = r.config.seatCount.reduce(fn$); i$ < to$; ++i$) { | |
it = i$; | |
results$.push([ | |
it, fn1$( | |
r.seatPosition(it)) | |
]); | |
} | |
return results$; | |
function fn1$(it){ | |
return [it[0] - r.config.cx, it[1]].reduce(function(a, b){ | |
return a + Math.pow(b, 2); | |
}, 0); | |
} | |
}()).sort(function(a, b){ | |
return a[1] - b[1]; | |
}); | |
} | |
return this.order[(ref1$ = (ref$ = this.map)[name]) != null | |
? ref1$ | |
: ref$[name] = this.idx++][0]; | |
} | |
}, | |
linear: { | |
idx: 0, | |
map: {}, | |
order: null, | |
indexOf: function(r, name){ | |
var ref$, ref1$; | |
return (ref1$ = (ref$ = this.map)[name]) != null | |
? ref1$ | |
: ref$[name] = this.idx++; | |
} | |
}, | |
random: { | |
idx: 0, | |
map: {}, | |
order: null, | |
indexOf: function(r, name){ | |
var len, res$, i$, it, ref$, t, i, ref1$; | |
if (!this.order) { | |
len = r.config.seatCount.reduce(curry$(function(x$, y$){ | |
return x$ + y$; | |
})); | |
res$ = []; | |
for (i$ = 0; i$ < len; ++i$) { | |
it = i$; | |
res$.push(it); | |
} | |
this.order = res$; | |
for (i$ = 0; i$ < len; ++i$) { | |
it = i$; | |
ref$ = [this.order[it], it + parseInt(Math.random() * (len - it))], t = ref$[0], i = ref$[1]; | |
this.order[it] = this.order[i]; | |
this.order[i] = t; | |
} | |
} | |
return this.order[(ref1$ = (ref$ = this.map)[name]) != null | |
? ref1$ | |
: ref$[name] = this.idx++]; | |
} | |
} | |
}, | |
_idx: 0, | |
_map: {}, | |
seatMappingDefault: function(name){ | |
var ref$, ref1$; | |
return (ref1$ = (ref$ = this._map)[name]) != null | |
? ref1$ | |
: ref$[name] = this._idx++; | |
}, | |
seatMapping: function(name){ | |
if (this.config.seatMapping) { | |
return this.config.seatMapping.indexOf.call(this.config.seatMapping, this, name); | |
} else { | |
return this.map.random.indexOf(this, name); | |
} | |
}, | |
remap: function(mapObj){ | |
var _pt, this$ = this; | |
this.config.seatMapping = mapObj; | |
_pt = function(it){ | |
return this$.seatPosition(this$.seatMapping(it.name)); | |
}; | |
return this.seats.transition().duration(750).attr('transform', function(it){ | |
return "translate(" + _pt(it)[0] + "," + _pt(it)[1] + ")"; | |
}); | |
}, | |
seatPosition: function(idx){ | |
var sc, res$, i$, len$, i, ret, ref$, row, len, j, m, v, fn$ = curry$(function(x$, y$){ | |
return x$ + y$; | |
}); | |
sc = this.config.seatCount; | |
res$ = []; | |
for (i$ = 0, len$ = sc.length; i$ < len$; ++i$) { | |
i = i$; | |
res$.push(slice$.call(sc, 0, i + 1 || 9e9).reduce(fn$)); | |
} | |
sc = res$; | |
ret = sc.map(function(it){ | |
return it - idx; | |
}).filter((function(it){ | |
return it > 0; | |
})); | |
ref$ = [this.config.seatCount.length, ret.length], row = ref$[0], len = ref$[1]; | |
ref$ = [row - len, ret[0] - 1, sc[row - len] - 1 - (len < row && sc[row - len - 1]) || 0], i = ref$[0], j = ref$[1], m = ref$[2]; | |
v = [Math.cos(Math.PI * j / m), Math.sin(Math.PI * j / m)]; | |
return [this.config.cx + v[0] * (160 + i * 60), this.config.cy - v[1] * (160 + i * 60)]; | |
}, | |
seats: null, | |
hName: {}, | |
hParty: {}, | |
generate: function(error, mlys){ | |
var ref$, _sc, _sc_total, idx, i$, len$, mly, key$, i, names, j$, len1$, name, defs, imgs, panel, _pt, it, lockcell, this$ = this; | |
ref$ = [ | |
{}, { | |
0: 0 | |
} | |
], this.hName = ref$[0], this.hParty = ref$[1]; | |
if (!this.config.seatCount) { | |
_sc = [0, 1, 2, 3, 4, 5].map(function(it){ | |
return parseInt(2 * Math.PI * (it * 60 + 160)); | |
}); | |
_sc_total = _sc.reduce(curry$(function(x$, y$){ | |
return x$ + y$; | |
})); | |
this.config.seatCount = _sc.map(function(it){ | |
return Math.round(it * mlys.length / _sc_total); | |
}); | |
} | |
idx = 0; | |
for (i$ = 0, len$ = mlys.length; i$ < len$; ++i$) { | |
mly = mlys[i$]; | |
this.hName[mly.name] = { | |
name: mly.name, | |
vote: 0, | |
party: mly.party, | |
idx: idx++ | |
}; | |
(ref$ = this.hParty)[key$ = mly.party] == null && (ref$[key$] = this.hParty[0]++); | |
} | |
for (i$ = 0, len$ = (ref$ = this.config.vote).length; i$ < len$; ++i$) { | |
i = i$; | |
names = ref$[i$]; | |
for (j$ = 0, len1$ = names.length; j$ < len1$; ++j$) { | |
name = names[j$]; | |
this.hName[name].vote = i + 1; | |
} | |
} | |
this.svg = d3.select(this.config.node).append('svg').attr('width', '100%').attr('height', '100%'); | |
defs = this.svg.selectAll('defs').data(mlys).enter().append('pattern').attr('id', function(it){ | |
return 'defs_h' + this$.hName[it.name].idx; | |
}).attr('patternUnits', 'userSpaceOnUse').attr('x', 30).attr('y', 30).attr('width', 50).attr('height', 50); | |
imgs = defs.append('image').attr('xlink:href', function(it){ | |
return "http://avatars.io/50a65bb26e293122b0000073/" + CryptoJS.MD5('MLY/' + it.name).toString() + "?size=small"; | |
}).attr('x', 0).attr('y', 0).attr('width', 50).attr('height', 50).attr('transform', "scale(0.9)"); | |
panel = this.svg.append('g').attr('transform', function(){ | |
return this$.config.transform; | |
}); | |
_pt = function(it){ | |
return this$.seatPosition(this$.seatMapping(it.name)); | |
}; | |
this.seats = panel.selectAll('g.seat').data((function(){ | |
var results$ = []; | |
for (it in this.hName) { | |
results$.push(this.hName[it]); | |
} | |
return results$; | |
}.call(this)).sort(function(a, b){ | |
return this$.hParty[a.party] - this$.hParty[b.party]; | |
})).enter().append('g').attr('transform', function(it){ | |
return "translate(" + _pt(it)[0] + "," + _pt(it)[1] + ")"; | |
}); | |
lockcell = null; | |
this.seats.append('circle').attr('class', 'mly-seat').attr('r', 20).attr('fill', function(it){ | |
return this$.colors[it.party]; | |
}).style('opacity', function(it){ | |
if (it.vote === 0) { | |
return 0.3; | |
} else { | |
return 1; | |
} | |
}).on('click', function(){ | |
if (lockcell) { | |
d3.select(lockcell).attr('fill', function(it){ | |
return this$.colors[it.party]; | |
}).transition().duration(500).attr('transform', "scale(1)").attr('stroke', 'none').style('opacity', function(it){ | |
if (it.vote === 0) { | |
return 0.3; | |
} else { | |
return 1; | |
} | |
}); | |
} | |
if (lockcell === d3.event.target) { | |
return lockcell = null; | |
} | |
lockcell = d3.event.target; | |
return d3.select(d3.event.target).attr('fill', function(it){ | |
return "url(#defs_h" + it.idx + ")"; | |
}).transition().duration(500).attr('transform', "scale(2)").attr('stroke', function(it){ | |
return this$.colors[it.party]; | |
}).attr('stroke-width', '3px').style('opacity', 1); | |
}); | |
this.seats.append('path').attr('d', function(it){ | |
switch (it.vote) { | |
case 1: | |
return "M-12 0 L0 10 L11 -11"; | |
case 2: | |
return "M-10,-10 L10,10 L0 0 L-10 10 L10 -10"; | |
case 3: | |
return "M-10 0 L10 00"; | |
case 9: | |
return "M15 0 A15 15 0 1 1 -15 0 A15 15 0 1 1 15 0"; | |
default: | |
return "M0 0"; | |
} | |
}).attr('stroke', function(it){ | |
switch (it.vote) { | |
case 1: | |
return '#0b0'; | |
case 2: | |
return '#b00'; | |
case 3: | |
return '#999'; | |
default: | |
return '#b00'; | |
} | |
}).attr('stroke-width', '5px').attr('fill', 'none'); | |
this.seats.append('rect').attr('class', 'mly-name-box').attr('x', -25).attr('y', 9).attr('width', 50).attr('height', 17).attr('rx', 10).attr('ry', 10).attr('fill', '#fff').style('opacity', 0.4); | |
return this.seats.append('text').attr('class', 'mly-name').attr('y', 22).attr('text-anchor', 'middle').text(function(it){ | |
return it.name; | |
}); | |
}, | |
render: function(config){ | |
var x$, this$ = this; | |
if (!config.vote) { | |
x$ = $(config.node); | |
x$.find('span.approval').each(function(){ | |
return (config.vote || (config.vote = []))[0] = split$.call($(this).text(), ' '); | |
}); | |
x$.find('span.veto').each(function(){ | |
return (config.vote || (config.vote = []))[1] = split$.call($(this).text(), ' '); | |
}); | |
x$.find('span.abstention').each(function(){ | |
return (config.vote || (config.vote = []))[2] = split$.call($(this).text(), ' '); | |
}); | |
x$.find('span').hide(); | |
} | |
import$(this.config, config); | |
return d3.json(config.namelist, function(error, json){ | |
return this$.generate.call(this$, error, json); | |
}); | |
} | |
}; | |
function curry$(f, args){ | |
return f.length > 1 ? function(){ | |
var params = args ? args.concat() : []; | |
return params.push.apply(params, arguments) < f.length && arguments.length ? | |
curry$.call(this, f, params) : f.apply(this, params); | |
} : f; | |
} | |
function import$(obj, src){ | |
var own = {}.hasOwnProperty; | |
for (var key in src) if (own.call(src, key)) obj[key] = src[key]; | |
return obj; | |
} | |
}).call(this); |
@lyvote = | |
svg: null | |
config: | |
cx: 500 | |
cy: 500 | |
#seat-count: [12 16 18 22 24 21] now seat-count is auto-calculated | |
transform: "" | |
node: \body | |
colors: | |
"KMT": \#55f | |
"DPP": \#090 | |
"NSU": \#fbb | |
"TSU": \#b26 | |
"PFP": \#f90 | |
"N/A": \#bbb | |
null: \#bbb | |
map: | |
qsort: | |
idx: 0 | |
map: {} | |
order: null | |
limit: 0 | |
init: (r) -> | |
len = r.config.seat-count.reduce (+) | |
@limit = 0 | |
@order = [it for it til len] | |
@order = [[it,(r.seat-position it)0] for it in @order] | |
for it til len | |
[t,i] = [@order[it],it + parseInt Math.random! * (len - it)] | |
@order[it] = @order[i] | |
@order[i] = t | |
_sort: (r, limit, level, L, R) -> | |
if level>limit then return | |
if L>=R then return | |
pi = L + parseInt Math.random! * (R - L + 1 ) | |
t = @order[L] | |
@order[L] = @order[pi] | |
@order[pi] = t | |
p = @order[L]1 | |
i = L+1 | |
j = R | |
while i < j | |
while @order[i]1<=p and i<j | |
i++ | |
while @order[j]1>p | |
j-- | |
if i>=j then break | |
t = @order[i] | |
@order[i] = @order[j] | |
@order[j] = t | |
t = @order[L] | |
@order[L] = @order[j] | |
@order[j] = t | |
@_sort(r, limit, level+1, L, j-1) | |
@_sort(r, limit, level+1, j+1, R) | |
sort: (r) -> | |
@_sort(r, @limit++, 0, 0, @order.length-1) | |
indexOf: (r, name) -> | |
@order[@map[name] ?= @idx++ ]0 | |
xorder: | |
idx: 0 | |
map: {} | |
order: null | |
indexOf: (r, name) -> | |
if !@order | |
@order = [[it,(r.seat-position it)0] for it til r.config.seat-count.reduce (+)].sort (a,b) -> a[1]-b[1] | |
return @order[@map[name] ?= @idx++ ]0 | |
strip: | |
idx: 0 | |
map: {} | |
order: null | |
indexOf: (r, name) -> | |
if !@order | |
len = r.config.seat-count.reduce (+) | |
@order = [0 to len by 2] +++ [1 to len by 2] | |
@order[@map[name] ?= @idx++ ] | |
circular: | |
idx: 0 | |
map: {} | |
order: null | |
indexOf: (r, name) -> | |
if !@order | |
@order = [[it, (r.seat-position it)|> -> [it[0]-r.config.cx,it[1]] .reduce ((a,b)->a+b**2),0] for it til r.config.seat-count.reduce (+)].sort (a,b) -> a[1]-b[1] | |
return @order[@map[name] ?= @idx++ ]0 | |
linear: | |
idx: 0 | |
map: {} | |
order: null | |
indexOf: (r, name) -> | |
return @map[name] ?= @idx++ | |
random: | |
idx: 0 | |
map: {} | |
order: null | |
indexOf: (r, name) -> | |
if !@order | |
len = r.config.seat-count.reduce (+) | |
@order = [it for it til len] | |
for it til len | |
[t,i] = [@order[it],it + parseInt Math.random! * (len - it)] | |
@order[it] = @order[i] | |
@order[i] = t | |
return @order[@map[name] ?= @idx++ ] | |
_idx: 0 | |
_map: {} | |
seat-mapping-default: (name) -> | |
@_map[name] ?= @_idx++ | |
seat-mapping: (name) -> | |
if @config.seat-mapping then @config.seat-mapping.indexOf .call @config.seat-mapping,@,name | |
else @map.random.indexOf @,name | |
remap: (map-obj) -> | |
@config.seat-mapping = map-obj | |
_pt = ~> @seat-position @seat-mapping it.name | |
@seats.transition! .duration 750 .attr \transform ~> "translate(#{(_pt it)0},#{(_pt it)1})" | |
seat-position: (idx) -> | |
sc = @config.seat-count | |
sc = [sc[to i].reduce (+) for ,i in sc] | |
ret = (sc.map (-> it - idx) .filter (> 0)) | |
[row, len] = [@config.seat-count.length, ret.length] | |
[i,j,m] = [row - len, ret[0]-1, sc[row - len] - 1 - (len<row && sc[row - len-1]) || 0 ] | |
v = [ Math.cos(Math.PI*j/m), Math.sin Math.PI*j/m ] | |
[ @config.cx + v[0]*(160+ i*60) , @config.cy - v[1]*(160 + i*60) ] | |
seats: null | |
h-name: {} | |
h-party: {} | |
generate: (error, mlys) -> | |
[@h-name,@h-party] = [{} {0:0}] | |
if !@config.seat-count | |
_sc = [0 til 6].map -> parseInt 2*Math.PI*(it*60+160) | |
_sc_total = _sc.reduce (+) | |
@config.seat-count = _sc.map -> Math.round it*mlys.length/_sc_total | |
idx = 0 | |
for mly in mlys | |
@h-name[mly.name] = | |
name: mly.name | |
vote: 0 | |
party: mly.party | |
idx: idx++ | |
@h-party[mly.party] ?= @h-party[0]++ | |
for names,i in @config.vote | |
for name in names | |
@h-name[name].vote = i+1 | |
@svg = d3.select @config.node .append \svg | |
.attr \width \100% | |
.attr \height \100% | |
defs = @svg.selectAll \defs .data mlys .enter! .append \pattern | |
.attr \id ~> \defs_h + @h-name[it.name].idx | |
.attr \patternUnits \userSpaceOnUse | |
.attr \x 30 | |
.attr \y 30 | |
.attr \width 50 | |
.attr \height 50 | |
imgs = defs.append \image | |
.attr \xlink:href -> "http://avatars.io/50a65bb26e293122b0000073/#{CryptoJS.MD5('MLY/'+it.name).toString()}?size=small" | |
.attr \x 0 | |
.attr \y 0 | |
.attr \width 50 | |
.attr \height 50 | |
.attr \transform "scale(0.9)" | |
panel = @svg.append \g | |
.attr \transform ~> @config.transform | |
_pt = ~> @seat-position @seat-mapping it.name | |
@seats = panel.selectAll \g.seat | |
.data [@h-name[it] for it of @h-name].sort( (a,b) ~> | |
@h-party[a.party] - @h-party[b.party]) .enter! .append \g | |
.attr \transform ~> "translate(#{(_pt it)0},#{(_pt it)1})" | |
lockcell = null | |
@seats.append \circle | |
.attr \class \mly-seat | |
.attr \r 20 | |
.attr \fill ~> @colors[it.party] | |
.style \opacity ~> if it.vote == 0 then 0.3 else 1 | |
.on \click ~> | |
if lockcell | |
d3.select lockcell .attr \fill ~> @colors[it.party] | |
.transition! .duration 500 | |
.attr \transform "scale(1)" | |
.attr \stroke \none | |
.style \opacity ~> if it.vote == 0 then 0.3 else 1 | |
if lockcell == d3.event.target | |
return lockcell := null | |
lockcell := d3.event.target | |
d3.select d3.event.target .attr \fill -> "url(\#defs_h#{it.idx})" | |
.transition! .duration 500 | |
.attr \transform "scale(2)" | |
.attr \stroke ~> @colors[it.party] | |
.attr \stroke-width \3px | |
.style \opacity 1 | |
@seats.append \path | |
.attr \d ~> switch it.vote | |
|1 => "M-12 0 L0 10 L11 -11" | |
|2 => "M-10,-10 L10,10 L0 0 L-10 10 L10 -10" | |
|3 => "M-10 0 L10 00" | |
|9 => "M15 0 A15 15 0 1 1 -15 0 A15 15 0 1 1 15 0" | |
|otherwise => "M0 0" | |
.attr \stroke ~> switch it.vote | |
|1 => \#0b0 | |
|2 => \#b00 | |
|3 => \#999 | |
|otherwise => \#b00 | |
.attr \stroke-width \5px | |
.attr \fill \none | |
@seats.append \rect | |
.attr \class \mly-name-box | |
.attr \x -25 | |
.attr \y 9 | |
.attr \width 50 | |
.attr \height 17 | |
.attr \rx 10 | |
.attr \ry 10 | |
.attr \fill \#fff | |
.style \opacity 0.4 | |
@seats.append \text | |
.attr \class \mly-name | |
.attr \y 22 | |
.attr \text-anchor \middle | |
.text (.name) | |
render: (config) -> | |
unless config.vote | |
$ config.node | |
..find \span.approval .each -> config.[]vote[0] = $ @ .text! / ' ' | |
..find \span.veto .each -> config.[]vote[1] = $ @ .text! / ' ' | |
..find \span.abstention .each -> config.[]vote[2] = $ @ .text! / ' ' | |
..find \span .hide! | |
@config <<< config | |
d3.json config.namelist, (error, json) ~> | |
@generate.call @, error, json | |
all: | |
jade --pretty index.jade | |
livescript -cp index.ls > index.js | |
livescript -cp lyvote.ls > lyvote.js |
[ { "name": "丁守中", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 1 ] }, | |
{ "name": "孔文吉", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "aborigine", "highland" ] }, | |
{ "name": "尤美女", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "王廷升", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "HUA", 0 ] }, | |
{ "name": "王育敏", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "王金平", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "王進士", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "PIF", 2 ] }, | |
{ "name": "王惠美", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "CHA", 1 ] }, | |
{ "name": "田秋堇", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "江啟臣", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TXG", 8 ] }, | |
{ "name": "江惠貞", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 7 ] }, | |
{ "name": "何欣純", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TXG", 7 ] }, | |
{ "name": "吳宜臻", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "吳育仁", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "吳育昇", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 1 ] }, | |
{ "name": "吳秉叡", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "呂玉玲", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TAO", 5 ] }, | |
{ "name": "呂學樟", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "HSZ", 0 ] }, | |
{ "name": "李昆澤", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 6 ] }, | |
{ "name": "李俊俋", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "CYI", 0 ] }, | |
{ "name": "李桐豪", | |
"party": "PFP", | |
"caucus": "PFP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "李貴敏", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "李慶華", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 12 ] }, | |
{ "name": "李應元", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "李鴻鈞", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 4 ] }, | |
{ "name": "邱文彥", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "邱志偉", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 2 ] }, | |
{ "name": "邱議瑩", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 1 ] }, | |
{ "name": "林世嘉", | |
"party": "TSU", | |
"caucus": "TSU", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "林正二", | |
"party": "PFP", | |
"caucus": "PFP", | |
"constuiency": [ "aborigine", "lowland" ] }, | |
{ "name": "林佳龍", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TXG", 6 ] }, | |
{ "name": "林岱樺", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 4 ] }, | |
{ "name": "林明溱", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "NAN", 2 ] }, | |
{ "name": "林郁方", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 5 ] }, | |
{ "name": "林國正", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "KHH", 9 ] }, | |
{ "name": "林淑芬", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TPQ", 2 ] }, | |
{ "name": "林滄敏", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "CHA", 2 ] }, | |
{ "name": "林德福", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 9 ] }, | |
{ "name": "林鴻池", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 6 ] }, | |
{ "name": "姚文智", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TPE", 2 ] }, | |
{ "name": "柯建銘", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "段宜康", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "洪秀柱", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "紀國棟", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "孫大千", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TAO", 6 ] }, | |
{ "name": "徐少萍", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "徐欣瑩", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "HSQ", 0 ] }, | |
{ "name": "徐耀昌", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "MIA", 2 ] }, | |
{ "name": "翁重鈞", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "CYQ", 1 ] }, | |
{ "name": "陳其邁", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "陳明文", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "CYQ", 2 ] }, | |
{ "name": "陳亭妃", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TNN", 3 ] }, | |
{ "name": "陳唐山", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TNN", 5 ] }, | |
{ "name": "陳根德", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TAO", 1 ] }, | |
{ "name": "陳淑慧", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "陳雪生", | |
"party": null, | |
"caucus": null, | |
"constuiency": [ "LJF", 0 ] }, | |
{ "name": "陳超明", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "MIA", 1 ] }, | |
{ "name": "陳節如", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "陳碧涵", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "陳歐珀", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "ILA", 0 ] }, | |
{ "name": "陳學聖", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TAO", 3 ] }, | |
{ "name": "陳鎮湘", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "馬文君", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "NAN", 1 ] }, | |
{ "name": "高志鵬", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TPQ", 3 ] }, | |
{ "name": "高金素梅", | |
"party": "NSU", | |
"caucus": null, | |
"constuiency": [ "aborigine", "highland" ] }, | |
{ "name": "張嘉郡", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "YUN", 1 ] }, | |
{ "name": "張慶忠", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 8 ] }, | |
{ "name": "張曉風", | |
"party": "PFP", | |
"caucus": "PFP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "許忠信", | |
"party": "TSU", | |
"caucus": "TSU", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "許添財", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TNN", 4 ] }, | |
{ "name": "許智傑", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 8 ] }, | |
{ "name": "曾巨威", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "葉宜津", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TNN", 1 ] }, | |
{ "name": "費鴻泰", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 7 ] }, | |
{ "name": "黃文玲", | |
"party": "TSU", | |
"caucus": "TSU", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "黃志雄", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 5 ] }, | |
{ "name": "黃昭順", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "KHH", 3 ] }, | |
{ "name": "黃偉哲", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TNN", 2 ] }, | |
{ "name": "楊玉欣", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "楊應雄", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "JME", 0 ] }, | |
{ "name": "楊曜", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "PEN", 0 ] }, | |
{ "name": "楊瓊瓔", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TXG", 3 ] }, | |
{ "name": "楊麗環", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TAO", 4 ] }, | |
{ "name": "詹凱臣", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "foreign" ] }, | |
{ "name": "廖正井", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TAO", 2 ] }, | |
{ "name": "廖國棟", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "aborigine", "lowland" ] }, | |
{ "name": "管碧玲", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 5 ] }, | |
{ "name": "蔡正元", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 4 ] }, | |
{ "name": "蔡其昌", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TXG", 1 ] }, | |
{ "name": "蔡煌瑯", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "蔡錦隆", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TXG", 4 ] }, | |
{ "name": "蔣乃辛", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 6 ] }, | |
{ "name": "趙天麟", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "KHH", 7 ] }, | |
{ "name": "鄭天財", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "aborigine", "lowland" ] }, | |
{ "name": "鄭汝芬", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "CHA", 3 ] }, | |
{ "name": "鄭麗君", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "劉建國", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "YUN", 2 ] }, | |
{ "name": "劉櫂豪", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "TTT", 0 ] }, | |
{ "name": "潘孟安", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "PIF", 3 ] }, | |
{ "name": "潘維剛", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "盧秀燕", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TXG", 5 ] }, | |
{ "name": "盧嘉辰", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 10 ] }, | |
{ "name": "蕭美琴", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "薛凌", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "賴士葆", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 8 ] }, | |
{ "name": "謝國樑", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "KEE", 0 ] }, | |
{ "name": "魏明谷", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "CHA", 4 ] }, | |
{ "name": "簡東明", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "aborigine", "highland" ] }, | |
{ "name": "顏清標", | |
"party": "NSU", | |
"caucus": null, | |
"constuiency": [ "TXG", 2 ] }, | |
{ "name": "羅明才", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPQ", 11 ] }, | |
{ "name": "羅淑蕾", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "TPE", 3 ] }, | |
{ "name": "蘇清泉", | |
"party": "KMT", | |
"caucus": "KMT", | |
"constuiency": [ "proportional" ] }, | |
{ "name": "蘇震清", | |
"party": "DPP", | |
"caucus": "DPP", | |
"constuiency": [ "PIF", 1 ] } ] |