Voxelize imageecharts sameColor').onChange(updateDataWhenChange); gui.addColor(config, 'color').onChange(updateDataWhenChange); ["roughness", "metalness"].forEach(function(propName) { gui.add(config, propName, 0, 1).step(0.01).onFinishChange(function() { myChart.setOption({ series: [{ realisticMaterial: { roughness: config.roughness, metalness: config.metalness } }] }); }); }); function updateControlAndLight() { myChart.setOption({ grid3D: { environment: config.showEnvironment ? 'auto' : '#000配置项内容和展示

配置项如下
      var canvas = document.createElement("canvas");
var ctx = canvas.getContext("2d");

var imgData;
var currentImg;

// Configurations
var config = {
    scale: 0.3,
    roughness: 0,
    metalness: 1,
    projection: "orthographic",
    depthOfField: 4,
    lockY: false,
    move: true,
    sameColor: false,
    color: '#777',
    colorContrast: 1.2,
    lightIntensity: 1,
    lightColor: '#fff',
    lightRotate: 30,
    lightPitch: 40,
    AO: 1.5,
    showEnvironment: false,
    
    barNumber: 80,
    barBevel: 0.18,
    barSize: 1.2
};

option = {
    tooltip: {},
    backgroundColor: "#000",
    xAxis3D: {
        type: "value"
    },
    yAxis3D: {
        type: "value"
    },
    zAxis3D: {
        type: "value",
        min: 0,
        max: 100
    },
    grid3D: {
        show: false,
        viewControl: {
            projection: "perspective",
            alpha: 45,
            beta: -45,
            panSensitivity: config.move ? 1 : 0,
            rotateSensitivity: config.lockY ? [1, 0] : 1,
            damping: 0.9,
            distance: 60
        },
        postEffect: {
            enable: true,
            bloom: {
                intensity: 0.2
            },
            screenSpaceAmbientOcclusion: {
                enable: true,
                intensity: 1.5,
                radius: 5,
                quality: "high"
            },
            screenSpaceReflection: {
                enable: true
            },
            depthOfField: {
                enable: true,
                blurRadius: config.depthOfField,
                fstop: 10,
                focalDistance: 55
            }
        },
        boxDepth: 100,
        boxHeight: 20,
        environment: "none",
        light: {
            main: {
                shadow: true,
                intensity: 2
            },
            ambientCubemap: {
                texture: '/asset/get/s/data-1491838644249-ry33I7YTe.hdr',
                exposure: 2,
                diffuseIntensity: 0.2,
                specularIntensity: 1.5
            }
        }
    }
};

function updateData(data, width, height) {
    console.time("update");
    var dataItem = [];
    var dataProvider = {
        getItem: function(i) {
            var r = data[i * 4];
            var g = data[i * 4 + 1];
            var b = data[i * 4 + 2];

            var lum = 0.2125 * r + 0.7154 * g + 0.0721 * b;
            lum = (lum - 125) * config.scale + 50;
            dataItem[0] = i % width;
            dataItem[1] = height - Math.floor(i / width);
            dataItem[2] = lum;
            return dataItem;
        },
        count: function() {
            return data.length / 4;
        }
    };

    myChart.setOption({
        grid3D: {
            boxWidth: 100 / height * width
        },
        series: [{
            animation: false,
            type: "bar3D",
            shading: "realistic",
            realisticMaterial: {
                roughness: config.roughness,
                metalness: config.metalness
            },
            barSize: config.barSize,
            bevelSize: config.barBevel,
            silent: true,
            itemStyle: {
                color: config.sameColor ? config.color : function(params) {
                    var i = params.dataIndex;
                    var r = data[i * 4] / 255;
                    var g = data[i * 4 + 1] / 255;
                    var b = data[i * 4 + 2] / 255;
                    var lum = 0.2125 * r + 0.7154 * g + 0.0721 * b;
                    r *= lum * config.colorContrast;
                    g *= lum * config.colorContrast;
                    b *= lum * config.colorContrast;
                    return [r, g, b, 1];
                }
            },
            data: dataProvider
        }]
    });

    console.timeEnd("update");

    setTimeout(function() {
        myChart.getZr().refresh()
    }, 100);
}

function loadImage(img) {
    var height = (canvas.height = Math.min(config.barNumber, img.height));
    var aspect = img.width / img.height;
    var width = (canvas.width = Math.round(height * aspect));

    ctx.drawImage(img, 0, 0, width, height);

    imgData = ctx.getImageData(0, 0, width, height);

    updateData(imgData.data, width, height);
}

