Dart + WebGL рдбрд╛рд░реНрдХ рд╕рд╛рдЗрдб рдкрд░ рдХреБрдХреАрдЬрд╝ рд╕реНрд╡рд╛рджрд┐рд╖реНрдЯ рд╣реИрдВ


рд╡реЗрдм рдЕрдиреБрдкреНрд░рдпреЛрдЧреЛрдВ рдХреЗ рд╡рд┐рдХрд╛рд╕ рдХрд╛ рдЗрддрд┐рд╣рд╛рд╕, рдПрдХреНрдХреЗрди рд╕реНрдХрд╛рдИрд╡реЙрдХрд░ рдХреЗ рдЬреАрд╡рди рд╕реЗ рдорд┐рд▓рддрд╛ рдЬреБрд▓рддрд╛ рд╣реИред рд▓рдЧрднрдЧ 15 рд╕рд╛рд▓ рдкрд╣рд▓реЗ рд╡реЗ рдХрдордЬреЛрд░ рдФрд░ рдЕрдирд╛рдбрд╝реА рдереЗред рд▓реЗрдХрд┐рди рдЕрдм рд╕рдордп рдмреАрдд рдЪреБрдХрд╛ рд╣реИ, рд╕рд┐рд░ рдореЗрдВ рдЯреЗрд╕реНрдЯреЛрд╕реНрдЯреЗрд░реЛрди рд╣рд┐рдЯ рд╣реЛ рдЬрд╛рддрд╛ рд╣реИ рдФрд░ рд╣рдорд╛рд░рд╛ "рдЕрдирдХреЗрдб" рдмреНрд░рд╛рдЙрдЬрд╝рд░ рдХрд╛рд░реНрдпрдХреНрд░рдореЛрдВ рдХреА рдЧреБрдгрд╡рддреНрддрд╛ рдФрд░ рдХрд╛рд░реНрдпрдХреНрд╖рдорддрд╛ рдХреЗ рд▓рд┐рдП рдЖрд╡рд╢реНрдпрдХрддрд╛рдУрдВ рдХреЗ рд▓рд╛рд▓-рдЧрд░реНрдо рд▓рд╛рд╡рд╛ рдореЗрдВ рдЧрд┐рд░ рдЬрд╛рддрд╛ рд╣реИред рдЕрдкрдиреА рдПрдХрдорд╛рддреНрд░ рдЬреАрд╡рд┐рдд рдЬрд╛рд╡рд╛рд╕реНрдХреНрд░рд┐рдкреНрдЯ рдХреЗ рд╕рд╛рде, рд╡рд╣ рдкреГрдереНрд╡реА рдХреЛ рдЕрдкрдиреЗ рдЕрдзреАрди рдХрд░ рд▓реЗрддрд╛ рд╣реИред рдпрд╣рд╛рдВ рдПрдХ рдЪреМрдХрд╕ рдкрд╛рдардХ рдзреНрдпрд╛рди рджреЗрдЧрд╛ рдХрд┐ рдЗрд╕ рддрд░рд╣ рд╣рдо рджреВрд░ рдирд╣реАрдВ рдЬрд╛рдПрдВрдЧреЗред рдПрдХ рдЕрдкреНрд░рддреНрдпрд╛рд╢рд┐рдд, рд▓реЗрдХрд┐рди рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ рдХрд╛рдлреА рдкреНрд░рд╛рдХреГрддрд┐рдХ рд╕рд╛рдЬрд┐рд╢ рдореЛрдбрд╝, рдФрд░ рдЙрджреНрдзрд╛рд░рдХрд░реНрддрд╛ рдбрд╛рд░реНрдЯ рджреГрд╢реНрдп рдкрд░ рджрд┐рдЦрд╛рдИ рджреЗрддрд╛ рд╣реИред рдЪрд▓реЛ рдЙрд╕рдХреЗ рд╕рд╛рде рдкрдХреНрд╖ рдХрд░рдиреЗ рдХреА рдХреЛрд╢рд┐рд╢ рдХрд░рддреЗ рд╣реИрдВред

