Merge branch 'main' of https://gitlab.com/jeseibel/distant-horizons-core
This commit is contained in:
+10
-6
@@ -114,14 +114,18 @@ public class FullDataArrayAccessor implements IFullDataAccessor
|
||||
{
|
||||
for (int z = 0; z < this.width; z++)
|
||||
{
|
||||
long[] sourceData = this.dataArrays[this.offset + x * this.dataWidth + z];
|
||||
long[] newData = new long[sourceData.length];
|
||||
for (int dataPointIndex = 0; dataPointIndex < newData.length; dataPointIndex++)
|
||||
long[] currentData = this.dataArrays[this.offset + x * this.dataWidth + z];
|
||||
// may be null if no data exists for this column yet
|
||||
if (currentData != null)
|
||||
{
|
||||
newData[dataPointIndex] = FullDataPointUtil.remap(remappedIds, sourceData[dataPointIndex]);
|
||||
long[] newData = new long[currentData.length]; // TODO what to do if null?
|
||||
for (int dataPointIndex = 0; dataPointIndex < newData.length; dataPointIndex++)
|
||||
{
|
||||
newData[dataPointIndex] = FullDataPointUtil.remap(remappedIds, currentData[dataPointIndex]);
|
||||
}
|
||||
|
||||
target.dataArrays[target.offset + x * target.dataWidth + z] = newData;
|
||||
}
|
||||
|
||||
target.dataArrays[target.offset + x * target.dataWidth + z] = newData;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+6
-7
@@ -28,8 +28,7 @@ import com.seibel.distanthorizons.core.util.objects.dataStreams.DhDataInputStrea
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.*;
|
||||
import java.util.concurrent.locks.ReadWriteLock;
|
||||
import java.util.concurrent.locks.ReentrantReadWriteLock;
|
||||
import java.util.concurrent.locks.ReentrantLock;
|
||||
|
||||
public abstract class AbstractFullDataSourceLoader
|
||||
{
|
||||
@@ -46,7 +45,7 @@ public abstract class AbstractFullDataSourceLoader
|
||||
|
||||
/** used when pooling data sources */
|
||||
private final ArrayList<IFullDataSource> cachedSources = new ArrayList<>();
|
||||
private final ReadWriteLock cacheReadWriteLock = new ReentrantReadWriteLock();
|
||||
private final ReentrantLock cacheLock = new ReentrantLock();
|
||||
|
||||
|
||||
|
||||
@@ -159,7 +158,7 @@ public abstract class AbstractFullDataSourceLoader
|
||||
{
|
||||
try
|
||||
{
|
||||
this.cacheReadWriteLock.readLock().lock();
|
||||
this.cacheLock.lock();
|
||||
|
||||
int index = this.cachedSources.size() - 1;
|
||||
if (index == -1)
|
||||
@@ -173,7 +172,7 @@ public abstract class AbstractFullDataSourceLoader
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.cacheReadWriteLock.readLock().unlock();
|
||||
this.cacheLock.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -198,12 +197,12 @@ public abstract class AbstractFullDataSourceLoader
|
||||
|
||||
try
|
||||
{
|
||||
this.cacheReadWriteLock.writeLock().lock();
|
||||
this.cacheLock.lock();
|
||||
this.cachedSources.add(dataSource);
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.cacheReadWriteLock.writeLock().unlock();
|
||||
this.cacheLock.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+3
@@ -297,6 +297,8 @@ public class CompleteFullDataSource extends FullDataArrayAccessor implements IFu
|
||||
|
||||
@Override
|
||||
public SingleColumnFullDataAccessor tryGet(int relativeX, int relativeZ) { return this.get(relativeX, relativeZ); }
|
||||
@Override
|
||||
public SingleColumnFullDataAccessor getOrCreate(int relativeX, int relativeZ) { return this.get(relativeX, relativeZ); }
|
||||
|
||||
@Override
|
||||
public void update(ChunkSizedFullDataAccessor chunkDataView)
|
||||
@@ -461,6 +463,7 @@ public class CompleteFullDataSource extends FullDataArrayAccessor implements IFu
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() { return this.isEmpty; }
|
||||
@Override
|
||||
public void markNotEmpty() { this.isEmpty = false; }
|
||||
|
||||
@Override
|
||||
|
||||
+22
-125
@@ -410,18 +410,31 @@ public class HighDetailIncompleteFullDataSource implements IIncompleteFullDataSo
|
||||
// data //
|
||||
//======//
|
||||
|
||||
public SingleColumnFullDataAccessor tryGet(int relativeX, int relativeZ)
|
||||
@Override
|
||||
public SingleColumnFullDataAccessor tryGet(int relativeX, int relativeZ) { return this.tryGetOrCreate(relativeX, relativeZ, false); }
|
||||
@Override
|
||||
public SingleColumnFullDataAccessor getOrCreate(int relativeX, int relativeZ) { return this.tryGetOrCreate(relativeX, relativeZ, true); }
|
||||
private SingleColumnFullDataAccessor tryGetOrCreate(int relativeX, int relativeZ, boolean createIfMissing)
|
||||
{
|
||||
LodUtil.assertTrue(relativeX >= 0 && relativeX < SECTION_SIZE && relativeZ >= 0 && relativeZ < SECTION_SIZE);
|
||||
int chunkX = relativeX / this.dataPointsPerSection;
|
||||
int chunkZ = relativeZ / this.dataPointsPerSection;
|
||||
FullDataArrayAccessor chunk = this.sparseData[chunkX * this.sectionCount + chunkZ];
|
||||
if (chunk == null)
|
||||
FullDataArrayAccessor accessor = this.sparseData[chunkX * this.sectionCount + chunkZ];
|
||||
if (accessor == null)
|
||||
{
|
||||
return null;
|
||||
if (createIfMissing)
|
||||
{
|
||||
// create the missing data so the following get() will succeed
|
||||
accessor = new FullDataArrayAccessor(this.mapping, new long[this.dataPointsPerSection * this.dataPointsPerSection][], this.dataPointsPerSection);
|
||||
this.sparseData[chunkX * this.sectionCount + chunkZ] = accessor;
|
||||
}
|
||||
else
|
||||
{
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
return chunk.get(relativeX % this.dataPointsPerSection, relativeZ % this.dataPointsPerSection);
|
||||
return accessor.get(relativeX % this.dataPointsPerSection, relativeZ % this.dataPointsPerSection);
|
||||
}
|
||||
|
||||
|
||||
@@ -470,6 +483,8 @@ public class HighDetailIncompleteFullDataSource implements IIncompleteFullDataSo
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() { return this.isEmpty; }
|
||||
@Override
|
||||
public void markNotEmpty() { this.isEmpty = false; }
|
||||
|
||||
@Override
|
||||
public int getWidthInDataPoints() { return SECTION_SIZE; }
|
||||
@@ -520,121 +535,6 @@ public class HighDetailIncompleteFullDataSource implements IIncompleteFullDataSo
|
||||
|
||||
// data sampling //
|
||||
|
||||
@Override
|
||||
public void sampleFrom(IFullDataSource fullDataSource)
|
||||
{
|
||||
DhSectionPos pos = fullDataSource.getSectionPos();
|
||||
LodUtil.assertTrue(pos.getDetailLevel() < this.sectionPos.getDetailLevel());
|
||||
LodUtil.assertTrue(pos.overlapsExactly(this.sectionPos));
|
||||
if (fullDataSource.isEmpty())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if (fullDataSource instanceof CompleteFullDataSource)
|
||||
{
|
||||
this.sampleFrom((CompleteFullDataSource) fullDataSource);
|
||||
}
|
||||
else if (fullDataSource instanceof HighDetailIncompleteFullDataSource)
|
||||
{
|
||||
this.sampleFrom((HighDetailIncompleteFullDataSource) fullDataSource);
|
||||
}
|
||||
else if (fullDataSource instanceof LowDetailIncompleteFullDataSource)
|
||||
{
|
||||
// this.sampleFrom((LowDetailIncompleteFullDataSource) fullDataSource);
|
||||
LodUtil.assertNotReach("SampleFrom not implemented for [" + IFullDataSource.class.getSimpleName() + "] with class [" + fullDataSource.getClass().getSimpleName() + "].");
|
||||
}
|
||||
else
|
||||
{
|
||||
LodUtil.assertNotReach("SampleFrom not implemented for [" + IFullDataSource.class.getSimpleName() + "] with class [" + fullDataSource.getClass().getSimpleName() + "].");
|
||||
}
|
||||
}
|
||||
|
||||
private void sampleFrom(CompleteFullDataSource completeDataSource)
|
||||
{
|
||||
DhSectionPos pos = completeDataSource.getSectionPos();
|
||||
this.isEmpty = false;
|
||||
|
||||
DhLodPos basePos = this.sectionPos.getMinCornerLodPos(SPARSE_UNIT_DETAIL);
|
||||
DhLodPos dataPos = pos.getMinCornerLodPos(SPARSE_UNIT_DETAIL);
|
||||
|
||||
int coveredChunks = pos.getWidthCountForLowerDetailedSection(SPARSE_UNIT_DETAIL);
|
||||
int sourceDataPerChunk = SPARSE_UNIT_SIZE >>> completeDataSource.getDataDetailLevel();
|
||||
LodUtil.assertTrue((coveredChunks * sourceDataPerChunk) == CompleteFullDataSource.WIDTH);
|
||||
|
||||
int xDataOffset = dataPos.x - basePos.x;
|
||||
int zDataOffset = dataPos.z - basePos.z;
|
||||
LodUtil.assertTrue(xDataOffset >= 0 && xDataOffset < this.sectionCount && zDataOffset >= 0 && zDataOffset < this.sectionCount);
|
||||
|
||||
for (int xOffset = 0; xOffset < coveredChunks; xOffset++)
|
||||
{
|
||||
for (int zOffset = 0; zOffset < coveredChunks; zOffset++)
|
||||
{
|
||||
FullDataArrayAccessor sourceChunk = completeDataSource.subView(sourceDataPerChunk, xOffset * sourceDataPerChunk, zOffset * sourceDataPerChunk);
|
||||
FullDataArrayAccessor newFullDataAccessor = new FullDataArrayAccessor(this.mapping, new long[this.dataPointsPerSection * this.dataPointsPerSection][], this.dataPointsPerSection);
|
||||
newFullDataAccessor.downsampleFrom(sourceChunk);
|
||||
this.sparseData[(xOffset + xDataOffset) * this.sectionCount + (zOffset + zDataOffset)] = newFullDataAccessor;
|
||||
}
|
||||
}
|
||||
}
|
||||
private void sampleFrom(HighDetailIncompleteFullDataSource sparseDataSource)
|
||||
{
|
||||
DhSectionPos pos = sparseDataSource.getSectionPos();
|
||||
this.isEmpty = false;
|
||||
|
||||
DhLodPos basePos = this.sectionPos.getMinCornerLodPos(SPARSE_UNIT_DETAIL);
|
||||
DhLodPos dataPos = pos.getMinCornerLodPos(SPARSE_UNIT_DETAIL);
|
||||
|
||||
int offsetX = dataPos.x - basePos.x;
|
||||
int offsetZ = dataPos.z - basePos.z;
|
||||
LodUtil.assertTrue(offsetX >= 0 && offsetX < this.sectionCount && offsetZ >= 0 && offsetZ < this.sectionCount);
|
||||
|
||||
for (int xOffset = 0; xOffset < sparseDataSource.sectionCount; xOffset++)
|
||||
{
|
||||
for (int zOffset = 0; zOffset < sparseDataSource.sectionCount; zOffset++)
|
||||
{
|
||||
FullDataArrayAccessor sourceChunk = sparseDataSource.sparseData[xOffset * sparseDataSource.sectionCount + zOffset];
|
||||
if (sourceChunk != null)
|
||||
{
|
||||
FullDataArrayAccessor newFullDataAccessor = new FullDataArrayAccessor(this.mapping, new long[this.dataPointsPerSection * this.dataPointsPerSection][], this.dataPointsPerSection);
|
||||
newFullDataAccessor.downsampleFrom(sourceChunk);
|
||||
this.sparseData[(xOffset + offsetX) * this.sectionCount + (zOffset + offsetZ)] = newFullDataAccessor;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
private void sampleFrom(LowDetailIncompleteFullDataSource spottyDataSource)
|
||||
{
|
||||
// TODO implement
|
||||
|
||||
// DhSectionPos pos = spottyDataSource.getSectionPos();
|
||||
// this.isEmpty = false;
|
||||
//
|
||||
// DhLodPos basePos = this.sectionPos.getCorner(SPARSE_UNIT_DETAIL);
|
||||
// DhLodPos dataPos = pos.getCorner(SPARSE_UNIT_DETAIL);
|
||||
//
|
||||
// int coveredChunks = pos.getWidth(SPARSE_UNIT_DETAIL).numberOfLodSectionsWide;
|
||||
// int sourceDataPerChunk = SPARSE_UNIT_SIZE >>> spottyDataSource.getDataDetailLevel();
|
||||
// LodUtil.assertTrue((coveredChunks * sourceDataPerChunk) == CompleteFullDataSource.WIDTH);
|
||||
//
|
||||
// int xDataOffset = dataPos.x - basePos.x;
|
||||
// int zDataOffset = dataPos.z - basePos.z;
|
||||
// LodUtil.assertTrue(xDataOffset >= 0 && xDataOffset < this.sectionCount && zDataOffset >= 0 && zDataOffset < this.sectionCount);
|
||||
//
|
||||
// for (int xOffset = 0; xOffset < coveredChunks; xOffset++)
|
||||
// {
|
||||
// for (int zOffset = 0; zOffset < coveredChunks; zOffset++)
|
||||
// {
|
||||
// FullDataArrayAccessor sourceChunk = spottyDataSource.subView(sourceDataPerChunk, xOffset * sourceDataPerChunk, zOffset * sourceDataPerChunk);
|
||||
// FullDataArrayAccessor newFullDataAccessor = new FullDataArrayAccessor(this.mapping, new long[this.dataPointsPerSection * this.dataPointsPerSection][], this.dataPointsPerSection);
|
||||
// newFullDataAccessor.downsampleFrom(sourceChunk);
|
||||
// this.sparseData[(xOffset + xDataOffset) * this.sectionCount + (zOffset + zDataOffset)] = newFullDataAccessor;
|
||||
// }
|
||||
// }
|
||||
}
|
||||
|
||||
|
||||
private void applyToFullDataSource(CompleteFullDataSource dataSource)
|
||||
{
|
||||
LodUtil.assertTrue(dataSource.getSectionPos().equals(this.sectionPos));
|
||||
@@ -670,16 +570,13 @@ public class HighDetailIncompleteFullDataSource implements IIncompleteFullDataSo
|
||||
return this;
|
||||
}
|
||||
}
|
||||
isPromoted = true;
|
||||
this.isPromoted = true;
|
||||
CompleteFullDataSource fullDataSource = CompleteFullDataSource.createEmpty(this.sectionPos);
|
||||
this.applyToFullDataSource(fullDataSource);
|
||||
return fullDataSource;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasBeenPromoted()
|
||||
{
|
||||
return isPromoted;
|
||||
}
|
||||
public boolean hasBeenPromoted() { return this.isPromoted; }
|
||||
|
||||
}
|
||||
|
||||
+21
-170
@@ -284,7 +284,23 @@ public class LowDetailIncompleteFullDataSource extends FullDataArrayAccessor imp
|
||||
//======//
|
||||
|
||||
@Override
|
||||
public SingleColumnFullDataAccessor tryGet(int relativeX, int relativeZ) { return this.isColumnNotEmpty.get(relativeX * WIDTH + relativeZ) ? this.get(relativeX, relativeZ) : null; }
|
||||
public SingleColumnFullDataAccessor tryGet(int relativeX, int relativeZ) { return this.tryGetOrCreate(relativeX, relativeZ, false); }
|
||||
@Override
|
||||
public SingleColumnFullDataAccessor getOrCreate(int relativeX, int relativeZ) { return this.tryGetOrCreate(relativeX, relativeZ, true); }
|
||||
private SingleColumnFullDataAccessor tryGetOrCreate(int relativeX, int relativeZ, boolean createIfMissing)
|
||||
{
|
||||
int notEmptyIndex = relativeX * WIDTH + relativeZ;
|
||||
boolean columnEmpty = this.isColumnNotEmpty.get(notEmptyIndex);
|
||||
|
||||
// "create" the missing column if necessary
|
||||
if (columnEmpty && createIfMissing)
|
||||
{
|
||||
this.isColumnNotEmpty.set(notEmptyIndex, true);
|
||||
columnEmpty = false;
|
||||
}
|
||||
|
||||
return !columnEmpty ? this.get(relativeX, relativeZ) : null;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -314,6 +330,7 @@ public class LowDetailIncompleteFullDataSource extends FullDataArrayAccessor imp
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() { return this.isEmpty; }
|
||||
@Override
|
||||
public void markNotEmpty() { this.isEmpty = false; }
|
||||
|
||||
@Override
|
||||
@@ -359,170 +376,6 @@ public class LowDetailIncompleteFullDataSource extends FullDataArrayAccessor imp
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void sampleFrom(IFullDataSource fullDataSource)
|
||||
{
|
||||
DhSectionPos pos = fullDataSource.getSectionPos();
|
||||
LodUtil.assertTrue(pos.getDetailLevel() < this.sectionPos.getDetailLevel());
|
||||
LodUtil.assertTrue(pos.overlapsExactly(this.sectionPos));
|
||||
|
||||
if (fullDataSource.isEmpty())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if (fullDataSource instanceof CompleteFullDataSource)
|
||||
{
|
||||
this.sampleFrom((CompleteFullDataSource) fullDataSource);
|
||||
}
|
||||
else if (fullDataSource instanceof HighDetailIncompleteFullDataSource)
|
||||
{
|
||||
this.sampleFrom((HighDetailIncompleteFullDataSource) fullDataSource);
|
||||
}
|
||||
else if (fullDataSource instanceof LowDetailIncompleteFullDataSource)
|
||||
{
|
||||
this.sampleFrom((LowDetailIncompleteFullDataSource) fullDataSource);
|
||||
// LodUtil.assertNotReach("SampleFrom not implemented for ["+IFullDataSource.class.getSimpleName()+"] with class ["+fullDataSource.getClass().getSimpleName()+"].");
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO implement
|
||||
LodUtil.assertNotReach("SampleFrom not implemented for [" + this.getClass().getSimpleName() + "] with class [" + fullDataSource.getClass().getSimpleName() + "].");
|
||||
}
|
||||
}
|
||||
|
||||
private void sampleFrom(HighDetailIncompleteFullDataSource sparseSource)
|
||||
{
|
||||
DhLodPos thisLodPos = this.sectionPos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
DhSectionPos pos = sparseSource.getSectionPos();
|
||||
|
||||
this.isEmpty = false;
|
||||
|
||||
if (this.getDataDetailLevel() > this.sectionPos.getDetailLevel())
|
||||
{
|
||||
DhLodPos dataLodPos = pos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
|
||||
int offsetX = dataLodPos.x - thisLodPos.x;
|
||||
int offsetZ = dataLodPos.z - thisLodPos.z;
|
||||
LodUtil.assertTrue(offsetX >= 0 && offsetX < WIDTH && offsetZ >= 0 && offsetZ < WIDTH);
|
||||
|
||||
int chunksPerData = 1 << (this.getDataDetailLevel() - HighDetailIncompleteFullDataSource.SPARSE_UNIT_DETAIL);
|
||||
int dataSpan = this.sectionPos.getWidthCountForLowerDetailedSection(this.getDataDetailLevel());
|
||||
|
||||
for (int xOffset = 0; xOffset < dataSpan; xOffset++)
|
||||
{
|
||||
for (int zOffset = 0; zOffset < dataSpan; zOffset++)
|
||||
{
|
||||
SingleColumnFullDataAccessor column = sparseSource.tryGet(
|
||||
xOffset * chunksPerData * sparseSource.dataPointsPerSection,
|
||||
zOffset * chunksPerData * sparseSource.dataPointsPerSection);
|
||||
|
||||
if (column != null)
|
||||
{
|
||||
column.deepCopyTo(this.get(offsetX + xOffset, offsetZ + zOffset));
|
||||
this.isColumnNotEmpty.set((offsetX + xOffset) * WIDTH + offsetZ + zOffset, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
DhLodPos dataLodPos = pos.getSectionBBoxPos();
|
||||
int lowerSectionsPerData = this.sectionPos.getWidthCountForLowerDetailedSection(dataLodPos.detailLevel);
|
||||
if (dataLodPos.x % lowerSectionsPerData != 0 || dataLodPos.z % lowerSectionsPerData != 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
dataLodPos = dataLodPos.convertToDetailLevel(this.getDataDetailLevel());
|
||||
int offsetX = dataLodPos.x - thisLodPos.x;
|
||||
int offsetZ = dataLodPos.z - thisLodPos.z;
|
||||
|
||||
SingleColumnFullDataAccessor column = sparseSource.tryGet(0, 0);
|
||||
if (column != null)
|
||||
{
|
||||
column.deepCopyTo(this.get(offsetX, offsetZ));
|
||||
this.isColumnNotEmpty.set(offsetX * WIDTH + offsetZ, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void sampleFrom(CompleteFullDataSource inputSource)
|
||||
{
|
||||
DhSectionPos inputPos = inputSource.getSectionPos();
|
||||
this.isEmpty = false;
|
||||
|
||||
|
||||
DhLodPos baseOffset = this.sectionPos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
DhSectionPos inputOffset = inputPos.convertNewToDetailLevel(this.getDataDetailLevel());
|
||||
int offsetX = inputOffset.getX() - baseOffset.x;
|
||||
int offsetZ = inputOffset.getZ() - baseOffset.z;
|
||||
|
||||
|
||||
int numberOfDataPointsToUpdate = WIDTH / this.sectionPos.getWidthCountForLowerDetailedSection(inputSource.getSectionPos().getDetailLevel()); // can be 0 if the input source is significantly smaller than this data source
|
||||
// should be 1 at minimum, to prevent divide by zero errors (and because trying to get 0 data points doesn't make any sense)
|
||||
numberOfDataPointsToUpdate = Math.max(1, numberOfDataPointsToUpdate);
|
||||
|
||||
|
||||
int inputFractionWidth = inputSource.width() / numberOfDataPointsToUpdate;
|
||||
for (int x = 0; x < numberOfDataPointsToUpdate; x++)
|
||||
{
|
||||
for (int z = 0; z < numberOfDataPointsToUpdate; z++)
|
||||
{
|
||||
SingleColumnFullDataAccessor thisDataColumn = this.get(offsetX + x, offsetZ + z);
|
||||
SingleColumnFullDataAccessor inputDataColumn = inputSource.get(inputFractionWidth * x, inputFractionWidth * z);
|
||||
inputDataColumn.deepCopyTo(thisDataColumn);
|
||||
|
||||
int notEmptyIndex = (offsetX + x) * WIDTH + (offsetZ + z);
|
||||
this.isColumnNotEmpty.set(notEmptyIndex, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void sampleFrom(LowDetailIncompleteFullDataSource spottySource)
|
||||
{
|
||||
DhSectionPos pos = spottySource.getSectionPos();
|
||||
this.isEmpty = false;
|
||||
this.downsampleFrom(spottySource);
|
||||
|
||||
|
||||
if (this.getDataDetailLevel() > this.sectionPos.getDetailLevel())
|
||||
{
|
||||
DhLodPos thisLodPos = this.sectionPos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
DhLodPos dataLodPos = pos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
|
||||
int offsetX = dataLodPos.x - thisLodPos.x;
|
||||
int offsetZ = dataLodPos.z - thisLodPos.z;
|
||||
int dataWidth = this.sectionPos.getWidthCountForLowerDetailedSection(this.getDataDetailLevel());
|
||||
|
||||
for (int xOffset = 0; xOffset < dataWidth; xOffset++)
|
||||
{
|
||||
for (int zOffset = 0; zOffset < dataWidth; zOffset++)
|
||||
{
|
||||
this.isColumnNotEmpty.set((offsetX + xOffset) * WIDTH + offsetZ + zOffset, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
DhLodPos dataPos = pos.getSectionBBoxPos();
|
||||
int lowerSectionsPerData = this.sectionPos.getWidthCountForLowerDetailedSection(dataPos.detailLevel);
|
||||
if (dataPos.x % lowerSectionsPerData != 0 || dataPos.z % lowerSectionsPerData != 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
DhLodPos basePos = this.sectionPos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
dataPos = dataPos.convertToDetailLevel(this.getDataDetailLevel());
|
||||
int offsetX = dataPos.x - basePos.x;
|
||||
int offsetZ = dataPos.z - basePos.z;
|
||||
this.isColumnNotEmpty.set(offsetX * WIDTH + offsetZ, true);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public IFullDataSource tryPromotingToCompleteDataSource()
|
||||
{
|
||||
@@ -535,15 +388,13 @@ public class LowDetailIncompleteFullDataSource extends FullDataArrayAccessor imp
|
||||
{
|
||||
return this;
|
||||
}
|
||||
isPromoted = true;
|
||||
this.isPromoted = true;
|
||||
return new CompleteFullDataSource(this.sectionPos, this.mapping, this.dataArrays);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasBeenPromoted()
|
||||
{
|
||||
return isPromoted;
|
||||
}
|
||||
public boolean hasBeenPromoted() { return this.isPromoted; }
|
||||
|
||||
|
||||
|
||||
//================//
|
||||
|
||||
+6
@@ -69,6 +69,7 @@ public interface IFullDataSource
|
||||
void update(ChunkSizedFullDataAccessor data);
|
||||
|
||||
boolean isEmpty();
|
||||
void markNotEmpty();
|
||||
|
||||
/** AKA; the max relative position that {@link IFullDataSource#tryGet(int, int)} can accept for either X or Z */
|
||||
int getWidthInDataPoints();
|
||||
@@ -85,6 +86,11 @@ public interface IFullDataSource
|
||||
* @return null if the data doesn't exist
|
||||
*/
|
||||
SingleColumnFullDataAccessor tryGet(int relativeX, int relativeZ);
|
||||
/**
|
||||
* Attempts to get the data column for the given relative x and z position. <br>
|
||||
* If no data exists yet an empty data column will be created.
|
||||
*/
|
||||
SingleColumnFullDataAccessor getOrCreate(int relativeX, int relativeZ);
|
||||
|
||||
FullDataPointIdMap getMapping();
|
||||
|
||||
|
||||
+45
-1
@@ -19,7 +19,11 @@
|
||||
|
||||
package com.seibel.distanthorizons.core.dataObjects.fullData.sources.interfaces;
|
||||
|
||||
import com.seibel.distanthorizons.core.dataObjects.fullData.accessor.SingleColumnFullDataAccessor;
|
||||
import com.seibel.distanthorizons.core.dataObjects.fullData.sources.CompleteFullDataSource;
|
||||
import com.seibel.distanthorizons.core.pos.DhLodPos;
|
||||
import com.seibel.distanthorizons.core.pos.DhSectionPos;
|
||||
import com.seibel.distanthorizons.core.util.LodUtil;
|
||||
|
||||
public interface IIncompleteFullDataSource extends IFullDataSource
|
||||
{
|
||||
@@ -28,7 +32,47 @@ public interface IIncompleteFullDataSource extends IFullDataSource
|
||||
*
|
||||
* This can be used to either merge same sized data sources or downsample to
|
||||
*/
|
||||
void sampleFrom(IFullDataSource fullDataSource);
|
||||
default void sampleFrom(IFullDataSource inputSource)
|
||||
{
|
||||
DhSectionPos inputPos = inputSource.getSectionPos();
|
||||
DhSectionPos thisPos = this.getSectionPos();
|
||||
LodUtil.assertTrue(inputPos.getDetailLevel() < thisPos.getDetailLevel());
|
||||
LodUtil.assertTrue(inputPos.overlapsExactly(this.getSectionPos()));
|
||||
|
||||
if (inputSource.isEmpty())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
this.markNotEmpty();
|
||||
|
||||
DhLodPos baseOffset = thisPos.getMinCornerLodPos(this.getDataDetailLevel());
|
||||
DhSectionPos inputOffset = inputPos.convertNewToDetailLevel(this.getDataDetailLevel());
|
||||
int offsetX = inputOffset.getX() - baseOffset.x;
|
||||
int offsetZ = inputOffset.getZ() - baseOffset.z;
|
||||
|
||||
|
||||
int numberOfDataPointsToUpdate = this.getWidthInDataPoints() / thisPos.getWidthCountForLowerDetailedSection(inputSource.getSectionPos().getDetailLevel()); // can be 0 if the input source is significantly smaller than this data source
|
||||
// should be 1 at minimum, to prevent divide by zero errors (and because trying to get 0 or a fractional data point doesn't make any sense)
|
||||
numberOfDataPointsToUpdate = Math.max(1, numberOfDataPointsToUpdate);
|
||||
|
||||
|
||||
int inputFractionWidth = inputSource.getWidthInDataPoints() / numberOfDataPointsToUpdate;
|
||||
for (int x = 0; x < numberOfDataPointsToUpdate; x++)
|
||||
{
|
||||
for (int z = 0; z < numberOfDataPointsToUpdate; z++)
|
||||
{
|
||||
SingleColumnFullDataAccessor thisDataColumn = this.getOrCreate(offsetX + x, offsetZ + z);
|
||||
SingleColumnFullDataAccessor inputDataColumn = inputSource.tryGet(inputFractionWidth * x, inputFractionWidth * z);
|
||||
|
||||
if (inputDataColumn != null)
|
||||
{
|
||||
inputDataColumn.deepCopyTo(thisDataColumn);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempts to convert this {@link IIncompleteFullDataSource} into a {@link CompleteFullDataSource}.
|
||||
|
||||
+2
-2
@@ -386,7 +386,7 @@ public class FullDataFileHandler implements IFullDataSourceProvider
|
||||
FullDataMetaFile existingFile = existingFiles.get(i);
|
||||
|
||||
|
||||
CompletableFuture<IFullDataSource> loadFileFuture = usePooledDataSources ? existingFile.getOrLoadCachedDataSourceAsync() : existingFile.getDataSourceWithoutCachingAsync();
|
||||
CompletableFuture<IFullDataSource> loadFileFuture = usePooledDataSources ? existingFile.getDataSourceWithoutCachingAsync() : existingFile.getOrLoadCachedDataSourceAsync();
|
||||
|
||||
CompletableFuture<IFullDataSource> sampleSourceFuture = loadFileFuture.whenComplete((existingFullDataSource, ex) ->
|
||||
{
|
||||
@@ -415,7 +415,7 @@ public class FullDataFileHandler implements IFullDataSourceProvider
|
||||
}
|
||||
|
||||
// pooling temporary data sources massively reduces garbage collector overhead when just sampling (going from ~8 GB/sec to ~90 MB/sec)
|
||||
if (!usePooledDataSources && !existingFile.cacheLoadingDataSource)
|
||||
if (usePooledDataSources && !existingFile.cacheLoadingDataSource)
|
||||
{
|
||||
existingFile.clearCachedDataSource();
|
||||
|
||||
|
||||
@@ -277,7 +277,7 @@ public class LodQuadTree extends QuadTree<LodRenderSection> implements AutoClose
|
||||
{
|
||||
// this is the detail level we want to render //
|
||||
// prepare this section for rendering
|
||||
renderSection.loadRenderSource(this.renderSourceProvider, this.level);
|
||||
renderSection.loadRenderSource(this.renderSourceProvider, this.level); // TODO this should fire for the lowest detail level first, wait for it to finish then fire the next highest to prevent waiting forever for 2 million chunk section to finish sampling everything
|
||||
|
||||
// wait for the parent to disable before enabling this section, so we don't overdraw/overlap render sections
|
||||
if (!parentRenderSectionIsEnabled && renderSection.canRenderNow())
|
||||
|
||||
@@ -333,7 +333,7 @@
|
||||
|
||||
"distanthorizons.config.client.advanced.multiplayer.serverFolderNameMode":
|
||||
"Server Folder Mode",
|
||||
"distanthorizons.config.client.multiplayer.serverFolderNameMode.@tooltip":
|
||||
"distanthorizons.config.client.advanced.multiplayer.serverFolderNameMode.@tooltip":
|
||||
"Determines the folder format for local multiplayer data.\n\n§6Name Only:§r\nUses the server browser name. Ex: \"Minecraft Server\"\n§6Name IP:§r\n\"Minecraft Server, IP 192.168.1.40\"\n§6Name, IP, Port:§r\n\"Minecraft Server, IP 192.168.1.40:25565\"\n§6Name, IP, Port, MC Version:§r\n\"Minecraft Server, IP 192.168.1.40:25565, GameVersion 1.18.1\"\n\n§c§lCaution:§r changing while connected to a multiplayer server may cause glitches.",
|
||||
"distanthorizons.config.client.advanced.multiplayer.multiverseSimilarityRequiredPercent":
|
||||
"Multiverse Required Similarity %",
|
||||
|
||||
@@ -1,94 +1,62 @@
|
||||
{
|
||||
"distanthorizons.title":
|
||||
"Distant Horizons",
|
||||
"Distant Horizons",
|
||||
|
||||
|
||||
"distanthorizons.general.true":
|
||||
"Вкл.",
|
||||
"distanthorizons.general.false":
|
||||
"Выкл.",
|
||||
"distanthorizons.general.yes":
|
||||
"Да",
|
||||
"distanthorizons.general.no":
|
||||
"Нет",
|
||||
"distanthorizons.general.back":
|
||||
"Назад",
|
||||
"distanthorizons.general.next":
|
||||
"Следующий",
|
||||
"distanthorizons.general.done":
|
||||
"Готово",
|
||||
"distanthorizons.general.cancel":
|
||||
"Отмена",
|
||||
"distanthorizons.general.reset":
|
||||
"Сброc",
|
||||
"distanthorizons.general.true": "Вкл.",
|
||||
"distanthorizons.general.false": "Выкл.",
|
||||
"distanthorizons.general.reset": "Сброc",
|
||||
"distanthorizons.general.back": "Назад",
|
||||
"distanthorizons.general.next": "Следующий",
|
||||
"distanthorizons.general.done": "Готово",
|
||||
"distanthorizons.general.cancel": "Отмена",
|
||||
"distanthorizons.general.yes": "Да",
|
||||
"distanthorizons.general.no": "Нет",
|
||||
|
||||
|
||||
|
||||
|
||||
"distanthorizons.updater.title":
|
||||
"Автоматическое обновление Distant Horizons",
|
||||
"distanthorizons.updater.text1":
|
||||
"§lДоступно новое обновление!",
|
||||
"distanthorizons.updater.text2":
|
||||
"§fВы хотите перейти с %s§f на %s§f?",
|
||||
"distanthorizons.updater.later":
|
||||
"Не сейчас",
|
||||
"distanthorizons.updater.never":
|
||||
"Не показывать снова",
|
||||
"distanthorizons.updater.update":
|
||||
"Обновить",
|
||||
"distanthorizons.updater.update.@tooltip":
|
||||
"Обновить мод 1 раз\n(обновляется при закрытии игры)",
|
||||
"distanthorizons.updater.silent":
|
||||
"Всегда тихое обновление",
|
||||
"distanthorizons.updater.silent.@tooltip":
|
||||
"Каждый раз, когда доступно обновление, оно будет обновляться\n(§6ПРЕДУПРЕЖДЕНИЕ§r: Оно не будет запрашивать у пользователя разрешение на обновление, но будет поддерживать мод в актуальном состоянии)",
|
||||
"distanthorizons.updater.waitingForClose":
|
||||
"Обновление Distant Horizons завершится после перезапуска игры",
|
||||
"distanthorizons.updater.title": "Автоматическое обновление Distant Horizons",
|
||||
"distanthorizons.updater.text1": "§lДоступно новое обновление!",
|
||||
"distanthorizons.updater.text2": "§fВы хотите перейти с %s§f на %s§f?",
|
||||
"distanthorizons.updater.later": "Не сейчас",
|
||||
"distanthorizons.updater.never": "Не показывать снова",
|
||||
"distanthorizons.updater.update": "Обновить",
|
||||
"distanthorizons.updater.update.@tooltip": "Обновить мод 1 раз\n(обновляется при закрытии игры)",
|
||||
"distanthorizons.updater.silent": "Всегда тихое обновление",
|
||||
"distanthorizons.updater.silent.@tooltip": "Каждый раз, когда доступно обновление, оно будет обновляться\n(§6ПРЕДУПРЕЖДЕНИЕ§r: Оно не будет запрашивать у пользователя разрешение на обновление, но будет поддерживать мод в актуальном состоянии)",
|
||||
"distanthorizons.updater.waitingForClose": "Обновление Distant Horizons завершится после перезапуска игры",
|
||||
|
||||
|
||||
|
||||
|
||||
"distanthorizons.config.title":
|
||||
"Конфигурация Distant Horizons",
|
||||
"distanthorizons.config.client":
|
||||
"Клиент",
|
||||
"distanthorizons.config.title": "Конфигурация Distant Horizons",
|
||||
|
||||
"distanthorizons.config.client.quickEnableRendering":
|
||||
"Включить рендеринг",
|
||||
"distanthorizons.config.client.quickEnableRendering.@tooltip":
|
||||
"Определяет, отображает ли Distant Horizons LODs.",
|
||||
|
||||
"distanthorizons.config.client.qualityPresetSetting":
|
||||
"Предустановленное качество",
|
||||
"distanthorizons.config.client.qualityPresetSetting.@tooltip":
|
||||
"Изменяет ряд графических настроек для быстрого изменения качества рендеринга Distant Horizons. \n\nУменьшите этот параметр, если ваш графический процессор максимально загружен или у вас возникли проблемы с частотой кадров.",
|
||||
"distanthorizons.config.client.threadPresetSetting":
|
||||
"Загруженность процессора",
|
||||
"distanthorizons.config.client.threadPresetSetting.@tooltip":
|
||||
"Изменяет количество потоков, которые будут использоваться в Distant Horizons. \n\nУвеличение этого параметра улучшит скорость удаленного генератора (Distant Generator) и скорость загрузки LOD, \nно также увеличит использование процессора/памяти и может привести к заиканию. \n\nПримечание: на процессорах с 4 ядрами или меньше эти настройки будут менее эффективными, \nи некоторые настройки дадут аналогичные результаты.",
|
||||
|
||||
"distanthorizons.config.client.optionsButton":
|
||||
"Отобразить кнопку Параметров",
|
||||
"distanthorizons.config.client.optionsButton.@tooltip":
|
||||
"Показать кнопку Параметров слева от кнопки FOV.",
|
||||
"distanthorizons.config.client": "Клиент",
|
||||
|
||||
"distanthorizons.config.client.quickEnableRendering": "Включить рендеринг",
|
||||
"distanthorizons.config.client.quickEnableRendering.@tooltip": "Определяет, отображает ли Distant Horizons LODs.",
|
||||
"distanthorizons.config.client.qualityPresetSetting": "Предустановленное качество",
|
||||
"distanthorizons.config.client.qualityPresetSetting.@tooltip": "Изменяет ряд графических настроек для быстрого изменения качества рендеринга Distant Horizons. \n\nУменьшите этот параметр, если ваш графический процессор максимально загружен или у вас возникли проблемы с частотой кадров.",
|
||||
"distanthorizons.config.client.threadPresetSetting": "Загруженность процессора",
|
||||
"distanthorizons.config.client.threadPresetSetting.@tooltip": "Изменяет количество потоков, которые будут использоваться в Distant Horizons. \n\nУвеличение этого параметра улучшит скорость удаленного генератора (Distant Generator) и скорость загрузки LOD, \nно также увеличит использование процессора/памяти и может привести к заиканию. \n\nПримечание: на процессорах с 4 ядрами или меньше эти настройки будут менее эффективными, \nи некоторые настройки дадут аналогичные результаты.",
|
||||
"distanthorizons.config.client.optionsButton": "Отобразить кнопку Параметров",
|
||||
"distanthorizons.config.client.optionsButton.@tooltip": "Показать кнопку Параметров слева от кнопки FOV.",
|
||||
|
||||
|
||||
|
||||
"distanthorizons.config.client.advanced":
|
||||
"Расширенные параметры",
|
||||
"distanthorizons.config.client.advanced": "Расширенные параметры",
|
||||
|
||||
"distanthorizons.config.client.advanced.graphics":
|
||||
"Графика",
|
||||
"distanthorizons.config.client.advanced.graphics.quality":
|
||||
"Качество рендеринга",
|
||||
"distanthorizons.config.client.advanced.graphics": "Графика",
|
||||
|
||||
"distanthorizons.config.client.advanced.graphics.quality": "Качество рендеринга",
|
||||
|
||||
"distanthorizons.config.client.advanced.graphics.quality.maxHorizontalResolution": "Максимальное горизонтальное разрешение",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.maxHorizontalResolution.@tooltip": "Изображения с максимальной детализацией отображаются на.\n\n§6Самый быстрый:§r Чанк\n§6Самый красивый:§r Блок",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.lodChunkRenderDistance": "Расстояние рендеринга LOD",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.lodChunkRenderDistance.@tooltip": "Расстояние рендеринга Distant Horizons, измеряемое в чанках. \n\nПримечание: это максимально возможное число. \nДальность рендеринга может быть выше или ниже этого числа \nв зависимости от других графических настроек.",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.verticalQuality": "Вертикальное качество",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.verticalQuality.@tooltip": "На сколько хорошо LOD (уровень детализации) отображает выступы, пещеры, обрывы и т.д.\n\nБолее высокие параметры будут увеличивать использование памяти и GPU.",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.verticalQuality.@tooltip": "На сколько хорошо LOD отображает выступы, пещеры, обрывы и т.д.\n\nБолее высокие параметры будут увеличивать использование памяти и GPU.",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.horizontalScale": "Горизонтальная шкала",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.horizontalScale.@tooltip": "На сколько быстро уровни детализации (LOD) снижают качество.\n\nБольшие значения улучшат вид дальней местности, \nно увеличат использование памяти и GPU.",
|
||||
"distanthorizons.config.client.advanced.graphics.quality.horizontalQuality": "Горизонтальное качество",
|
||||
@@ -105,11 +73,11 @@
|
||||
"distanthorizons.config.client.advanced.graphics.fog": "Туман",
|
||||
|
||||
"distanthorizons.config.client.advanced.graphics.fog.drawMode": "Режим отображения тумана",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.drawMode.@tooltip": "Когда будет отрисовываться туман на LODs (уровнях детализации).",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.drawMode.@tooltip": "Когда будет отрисовываться туман на LOD-ах (уровнях детализации).",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.distance": "Дальность тумана",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.distance.@tooltip": "Дальность(и), на которой туман будет отрисовываться на LODs.",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.distance.@tooltip": "Дальность(и), на которой туман будет отрисовываться на LOD-ах.",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.colorMode": "Режим цвета тумана",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.colorMode.@tooltip": "Цвет тумана на LODs.",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.colorMode.@tooltip": "Цвет тумана на LOD-ах.",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.disableVanillaFog": "Отключить ванильный туман",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.disableVanillaFog.@tooltip": "§6Вкл.:§r отключает туман Minecraft на ванильных чанках. \n§6Выкл.:§r Minecraft отрисовывает туман как обычно. \n\nМожет вызывать проблемы с другими модами, изменяющими туман. \nОтключите, если ванильные чанки полностью покрыты туманом.",
|
||||
"distanthorizons.config.client.advanced.graphics.fog.advancedFog": "Дополнительные настройки тумана",
|
||||
@@ -127,12 +95,12 @@
|
||||
"distanthorizons.config.client.advanced.graphics.fog.advancedFog.farFogDensity.@tooltip": "Какая должна быть плотность дальнего тумана? ",
|
||||
|
||||
|
||||
"distanthorizons.config.client.advanced.graphics.ssao": "Окружающая окклюзия (Ambient Occlusion)",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao": "Окружающая окклюзия",
|
||||
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.enabled": "Включить окружающую окклюзию (Ambient Occlusion)",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.enabled.@tooltip": "Окружающая окклюзия добавляет глубину к освещению блоков.",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.sampleCount": "Количество образцов",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.sampleCount.@tooltip": "Определяет, сколько точек в пространстве отбирается для теста окклюзии. \nБольшее количество улучшит качество и уменьшит полосирование, но увеличит нагрузку на ГПУ.",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.sampleCount.@tooltip": "Определяет, сколько точек в пространстве отбирается для теста окклюзии. \nБольшее количество улучшит качество и уменьшит полосирование, но увеличит нагрузку на графический процессор.",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.radius": "Радиус",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.radius.@tooltip": "Определяет радиус применения эффекта окружающей окклюзии в блоках.",
|
||||
"distanthorizons.config.client.advanced.graphics.ssao.strength": "Сила",
|
||||
@@ -232,25 +200,20 @@
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfWorldGenerationThreads": "Количество потоков генерации мира",
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfWorldGenerationThreads.@tooltip": "Сколько потоков следует использовать при генерации LODs вне обычной зоны отрисовки? \n\nЕсли это число меньше 1, оно будет рассматриваться как процент времени, в течение которого один поток может работать, прежде чем перейти в режим ожидания. \n\nЕсли у вас есть проблемы с прерываниями при генерации дальних LODs, уменьшите это число. Если вы хотите увеличить скорость генерации LOD, увеличьте это число. \n\nКоличество потоков для генерации LOD и количество потоков для построения буферов независимы друг от друга. Если их сумма больше количества ядер вашего процессора, это нормально.",
|
||||
"distanthorizons.config.client.advanced.multiThreading.runTimeRatioForWorldGenerationThreads": "Процент времени выполнения для потоков генерации мира",
|
||||
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfBufferBuilderThreads": "Количество потоков построения буферов",
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfBufferBuilderThreads.@tooltip": "Количество потоков, используемых при построении данных геометрии. \nМожет быть только от 1 до количества процессорных ядер вашего CPU.",
|
||||
"distanthorizons.config.client.advanced.multiThreading.runTimeRatioForBufferBuilderThreads": "Процент времени выполнения для потоков построения буферов",
|
||||
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfFileHandlerThreads": "Количество потоков обработки файлов",
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfFileHandlerThreads.@tooltip": "Количество потоков, используемых при построении буферов вершин (вещей, отправляемых на ваш GPU для отрисовки LODs). \nМожет быть только от 1 до количества процессорных ядер вашего CPU.",
|
||||
"distanthorizons.config.client.advanced.multiThreading.runTimeRatioForFileHandlerThreads": "Процент времени выполнения для потоков обработки файлов",
|
||||
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfDataTransformerThreads": "Количество потоков преобразования данных",
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfDataTransformerThreads.@tooltip": "Количество потоков, используемых при преобразовании данных ID в данные, подходящие для отрисовки. \n(Это, как правило, происходит при генерации нового ландшафта или изменении настроек графики). \nМожет быть только от 1 до количества процессорных ядер вашего CPU.",
|
||||
"distanthorizons.config.client.advanced.multiThreading.runTimeRatioForDataTransformerThreads": "Процент времени выполнения для потоков преобразования данных",
|
||||
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfChunkLodConverterThreads": "Количество потоков преобразования LOD чанков",
|
||||
"distanthorizons.config.client.advanced.multiThreading.numberOfChunkLodConverterThreads.@tooltip": "Сколько потоков следует использовать для преобразования чанков Minecraft в данные LOD? \nЭти потоки работают как при генерации мира, так и при загрузке, выгрузке и модификации чанков.",
|
||||
"distanthorizons.config.client.advanced.multiThreading.runTimeRatioForChunkLodConverterThreads": "Процент времени выполнения для потоков преобразования LOD чанков",
|
||||
|
||||
|
||||
|
||||
"distanthorizons.config.client.advanced.debugging": "Отладка",
|
||||
"distanthorizons.config.client.advanced.debugging.rendererMode": "Режим рендера",
|
||||
"distanthorizons.config.client.advanced.debugging.debugRendering": "Отладка рендера",
|
||||
@@ -331,7 +294,6 @@
|
||||
"distanthorizons.config.client.advanced.debugging.debugWireframe.showRenderDataFileStatus": "Показать статус файла данных отрисовки",
|
||||
|
||||
"distanthorizons.config.client.resetSettingsConfirmation": "Сбросить все настройки?",
|
||||
|
||||
"distanthorizons.config.client.resetSettingsConfirmation.resetConfirmationNote": "Вы уверены? Это действие нельзя отменить!",
|
||||
"distanthorizons.config.client.resetSettingsConfirmation.resetAllSettings": "Сбросить все настройки",
|
||||
|
||||
@@ -470,31 +432,19 @@
|
||||
"distanthorizons.config.enum.ELoggerMode.LOG_WARNING_TO_CHAT_AND_INFO_TO_FILE": "Файл: Информация, Чат: Предупреждения",
|
||||
"distanthorizons.config.enum.ELoggerMode.LOG_ERROR_TO_CHAT_AND_INFO_TO_FILE": "Файл: Информация, Чат: Ошибки",
|
||||
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.AUTO":
|
||||
"Авто",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.BUFFER_STORAGE":
|
||||
"Хранение буфера",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.SUB_DATA":
|
||||
"Данные SUB",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.BUFFER_MAPPING":
|
||||
"Отображение буфера",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.DATA":
|
||||
"Данные",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.AUTO": "Авто",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.BUFFER_STORAGE": "Хранение буфера",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.SUB_DATA": "Данные SUB",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.BUFFER_MAPPING": "Отображение буфера",
|
||||
"distanthorizons.config.enum.EGpuUploadMethod.DATA": "Данные",
|
||||
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.CONSTANT":
|
||||
"Постоянно",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.FREQUENT":
|
||||
"Часто",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.NORMAL":
|
||||
"Обычно",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.RARE":
|
||||
"Редко",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.CONSTANT": "Постоянно",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.FREQUENT": "Часто",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.NORMAL": "Обычно",
|
||||
"distanthorizons.config.enum.EBufferRebuildTimes.RARE": "Редко",
|
||||
|
||||
"distanthorizons.config.enum.ELodShading.MINECRAFT":
|
||||
"Майнкрафт-овское",
|
||||
"distanthorizons.config.enum.ELodShading.OLD_LIGHTING":
|
||||
"Старое освещение",
|
||||
"distanthorizons.config.enum.ELodShading.NONE":
|
||||
"Ничего"
|
||||
"distanthorizons.config.enum.ELodShading.MINECRAFT": "Майнкрафт-овское",
|
||||
"distanthorizons.config.enum.ELodShading.OLD_LIGHTING": "Старое освещение",
|
||||
"distanthorizons.config.enum.ELodShading.NONE": "Ничего"
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user