var gui = new dat.GUI();

function updateDataWhenChange() {
    if (imgData) {
        updateData(imgData.data, imgData.width, imgData.height);
    }
}
gui.add(config, "scale", -1, 1).onFinishChange(updateDataWhenChange);
gui.add(config, "colorContrast", 0, 2).onFinishChange(updateDataWhenChange);
gui.add(config, 'sameColor').onChange(updateDataWhenChange);
gui.addColor(config, 'color').onChange(updateDataWhenChange);

["roughness", "metalness"].forEach(function(propName) {
    gui.add(config, propName, 0, 1).step(0.01).onFinishChange(function() {
        myChart.setOption({
            series: [{
                realisticMaterial: {
                    roughness: config.roughness,
                    metalness: config.metalness
                }
            }]
        });
    });
});

function updateControlAndLight() {
    myChart.setOption({
        grid3D: {
            environment: config.showEnvironment ? 'auto' : '#000',
            viewControl: {
                panSensitivity: config.move ? 1 : 0,
                rotateSensitivity: config.lockY ? [1, 0] : 1
            },
            light: {
                main: {
                    intensity: config.lightIntensity,
                    color: config.lightColor,
                    alpha: config.lightPitch,
                    beta: config.lightRotate
                },
                ambientCubemap: {
                    texture: '/asset/get/s/data-1491838644249-ry33I7YTe.hdr'
                }
            },
            postEffect: {
                screenSpaceAmbientOcclusion: {
                    intensity: config.AO
                }
            }
        }
    });
}

gui.add(config, 'lightIntensity', 0, 10).onChange(updateControlAndLight);
gui.add(config, 'lightRotate', -180, 180).onChange(updateControlAndLight);
gui.add(config, 'lightPitch', 10, 90).onChange(updateControlAndLight);
// gui.add(config, 'AO', 0, 2).onChange(updateControlAndLight);
// gui.addColor(config, 'lightColor').onChange(updateControlAndLight);

// FIXME Not work
// gui.add(config, 'showEnvironment').onChange(updateControlAndLight);
// gui.add(config, 'environment', ['canyon', 'pisa']).onChange(updateControlAndLight);

// gui.add(config, 'move').onChange(updateControlAndLight);
// gui.add(config, 'lockY').onChange(updateControlAndLight);

gui.add(config, 'barNumber', 0, 256).onFinishChange(function () {
    loadImage(currentImg);
});
gui.add(config, 'barSize', 0, 2).onFinishChange(function () {
    myChart.setOption({
        series: [{
            barSize: config.barSize
        }]
    })
});
gui.add(config, 'barBevel', 0, 1).onFinishChange(function () {
    myChart.setOption({
        series: [{
            bevelSize: config.barBevel
        }]
    })
});
gui.add(config, 'depthOfField', 0., 10).onFinishChange(function () {
    myChart.setOption({
        grid3D: {
            postEffect: {
                depthOfField: {
                    blurRadius: config.depthOfField
                }
            },
        }
    }) 
});


// Handle file uploads.
function readFile(file) {
    if (!file || !file.type.match(/image/)) {
        return;
    }

    var fileReader = new FileReader();
    fileReader.onload = function(e) {
        img = new Image();
        img.onload = function() {
            loadImage(img);
            currentImg = img;
        };
        img.src = e.target.result;
    };
    fileReader.readAsDataURL(file);
}

$('<div id="image-upload">Drop files here or click to upload</div>').appendTo(
    $('#chart-panel')
).css({
  width: '300px',
  height: '100px',
  'line-height': '100px',
  'text-align': 'center',
  cursor: 'pointer',
  background: 'rgba(255, 255, 255, 0.2)',
  'border-radius': '4px',
  border: '2px dashed #999',
  position: 'absolute',
  right: '10px',
  bottom: '10px',
  'z-index': '10',
  color: '#fff'
})

$("#image-upload").on("dragover", function(e) {
    e.stopPropagation();
    e.preventDefault();
});
$("#image-upload")[0].addEventListener("drop", function(e) {
    e.stopPropagation();
    e.preventDefault();

    var files = e.dataTransfer.files;
    return readFile(files[0]);
});
$("#image-upload").on("click", function() {
    var $file = $('<input type="file" />');
    $file.on("change", function(e) {
        readFile(e.target.files[0]);
    });
    $file.click();
});

// Default
var img = new Image();
img.onload = function() {
    loadImage(img);
    currentImg = img;
};
img.src = "/asset/get/s/data-1502210091353-S1mNuDPDW.png";
    
截图如下