рдбрд╛рд░реНрдЯ рдХреНрдпреЛрдВ, рдХреЗрд╡рд▓ рдЗрд╕рд▓рд┐рдП рдХрд┐ рдпрд╣ рдЯрд╛рдЗрдк рдХрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ рдФрд░ рдЗрд╕рдореЗрдВ рд╕реА-рд▓рд╛рдЗрдХ рд╕рд┐рдВрдЯреИрдХреНрд╕ рд╣реИред рдЗрд╕рдХреЗ рдЕрд▓рд╛рд╡рд╛, Google рдбрд╛рд░реНрдЯ рдХреЗ рд▓рд┐рдП VirtualMachine рд╡рд┐рдХрд╕рд┐рдд рдХрд░ рд░рд╣рд╛ рд╣реИ, рдЬреЛ рд▓рдВрдмреА рдЕрд╡рдзрд┐ рдореЗрдВ рдЗрд╕ рднрд╛рд╖рд╛ рдХреЗ рдкреНрд░рджрд░реНрд╢рди рдореЗрдВ рдПрдХ рдорд╣рддреНрд╡рдкреВрд░реНрдг рд▓рд╛рдн рджреЗ рд╕рдХрддрд╛ рд╣реИред

рдХреНрдпреЛрдВ WebGL, рдХреНрдпреЛрдВрдХрд┐ рдбрд╛рд░реНрдЯ рдЬреИрд╕реА рдпрд╣ рддрдХрдиреАрдХ рд╕рдмрд╕реЗ рдЖрдЧреЗ рд╣реИ, рдФрд░ рдмреНрд░рд╛рдЙрдЬрд╝рд░ рдореЗрдВ 3D, рдореЗрд░реА рд░рд╛рдп рдореЗрдВ, рдПрдХ рдмрд╣реБрдд рд╣реА рджрд┐рд▓рдЪрд╕реНрдк рд╡рд┐рд╖рдп рд╣реИред

рдпрд╣ рдмреНрд░рд╛рдЙрдЬрд╝рд░ рддрдХрдиреАрдХ рд╕реЗ рдмреЛрд░реНрдб рдЧреЗрдо рдХреА рдЧреБрдгрд╡рддреНрддрд╛ рдХреА рдЙрдореНрдореАрдж рдХрд░рдиреЗ рдХрд╛ рдХреЛрдИ рдорддрд▓рдм рдирд╣реАрдВ рд╣реИред WebGL OpenGL 2.0 рд╣реИ, рдЬрд┐рд╕рдХрд╛ рдЕрд░реНрде рд╣реИ рдХрд┐ рд╣рдорд╛рд░реЗ рдкрд╛рд╕ рдХреЗрд╡рд▓ рд╣рдорд╛рд░реЗ рд╣рд╛рдереЛрдВ рдореЗрдВ рд╡рд░реНрдЯреЗрдХреНрд╕ рдФрд░ рдЯреБрдХрдбрд╝рд╛ рд╢реЗрдб рд╣реИрдВ, рдЬрд┐рд╕рдХрд╛ рдЕрд░реНрде рд╣реИ рдХрд┐ рддрд╕реНрд╡реАрд░ рдХреА рдЧреБрдгрд╡рддреНрддрд╛ рд▓рдЧрднрдЧ 5 рд╡рд░реНрд╖реЛрдВ рддрдХ рдмреЛрд░реНрдб рдЧреЗрдо рд╕реЗ рдкреАрдЫреЗ рд░рд╣ рдЬрд╛рдПрдЧреАред рдЕрдкрдиреЗ рд╢рд┐рд▓реНрдк рдХреЗ рд╕реНрд╡рд╛рдореА рдХреЗ рд▓рд┐рдП, рдпрд╣ рдПрдХ рдмрд╛рдзрд╛ рдирд╣реАрдВ рд╣реИ, рдЯреИрдВрдХреЛрдВ рдиреЗ рдЗрд╕реЗ рдСрдирд▓рд╛рдЗрди рд╕рд╛рдмрд┐рдд рдХрд┐рдпрд╛, рдФрд░ рдпрд╣рд╛рдВ рддрдХ тАЛтАЛрдХрд┐ рдпрд╣ рдкрд╣рд▓реЗ рдЯреИрдВрдХреЛрдВ рдХреЗ рд░рдЪрдирд╛рдХрд╛рд░реЛрдВ рдХреЗ рд╣рд╛рдереЛрдВ рдореЗрдВ рдирд╣реАрдВ рдерд╛ред

