Commit 40550007 authored by Jan Kremer's avatar Jan Kremer

Working on 2D plots. Added ParallelFor in the code for brushing.

parent ba699bd9
......@@ -11,7 +11,7 @@ class Plot:
def begin_play(self):
self.uobject.get_owner().bind_event('OnRedraw', self.redraw)
def redraw(self, x, y, r, g, b):
def redraw(self, x, y, c):
width=1024
height=1024
canvas = app.Canvas(size=(width, height))
......@@ -39,9 +39,8 @@ class Plot:
program = gloo.Program(vert=vertex, frag=fragment)
N = 4000000
data = np.c_[x,y]
data2 = np.c_[r,g,b]
data = np.c_[x[0:100000],y[0:100000]]
data2 = np.c_[c]
program['a_color'] = data2.astype('float32')
program['a_position'] = data.astype('float32')
......
No preview for this file type
......@@ -51,11 +51,11 @@ bHQDistortion=False
bUpdateOnRT=True
[WindowsApplication.Accessibility]
StickyKeysHotkey=True
ToggleKeysHotkey=True
FilterKeysHotkey=True
StickyKeysConfirmation=True
ToggleKeysConfirmation=True
FilterKeysConfirmation=True
StickyKeysHotkey=False
ToggleKeysHotkey=False
FilterKeysHotkey=False
StickyKeysConfirmation=False
ToggleKeysConfirmation=False
FilterKeysConfirmation=False
......@@ -4,6 +4,7 @@
#include "HDF5Library.h"
#include "PointCloudComponent.h"
#include "Runtime/Engine/Classes/Kismet/KismetMathLibrary.h"
#include "Runtime/Core/Public/Async/ParallelFor.h"
// Sets default values
APlot3D::APlot3D()
......@@ -28,10 +29,6 @@ void APlot3D::BeginPlay()
void APlot3D::InitPoints()
{
TArray<float> X;
TArray<float> Y;
TArray<float> Z;
UHDF5Library::ImportData(X, Y, Z, U, V, W);
int32 Num;
......@@ -67,9 +64,10 @@ void APlot3D::InitPoints()
for (int32 i = 0; i < Num; i++)
{
FColor Color = CalculateColorOfPoint(i, MaxLength, MinLength);
FColor TempColor = CalculateColorOfPoint(i, MaxLength, MinLength);
Points.Emplace(FVector(X[i], Y[i], Z[i]), Color, true);
Color.Emplace(FVector(TempColor.R, TempColor.G, TempColor.B));
Points.Emplace(FVector(X[i], Y[i], Z[i]), TempColor, true);
}
}
......@@ -113,7 +111,6 @@ FVector APlot3D::CalculateWorldLocOfPoint(FPointCloudPoint * Point)
return SumVec;
}
// Called every frame
void APlot3D::Tick(float DeltaTime)
{
Super::Tick(DeltaTime);
......@@ -135,6 +132,11 @@ void APlot3D::BrushPoints(TArray<int32> BrushPoints, bool Add, bool Rebuild)
void APlot3D::BrushPoint(int32 PointIndex, bool Add)
{
if (PointIndex == -1)
{
return;
}
Points[PointIndex].SetEnabled(!Add);
/*
......@@ -156,6 +158,11 @@ void APlot3D::ResetPoints(bool Rebuild)
BrushPoint(i, false);
}
/*ParallelFor(Points.Num(), [this](int32 CurrIdx)
{
BrushPoint(CurrIdx, false);
});*/
if (Rebuild)
{
RebuildCloud();
......@@ -169,6 +176,21 @@ void APlot3D::InvertPoints(bool Rebuild)
BrushPoint(i, Points[i].IsEnabled());
}
/*ParallelFor(Points.Num(), [this](int32 CurrIdx)
{
BrushPoint(CurrIdx, Points[CurrIdx].IsEnabled());
});*/
/*ParallelFor(4, [this](int32 CurrIdx)
{
int32 Start = Points.Num() / 4 * CurrIdx;
int32 End = Points.Num() / 4 * (CurrIdx + 1);
for (int i = Start; i < End; ++i)
{
BrushPoint(i, Points[i].IsEnabled());
}
});*/
if (Rebuild)
{
RebuildCloud();
......@@ -178,10 +200,11 @@ void APlot3D::InvertPoints(bool Rebuild)
void APlot3D::AddFilter_Planes(FVector NormalRight, FVector LocationRight, bool UseTwoPlanes, FVector NormalLeft, FVector LocationLeft, bool Add, bool Rebuild, bool Invert)
{
TArray<int32> Indexes = TArray<int32>();
Indexes.Init(-1, Points.Num());
for (int i = 0; i < Points.Num(); ++i)
ParallelFor(Points.Num(), [this, Invert, &Indexes, LocationRight, LocationLeft, NormalRight, NormalLeft, UseTwoPlanes, Add](int32 CurrIdx)
{
FVector WorldLoc = CalculateWorldLocOfPoint(&Points[i]);
FVector WorldLoc = CalculateWorldLocOfPoint(&Points[CurrIdx]);
FVector DifferenceRight = WorldLoc - LocationRight;
FVector DifferenceLeft = WorldLoc - LocationLeft;
float DotRight = UKismetMathLibrary::Dot_VectorVector(DifferenceRight, NormalRight);
......@@ -191,59 +214,94 @@ void APlot3D::AddFilter_Planes(FVector NormalRight, FVector LocationRight, bool
{
if (DotRight >= 0.f && (DotLeft >= 0.f || !UseTwoPlanes))
{
Indexes.Emplace(i);
Indexes[CurrIdx] = CurrIdx;
}
}
else
{
if (DotRight <= 0.f && (DotLeft <= 0.f || !UseTwoPlanes))
{
Indexes.Emplace(i);
Indexes[CurrIdx] = CurrIdx;
}
}
}
});
BrushPoints(Indexes, Add, Rebuild);
}
void APlot3D::AddFilter_ValueRange(EAxisType XType, float XMin, float XMax, EAxisType YType, float YMin, float YMax, bool Add, bool Rebuild)
{
float XValue, YValue;
TArray<float> * XArray = nullptr;
TArray<float> * YArray = nullptr;
TArray<int32> Indexes = TArray<int32>();
for (int i = 0; i < Points.Num(); ++i)
switch (XType)
{
switch (XType)
{
case EAxisType::X:
XValue = Points[i].Location.X;
break;
case EAxisType::Y:
XValue = Points[i].Location.Y;
break;
case EAxisType::Z:
XValue = Points[i].Location.Z;
break;
default:
break;
}
case EAxisType::X:
XArray = &X;
break;
case EAxisType::Y:
XArray = &Y;
break;
case EAxisType::Z:
XArray = &Z;
break;
case EAxisType::U:
XArray = &U;
break;
case EAxisType::V:
XArray = &V;
break;
case EAxisType::W:
XArray = &W;
break;
case EAxisType::LengthUVW:
XArray = &Length;
break;
default:
break;
}
switch (YType)
{
case EAxisType::X:
YArray = &X;
break;
case EAxisType::Y:
YArray = &Y;
break;
case EAxisType::Z:
YArray = &Z;
break;
case EAxisType::U:
YArray = &U;
break;
case EAxisType::V:
YArray = &V;
break;
case EAxisType::W:
YArray = &W;
break;
case EAxisType::LengthUVW:
YArray = &Length;
break;
default:
break;
}
switch (YType)
/*
Indexes.Init(-1, Points.Num());
ParallelFor(Points.Num(), [this, XArray, YArray, XMin, XMax, YMin, YMax, Add, &Indexes](int32 CurrIdx)
{
if ((*XArray)[CurrIdx] >= XMin && (*XArray)[CurrIdx] <= XMax && (*YArray)[CurrIdx] >= YMin && (*YArray)[CurrIdx] <= YMax)
{
case EAxisType::U:
YValue = U[i];
break;
case EAxisType::V:
YValue = V[i];
break;
case EAxisType::W:
YValue = W[i];
break;
default:
break;
Indexes[CurrIdx] = CurrIdx;
}
});*/
if (XValue >= XMin && XValue <= XMax && YValue >= YMin && YValue <= YMax)
for (int i = 0; i < Points.Num(); ++i)
{
if ((*XArray)[i] >= XMin && (*XArray)[i] <= XMax && (*YArray)[i] >= YMin && (*YArray)[i] <= YMax)
{
Indexes.Emplace(i);
}
......@@ -256,14 +314,24 @@ void APlot3D::AddFilter_Box(FTransform Transform, FVector Extent, bool Add, bool
{
TArray<int32> Indexes = TArray<int32>();
for (int i = 0; i < Points.Num(); ++i)
/*for (int i = 0; i < Points.Num(); ++i)
{
FVector WorldLoc = CalculateWorldLocOfPoint(&Points[i]);
if (UKismetMathLibrary::IsPointInBoxWithTransform(WorldLoc, Transform, Extent))
{
Indexes.Emplace(i);
}
}
}*/
Indexes.Init(-1, Points.Num());
ParallelFor(Points.Num(), [this, Transform, Extent, Add, &Indexes](int32 CurrIdx)
{
FVector WorldLoc = CalculateWorldLocOfPoint(&Points[CurrIdx]);
if (UKismetMathLibrary::IsPointInBoxWithTransform(WorldLoc, Transform, Extent))
{
Indexes[CurrIdx] = CurrIdx;
}
});
BrushPoints(Indexes, Add, Rebuild);
}
......@@ -272,14 +340,24 @@ void APlot3D::AddFilter_Sphere(FVector Location, float Radius, bool Add, bool Re
{
TArray<int32> Indexes = TArray<int32>();
for (int i = 0; i < Points.Num(); ++i)
/*for (int i = 0; i < Points.Num(); ++i)
{
FVector WorldLoc = CalculateWorldLocOfPoint(&Points[i]);
if ((Location - WorldLoc).Size() <= Radius)
{
Indexes.Emplace(i);
}
}
}*/
Indexes.Init(-1, Points.Num());
ParallelFor(Points.Num(), [this, Location, Radius, Add, &Indexes](int32 CurrIdx)
{
FVector WorldLoc = CalculateWorldLocOfPoint(&Points[CurrIdx]);
if ((Location - WorldLoc).Size() <= Radius)
{
Indexes[CurrIdx] = CurrIdx;
}
});
BrushPoints(Indexes, Add, Rebuild);
}
......
......@@ -45,16 +45,28 @@ public:
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadOnly)
TArray<FPointCloudPoint> Points;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadOnly)
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> X;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> Y;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> Z;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<FVector> Color;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> U;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadOnly)
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> V;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadOnly)
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> W;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadOnly)
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadWrite)
TArray<float> Length;
UPROPERTY(Category = Plot3D, VisibleAnywhere, BlueprintReadOnly)
......
......@@ -72,6 +72,38 @@ void UPlotCanvas::DrawFromData()
UpdateCanvas();
}
void UPlotCanvas::DrawParallelCoordinatesPlot()
{
APawn* Pawn = UGameplayStatics::GetPlayerPawn(this, 0);
APawnBase* PawnBase = Cast<APawnBase>(Pawn);
for (int i = 0; i < PawnBase->Plot3D->Points.Num(); ++i)
{
int32 x0 = 0;
int32 x1 = canvasWidth * 1 / 5;
int32 x2 = canvasWidth * 2 / 5;
int32 x3 = canvasWidth * 3 / 5;
int32 x4 = canvasWidth * 4 / 5;
int32 x5 = canvasWidth;
int32 y0 = (PawnBase->Plot3D->Points[i].Location.X - PawnBase->Plot3D->MinX) / (PawnBase->Plot3D->MaxX - PawnBase->Plot3D->MinX) * canvasHeight / 4;
int32 y1 = (PawnBase->Plot3D->Points[i].Location.Y - PawnBase->Plot3D->MinY) / (PawnBase->Plot3D->MaxY - PawnBase->Plot3D->MinY) * canvasHeight / 4;
int32 y2 = (PawnBase->Plot3D->Points[i].Location.Z - PawnBase->Plot3D->MinZ) / (PawnBase->Plot3D->MaxZ - PawnBase->Plot3D->MinZ) * canvasHeight / 4;
int32 y3 = (PawnBase->Plot3D->U[i] - PawnBase->Plot3D->MinU) / (PawnBase->Plot3D->MaxU - PawnBase->Plot3D->MinU) * canvasHeight / 4;
int32 y4 = (PawnBase->Plot3D->V[i] - PawnBase->Plot3D->MinV) / (PawnBase->Plot3D->MaxV - PawnBase->Plot3D->MinV) * canvasHeight / 4;
int32 y5 = (PawnBase->Plot3D->W[i] - PawnBase->Plot3D->MinW) / (PawnBase->Plot3D->MaxW - PawnBase->Plot3D->MinW) * canvasHeight / 4;
uint8 r = PawnBase->Plot3D->Points[i].Color.R;
uint8 g = PawnBase->Plot3D->Points[i].Color.G;
uint8 b = PawnBase->Plot3D->Points[i].Color.B;
DrawLine(x0, y0, x1, y1, r, g, b, 255);
DrawLine(x1, y1, x2, y2, r, g, b, 255);
DrawLine(x2, y2, x3, y3, r, g, b, 255);
DrawLine(x3, y3, x4, y4, r, g, b, 255);
DrawLine(x4, y4, x5, y5, r, g, b, 255);
}
UpdateCanvas();
}
void UPlotCanvas::DrawDot(const int32 pixelCoordX, const int32 pixelCoordY)
{
uint8* canvasPixelPtr = canvasPixelData.get();
......@@ -88,16 +120,21 @@ void UPlotCanvas::DrawDot(const int32 pixelCoordX, const int32 pixelCoordY)
{
int32 tx = pixelCoordX + px;
int32 ty = pixelCoordY + py;
if (tx >= 0 && tx < canvasWidth && ty >= 0 && ty < canvasHeight)
{
canvasPixelPtr = canvasPixelData.get() + (tx + ty * canvasWidth) * bytesPerPixel;
setPixelColor(canvasPixelPtr, *(canvasBrushPixelPtr + 2), *(canvasBrushPixelPtr + 1), *(canvasBrushPixelPtr), *(canvasBrushPixelPtr + 3));
}
DrawPixel(tx, ty, *(canvasBrushPixelPtr + 2), *(canvasBrushPixelPtr + 1), *(canvasBrushPixelPtr), *(canvasBrushPixelPtr + 3));
}
}
}
}
void UPlotCanvas::DrawPixel(const int32 x, const int32 y, const uint8 r, const uint8 g, const uint8 b, const uint8 a)
{
if (x >= 0 && x < canvasWidth && y >= 0 && y < canvasHeight)
{
uint8* canvasPixelPtr = canvasPixelData.get() + (x + y * canvasWidth) * bytesPerPixel;
setPixelColor(canvasPixelPtr, r, g, b, a);
}
}
void UPlotCanvas::ClearCanvas()
{
uint8* canvasPixelPtr = canvasPixelData.get();
......@@ -123,4 +160,49 @@ void UPlotCanvas::setPixelColor(uint8*& pointer, uint8 red, uint8 green, uint8 b
*(pointer + 1) = green; //g
*(pointer + 2) = red; //r
*(pointer + 3) = alpha; //a
}
void UPlotCanvas::DrawLine(int32 x1, int32 y1, int32 x2, int32 y2, const uint8 r, const uint8 g, const uint8 b, const uint8 a)
{
// Bresenham's line algorithm
const bool steep = (fabs(y2 - y1) > fabs(x2 - x1));
if (steep)
{
std::swap(x1, y1);
std::swap(x2, y2);
}
if (x1 > x2)
{
std::swap(x1, x2);
std::swap(y1, y2);
}
const float dx = x2 - x1;
const float dy = fabs(y2 - y1);
float error = dx / 2.0f;
const int ystep = (y1 < y2) ? 1 : -1;
int y = (int)y1;
const int maxX = (int)x2;
for (int x = (int)x1; x < maxX; x++)
{
if (steep)
{
DrawPixel(y, x, r, g, b, a);
}
else
{
DrawPixel(x, y, r, g, b, a);
}
error -= dy;
if (error < 0)
{
y += ystep;
error += dx;
}
}
}
\ No newline at end of file
......@@ -34,9 +34,18 @@ public:
UFUNCTION(BlueprintCallable, Category = DrawingTools)
void DrawFromData();
UFUNCTION(BlueprintCallable, Category = DrawingTools)
void DrawParallelCoordinatesPlot();
UFUNCTION(BlueprintCallable, Category = DrawingTools)
void DrawDot(const int32 pixelCoordX, const int32 pixelCoordY);
UFUNCTION(BlueprintCallable, Category = DrawingTools)
void DrawPixel(const int32 x, const int32 y, const uint8 r, const uint8 g, const uint8 b, const uint8 a);
UFUNCTION(BlueprintCallable)
void DrawLine(int32 x1, int32 y1, int32 x2, int32 y2, const uint8 r, const uint8 g, const uint8 b, const uint8 a);
private:
// canvas
......
......@@ -26,7 +26,7 @@ void UPlotRenderTarget::OnUpdate(UCanvas * Canvas, int32 Width, int32 Height)
for (int i = 0; i < PawnBase->Plot3D->Points.Num(); ++i)
{
FVector2D Location = FVector2D(PawnBase->Plot3D->Points[i].Location.X * 10000 + Width / 2, PawnBase->Plot3D->U[i] * 5 + Height / 2);
FVector2D LocationB = Location + FVector2D(0, 100);
FVector2D LocationB = Location + FVector2D(0, 1);
/*
* Still not fast enough. Using other way to draw the graph.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment