首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >从零开始生成图像?

从零开始生成图像?
EN

Stack Overflow用户
提问于 2022-06-28 07:35:12
回答 2查看 142关注 0票数 1

我将如何从头开始创建像素图像?我正在使用web技术(html/css/javascript/react),如何获取一些信息(例如像素1为#ff5733颜色,像素2为#ff3829颜色)并为此生成相应的像素图像?如果有人能指出我在生成图像方面的正确方向,那就太棒了。

我只能在网上找到关于如何像素化现有图像的信息。任何帮助都是非常感谢的。谢谢。

编辑:下面的两个答案真的很好!谢谢大家的大力帮助!

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2022-06-28 08:21:27

假设您有一个二维的颜色值数组--由变量mypixels表示--您可以使用一组for循环来绘制画布上的每个像素,然后将其转换为图像:

代码语言:javascript
运行
复制
document.addEventListener('DOMContentLoaded', () => {

 var mypixels = [
  ['#FFF', '#FFF', '#FFF', '#FFF', '#FFF', '#FFF', '#FFF'],
  ['#FFF', '#FFF', '#F00', '#FFF', '#F70', '#FFF', '#FFF'],
  ['#FFF', '#FFF', '#F70', '#FFF', '#FF0', '#FFF', '#FFF'],
  ['#FFF', '#FFF', '#FF0', '#FFF', '#0F0', '#FFF', '#FFF'],
  ['#FFF', '#FFF', '#FFF', '#FFF', '#FFF', '#FFF', '#FFF'],
  ['#FFF', '#FF0', '#FFF', '#FFF', '#FFF', '#F0F', '#FFF'],
  ['#FFF', '#FFF', '#0F0', '#0FF', '#00F', '#FFF', '#FFF'],
  ['#FFF', '#FFF', '#FFF', '#FFF', '#FFF', '#FFF', '#FFF']
 ];

 function createImage(pixels) {
  var canvas = document.createElement('canvas');
  canvas.width = pixels[0].length;
  canvas.height = pixels.length;
  var context = canvas.getContext('2d');
  for(var r = 0; r < canvas.height; r++) {
   for(var c = 0; c < canvas.width; c++) {
    context.fillStyle = pixels[r][c];
    context.fillRect(c, r, 1, 1);
   }
  }
  return canvas.toDataURL('image/png');
 }

 document.querySelector('img').src = createImage(mypixels);

});
代码语言:javascript
运行
复制
img {
 width: 200px;
 height: 100px;
 border: 1px dashed black;
 background-color: lightgray;
 image-rendering: pixelated;
 object-fit: contain;
}
代码语言:javascript
运行
复制
<!DOCTYPE html>
<html>
 <head>
 </head>
 <body>
  <img/>
 </body>
</html>

有关Javascript的更多信息,MDN Web文档有一个很好的参考,W3Schools有一个很好的初学者友好演练。希望这对你有用!

票数 4
EN

Stack Overflow用户

发布于 2022-06-28 08:23:36

更新

SVG解决方案与下载图像。

概述

在html/css/js上下文中动态创建位图图像的方法有多种。它们中没有一个是有效的,它们似乎也没有特别的用处--尽管有一个网站为慈善目的出售个人像素的先例.

展示了下列备选方案:

  1. 表示像素的div网格。
  2. 表示一行像素的线性梯度。
  3. 一个嵌入的svg,带有代表像素的rect元素(更新:带有下载链接)

1.表示像素的div网格

Idea

动态创建在表格网格中组织的1x1div,以表示图像的像素,并根据相应像素的值设置它们的背景色。

图像数据是以行为主方式组织成数组的像素的html颜色代码。为了演示目的,呈现的“像素”被设置为16x16大小。

代码语言:javascript
运行
复制
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta http-equiv="Content-Type"   content="text/html;charset=utf-8">
        <meta http-equiv="expires"        content="0">
        <meta http-equiv="cache-control"  content="private">
        <meta http-equiv="pragma"         content="no-cache">
        <title>SO - Bitmap divs</title>
        <!--
        -->
        <style type="text/css">
            body {
                background-color:   #eee;
            }
            .bitmap {
                display:    table;
            }
            .bitmap > div {
                display:    table-row;
            }
            .pixel {
                width:              16px;
                height:             16px;
                display:            table-cell;
            }
        </style>
        <script type=text/javascript>
            document.addEventListener ( 'DOMContentLoaded', () => {
                // Image definition as pixel bitmap
                let aas_smiley = [
                    [ ['#aaaaaa'], ['#aaaaaa'], ['#000000'], ['#000000'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#aaaaaa'], ['#000000'], ['#000000'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                ];
                
                let e_table = document.querySelector('.bitmap')
                  ;
                  
                aas_smiley.forEach ( pa_line => { 
                    let e_row = document.createElement('div')
                      ;
                    
                    pa_line.forEach ( (pa_pixel, pn_idx) => {
                        let e_d = document.createElement('div')
                          ;
                          
                        e_d.classList.add('pixel');
                        e_d.setAttribute('style', `background-color: ${pa_pixel[0]};`);
                        e_row.append(e_d);
                    });
                    e_table.append(e_row);  
                });
            });
        </script>
    </head>
    <body>
        <div class="bitmap"></div>
    </body>
</html>

2.表示一行像素的线性梯度

Idea

一个类似的效果可以通过创建一个在相同颜色值之间进行插值的像素宽子梯度的退化线性梯度来实现。

这里的一个小的技术差别是携带梯度数据的div覆盖整个表行,因此表布局是nx1。

代码语言:javascript
运行
复制
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta http-equiv="Content-Type"   content="text/html;charset=utf-8">
        <meta http-equiv="expires"        content="0">
        <meta http-equiv="cache-control"  content="private">
        <meta http-equiv="pragma"         content="no-cache">
        <title>SO - Bitmap divs</title>
        <!--
        -->
        <style type="text/css">
            body {
                background-color:   #eee;
            }
            .bitmap {
                display:    table;
            }
            .bitmap > div {
                display:            table-row;
                width:              128px;
                height:             16px;
            }
            .bitmap > div > div {
                width:              128px;
                height:             16px;
                display:            table-cell;
            }
        </style>
        <script type=text/javascript>
            document.addEventListener ( 'DOMContentLoaded', () => {
                // Image definition as pixel bitmap
                let aas_smiley = [
                    [ ['#aaaaaa'], ['#aaaaaa'], ['#000000'], ['#000000'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#aaaaaa'], ['#000000'], ['#000000'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                ];
                
                const n_factor = 16;
                let e_table = document.querySelector('.bitmap')
                  ;
                  
                aas_smiley.forEach ( pa_line => { 
                    let e_row  = document.createElement('div')
                      , e_cell = document.createElement('div')
                      , as_gradient = []
                      , s_gradientStyle
                      , s_lastPixel
                      ;
                    
                    pa_line.forEach ( (pa_pixel, pn_idx) => {
                        if (pn_idx === 0) {
                            as_gradient.push ( `to right` );
                        } else {
                            as_gradient.push ( `${s_lastPixel} ${pn_idx * n_factor}px, ${pa_pixel[0]} ${pn_idx * n_factor}px` );
                        }
                        s_lastPixel = pa_pixel[0];
                    });
                    
                    s_gradientStyle = `background: linear-gradient(${as_gradient.join(', ')});`;
                    e_cell.setAttribute('style', s_gradientStyle);
                    e_row.append(e_cell);
                    e_table.append(e_row);
                });
            });
        </script>
        
    </head>
    <body>
        <div class="bitmap"></div>
    </body>
</html>

3.一个嵌入的svg,它的rect元素表示像素

Idea

创建表示像素的rect元素。

注意,需要在svg命名空间中创建元素。

更新下面的代码是通过数据url生成额外下载链接的。原则上,这种技术可以用于生成可下载的数据,其格式有MIME类型,特别是传统的图像格式,如gif、jpeg、png、tiff。当然,你得先得到结构良好的八重奏序列.

数据urls也可以内联显示。为此,创建一个img元素并将其src属性设置为数据url字符串。(请参阅注释掉的代码部分)。

代码语言:javascript
运行
复制
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta http-equiv="Content-Type"   content="text/html;charset=utf-8">
        <meta http-equiv="expires"        content="0">
        <meta http-equiv="cache-control"  content="private">
        <meta http-equiv="pragma"         content="no-cache">
        <title>SO - Bitmap (svg)</title>
        <!--
        -->
        <style type="text/css">
            body {
                background-color:   #eee;
            }
        </style>
        <script type=text/javascript>
            document.addEventListener ( 'DOMContentLoaded', () => {
                // Image definition as pixel bitmap
                let aas_smiley = [
                    [ ['#aaaaaa'], ['#aaaaaa'], ['#000000'], ['#000000'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#000000'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#000000'], ['#cccc00'], ['#cccc00'], ['#cccc00'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#aaaaaa'], ['#000000'], ['#000000'], ['#000000'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                  , [ ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'], ['#aaaaaa'] ]
                ];
                
                const n_factor = 16;
                let e_svg = document.querySelector('svg')
                  ;
                  
                aas_smiley.forEach ( (pa_line, pn_row) => { 
                    pa_line.forEach ( (pa_pixel, pn_col) => {
                        let e_rect = document.createElementNS("http://www.w3.org/2000/svg", 'rect')
                          ;
                          
                        e_rect.setAttribute('x', `${pn_col}`);
                        e_rect.setAttribute('y', `${pn_row}`);
                        e_rect.setAttribute('width' , '1');
                        e_rect.setAttribute('height', '1');
                        e_rect.setAttribute('fill'  , pa_pixel[0]);

                        e_svg.append(e_rect);
                    });
                });

                // Goodie: Downloadable Image
                let s_svg       = e_svg.outerHTML
                  , s_datauri   = `data:image/svg+xml;utf8;base64,${btoa(s_svg)}`
                  , e_a         = document.createElement('a')
                  , e_body      = document.querySelector('body')
                  ;
                  
                e_a.setAttribute('href'     , s_datauri);
                e_a.setAttribute('download' , 'smiley.svg');
                e_a.innerText = 'Download as "smiley.svg"';
                e_body.append(e_a);

                // Optional: Render as inline image with data url
                // let e_img = document.createElement('img')
                //   ;
                // e_img.setAttribute('src'     , s_datauri);
                // e_body.append(e_img);
            });
        </script>
        
    </head>
    <body>
        <svg
            width="128"
            height="128"
            viewBox="0 0 16 16"
            xmlns="http://www.w3.org/2000/svg"
        >
        </svg>
    </body>
</html>

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72782407

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档