рд╕рдмрд╕реЗ рдкрд╣рд▓реЗ рд╣рдореЗрдВ рдЖрдИрдбреАрдИ рдбрд╛рд░реНрдЯ рд╕рдВрдкрд╛рджрдХ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИред рдЗрд╕реЗ рдЖрдзрд┐рдХрд╛рд░рд┐рдХ рд╡реЗрдмрд╕рд╛рдЗрдЯ www.dartlang.org рд╕реЗ рдбрд╛рдЙрдирд▓реЛрдб рдХрд┐рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИ
рдЗрд╕ рдЖрдИрдбреАрдИ рдХрд╛ рдЖрдзрд╛рд░, рдХрдИ, рдкрд░рд┐рдЪрд┐рдд, рдЧреНрд░рд╣рдг рдХреЗ рд▓рд┐рдП рд╣реИ, рдЗрд╕рд▓рд┐рдП, рдмрд┐рдЯрдиреЗрд╕ рдХреЗ рд╕рдВрд╕реНрдХрд░рдг рдХреЛ рдбрд╛рдЙрдирд▓реЛрдб рдХрд░рдиреЗ рдХреА рд╕рд▓рд╛рд╣ рджреА рдЬрд╛рддреА рд╣реИ рдЬрд┐рд╕реЗ рдЖрдкрдиреЗ рдЬрд╛рд╡рд╛ рд╕реНрдерд╛рдкрд┐рдд рдХрд┐рдпрд╛ рд╣реИред рдЕрдиреНрдпрдерд╛, рдЖрдк рдЗрд╕реЗ рд╢реБрд░реВ рдирд╣реАрдВ рдХрд░ рдкрд╛рдПрдВрдЧреЗред

рдПрдХ рдирдпрд╛ рдкреНрд░реЛрдЬреЗрдХреНрдЯ рдмрдирд╛рдПрдВ: рдлрд╝рд╛рдЗрд▓-> рдирдпрд╛ рдПрдкреНрд▓рд┐рдХреЗрд╢рдиред
import 'dart:html'; void main() { } 

рдпрд╣ рдбрд╛рд░реНрдЯ рдкрд░ рдЖрд╡реЗрджрди рдХрд╛ рдиреНрдпреВрдирддрдо рд╡рд┐рдиреНрдпрд╛рд╕ рд╣реИред рдмрд╛рдХреА рдХреЛ рд╕реБрд░рдХреНрд╖рд┐рдд рд╣рдЯрд╛рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИред
рдХрд┐рд╕реА рд╡рд┐рд╢реЗрд╖ рдЖрдИрдбреА рд╡рд╛рд▓реЗ рдПрдХ рдкреГрд╖реНрда рд╕реЗ рдПрдХ рддрддреНрд╡ рдкрд░ рдЕрдкрдиреЗ рд╣рд╛рде рдкрд╛рдиреЗ рдХреЗ рд▓рд┐рдП, рдЖрдкрдХреЛ рдЗрд╕ рддрд░рд╣ рдХреНрд╡реЗрд░реА рдлрд╝рдВрдХреНрд╢рди рдХреЛ рдХреЙрд▓ рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ:
var someElement = querySelector ("# someid");
рдиреНрдпреВрдирддрдо HTML рдлрд╝рд╛рдЗрд▓ рдкрд░ рдПрдХ рдирдЬрд╝рд░ рдбрд╛рд▓реЗрдВ рдЬреЛ рд╣рдо рдкреНрд░рдпреЛрдЧреЛрдВ рдХреЗ рд▓рд┐рдП рдЙрдкрдпреЛрдЧ рдХрд░реЗрдВрдЧреЗ:
 <!DOCTYPE html> <html> <body> <!--      --> <p id="status"></p> <!--    --> <canvas id="canvas3d" width="800" height="600"></canvas> <!--      --> <script src="Simple.dart" type="application/dart"></script> <script src="packages/browser/dart.js"></script> </body> </html> 


рдпрд╣ рдбрд╛рд░реНрдЯ рдХреЛрдб рдХреИрд╕рд╛ рджрд┐рдЦреЗрдЧрд╛, рдкреГрд╖реНрда рдкрд░ рдПрдХ рдЫреЛрдЯрд╛ рд╕рдВрджреЗрд╢ рдкреНрд░рджрд░реНрд╢рд┐рдд рдХрд░рддрд╛ рд╣реИ:
 import 'dart:html'; void main() { var status = querySelector('#status'); status.innerHtml = '<p>    Dart.</p>'; } 

рдЖрдк рдкреНрд░рд╛рд░рдВрдн рдмрдЯрди рджрдмрд╛рдХрд░ рдкреНрд░рджрд░реНрд╢рди рдХреА рдЬрд╛рдВрдЪ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ:

рд╡реЗрдм рдкрд░ рдкреНрд░рдХрд╛рд╢рди рдХреЗ рд▓рд┐рдП рд╕рдВрдХрд▓рди - рдкреНрд░реЛрдЬреЗрдХреНрдЯ рдлрд╝рд╛рдЗрд▓ рдЯреНрд░реА рдХреЗ рд╕рд╛рде рд╡рд┐рдВрдбреЛ рдореЗрдВ рдбрд╛рд░реНрдЯ рдлрд╝рд╛рдЗрд▓ рдкрд░ рдЖрд░рдПрдордмреА рдХреНрд▓рд┐рдХ рдХрд░рдХреЗ рдФрд░ "рдЬрд╛рд╡рд╛рд╕реНрдХреНрд░рд┐рдкреНрдЯ рдХреЗ рд░реВрдк рдореЗрдВ рдЪрд▓рд╛рдПрдБ" рдкрд░ рдХреНрд▓рд┐рдХ рдХрд░реЗрдВ:

3 рдбреА рдЧреНрд░рд╛рдлрд┐рдХреНрд╕ рдкреНрд░рджрд░реНрд╢рд┐рдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рд╣рдореЗрдВ рдХреИрдирд╡рд╛рд╕ рд╕реЗ 3 рдбреА рд╕рдВрджрд░реНрдн рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ, рдЬрд┐рд╕ рдкрд░ рд╣рдо рдЖрдХрд░реНрд╖рд┐рдд рдХрд░реЗрдВрдЧреЗред
 //  canvas = document.querySelector('#canvas3d'); // webGl     gl = (canvas.getContext("webgl")!=null)?canvas.getContext("webgl") : canvas.getContext("experimental-webgl"); 

рдпрджрд┐ рдЗрд╕ рдЕрдиреБрд░реЛрдз рдХреЗ рдмрд╛рдж gl рд╢реВрдиреНрдп рд╣реИ, рддреЛ рдмреНрд░рд╛рдЙрдЬрд╝рд░ webGl рдХрд╛ рд╕рдорд░реНрдерди рдирд╣реАрдВ рдХрд░рддрд╛ рд╣реИред
 if (gl == null) { status.innerHtml = '<p>,     WebGl</p>'; } 

рд╕рдВрджрд░реНрдн рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХреЗ рдмрд╛рдж, рдЗрд╕реЗ рд╢реБрд░реВ рдХрд░рдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реИ, рдорд╛рдкрджрдВрдбреЛрдВ рдХреЗ рд░реВрдк рдореЗрдВ рдХреНрд╖реИрддрд┐рдЬ рдкрд╛рд░реА, рдКрд░реНрдзреНрд╡рд╛рдзрд░ рдкрд╛рд░реА, рдкреНрд░рджрд░реНрд╢рди рдлреНрд░реЗрдо рдХреА рдЪреМрдбрд╝рд╛рдИ рдФрд░ рдКрдВрдЪрд╛рдИ:
 gl.viewport(0, 0, canvas.width, canvas.height); 

рдХреИрдирд╡рд╛рд╕ рдкрд░ рдХрдо рд╕реЗ рдХрдо рдХреБрдЫ рдкреНрд░рджрд░реНрд╢рд┐рдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рдЖрдкрдХреЛ рджреЛ рд╢реЗрдбреНрд╕, рдПрдХ рд╢реАрд░реНрд╖ рдФрд░ рдПрдХ рдЯреБрдХрдбрд╝рд╛ (рдЙрд░реНрдл рдкрд┐рдХреНрд╕реЗрд▓) рд▓реЛрдб рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИред
 //  String vsSource = """ attribute vec3 aPosition; void main() { gl_Position = vec4(aPosition, 1); }"""; //   String fsSource = """ precision mediump float; uniform vec4 uColor; void main() { gl_FragColor = uColor; }"""; // ,        . // WebGLShader vs = gl.createShader(WebGLRenderingContext.VERTEX_SHADER); gl.shaderSource(vs, vsSource); gl.compileShader(vs); WebGLShader fs = gl.createShader(WebGLRenderingContext.FRAGMENT_SHADER); gl.shaderSource(fs, fsSource); gl.compileShader(fs); //    GPU WebGLProgram p = gl.createProgram(); gl.attachShader(p, vs); gl.attachShader(p, fs); gl.linkProgram(p); gl.useProgram(p); //    . if (!gl.getShaderParameter(vs, WebGLRenderingContext.COMPILE_STATUS)) { print(gl.getShaderInfoLog(vs)); } if (!gl.getShaderParameter(fs, WebGLRenderingContext.COMPILE_STATUS)) { print(gl.getShaderInfoLog(fs)); } if (!gl.getProgramParameter(p, WebGLRenderingContext.LINK_STATUS)) { print(gl.getProgramInfoLog(p)); } 

