12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181 |
- using OpenCvSharp;
- using System;
- using System.Drawing;
- using System.Drawing.Imaging;
- using System.IO;
- namespace PaintDotNet.Data.SurfacePlot
- {
- class SurfacePlot
- {
- private int gridWidth = 256;
- private int gridHeight = 256;
- private SurfacePlotData[] plotList = null;
- //Bitmap image;
- private int[] bufferPixels;
- private double[] zbufferPixels;
- private int bufferWidth;
- private int bufferHeight;
- private int lutNr = JRenderer3D.LUT_ORIGINAL;
- public Lut lut;
- private Transform tr;
- private double light;
- private int surfacePlotMode;
- private double xCenter;
- private double yCenter;
- private double zCenter;
- private int min = 0;
- private int max = 100;
- private int inversefactor = 1;
- private int[] pixelsOrigColor;
- private int[] pixelsOrigLum;
- private int widthOrig;
- private int heightOrig;
- private int widthTex;
- private int heightTex;
- private int[] pixelsTexColor;
- //private byte[] maskPixels;
- public bool hasOtherLut = false;
- public void draw()
- {
- surfacePlotLines();
- /**
- if (surfacePlotMode == JRenderer3D.SURFACEPLOT_FILLED)
- surfacePlotFilled();
- else if (surfacePlotMode == JRenderer3D.SURFACEPLOT_ISOLINES)
- surfacePlotIsoLines();
- else if (surfacePlotMode == JRenderer3D.SURFACEPLOT_MESH)
- surfacePlotMesh();
- else if (surfacePlotMode == JRenderer3D.SURFACEPLOT_LINES)
- surfacePlotLines();
- else if (surfacePlotMode == JRenderer3D.SURFACEPLOT_DOTS)
- surfacePlotDots();
- else if (surfacePlotMode == JRenderer3D.SURFACEPLOT_DOTSNOLIGHT)
- surfacePlotDotsNoLight();
- **/
- }
- public unsafe void setSurfacePlotImage(Bitmap imp)
- {
- int widthTmp = imp.Width;
- int heightTmp = imp.Height;
- int[] pixelsTmp = new int[widthTmp * heightTmp];
- Mat mat = OpenCvSharp.Extensions.BitmapConverter.ToMat(imp);
- lut = new Lut();
- int kk = 0;
- for (int i = 0; i < mat.Rows; i++)
- {
- for (int j = 0; j < mat.Cols; j++)
- {
- pixelsTmp[kk] = mat.At<int>(i, j);
- kk++;
- }
- }
- bool isLut = false; //ip.isColorLut();
- if (isLut)
- {
- lut.readLut(imp);
- hasOtherLut = true;
- }
- byte[] lutPixels = null;
- int bitDepth = Image.GetPixelFormatSize(imp.PixelFormat); //Depth();
- if (isLut)
- {
- if (bitDepth == 8)
- {
- lutPixels = ToByteArray(imp);//.(byte[])ip.getPixels();
- }
- else
- {
- lutPixels = new byte[widthTmp * heightTmp];
- double min_ = 0; //ip.getMin();
- double max_ = 255; //ip.getMax();
- double a = 0, b = 1;
- /**
- Calibration cal = imp.getCalibration();
- if (cal != null)
- {
- if (cal.calibrated())
- {
- min_ = cal.getCValue((int)min_);
- max_ = cal.getCValue((int)max_);
- double[] coef = cal.getCoefficients();
- if (coef != null)
- {
- a = coef[0];
- b = coef[1];
- }
- }
- }
- **/
- float scale = (float)(255f / (max_ - min_));
- if (bitDepth == 16)
- {
- byte[] pixels = ToByteArray(imp);
- int pos = 0;
- for (int y = 0; y < heightTmp; y++)
- {
- for (int x = 0; x < widthTmp; x++)
- {
- int val = (int)((int)(0xFFFF & pixels[pos++]) * b + a - min_);
- if (val < 0f) val = 0;
- val = (int)(val * scale);
- if (val > 255) val = 255;
- lutPixels[y * widthTmp + x] = (byte)(val);
- }
- }
- }
- if (bitDepth == 32)
- {
- byte[] pixels = ToByteArray(imp);
- int pos = 0;
- for (int y = 0; y < heightTmp; y++)
- {
- for (int x = 0; x < widthTmp; x++)
- {
- // float value = (float) (pixels[pos++] - min);
- float value = (float)(pixels[pos++] - min_); // LL ==============
- if (value < 0f) value = 0f;
- int ivalue = (int)(value * scale);
- if (ivalue > 255) ivalue = 255;
- lutPixels[y * widthTmp + x] = (byte)(ivalue);
- }
- }
- }
- }
- }
- Mat roi = null;//.getRoi();
- if (roi != null)
- {
- /**
- ImageProcessor mask = roi.getMask();
- ImageProcessor ipMask;
- maskPixels = null;
- if (mask != null)
- {
- ipMask = mask.duplicate();
- maskPixels = (byte[])ipMask.getPixels();
- }
- Rectangle rect = new Rectangle(); //roi.getBounds();
- if (rect.X < 0)
- rect.X = 0;
- if (rect.Y < 0)
- rect.Y = 0;
- widthOrig = rect.Width;
- heightOrig = rect.Height;
- pixelsOrigColor = new int[widthOrig * heightOrig];
- pixelsOrigLum = new int[widthOrig * heightOrig];
- for (int j = 0, y = rect.Y; y < rect.Y + rect.Height; y++)
- {
- int offset = y * widthTmp;
- for (int x = rect.X; x < rect.X + rect.Width; x++, j++)
- {
- int i = offset + x;
- int c = pixelsOrigColor[j] = pixelsTmp[i];
- int lum;
- if (!isLut)
- {
- int r = ((c >> 16) & 255);
- int g = ((c >> 8) & 255);
- int b = ((c) & 255);
- lum = (int)(0.299 * r + 0.587 * g + 0.114 * b);
- }
- else
- lum = (int)(0xFF & lutPixels[i]);
- pixelsOrigLum[j] = lum;
- }
- }**/
- }
- else
- {
- widthOrig = widthTmp;
- heightOrig = heightTmp;
- pixelsOrigColor = new int[widthOrig * heightOrig];
- pixelsOrigLum = new int[widthOrig * heightOrig];
- for (int y = 0; y < heightTmp; y++)
- {
- for (int x = 0; x < widthTmp; x++)
- {
- int pos = y * widthTmp + x;
- int c = pixelsOrigColor[pos] = pixelsTmp[pos];
- int lum;
- int r = ((c >> 16) & 255);
- int g = ((c >> 8) & 255);
- int b = ((c) & 255);
- if (!isLut)
- {
- lum = (int)Math.Round(0.299 * r + 0.587 * g + 0.114 * b);
- }
- else
- {
- lum = lutPixels[pos]; //(int)(0xFF & lutPixels[pos]);
- }
- pixelsOrigLum[pos] = lum;
- }
- }
- }
- }
- public void setSurfacePlotTextureImage(Bitmap imp)
- {
- widthTex = imp.Width;
- heightTex = imp.Height;
- pixelsTexColor = new int[widthTex * heightTex];
- /**
- image = imp;
- int kk = 0;
- for (int i = 0; i < image.Width; i++)
- {
- for (int j = 0; j < image.Height; j++)
- {
- pixelsTexColor[kk] = image.GetPixel(i, j).ToArgb();
- kk++;
- }
- }
- **/
- /**
- PixelGrabber pg = new PixelGrabber(image, 0, 0, widthTex, heightTex, pixelsTexColor, 0, widthTex);
- try
- {
- pg.grabPixels();
- }
- catch (Exception ex)
- {
- //---IJ.error("error grabbing pixels");
- pixelsTexColor = null;
- }
- **/
- }
- public void resample()
- {
- plotList = new SurfacePlotData[gridWidth * gridHeight];
- if (pixelsOrigColor != null && pixelsOrigLum != null)
- {
- double xOffset = xCenter;
- double yOffset = yCenter;
- double sx = widthOrig / (double)gridWidth;
- double sy = heightOrig / (double)gridHeight;
- for (int y = 0; y < gridHeight; y++)
- {
- int yB = (int)(y * sy);
- for (int x = 0; x < gridWidth; x++)
- {
- int posGrid = y * gridWidth + x;
- int xB = (int)(x * sx);
- int posOrig = yB * widthOrig + xB;
- plotList[posGrid] = new SurfacePlotData();
- plotList[posGrid].color = pixelsOrigColor[posOrig];
- plotList[posGrid].x = sx * (x + 0.5) - xOffset;
- plotList[posGrid].y = sy * (y + 0.5) - yOffset;
- plotList[posGrid].z = plotList[posGrid].zf = plotList[posGrid].lum =
- pixelsOrigLum[posOrig] - zCenter;
- /**
- if (maskPixels != null)
- {
- if (maskPixels[posOrig] != 0)
- plotList[posGrid].isVisible = true;
- else
- plotList[posGrid].isVisible = false;
- }
- else**/
- plotList[posGrid].isVisible = true;
- }
- }
- }
- if (pixelsTexColor != null)
- {
- double sx = widthTex / (double)gridWidth;
- double sy = heightTex / (double)gridHeight;
- for (int y = 0; y < gridHeight; y++)
- {
- int yB = (int)(y * sy);
- for (int x = 0; x < gridWidth; x++)
- {
- int pos = y * gridWidth + x;
- int xB = (int)(x * sx);
- plotList[pos].color = pixelsTexColor[yB * widthTex + xB];
- }
- }
- }
- computeNormals();
- }
- private void computeNormals()
- {
- for (int y = 0; y < gridHeight; y++)
- {
- for (int x = 0; x < gridWidth; x++)
- {
- int i = y * gridWidth + x;
- double dx1 = 0;
- double dy1 = 0;
- double dz1 = 0;
- for (int y_ = -1; y_ <= 1; y_++)
- {
- int yn = y + y_;
- if (yn < 0) yn = 0;
- if (yn >= gridHeight) yn = gridHeight - 1;
- for (int x_ = -1; x_ < 1; x_++)
- {
- int xn = x + x_;
- if (xn < 0) xn = 0;
- if (xn >= gridWidth) xn = gridWidth - 1;
- int xn1 = xn + 1;
- if (xn1 < 0) xn1 = 0;
- if (xn1 >= gridWidth) xn1 = gridWidth - 1;
- int posn = yn * gridWidth + xn;
- int posn1 = yn * gridWidth + xn1;
- dx1 += plotList[posn1].x - plotList[posn].x;
- dz1 += plotList[posn1].z - plotList[posn].z;
- }
- }
- double dx2 = 0;
- double dy2 = 0;
- double dz2 = 0;
- for (int y_ = -1; y_ < 1; y_++)
- {
- int yn = y + y_;
- if (yn < 0) yn = 0;
- if (yn >= gridHeight) yn = gridHeight - 1;
- int yn1 = yn + 1;
- if (yn1 < 0) yn1 = 0;
- if (yn1 >= gridHeight) yn1 = gridHeight - 1;
- for (int x_ = -1; x_ <= 1; x_++)
- {
- int xn = x + x_;
- if (xn < 0) xn = 0;
- if (xn >= gridWidth) xn = gridWidth - 1;
- int posn = yn * gridWidth + xn;
- int posn1 = yn1 * gridWidth + xn;
- dy2 += plotList[posn1].y - plotList[posn].y;
- dz2 += plotList[posn1].z - plotList[posn].z;
- }
- }
- // outer product
- double dx = (dy1 * dz2 - dz1 * dy2);
- double dy = (dz1 * dx2 - dx1 * dz2);
- double dz = (dx1 * dy2 - dy1 * dx2);
- double len = Math.Sqrt(dx * dx + dy * dy + dz * dz);
- plotList[i].dx = dx / len;
- plotList[i].dy = dy / len;
- plotList[i].dz = dz / len;
- }
- }
- }
- public void applyMinMax()
- {
- //System.out.println("applyMinMax inverseFactor: " + inversefactor);
- int add = 0;
- if (inversefactor == -1)
- add = -1;
- for (int i = 0; i < gridHeight * gridWidth; i++)
- {
- double val = (100 * (plotList[i].zf + zCenter - 2.55 * (min)) / (max - min) - zCenter);
- plotList[i].z = inversefactor * Math.Min(Math.Max(-128, val), 127) + add;
- }
- computeNormals();
- }
- public void applySmoothingFilter(double rad)
- {
- float[] pixels = new float[gridHeight * gridWidth];
- for (int i = 0; i < gridHeight * gridWidth; i++)
- {
- pixels[i] = (float)plotList[i].lum;
- }
- /**
- ImageProcessor ip = new FloatProcessor(gridWidth, gridHeight, pixels, null);
- new GaussianBlur().blur(ip, rad);
- pixels = (float[])ip.getPixels();
- for (int i = 0; i < gridHeight * gridWidth; i++)
- {
- plotList[i].z = plotList[i].zf = pixels[i];
- }
- applyMinMax();
- **/
- }
- public static byte[] ToByteArray(Bitmap bmp)
- {
- MemoryStream ms = new MemoryStream();
- bmp.Save(ms, ImageFormat.Jpeg);
- ms.Seek(0, SeekOrigin.Begin); //一定不要忘记将流的初始位置重置
- //byte[] bytes = new byte[ms.Length];
- byte[] bytes = new byte[bmp.Height * bmp.Width];
- ms.Read(bytes, 0, bytes.Length); //如果上面流没有seek 则这里读取的数据全会为0
- ms.Dispose();
- return bytes;
- }
- /**************************************************************************************
- *
- * Drawing Routines
- *
- **************************************************************************************/
- private int getColor(SurfacePlotData p0)
- {
- int c0 = p0.color;
- /**
- if (lutNr == JRenderer3D.LUT_ORIGINAL)
- {
- c0 = p0.color;
- }
- else if (lutNr == JRenderer3D.LUT_GRADIENT)
- {
- c0 = ((int)(p0.dx * 127 + 127) << 16) | ((int)(p0.dy * 127 + 127) << 8) | (int)(p0.dz * 127 + 127);
- }
- else if (lutNr == JRenderer3D.LUT_GRADIENT2)
- {
- c0 = ((int)(p0.dx2 * 127 + 127) << 16) | ((int)(p0.dy2 * 127 + 127) << 8) | (int)(0);
- }
- else
- {
- int index = (int)(p0.z + 128);
- if (index > 255)
- index = 255;
- if (index < 0)
- index = 0;
- c0 = lut.colors[index];
- }
- **/
- return c0;
- }
- private void surfacePlotFilled()
- {
- for (int row = 0; row < gridHeight - 1; row++)
- {
- for (int col = 0; col < gridWidth - 1; col++)
- {
- int i = row * gridWidth + col;
- SurfacePlotData p0 = plotList[i];
- if (p0.isVisible)
- {
- SurfacePlotData p1 = plotList[i + 1];
- SurfacePlotData p2 = plotList[i + gridWidth];
- SurfacePlotData p3 = plotList[i + gridWidth + 1];
- if (p1.isVisible && p2.isVisible && p3.isVisible)
- {
- tr.transform(p0);
- double x0 = tr.X, y0 = tr.Y, z0 = tr.Z;
- tr.x = p0.dx;
- tr.y = p0.dy;
- double light0 = tr.getScalarProduct();
- tr.transform(p1);
- double x1 = tr.X, y1 = tr.Y, z1 = tr.Z;
- tr.x = p1.dx;
- tr.y = p1.dy;
- double light1 = tr.getScalarProduct();
- tr.transform(p2);
- double x2 = tr.X, y2 = tr.Y, z2 = tr.Z;
- tr.x = p2.dx;
- tr.y = p2.dy;
- double light2 = tr.getScalarProduct();
- tr.transform(p3);
- double x3 = tr.X, y3 = tr.Y, z3 = tr.Z;
- tr.x = p3.dx;
- tr.y = p3.dy;
- double light3 = tr.getScalarProduct();
- if (!(x0 >= bufferWidth && x0 < 0 && y0 >= bufferHeight && y0 < 0 &&
- x1 >= bufferWidth && x1 < 0 && y1 >= bufferHeight && y1 < 0 &&
- x2 >= bufferWidth && x2 < 0 && y2 >= bufferHeight && y2 < 0 &&
- x3 >= bufferWidth && x3 < 0 && y3 >= bufferHeight && y3 < 0))
- {
- int c0 = getColor(p0);
- int c1 = getColor(p1);
- int c2 = getColor(p2);
- int c3 = getColor(p3);
- int r0 = ((c0 >> 16) & 0xff);
- int g0 = ((c0 >> 8) & 0xff);
- int b0 = ((c0) & 0xff);
- int r1 = ((c1 >> 16) & 0xff);
- int g1 = ((c1 >> 8) & 0xff);
- int b1 = ((c1) & 0xff);
- int r2 = ((c2 >> 16) & 0xff);
- int g2 = ((c2 >> 8) & 0xff);
- int b2 = ((c2) & 0xff);
- int r3 = ((c3 >> 16) & 0xff);
- int g3 = ((c3 >> 8) & 0xff);
- int b3 = ((c3) & 0xff);
- double n13 = Math.Abs(y1 - y3) + Math.Abs(x1 - x3);
- double n02 = Math.Abs(y0 - y2) + Math.Abs(x0 - x2);
- // double n13 = Math.sqrt((y1-y3)*(y1-y3) + (x1-x3)*(x1-x3));
- // double n02 = Math.sqrt((y0-y2)*(y0-y2) + (x0-x2)*(x0-x2));
- int stepsY = (int)(Math.Max(n13, n02) + 1);
- double dy = 1 / stepsY;
- double dx02 = (x2 - x0) * dy;
- double dy02 = (y2 - y0) * dy;
- double dx13 = (x3 - x1) * dy;
- double dy13 = (y3 - y1) * dy;
- double x02 = x0;
- double y02 = y0;
- double x13 = x1;
- double y13 = y1;
- double v = 0;
- for (int sy = 0; sy < stepsY; sy++, v += dy)
- {
- x02 += dx02;
- y02 += dy02;
- x13 += dx13;
- y13 += dy13;
- //int stepsX = (int) (Math.abs(x02-x13) + Math.abs(y02-y13) + 1);
- int stepsX = (int)(Math.Abs(x02 - x13) + Math.Abs(y02 - y13) + 1);
- double dx = 1 / stepsX;
- double dx0213 = (x13 - x02) * dx;
- double dy0213 = (y13 - y02) * dx;
- double x0213 = x02;
- double y0213 = y02;
- double h = 0;
- for (int sx = 0; sx < stepsX; sx++, h += dx)
- {
- x0213 += dx0213;
- y0213 += dy0213;
- if (x0213 >= 0 && x0213 < bufferWidth && y0213 >= 0 && y0213 < bufferHeight)
- {
- double d0 = (1 - h) * (1 - v);
- double d1 = h * (1 - v);
- double d2 = (1 - h) * v;
- double d3 = h * v;
- double z = d0 * z0 + d1 * z1 + d2 * z2 + d3 * z3;
- // System.out.println("x: " + (int)x0213 + " y: " + (int)y0213);
- int pos = (int)y0213 * bufferWidth + (int)x0213;
- if (z < zbufferPixels[pos])
- {
- zbufferPixels[pos] = z;
- int r = (int)(r3 * d3 + r2 * d2 + r1 * d1 + r0 * d0);
- int g = (int)(g3 * d3 + g2 * d2 + g1 * d1 + g0 * d0);
- int b = (int)(b3 * d3 + b2 * d2 + b1 * d1 + b0 * d0);
- double light0123 = d3 * light3 + d2 * light2 + d1 * light1 + d0 * light0;
- double l = -light * light0123 * 255;
- r = (int)Math.Min(255, Math.Max(0, r + l));
- g = (int)Math.Min(255, Math.Max(0, g + l));
- b = (int)Math.Min(255, Math.Max(0, b + l));
- uint temp = (uint)(0xff000000 | (uint)(r << 16) | (uint)(g << 8) | (uint)b);
- bufferPixels[pos] = (int)temp;//(0xff000000 | (r << 16) | (g << 8) | b);
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- private void surfacePlotIsoLines()
- {
- for (int row = 0; row < gridHeight - 1; row++)
- {
- for (int col = 0; col < gridWidth - 1; col++)
- {
- int i = row * gridWidth + col;
- SurfacePlotData p0 = plotList[i];
- if (p0.isVisible)
- {
- SurfacePlotData p1 = plotList[i + 1];
- SurfacePlotData p2 = plotList[i + gridWidth];
- SurfacePlotData p3 = plotList[i + gridWidth + 1];
- if ((p1.isVisible) && (p2.isVisible) && (p3.isVisible))
- {
- tr.transform(p0);
- double x0 = tr.X, y0 = tr.Y, z0 = tr.Z;
- tr.x = p0.dx;
- tr.y = p0.dy;
- double light0 = tr.getScalarProduct();
- tr.transform(p1);
- double x1 = tr.X, y1 = tr.Y, z1 = tr.Z;
- tr.x = p1.dx;
- tr.y = p1.dy;
- double light1 = tr.getScalarProduct();
- tr.transform(p2);
- double x2 = tr.X, y2 = tr.Y, z2 = tr.Z;
- tr.x = p2.dx;
- tr.y = p2.dy;
- double light2 = tr.getScalarProduct();
- tr.transform(p3);
- double x3 = tr.X, y3 = tr.Y, z3 = tr.Z;
- tr.x = p3.dx;
- tr.y = p3.dy;
- double light3 = tr.getScalarProduct();
- if (!(x0 >= bufferWidth && x0 < 0 && y0 >= bufferHeight && y0 < 0 &&
- x1 >= bufferWidth && x1 < 0 && y1 >= bufferHeight && y1 < 0 &&
- x2 >= bufferWidth && x2 < 0 && y2 >= bufferHeight && y2 < 0 &&
- x3 >= bufferWidth && x3 < 0 && y3 >= bufferHeight && y3 < 0))
- {
- int c0 = getColor(p0);
- int c1 = getColor(p1);
- int c2 = getColor(p2);
- int c3 = getColor(p3);
- double lum0 = p0.z;
- double lum1 = p1.z;
- double lum2 = p2.z;
- double lum3 = p3.z;
- int r0 = ((c0 >> 16) & 0xff);
- int g0 = ((c0 >> 8) & 0xff);
- int b0 = ((c0) & 0xff);
- int r1 = ((c1 >> 16) & 0xff);
- int g1 = ((c1 >> 8) & 0xff);
- int b1 = ((c1) & 0xff);
- int r2 = ((c2 >> 16) & 0xff);
- int g2 = ((c2 >> 8) & 0xff);
- int b2 = ((c2) & 0xff);
- int r3 = ((c3 >> 16) & 0xff);
- int g3 = ((c3 >> 8) & 0xff);
- int b3 = ((c3) & 0xff);
- double n13 = Math.Abs(x1 - x3) + Math.Abs(y1 - y3);
- double n02 = Math.Abs(x0 - x2) + Math.Abs(y0 - y2);
- int stepsY = (int)(Math.Max(n13, n02) + 1);
- double dy = 1 / stepsY;
- double dx02 = (x2 - x0) * dy;
- double dy02 = (y2 - y0) * dy;
- double dx13 = (x3 - x1) * dy;
- double dy13 = (y3 - y1) * dy;
- double x02 = x0;
- double y02 = y0;
- double x13 = x1;
- double y13 = y1;
- double v = 0;
- for (int sy = 0; sy < stepsY; sy++, v += dy)
- {
- x02 += dx02;
- y02 += dy02;
- x13 += dx13;
- y13 += dy13;
- int stepsX = (int)(Math.Abs(x02 - x13) + Math.Abs(y02 - y13) + 1);
- double dx = 1 / stepsX;
- double dx0213 = (x13 - x02) * dx;
- double dy0213 = (y13 - y02) * dx;
- double x0213 = x02;
- double y0213 = y02;
- double h = 0;
- for (int sx = 0; sx < stepsX; sx++, h += dx)
- {
- x0213 += dx0213;
- y0213 += dy0213;
- double d0 = (1 - h) * (1 - v);
- double d1 = h * (1 - v);
- double d2 = (1 - h) * v;
- double d3 = h * v;
- double z = d0 * z0 + d1 * z1 + d2 * z2 + d3 * z3;
- if (x0213 >= 0 && x0213 < bufferWidth && y0213 >= 0 && y0213 < bufferHeight)
- {
- int pos = (int)y0213 * bufferWidth + (int)x0213;
- if (z < zbufferPixels[pos])
- {
- double lum = d0 * lum0 + d1 * lum1 + d2 * lum2 + d3 * lum3 + 132;
- if (lum - 12 * (int)(lum / 12) < 1.5)
- {
- zbufferPixels[pos] = z;
- int r = (int)(r3 * d3 + r2 * d2 + r1 * d1 + r0 * d0);
- int g = (int)(g3 * d3 + g2 * d2 + g1 * d1 + g0 * d0);
- int b = (int)(b3 * d3 + b2 * d2 + b1 * d1 + b0 * d0);
- double light0123 = d3 * light3 + d2 * light2 + d1 * light1 + d0 * light0;
- double l = -light * light0123 * 255;
- r = (int)Math.Min(255, Math.Max(0, r + l));
- g = (int)Math.Min(255, Math.Max(0, g + l));
- b = (int)Math.Min(255, Math.Max(0, b + l));
- //uint temp = (uint)(0xff000000 | (uint)(r << 16) | (uint)(g << 8) | (uint)b);
- bufferPixels[pos] = (int)(((uint)r << 16) | (ushort)(((ushort)g << 8) | b));
- //bufferPixels[pos] = (int)temp;// (0xff000000 | (r << 16) | (g << 8) | b);
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- }
- private void surfacePlotMesh()
- {
- for (int row = 0; row < gridHeight; row++)
- {
- for (int col = 0; col < gridWidth; col++)
- {
- int i = row * gridWidth + col;
- SurfacePlotData p0 = plotList[i];
- int r0, g0, b0, r1, g1, b1, r2, g2, b2;
- if (p0.isVisible)
- {
- tr.transform(p0);
- double x0 = tr.X, y0 = tr.Y, z0 = tr.Z;
- int c0 = getColor(p0);
- r0 = ((c0 >> 16) & 0xff);
- g0 = ((c0 >> 8) & 0xff);
- b0 = ((c0) & 0xff);
- SurfacePlotData p1 = (col < gridWidth - 1) ? plotList[i + 1] : plotList[i];
- if (p1.isVisible)
- {
- tr.transform(p1);
- double x1 = tr.X, y1 = tr.Y, z1 = tr.Z;
- double dx10 = x1 - x0, dy10 = y1 - y0, dz10 = z1 - z0;
- int c1 = getColor(p1);
- r1 = ((c1 >> 16) & 0xff);
- g1 = ((c1 >> 8) & 0xff);
- b1 = ((c1) & 0xff);
- int numSteps = (int)(Math.Max(Math.Abs(dx10), Math.Abs(dy10)) + 1);
- double step = 1 / numSteps;
- for (int s = 0; s < numSteps; s++)
- {
- double f = s * step;
- int x = (int)(x0 + f * dx10);
- int y = (int)(y0 + f * dy10);
- if (x >= 0 && y >= 0 && x < bufferWidth && y < bufferHeight)
- {
- int pos = y * bufferWidth + x;
- int z = (int)(z0 + f * dz10);
- if (z < zbufferPixels[pos])
- {
- zbufferPixels[pos] = z;
- int r = (int)(f * r1 + (1 - f) * r0);
- int g = (int)(f * g1 + (1 - f) * g0);
- int b = (int)(f * b1 + (1 - f) * b0);
- tr.x = p0.dx;
- tr.y = p0.dy;
- double l = -light * tr.getScalarProduct() * 255;
- r = (int)Math.Min(255, Math.Max(0, r + l));
- g = (int)Math.Min(255, Math.Max(0, g + l));
- b = (int)Math.Min(255, Math.Max(0, b + l));
- bufferPixels[pos] = (int)(((uint)r << 16) | (ushort)(((ushort)g << 8) | b));
- //uint temp = (uint)(0xff000000 | (uint)(r << 16) | (uint)(g << 8) | (uint)b);
- //bufferPixels[pos] = (int)temp; //(int)(0xff000000 | (r << 16) | (g << 8) | b);
- }
- }
- }
- }
- SurfacePlotData p2 = (row < gridHeight - 1) ? plotList[i + gridWidth] : plotList[i];
- if (p2.isVisible)
- {
- tr.transform(p2);
- double x2 = tr.X, y2 = tr.Y, z2 = tr.Z;
- double dx20 = x2 - x0, dy20 = y2 - y0, dz20 = z2 - z0;
- int c2 = getColor(p2);
- r2 = ((c2 >> 16) & 0xff);
- g2 = ((c2 >> 8) & 0xff);
- b2 = ((c2) & 0xff);
- int numSteps = (int)(Math.Max(Math.Abs(dx20), Math.Abs(dy20)) + 1);
- double step = 1 / numSteps;
- for (int s = 0; s < numSteps; s++)
- {
- double f = s * step;
- int x = (int)(x0 + f * dx20);
- int y = (int)(y0 + f * dy20);
- if (x >= 0 && y >= 0 && x < bufferWidth && y < bufferHeight)
- {
- int pos = y * bufferWidth + x;
- int z = (int)(z0 + f * dz20);
- if (z < zbufferPixels[pos])
- {
- zbufferPixels[pos] = z;
- int r = (int)(f * r2 + (1 - f) * r0);
- int g = (int)(f * g2 + (1 - f) * g0);
- int b = (int)(f * b2 + (1 - f) * b0);
- tr.x = p0.dx;
- tr.y = p0.dy;
- double l = -light * tr.getScalarProduct() * 255;
- r = (int)Math.Min(255, Math.Max(0, r + l));
- g = (int)Math.Min(255, Math.Max(0, g + l));
- b = (int)Math.Min(255, Math.Max(0, b + l));
- bufferPixels[pos] = (int)(((uint)r << 16) | (ushort)(((ushort)g << 8) | b));
- /**
- uint temp = (uint)(0xff000000 | (uint)(r << 16) | (uint)(g << 8) | (uint)b);
- bufferPixels[pos] = (int)(temp);
- **/
- }
- }
- }
- }
- }
- }
- }
- }
- private void surfacePlotLines()
- {
- for (int row = 0; row < gridHeight; row++)
- {
- for (int col = 0; col < gridWidth - 1; col++)
- {
- int i = row * gridWidth + col;
- SurfacePlotData p0 = plotList[i];
- SurfacePlotData p1 = plotList[i + 1];
- if (p0.isVisible && p1.isVisible)
- {
- tr.transform(p0);
- double x0 = tr.X, y0 = tr.Y, z0 = tr.Z;
- int c0 = getColor(p0);
- int r0 = ((c0 >> 16) & 0xff);
- int g0 = ((c0 >> 8) & 0xff);
- int b0 = ((c0) & 0xff);
- tr.transform(p1);
- double x1 = tr.X, y1 = tr.Y, z1 = tr.Z;
- double dx1 = x1 - x0, dy1 = y1 - y0, dz1 = z1 - z0;
- int numSteps = (int)(Math.Max(Math.Abs(dx1), Math.Abs(dy1)) + 1);
- int c1 = getColor(p1);
- int r1 = ((c1 >> 16) & 0xff);
- int g1 = ((c1 >> 8) & 0xff);
- int b1 = ((c1) & 0xff);
- double step = 1 / numSteps;
- int r, g, b;
- for (int s = 0; s < numSteps; s++)
- {
- double f = s * step;
- int x = (int)(x0 + f * dx1);
- int y = (int)(y0 + f * dy1);
- if (x >= 0 && y >= 0 && x < bufferWidth && y < bufferHeight)
- {
- int pos = y * bufferWidth + x;
- double z = z0 + f * dz1;
- if (z < zbufferPixels[pos])
- {
- zbufferPixels[pos] = z;
- r = (int)((1 - f) * r0 + f * r1);
- g = (int)((1 - f) * g0 + f * g1);
- b = (int)((1 - f) * b0 + f * b1);
- tr.x = p0.dx;
- tr.y = p0.dy;
- double l = -light * tr.getScalarProduct() * 255;
- r = (int)Math.Min(255, Math.Max(0, r + l));
- g = (int)Math.Min(255, Math.Max(0, g + l));
- b = (int)Math.Min(255, Math.Max(0, b + l));
- bufferPixels[pos] = (int)(((uint)r << 16) | (ushort)(((ushort)g << 8) | b));
- /*
- long lv = (0xff000000 | (r << 16) | (g << 8) | b);
- if (lv > int.MaxValue)
- {
- bufferPixels[pos] = int.MaxValue;
- }
- else {
- bufferPixels[pos] = (int)lv;
- }**/
- }
- }
- }
- }
- }
- }
- }
- private void surfacePlotDots()
- {
- for (int i = plotList.Length - 1; i >= 0; i--)
- {
- SurfacePlotData p0 = plotList[i];
- if (p0.isVisible)
- {
- tr.transform(p0);
- int x = (int)tr.X, y = (int)tr.Y;
- if (x >= 0 && y >= 0 && x < bufferWidth && y < bufferHeight)
- {
- int pos = y * bufferWidth + x;
- int z = (int)tr.Z;
- if (z < zbufferPixels[pos])
- {
- zbufferPixels[pos] = z;
- int c0 = getColor(p0);
- int r0 = ((c0 >> 16) & 0xff);
- int g0 = ((c0 >> 8) & 0xff);
- int b0 = ((c0) & 0xff);
- tr.x = p0.dx;
- tr.y = p0.dy;
- double l = -light * tr.getScalarProduct() * 255;
- int r = (int)Math.Min(255, Math.Max(0, r0 + l));
- int g = (int)Math.Min(255, Math.Max(0, g0 + l));
- int b = (int)Math.Min(255, Math.Max(0, b0 + l));
- uint temp = (uint)(0xff000000 | (uint)(r << 16) | (uint)(g << 8) | (uint)b);
- bufferPixels[pos] = (int)temp; //(int)(0xff000000 | (r << 16) | (g << 8) | b);
- }
- }
- }
- }
- }
- public void surfacePlotDotsNoLight()
- {
- int delta = Math.Max(gridHeight, gridWidth) / 128;
- if (delta < 1)
- delta = 1;
- for (int row = 0; row < gridHeight; row += delta)
- {
- for (int col = 0; col < gridWidth; col += delta)
- {
- int i = row * gridWidth + col;
- SurfacePlotData p0 = plotList[i];
- if (p0.isVisible)
- {
- tr.transform(p0);
- int x = (int)tr.X;
- int y = (int)tr.Y;
- if (x >= 0 && y >= 0 && x < bufferWidth - 1 && y < bufferHeight - 1)
- {
- int pos = y * bufferWidth + x;
- int z = (int)tr.Z;
- if (z < zbufferPixels[pos])
- {
- int c0 = (int)(0xFF000000 | getColor(p0));
- zbufferPixels[pos] = z;
- zbufferPixels[pos + 1] = z;
- zbufferPixels[pos + bufferWidth] = z;
- zbufferPixels[pos + bufferWidth + 1] = z;
- bufferPixels[pos] = c0;
- bufferPixels[pos + 1] = c0;
- bufferPixels[pos + bufferWidth] = c0;
- bufferPixels[pos + bufferWidth + 1] = c0;
- }
- }
- }
- }
- }
- }
- public void setSurfacePLotSetLight(double light)
- {
- this.light = light;
- }
- public void setSurfaceGridSize(int width, int height)
- {
- this.gridWidth = width;
- this.gridHeight = height;
- }
- public void setSurfacePlotMode(int surfacePlotMode)
- {
- this.surfacePlotMode = surfacePlotMode;
- }
- public void setBuffers(int[] bufferPixels, double[] zbufferPixels, int bufferWidth, int bufferHeight)
- {
- this.bufferPixels = bufferPixels;
- this.zbufferPixels = zbufferPixels;
- this.bufferWidth = bufferWidth;
- this.bufferHeight = bufferHeight;
- }
- public void setTransform(Transform transform)
- {
- this.tr = transform;
- }
- public void setSurfacePlotCenter(double xCenter, double yCenter, double zCenter)
- {
- this.xCenter = xCenter;
- this.yCenter = yCenter;
- this.zCenter = zCenter;
- }
- public void setSurfacePlotLut(int lutNr)
- {
- this.lutNr = lutNr;
- if (lut != null)
- lut.setLut(lutNr);
- }
- public int getSurfacePlotLut()
- {
- return lut.getLutNr();
- }
- public void setMinMax(int min, int max)
- {
- this.min = min;
- this.max = max;
- }
- public void setInverse(bool b)
- {
- inversefactor = (b) ? -1 : 1;
- for (int i = 0; i < plotList.Length; i++)
- plotList[i].z = inversefactor * plotList[i].zf;
- }
- public int getInversefactor()
- {
- return inversefactor;
- }
- }
- }
|