<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Canvas - Histogram</title>
<style type="text/css">
* {
box-sizing: border-box;
}
canvas {
}
.histogram {
}
input, label {
cursor: pointer;
user-select: none;
}
</style>
</head>
<body>
<canvas id="canvas"></canvas>
<canvas id="histogram" class="histogram"></canvas>
<div>
<input type="radio" id="original" name="color" checked />
<label for="original">Original</label>
<br />
<input type="radio" id="red-weight-method" name="color" />
<label for="red-weight-method">Red Weight Method</label>
<input type="radio" id="green-weight-method" name="color" />
<label for="green-weight-method">Green Weight Method</label>
<input type="radio" id="blue-weight-method" name="color" />
<label for="blue-weight-method">Blue Weight Method</label>
<br />
<input type="radio" id="mean-value-method" name="color" />
<label for="mean-value-method">Mean Value Method</label>
<input type="radio" id="max-value-method" name="color" />
<label for="max-value-method">Max Value Method</label>
<input type="radio" id="weighted-average-method" name="color" />
<label for="weighted-average-method">Weighted Average Method</label>
<br />
</div>
<script type="text/javascript">
window.onload = (event) => {
console.log(event)
main()
}
function main() {
const canvas = document.getElementById("canvas")
const ctx = canvas.getContext("2d")
const histogram = document.getElementById("histogram")
const histogramContext = histogram.getContext("2d")
const image = new Image()
image.onload = (event) => {
canvas.width = image.width
canvas.height = image.height
ctx.drawImage(image, 0, 0)
const originalImageData = ctx.getImageData(0, 0, image.width, image.height)
let grayImageData = null
const grayList = new Array(256)
document.getElementById("original").onchange = (event) => {
ctx.putImageData(originalImageData, 0, 0)
}
document.getElementById("red-weight-method").onchange = (event) => {
const imageData = ctx.createImageData(originalImageData)
for (let i = 0; i < grayList.length; i++) {
grayList[i] = 0
}
let gray = 0;
for (let i = 0; i < originalImageData.data.length; i += 4) {
gray = originalImageData.data[i + 0]
imageData.data[i + 0] = gray
imageData.data[i + 1] = gray
imageData.data[i + 2] = gray
imageData.data[i + 3] = originalImageData.data[i + 3]
grayList[gray] += 1
}
ctx.putImageData(imageData, 0, 0)
grayImageData = ctx.getImageData(0, 0, image.width, image.height)
const sum = grayList.reduce((accumulator, currentValue, index, array) => {
return accumulator + currentValue
})
console.log(grayList)
console.log("sum = " + sum, "max = " + Math.max(...grayList), "remainder = " + Math.max(...grayList) % 100)
histogram.width = 256 * 2
histogram.height = (Math.max(...grayList) + 100 - Math.max(...grayList) % 100) / 20
histogramContext.strokeStyle = '#000000'
histogramContext.lineWidth = 1
for (let i = 0; i < grayList.length; i++) {
histogramContext.beginPath()
histogramContext.moveTo(i * 2, histogram.height)
histogramContext.lineTo(i * 2, grayList[i] / 20)
histogramContext.stroke()
}
}
document.getElementById("green-weight-method").onchange = (event) => {
const imageData = ctx.createImageData(originalImageData)
for (let i = 0; i < grayList.length; i++) {
grayList[i] = 0
}
let gray = 0;
for (let i = 0; i < originalImageData.data.length; i += 4) {
gray = originalImageData.data[i + 1]
imageData.data[i + 0] = gray
imageData.data[i + 1] = gray
imageData.data[i + 2] = gray
imageData.data[i + 3] = originalImageData.data[i + 3]
grayList[gray] += 1
}
ctx.putImageData(imageData, 0, 0)
grayImageData = ctx.getImageData(0, 0, image.width, image.height)
const sum = grayList.reduce((accumulator, currentValue, index, array) => {
return accumulator + currentValue
})
console.log(grayList)
console.log("sum = " + sum, "max = " + Math.max(...grayList), "remainder = " + Math.max(...grayList) % 100)
histogram.width = 256 * 2
histogram.height = (Math.max(...grayList) + 100 - Math.max(...grayList) % 100) / 20
histogramContext.strokeStyle = '#000000'
histogramContext.lineWidth = 1
for (let i = 0; i < grayList.length; i++) {
histogramContext.beginPath()
histogramContext.moveTo(i * 2, histogram.height)
histogramContext.lineTo(i * 2, grayList[i] / 20)
histogramContext.stroke()
}
}
document.getElementById("blue-weight-method").onchange = (event) => {
const imageData = ctx.createImageData(originalImageData)
for (let i = 0; i < grayList.length; i++) {
grayList[i] = 0
}
let gray = 0;
for (let i = 0; i < originalImageData.data.length; i += 4) {
gray = originalImageData.data[i + 2]
imageData.data[i + 0] = gray
imageData.data[i + 1] = gray
imageData.data[i + 2] = gray
imageData.data[i + 3] = originalImageData.data[i + 3]
grayList[gray] += 1
}
ctx.putImageData(imageData, 0, 0)
grayImageData = ctx.getImageData(0, 0, image.width, image.height)
const sum = grayList.reduce((accumulator, currentValue, index, array) => {
return accumulator + currentValue
})
console.log(grayList)
console.log("sum = " + sum, "max = " + Math.max(...grayList), "remainder = " + Math.max(...grayList) % 100)
histogram.width = 256 * 2
histogram.height = (Math.max(...grayList) + 100 - Math.max(...grayList) % 100) / 20
histogramContext.strokeStyle = '#000000'
histogramContext.lineWidth = 1
for (let i = 0; i < grayList.length; i++) {
histogramContext.beginPath()
histogramContext.moveTo(i * 2, histogram.height)
histogramContext.lineTo(i * 2, grayList[i] / 20)
histogramContext.stroke()
}
}
document.getElementById("mean-value-method").onchange = (event) => {
const imageData = ctx.createImageData(originalImageData)
for (let i = 0; i < grayList.length; i++) {
grayList[i] = 0
}
let gray = 0;
for (let i = 0; i < originalImageData.data.length; i += 4) {
gray = Math.round((originalImageData.data[i + 0] + originalImageData.data[i + 1] + originalImageData.data[i + 2]) / 3)
imageData.data[i + 0] = gray
imageData.data[i + 1] = gray
imageData.data[i + 2] = gray
imageData.data[i + 3] = originalImageData.data[i + 3]
grayList[gray] += 1
}
ctx.putImageData(imageData, 0, 0)
grayImageData = ctx.getImageData(0, 0, image.width, image.height)
const sum = grayList.reduce((accumulator, currentValue, index, array) => {
return accumulator + currentValue
})
console.log(grayList)
console.log("sum = " + sum, "max = " + Math.max(...grayList), "remainder = " + Math.max(...grayList) % 100)
histogram.width = 256 * 2
histogram.height = (Math.max(...grayList) + 100 - Math.max(...grayList) % 100) / 20
histogramContext.strokeStyle = '#000000'
histogramContext.lineWidth = 1
for (let i = 0; i < grayList.length; i++) {
histogramContext.beginPath()
histogramContext.moveTo(i * 2, histogram.height)
histogramContext.lineTo(i * 2, grayList[i] / 20)
histogramContext.stroke()
}
}
document.getElementById("max-value-method").onchange = (event) => {
const imageData = ctx.createImageData(originalImageData)
for (let i = 0; i < grayList.length; i++) {
grayList[i] = 0
}
let gray = 0;
for (let i = 0; i < originalImageData.data.length; i += 4) {
gray = Math.max(originalImageData.data[i + 0], originalImageData.data[i + 1], originalImageData.data[i + 2])
imageData.data[i + 0] = gray
imageData.data[i + 1] = gray
imageData.data[i + 2] = gray
imageData.data[i + 3] = originalImageData.data[i + 3]
grayList[gray] += 1
}
ctx.putImageData(imageData, 0, 0)
grayImageData = ctx.getImageData(0, 0, image.width, image.height)
const sum = grayList.reduce((accumulator, currentValue, index, array) => {
return accumulator + currentValue
})
console.log(grayList)
console.log("sum = " + sum, "max = " + Math.max(...grayList), "remainder = " + Math.max(...grayList) % 100)
histogram.width = 256 * 2
histogram.height = (Math.max(...grayList) + 100 - Math.max(...grayList) % 100) / 20
histogramContext.strokeStyle = '#000000'
histogramContext.lineWidth = 1
for (let i = 0; i < grayList.length; i++) {
histogramContext.beginPath()
histogramContext.moveTo(i * 2, histogram.height)
histogramContext.lineTo(i * 2, grayList[i] / 20)
histogramContext.stroke()
}
}
document.getElementById("weighted-average-method").onchange = (event) => {
const imageData = ctx.createImageData(originalImageData)
for (let i = 0; i < grayList.length; i++) {
grayList[i] = 0
}
let gray = 0;
for (let i = 0; i < originalImageData.data.length; i += 4) {
gray = Math.round(0.299 * originalImageData.data[i + 0] + 0.587 * originalImageData.data[i + 1] + 0.114 * originalImageData.data[i + 2])
imageData.data[i + 0] = gray
imageData.data[i + 1] = gray
imageData.data[i + 2] = gray
imageData.data[i + 3] = originalImageData.data[i + 3]
grayList[gray] += 1
}
ctx.putImageData(imageData, 0, 0)
grayImageData = ctx.getImageData(0, 0, image.width, image.height)
const sum = grayList.reduce((accumulator, currentValue, index, array) => {
return accumulator + currentValue
})
console.log(grayList)
console.log("sum = " + sum, "max = " + Math.max(...grayList), "remainder = " + Math.max(...grayList) % 100)
histogram.width = 256 * 2
histogram.height = (Math.max(...grayList) + 100 - Math.max(...grayList) % 100) / 20
histogramContext.strokeStyle = '#000000'
histogramContext.lineWidth = 1
for (let i = 0; i < grayList.length; i++) {
histogramContext.beginPath()
histogramContext.moveTo(i * 2, histogram.height)
histogramContext.lineTo(i * 2, grayList[i] / 20)
histogramContext.stroke()
}
}
}
image.src = "img/transformers.jpg"
}
</script>
</body>
</html>
参考
直方图,看这一篇就够了!
百度百科 - 质量分布图
百度百科 - 直方图(统计报告图)