рдкреНрд░рд┐рдВрдЯ рдХрдорд╛рдВрдб рдЗрд╕реНрддреЗрдорд╛рд▓ рдХреА рдЧрдИ рдЖрдИрдбреАрдИ рдХреЗ рд╕реМрджреЗрдмрд╛рдЬреА рдХрдВрд╕реЛрд▓ рдХреЛ рд╕реВрдЪрдирд╛ рдкреНрд░рд┐рдВрдЯ рдХрд░рддрд╛ рд╣реИред рдЕрдЧрд░ рдХреБрдЫ рдЧрд▓рдд рд╣реБрдЖ рд╣реИ, рддреЛ рдХрд╛рд░рдгреЛрдВ рдХреЛ рдкрдврд╝рд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИред
рдЕрдм рд╣рдореЗрдВ GPU рдореЗрдВ рд╢реАрд░реНрд╖ рдмрдлрд░ рдХреЛ рд▓реЛрдб рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ:
 //     Float32List vertices = new Float32List.fromList([ -0.4, 0.4, 1.0, 0.4, 0.4, 1.0, -0.4, -0.4, 1.0]); //       gl.bindBuffer(WebGLRenderingContext.ARRAY_BUFFER, gl.createBuffer()); gl.bufferDataTyped(WebGLRenderingContext.ARRAY_BUFFER, vertices, WebGLRenderingContext.STATIC_DRAW); //    int numItems = 3; //  ,       int aPosition = gl.getAttribLocation(program, "aPosition"); gl.enableVertexAttribArray(aPosition); gl.vertexAttribPointer(aPosition, 3, WebGLRenderingContext.FLOAT, false, 0, 0); //     (RedGreenBlueAlpha) gl.clearColor(0.9, 0.9, 0.9, 1); gl.clear(WebGLRenderingContext.COLOR_BUFFER_BIT); //  ,      WebGLUniformLocation uColor = gl.getUniformLocation(program, "uColor"); //          RGBA gl.uniform4fv(uColor, new Float32List.fromList([0.5, 0.9, 0.9, 1.0])); 

рдХреЗрд╡рд▓ рдПрдХ рд╣реА рдЪреАрдЬрд╝ рдХрд░рдирд╛ рдмрд╛рдХреА рд╣реИ: рд░реЗрдВрдбрд░ рдХрдорд╛рдВрдб рджреЗрдирд╛:
 gl.drawArrays(WebGLRenderingContext.TRIANGLES, 0, numItems); 

рдЕрдм рдЖрдк рдкрд░рд┐рдпреЛрдЬрдирд╛ рд╢реБрд░реВ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ рдФрд░ рдкрд░рд┐рдгрд╛рдо рджреЗрдЦ рд╕рдХрддреЗ рд╣реИрдВ:

рдЖрдк рд╕рдВрдкреВрд░реНрдг рдбрд╛рд░реНрдЯ рд╕реНрд░реЛрдд рдлрд╝рд╛рдЗрд▓ рдпрд╣рд╛рдВ рдбрд╛рдЙрдирд▓реЛрдб рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ: dl.dropbox.com/u/41059365/Simple.dart
рдЗрд╕ рд▓реЗрдЦ рдХрд╛ рдЙрджреНрджреЗрд╢реНрдп рдпрд╣ рдмрддрд╛рдирд╛ рдерд╛ рдХрд┐ рдбрд╛рд░реНрдЯ рдЬреЗрдПрд╕ рдХреЗ рд╕рдорд╛рди рд╣реЛ рд╕рдХрддрд╛ рд╣реИ, рд▓реЗрдХрд┐рди рдЕрдзрд┐рдХ рд╕реБрд╡рд┐рдзрд╛рдЬрдирдХ рд╣реИред рд╕реНрдЯреЗрдЯрд┐рдХ рдЯрд╛рдЗрдкрд┐рдВрдЧ рдФрд░ рдСрдЯреЛ-рдкреВрд░реНрддрд┐ рд╡рд┐рдХрд╛рд╕ рдХреЗ рд╕рдордп рдХреЛ рдмрд╣реБрдд рдХрдо рдХрд░ рджреЗрддреЗ рд╣реИрдВ, рдЬрд┐рд╕рд╕реЗ рдЕрдирд╛рд╡рд╢реНрдпрдХ рдЬрд╛рдирдХрд╛рд░реА рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╕рдорд╛рдкреНрдд рд╣реЛ рдЬрд╛рддреА рд╣реИред рдпреЗ рдФрд░ рдЕрдиреНрдп рдЙрдкрд╣рд╛рд░ рд╡реАрдбрд┐рдпреЛ рдореЗрдВ рдЕрдЪреНрдЫреА рддрд░рд╣ рд╕реЗ рд╡рд░реНрдгрд┐рдд рд╣реИрдВ, рдкрд╣рд▓реА рдЯрд┐рдкреНрдкрдгреА рдореЗрдВ рд▓рд┐рдВрдХред

рд╣рдорд╛рд░реА рд╕реАрде рдЕрднреА рднреА рдпреБрд╡рд╛ рд╣реИ, рд▓реЗрдХрд┐рди рд╡рд╣ рддреЗрдЬреА рд╕реЗ рдмрджрд▓ рд░рд╣рд╛ рд╣реИ рдФрд░ рдмрдбрд╝рд╛ рд╣реЛ рд░рд╣рд╛ рд╣реИред WebGl рдЗрд╕рдХреЗ рд╕рд╛рде рдордЬрдмреВрдд рд╣реЛ рд░рд╣рд╛ рд╣реИ, рдпрджреНрдпрдкрд┐ рдпрд╣ рдХреБрдЫ рдзреАрдорд╛ рд╣реИред рдбрд╛рд░реНрдЯ рдФрд░ рдЬреЗрдПрд╕ рдХреА рддреБрд▓рдирд╛ рдХрд░рддреЗ рд╣реБрдП, рдореИрдВ рдЙрди рд▓реЛрдЧреЛрдВ рдХреЗ рдкреНрд░рддрд┐ рдЕрдкрдирд╛ рдЧрд╣рд░рд╛ рд╕рдореНрдорд╛рди рд╡реНрдпрдХреНрдд рдХрд░рдирд╛ рдЪрд╛рд╣рддрд╛ рд╣реВрдВ рдЬреЛ рдЙрдирдореЗрдВ рд╕реЗ рджреВрд╕рд░реЗ рдкрд░ рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ рдЬрдЯрд┐рд▓ рдкрд░рд┐рдпреЛрдЬрдирд╛рдПрдВ рд▓рд┐рдЦрдиреЗ рдореЗрдВ рд╕рдХреНрд╖рдо рд╣реИрдВред рдбрд╛рд░реНрдЯ рдХреЗ рд▓рд┐рдП рддреАрд╕рд░реЗ рдкрдХреНрд╖ рдХреЗ рдкреБрд╕реНрддрдХрд╛рд▓рдпреЛрдВ рдХреА рд╕рдВрдЦреНрдпрд╛ рдЬреЗрдПрд╕ рдХреЗ рд▓рд┐рдП рдЕрддреБрд▓рдиреАрдп рд░реВрдк рд╕реЗ рдЫреЛрдЯреА рд╣реИ, рд▓реЗрдХрд┐рди рдЗрд╕рд╕реЗ рдЬреБрдбрд╝реА рднрд╛рд╖рд╛ рдФрд░ рдЙрдкрдХрд░рдг рдЗрддрдиреЗ рдЕрдЪреНрдЫреЗ рд╣реИрдВ рдХрд┐ рдпрд╣ рдирдИ рдкрд░рд┐рдпреЛрдЬрдирд╛рдУрдВ рдХреЗ рдкреАрдЫреЗ рдирд╣реАрдВ рдЬрд╛рдПрдЧрд╛ред рдФрд░ рдЪрд░рдг-рджрд░-рдЪрд░рдг рдХреЛрдб рдбреАрдмрдЧрд┐рдВрдЧ рдиреМрд╕рд┐рдЦрд┐рдП рдкреНрд░реЛрдЧреНрд░рд╛рдорд░ рдХреЗ рд▓рд┐рдП рдПрдХ рдЦрдЬрд╛рдирд╛ рд╣реИред рдХреБрдХреАрдЬрд╝ рдбрд╛рд░реНрдЯ рдХреА рддрд░рдл рд╣реИрдВ рдФрд░ рд╡рд╣ рдЬрд▓реНрдж рд╣реА рдкреВрд░реЗ рдЗрдВрдЯрд░рдиреЗрдЯ рдХрд╛ рдорд╛рд▓рд┐рдХ рдмрди рдЬрд╛рдПрдЧрд╛ред

Source: https://habr.com/ru/post/In161785/


All Articles