mirror of
https://github.com/Cubitect/cubiomes.git
synced 2025-01-09 03:57:46 +08:00
Made compatible with g++ and clang compilers + better docu for getting started.
This commit is contained in:
parent
8fa78be25b
commit
a9705edfb8
148
README.md
148
README.md
@ -4,20 +4,130 @@ Cubiomes is a standalone library, written in C, that mimics the Minecraft biome
|
||||
It is intended as a powerful tool to devise very fast, custom seed finding applications and large scale map viewers.
|
||||
|
||||
|
||||
### Audience
|
||||
#### Audience
|
||||
|
||||
You should be familiar with the C programming language, also a basic understanding of the Minecraft biome generation process would be helpful.
|
||||
A POSIX environment is required to compile the finders library and examples, but the core generator library may also work on other platforms.
|
||||
You should be familiar with the C programming language, also a basic understanding of the Minecraft biome generation process would be helpful.
|
||||
|
||||
|
||||
### Documentation
|
||||
## Getting Started
|
||||
|
||||
This section is meant to give you a quick starting point if you want to use this library to find your own biome dependent features.
|
||||
|
||||
### Biome Generator
|
||||
|
||||
Let's create a simple program called `find_jedge.c` which tests seeds for a Junge Edge biome at a predefined location.
|
||||
|
||||
```
|
||||
#include "finders.h"
|
||||
#include <stdio.h>
|
||||
|
||||
int main()
|
||||
{
|
||||
// First initialize the global biome table 'int biomes[256]'. This sets up
|
||||
// properties such as the category and temperature of each biome.
|
||||
initBiomes();
|
||||
|
||||
// Allocate and initialize a stack of biome layers that reflects the biome
|
||||
// generation of Minecraft 1.14
|
||||
LayerStack g = setupGenerator(MC_1_14);
|
||||
|
||||
int64_t seed;
|
||||
Pos pos = {0,0}; // block position to be checked
|
||||
|
||||
for (seed = 0; ; seed++)
|
||||
{
|
||||
// Go through the layers in the layer stack and initialize the seed
|
||||
// dependent aspects of the generator.
|
||||
applySeed(&g, seed);
|
||||
|
||||
// To get the biome at single block position we can use getBiomeAtPos().
|
||||
int biomeID = getBiomeAtPos(g, pos);
|
||||
if (biomeID == jungle_edge)
|
||||
break;
|
||||
}
|
||||
|
||||
printf("Seed %" PRId64 " has a Junge Edge biome at block position "
|
||||
"(%d, %d).\n", seed, pos.x, pos.z);
|
||||
|
||||
// Clean up.
|
||||
freeGenerator(g);
|
||||
|
||||
return 0;
|
||||
}
|
||||
```
|
||||
|
||||
You can compile this code either by directly adding a target to the makefile, or you can compile and link to a cubiomes archive:
|
||||
```
|
||||
$ cd cubiomes
|
||||
$ make libcubiomes
|
||||
```
|
||||
To compile, and link the cubiomes library you can use one of
|
||||
```
|
||||
$ cc find_jedge.c libcubiomes.a -lm # static
|
||||
$ cc find_jedge.c -L. -lcubiomes -lm # dynamic
|
||||
```
|
||||
Both options assume that your source code is saved as `find_jedge.c` in the cubiomes working directory. If your makefile is configured to use pthreads you also may need to add the `-lpthread` option to the compiler. Running the program should output:
|
||||
```
|
||||
$ ./a.out
|
||||
Seed 615 has a Junge Edge biome at block position (0, 0).
|
||||
```
|
||||
|
||||
We can also generate the biomes for a rectangular region using `getArea()` which also offers control over the entry layer, see the layer documentation for more information.
|
||||
|
||||
```
|
||||
#include "generator.h"
|
||||
#include "util.h"
|
||||
|
||||
int main()
|
||||
{
|
||||
unsigned char biomeColours[256][3];
|
||||
|
||||
// Initialize global biome table.
|
||||
initBiomes();
|
||||
// Initialize a colour map for biomes.
|
||||
initBiomeColours(biomeColours);
|
||||
|
||||
// Allocate and initialize a stack of biome layers.
|
||||
LayerStack g = setupGenerator(MC_1_14);
|
||||
// Extract the desired layer.
|
||||
Layer *layer = &g.layers[L_SHORE_16];
|
||||
|
||||
int64_t seed = 1661454332289;
|
||||
int areaX = -60, areaZ = -60;
|
||||
unsigned int areaWidth = 120, areaHeight = 120;
|
||||
unsigned int scale = 4;
|
||||
unsigned int imgWidth = areaWidth*scale, imgHeight = areaHeight*scale;
|
||||
|
||||
// Allocate a sufficient buffer for the biomes and for the image pixels.
|
||||
int *biomes = allocCache(layer, areaWidth, areaHeight);
|
||||
unsigned char *rgb = (unsigned char *) malloc(3*imgWidth*imgHeight);
|
||||
|
||||
// Apply the seed only for the required layers and generate the area.
|
||||
setWorldSeed(layer, seed);
|
||||
genArea(layer, biomes, areaX, areaZ, areaWidth, areaHeight);
|
||||
|
||||
// Map the biomes to a color buffer and save to an image.
|
||||
biomesToImage(rgb, biomeColours, biomes, areaWidth, areaHeight, scale, 2);
|
||||
savePPM("biomes_at_layer.ppm", rgb, imgWidth, imgHeight);
|
||||
|
||||
// Clean up.
|
||||
freeGenerator(g);
|
||||
free(biomes);
|
||||
free(rgb);
|
||||
|
||||
return 0;
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
### Layer Documentation
|
||||
|
||||
There is a reference document for the generator layers which contains a summary for most generator layers and their function within the generation process.
|
||||
|
||||
|
||||
### Examples
|
||||
|
||||
There are two example programs in this repository which can be compiled using the makefile provided.
|
||||
There are two example programs in this repository which can be compiled using the makefile.
|
||||
|
||||
|
||||
#### Finding Quad-Witch-Huts at a Specific Location
|
||||
@ -125,20 +235,20 @@ If you are looking to get the "Adventuring Time" achievment you might consider o
|
||||
|
||||
| Seed | All biome radius |
|
||||
|---------------|------------------|
|
||||
| -880424771806 | 644 |
|
||||
| 48382691805 | 633 |
|
||||
| 480800992945 | 649 |
|
||||
| 1065757415811 | 612 |
|
||||
| 1509124018794 | 645 |
|
||||
| 1550633690354 | 616 |
|
||||
| 1571479851306 | 631 |
|
||||
| 1925837979058 | 621 |
|
||||
| 2082386353360 | 649 |
|
||||
| 2087339213306 | 632 |
|
||||
| 2810140768300 | 637 |
|
||||
| 3053313529066 | 648 |
|
||||
| 3457626356584 | 649 |
|
||||
| 3548624619264 | 646 |
|
||||
| -880424771806 | 644 |
|
||||
| 48382691805 | 633 |
|
||||
| 480800992945 | 649 |
|
||||
| 1065757415811 | 612 |
|
||||
| 1509124018794 | 645 |
|
||||
| 1550633690354 | 616 |
|
||||
| 1571479851306 | 631 |
|
||||
| 1925837979058 | 621 |
|
||||
| 2082386353360 | 649 |
|
||||
| 2087339213306 | 632 |
|
||||
| 2810140768300 | 637 |
|
||||
| 3053313529066 | 648 |
|
||||
| 3457626356584 | 649 |
|
||||
| 3548624619264 | 646 |
|
||||
|
||||
|
||||
|
||||
|
@ -61,8 +61,8 @@ int main(int argc, char *argv[])
|
||||
" range search range (in blocks) [uint, default=1024]\n");
|
||||
exit(1);
|
||||
}
|
||||
if (argc <= 1 || sscanf(argv[1], "%"PRId64, &seedStart) != 1) seedStart = 0;
|
||||
if (argc <= 2 || sscanf(argv[2], "%"PRId64, &seedEnd) != 1) seedEnd = 100000000LL;
|
||||
if (argc <= 1 || sscanf(argv[1], "%" PRId64, &seedStart) != 1) seedStart = 0;
|
||||
if (argc <= 2 || sscanf(argv[2], "%" PRId64, &seedEnd) != 1) seedEnd = 100000000LL;
|
||||
if (argc <= 3 || sscanf(argv[3], "%u", &threads) != 1) threads = 1;
|
||||
if (argc <= 4 || sscanf(argv[4], "%u", &range) != 1) range = 1024;
|
||||
|
||||
@ -70,7 +70,7 @@ int main(int argc, char *argv[])
|
||||
filter = setupBiomeFilter(BIOMES_L13_OCEAN_MIX_4,
|
||||
sizeof(BIOMES_L13_OCEAN_MIX_4)/sizeof(int));
|
||||
|
||||
printf("Starting search through seeds %"PRId64 " to %"PRId64", using %u threads.\n"
|
||||
printf("Starting search through seeds %" PRId64 " to %" PRId64", using %u threads.\n"
|
||||
"Search radius = %u.\n", seedStart, seedEnd, threads, range);
|
||||
|
||||
thread_id_t threadID[threads];
|
||||
|
@ -28,14 +28,14 @@ int main(int argc, char *argv[])
|
||||
const char *seedFileName;
|
||||
StructureConfig featureConfig;
|
||||
|
||||
if(argc > 2)
|
||||
if (argc > 2)
|
||||
{
|
||||
if(sscanf(argv[1], "%d", ®PosX) != 1) regPosX = 0;
|
||||
if(sscanf(argv[2], "%d", ®PosZ) != 1) regPosZ = 0;
|
||||
if (sscanf(argv[1], "%d", ®PosX) != 1) regPosX = 0;
|
||||
if (sscanf(argv[2], "%d", ®PosZ) != 1) regPosZ = 0;
|
||||
|
||||
if(argc > 3)
|
||||
if (argc > 3)
|
||||
{
|
||||
if(sscanf(argv[3], "%d", &mcversion) != 1) mcversion = 0;
|
||||
if (sscanf(argv[3], "%d", &mcversion) != 1) mcversion = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -55,7 +55,7 @@ int main(int argc, char *argv[])
|
||||
regPosX -= 1;
|
||||
regPosZ -= 1;
|
||||
|
||||
if(mcversion == 113)
|
||||
if (mcversion >= 113)
|
||||
{
|
||||
featureConfig = SWAMP_HUT_CONFIG;
|
||||
seedFileName = "./seeds/quadhutbases_1_13_Q1.txt";
|
||||
@ -73,7 +73,7 @@ int main(int argc, char *argv[])
|
||||
g = setupGenerator(MC_1_7);
|
||||
}
|
||||
|
||||
if(access(seedFileName, F_OK))
|
||||
if (access(seedFileName, F_OK))
|
||||
{
|
||||
printf("Seed base file does not exist: Creating new one.\n"
|
||||
"This may take a few minutes...\n");
|
||||
@ -95,7 +95,7 @@ int main(int argc, char *argv[])
|
||||
// so we can test the biome at these positions.
|
||||
Pos qhpos[4];
|
||||
|
||||
// Setup a dummy layer for Layer 19: Biome.
|
||||
// Setup a dummy layer for Layer 19: Biome, to make preliminary seed tests.
|
||||
Layer layerBiomeDummy;
|
||||
setupLayer(256, &layerBiomeDummy, NULL, 200, NULL);
|
||||
|
||||
@ -105,7 +105,7 @@ int main(int argc, char *argv[])
|
||||
|
||||
|
||||
// Search for a swamp at the structure positions
|
||||
for(i = 0; i < qhcnt; i++)
|
||||
for (i = 0; i < qhcnt; i++)
|
||||
{
|
||||
base = moveStructure(qhcandidates[i], regPosX, regPosZ);
|
||||
|
||||
@ -115,7 +115,7 @@ int main(int argc, char *argv[])
|
||||
qhpos[3] = getStructurePos(featureConfig, base, 1+regPosX, 1+regPosZ);
|
||||
|
||||
/*
|
||||
for(j = 0; j < 4; j++)
|
||||
for (j = 0; j < 4; j++)
|
||||
{
|
||||
printf("(%d,%d) ", qhpos[j].x, qhpos[j].z);
|
||||
}
|
||||
@ -124,29 +124,31 @@ int main(int argc, char *argv[])
|
||||
|
||||
// This little magic code checks if there is a meaningful chance for
|
||||
// this seed base to generate swamps in the area.
|
||||
// The idea is that the conversion from Lush temperature to swamp is
|
||||
// independent of surroundings, so we can test the conversion
|
||||
// beforehand. Furthermore biomes tend to leak into the negative
|
||||
// The idea is, that the conversion from Lush temperature to swamp is
|
||||
// independent of surroundings, so we can test for this conversion
|
||||
// beforehand. Furthermore, biomes tend to leak into the negative
|
||||
// coordinates because of the Zoom layers, so the majority of hits will
|
||||
// occur when SouthEast corner (at a 1:256 scale) of the quad-hut has a
|
||||
// swamp. (This assumption misses about 1 in 500 quad-hut seeds.)
|
||||
// Finally, here we also exploit that the minecraft random number
|
||||
// generator is quite bad, such that for the "mcNextRand() mod 6" check
|
||||
// it has a period pattern of ~3 on the high seed-bits.
|
||||
for(j = 0; j < 5; j++)
|
||||
// generator is quite bad, the "mcNextRand() mod 6" check has a period
|
||||
// pattern of ~3 on the high seed-bits, which means we can avoid
|
||||
// checking all 16 high-bit combinations.
|
||||
for (j = 0; j < 5; j++)
|
||||
{
|
||||
seed = base + ((j+0x53) << 48);
|
||||
setWorldSeed(&layerBiomeDummy, seed);
|
||||
setChunkSeed(&layerBiomeDummy, areaX+1, areaZ+1);
|
||||
if(mcNextInt(&layerBiomeDummy, 6) == 5)
|
||||
if (mcNextInt(&layerBiomeDummy, 6) == 5)
|
||||
break;
|
||||
}
|
||||
if(j >= 5) continue;
|
||||
if (j >= 5)
|
||||
continue;
|
||||
|
||||
|
||||
int64_t hits = 0, swpc;
|
||||
|
||||
for(j = 0; j < 0x10000; j++)
|
||||
for (j = 0; j < 0x10000; j++)
|
||||
{
|
||||
seed = base + (j << 48);
|
||||
|
||||
@ -156,13 +158,13 @@ int main(int argc, char *argv[])
|
||||
setWorldSeed(&layerBiomeDummy, seed);
|
||||
|
||||
setChunkSeed(&layerBiomeDummy, areaX+1, areaZ+1);
|
||||
if(mcNextInt(&layerBiomeDummy, 6) != 5)
|
||||
if (mcNextInt(&layerBiomeDummy, 6) != 5)
|
||||
continue;
|
||||
|
||||
// This seed base does not seem to contain many quad huts, so make
|
||||
// a more detailed analysis of the surroundings and see if there is
|
||||
// enough potential for more swamps to justify searching further.
|
||||
if(hits == 0 && (j & 0xfff) == 0xfff)
|
||||
if (hits == 0 && (j & 0xfff) == 0xfff)
|
||||
{
|
||||
swpc = 0;
|
||||
setChunkSeed(&layerBiomeDummy, areaX, areaZ+1);
|
||||
@ -172,23 +174,24 @@ int main(int argc, char *argv[])
|
||||
setChunkSeed(&layerBiomeDummy, areaX, areaZ);
|
||||
swpc += mcNextInt(&layerBiomeDummy, 6) == 5;
|
||||
|
||||
if(swpc < (j > 0x1000 ? 2 : 1)) break;
|
||||
if (swpc < (j > 0x1000 ? 2 : 1))
|
||||
break;
|
||||
}
|
||||
|
||||
// Dismiss seeds that don't have a swamp near the quad temple.
|
||||
setWorldSeed(lFilterBiome, seed);
|
||||
genArea(lFilterBiome, biomeCache, (regPosX<<1)+2, (regPosZ<<1)+2, 1, 1);
|
||||
|
||||
if(biomeCache[0] != swamp)
|
||||
if (biomeCache[0] != swamp)
|
||||
continue;
|
||||
|
||||
applySeed(&g, seed);
|
||||
if(getBiomeAtPos(g, qhpos[0]) != swamp) continue;
|
||||
if(getBiomeAtPos(g, qhpos[1]) != swamp) continue;
|
||||
if(getBiomeAtPos(g, qhpos[2]) != swamp) continue;
|
||||
if(getBiomeAtPos(g, qhpos[3]) != swamp) continue;
|
||||
if (getBiomeAtPos(g, qhpos[0]) != swamp) continue;
|
||||
if (getBiomeAtPos(g, qhpos[1]) != swamp) continue;
|
||||
if (getBiomeAtPos(g, qhpos[2]) != swamp) continue;
|
||||
if (getBiomeAtPos(g, qhpos[3]) != swamp) continue;
|
||||
|
||||
printf("%"PRId64 "\n", seed);
|
||||
printf("%" PRId64 "\n", seed);
|
||||
hits++;
|
||||
}
|
||||
}
|
||||
|
84
finders.c
84
finders.c
@ -73,7 +73,7 @@ int64_t *loadSavedSeeds(const char *fnam, int64_t *scnt)
|
||||
|
||||
while (!feof(fp))
|
||||
{
|
||||
if (fscanf(fp, "%"PRId64, &seed) == 1) (*scnt)++;
|
||||
if (fscanf(fp, "%" PRId64, &seed) == 1) (*scnt)++;
|
||||
else while (!feof(fp) && fgetc(fp) != '\n');
|
||||
}
|
||||
|
||||
@ -83,7 +83,7 @@ int64_t *loadSavedSeeds(const char *fnam, int64_t *scnt)
|
||||
|
||||
for (int64_t i = 0; i < *scnt && !feof(fp);)
|
||||
{
|
||||
if (fscanf(fp, "%"PRId64, &baseSeeds[i]) == 1) i++;
|
||||
if (fscanf(fp, "%" PRId64, &baseSeeds[i]) == 1) i++;
|
||||
else while (!feof(fp) && fgetc(fp) != '\n');
|
||||
}
|
||||
|
||||
@ -563,14 +563,14 @@ static DWORD WINAPI search4QuadBasesThread(LPVOID data)
|
||||
|
||||
if (i < 32 && !fseek(fp, 1-i, SEEK_END) && fread(buf, i-1, 1, fp) > 0)
|
||||
{
|
||||
if (sscanf(buf, "%"PRId64, &seed) == 1)
|
||||
if (sscanf(buf, "%" PRId64, &seed) == 1)
|
||||
{
|
||||
while (lowerBits[lowerBitsIdx] <= (seed & 0xffff))
|
||||
lowerBitsIdx++;
|
||||
|
||||
seed = (seed & 0x0000ffffffff0000) + lowerBits[lowerBitsIdx];
|
||||
|
||||
printf("Thread %d starting from: %"PRId64"\n", info.threadID, seed);
|
||||
printf("Thread %d starting from: %" PRId64"\n", info.threadID, seed);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -586,9 +586,9 @@ static DWORD WINAPI search4QuadBasesThread(LPVOID data)
|
||||
{
|
||||
if (isQuadBase(info.sconf, seed, info.quality))
|
||||
{
|
||||
fprintf(fp, "%"PRId64"\n", seed);
|
||||
fprintf(fp, "%" PRId64"\n", seed);
|
||||
fflush(fp);
|
||||
//printf("Thread %d: %"PRId64"\n", info.threadID, seed);
|
||||
//printf("Thread %d: %" PRId64"\n", info.threadID, seed);
|
||||
}
|
||||
|
||||
lowerBitsIdx++;
|
||||
@ -851,7 +851,6 @@ int isTreasureChunk(int64_t seed, const int chunkX, const int chunkZ)
|
||||
}
|
||||
|
||||
|
||||
|
||||
//==============================================================================
|
||||
// Checking Biomes & Biome Helper Functions
|
||||
//==============================================================================
|
||||
@ -1134,31 +1133,50 @@ static double getGrassProbability(int64_t seed, int biome, int x, int z)
|
||||
// TODO: Try to determine the actual probabilities and build a statistic.
|
||||
switch (biome)
|
||||
{
|
||||
case plains: return 1.0;
|
||||
case mountains: return 0.8; // height dependent
|
||||
case forest: return 1.0;
|
||||
case taiga: return 1.0;
|
||||
case swamp: return 0.6; // height dependent
|
||||
case river: return 0.2;
|
||||
case beach: return 0.1;
|
||||
case wooded_hills: return 1.0;
|
||||
case taiga_hills: return 1.0;
|
||||
case mountain_edge: return 1.0; // height dependent
|
||||
case jungle: return 1.0;
|
||||
case jungle_hills: return 1.0;
|
||||
case jungleEdge: return 1.0;
|
||||
case birch_forest: return 1.0;
|
||||
case birch_forest_hills: return 1.0;
|
||||
case dark_forest: return 0.9;
|
||||
case snowy_taiga: return 0.1; // below trees
|
||||
case snowy_taiga_hills: return 0.1; // below trees
|
||||
case giant_tree_taiga: return 0.6;
|
||||
case giant_tree_taiga_hills: return 0.6;
|
||||
case wooded_mountains: return 0.2; // height dependent
|
||||
case savanna: return 1.0;
|
||||
case savanna_plateau: return 1.0;
|
||||
case wooded_badlands_plateau: return 0.1; // height dependent
|
||||
case badlands_plateau: return 0.1; // height dependent
|
||||
case plains: return 1.0;
|
||||
case mountains: return 0.8; // height dependent
|
||||
case forest: return 1.0;
|
||||
case taiga: return 1.0;
|
||||
case swamp: return 0.6; // height dependent
|
||||
case river: return 0.5;
|
||||
case beach: return 0.1;
|
||||
case wooded_hills: return 1.0;
|
||||
case taiga_hills: return 1.0;
|
||||
case mountain_edge: return 1.0; // height dependent
|
||||
case jungle: return 1.0;
|
||||
case jungle_hills: return 1.0;
|
||||
case jungle_edge: return 1.0;
|
||||
case birch_forest: return 1.0;
|
||||
case birch_forest_hills: return 1.0;
|
||||
case dark_forest: return 0.9;
|
||||
case snowy_taiga: return 0.2; // below trees
|
||||
case snowy_taiga_hills: return 0.2; // below trees
|
||||
case giant_tree_taiga: return 0.6;
|
||||
case giant_tree_taiga_hills: return 0.6;
|
||||
case wooded_mountains: return 0.2; // height dependent
|
||||
case savanna: return 1.0;
|
||||
case savanna_plateau: return 1.0;
|
||||
case wooded_badlands_plateau: return 0.1; // height dependent
|
||||
case badlands_plateau: return 0.1; // height dependent
|
||||
|
||||
case sunflower_plains: return 1.0;
|
||||
case gravelly_mountains: return 0.2;
|
||||
case flower_forest: return 1.0;
|
||||
case taiga_mountains: return 1.0;
|
||||
case swamp_hills: return 0.9;
|
||||
case modified_jungle: return 1.0;
|
||||
case modified_jungle_edge: return 1.0;
|
||||
case tall_birch_forest: return 1.0;
|
||||
case tall_birch_hills: return 1.0;
|
||||
case dark_forest_hills: return 0.9;
|
||||
case snowy_taiga_mountains: return 0.2;
|
||||
case giant_spruce_taiga: return 0.6;
|
||||
case giant_spruce_taiga_hills: return 0.6;
|
||||
case modified_gravelly_mountains: return 0.2;
|
||||
case shattered_savanna: return 1.0;
|
||||
case shattered_savanna_plateau: return 1.0;
|
||||
case bamboo_jungle: return 0.4;
|
||||
case bamboo_jungle_hills: return 0.4;
|
||||
// NOTE: in rare circumstances you can get also get grassy islands that are
|
||||
// completely in ocean variants...
|
||||
default: return 0;
|
||||
@ -1750,7 +1768,7 @@ BiomeFilter setupBiomeFilter(const int *biomeList, int listLen)
|
||||
|
||||
if (isShallowOcean(id))
|
||||
{
|
||||
bf.oceansToFind |= (1ULL < id);
|
||||
bf.oceansToFind |= (1ULL << id);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
15
finders.h
15
finders.h
@ -128,14 +128,10 @@ STRUCT(BiomeFilter)
|
||||
int doScale4Check;
|
||||
};
|
||||
|
||||
|
||||
//==============================================================================
|
||||
// Globals
|
||||
//==============================================================================
|
||||
|
||||
extern Biome biomes[256];
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
/******************************** SEED FINDING *********************************
|
||||
*
|
||||
@ -569,5 +565,8 @@ int64_t checkForBiomes(
|
||||
const BiomeFilter filter,
|
||||
const int minscale);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* FINDERS_H_ */
|
||||
|
12
generator.h
12
generator.h
@ -6,7 +6,8 @@
|
||||
/* Minecraft versions */
|
||||
enum MCversion
|
||||
{
|
||||
MC_1_7, MC_1_8, MC_1_9, MC_1_10, MC_1_11, MC_1_12, MC_1_13, MC_1_14,
|
||||
MC_1_7, MC_1_8, MC_1_9, MC_1_10, MC_1_11, MC_1_12, MC_1_13, MC_1_14,
|
||||
MC_1_15, MC_1_16,
|
||||
MCBE = 256
|
||||
};
|
||||
|
||||
@ -188,6 +189,11 @@ STRUCT(LayerStack)
|
||||
int layerCnt;
|
||||
};
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
/* Initialise an instance of a generator. */
|
||||
LayerStack setupGenerator(const int mcversion);
|
||||
|
||||
@ -223,5 +229,9 @@ void applySeed(LayerStack *g, int64_t seed);
|
||||
void genArea(Layer *layer, int *out, int areaX, int areaZ, int areaWidth, int areaHeight);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* GENERATOR_H_ */
|
||||
|
||||
|
18
layers.c
18
layers.c
@ -183,6 +183,7 @@ void mapIsland(Layer *l, int * __restrict out, int areaX, int areaZ, int areaWid
|
||||
}
|
||||
}
|
||||
|
||||
// FIXME: currently SIMD only works properly for certain sizes
|
||||
#if defined USE_SIMD && defined __AVX2__
|
||||
|
||||
void mapZoom(Layer *l, int* __restrict out, int areaX, int areaZ, int areaWidth, int areaHeight)
|
||||
@ -200,7 +201,7 @@ void mapZoom(Layer *l, int* __restrict out, int areaX, int areaZ, int areaWidth,
|
||||
int pX = areaX&0xFFFFFFFE;
|
||||
__m256i xs = _mm256_set_epi32(pX+14, pX+12, pX+10, pX+8, pX+6, pX+4, pX+2, pX), zs;
|
||||
__m256i v2 = _mm256_set1_epi32(2), v16 = _mm256_set1_epi32(16);
|
||||
int* buf = malloc((newWidth+1)*((areaHeight+2)|1)*sizeof(*buf));
|
||||
int* buf = (int*) malloc((newWidth+1)*((areaHeight+2)|1)*sizeof(*buf));
|
||||
int* idx = buf;
|
||||
int* outIdx = out;
|
||||
//z first!
|
||||
@ -262,7 +263,7 @@ void mapZoom(Layer *l, int* __restrict out, int areaX, int areaZ, int areaWidth,
|
||||
int pX = areaX&0xFFFFFFFE;
|
||||
__m128i xs = _mm_set_epi32(pX+6, pX+4, pX+2, pX), zs;
|
||||
__m128i v2 = _mm_set1_epi32(2), v8 = _mm_set1_epi32(8);
|
||||
int* buf = malloc((newWidth+1)*(areaHeight+2|1)*sizeof(*buf));
|
||||
int* buf = (int*) malloc((newWidth+1)*(areaHeight+2|1)*sizeof(*buf));
|
||||
int* idx = buf;
|
||||
int* outIdx = out;
|
||||
//z first!
|
||||
@ -314,27 +315,28 @@ void mapZoom(Layer *l, int * __restrict out, int areaX, int areaZ, int areaWidth
|
||||
{
|
||||
int pX = areaX >> 1;
|
||||
int pZ = areaZ >> 1;
|
||||
int pWidth = (areaWidth >> 1) + 2;
|
||||
int pHeight = (areaHeight >> 1) + 2;
|
||||
int pWidth = ((areaX + areaWidth ) >> 1) - pX + 1;
|
||||
int pHeight = ((areaZ + areaHeight) >> 1) - pZ + 1;
|
||||
int x, z;
|
||||
|
||||
//printf("[%d %d] [%d %d]\n", pX, pZ, pWidth, pHeight);
|
||||
l->p->getMap(l->p, out, pX, pZ, pWidth, pHeight);
|
||||
|
||||
int newWidth = (pWidth-1) << 1;
|
||||
int newHeight = (pHeight-1) << 1;
|
||||
int newWidth = (pWidth) << 1;
|
||||
int newHeight = (pHeight) << 1;
|
||||
int idx, a, b;
|
||||
int *buf = (int *)malloc((newWidth+1)*(newHeight+1)*sizeof(*buf));
|
||||
|
||||
const int ws = (int)l->worldSeed;
|
||||
const int ss = ws * (ws * 1284865837 + 4150755663);
|
||||
|
||||
for (z = 0; z < pHeight - 1; z++)
|
||||
for (z = 0; z < pHeight; z++)
|
||||
{
|
||||
idx = (z << 1) * newWidth;
|
||||
a = out[(z+0)*pWidth];
|
||||
b = out[(z+1)*pWidth];
|
||||
|
||||
for (x = 0; x < pWidth - 1; x++)
|
||||
for (x = 0; x < pWidth; x++)
|
||||
{
|
||||
int a1 = out[x+1 + (z+0)*pWidth];
|
||||
int b1 = out[x+1 + (z+1)*pWidth];
|
||||
|
29
layers.h
29
layers.h
@ -3,6 +3,8 @@
|
||||
|
||||
#include "javarnd.h"
|
||||
|
||||
#define __STDC_FORMAT_MACROS 1
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
#include <inttypes.h>
|
||||
@ -11,15 +13,21 @@
|
||||
#define NULL ((void*)0)
|
||||
#endif
|
||||
|
||||
#define SIMD_NOTIFY 0
|
||||
|
||||
#if defined USE_SIMD && __AVX2__
|
||||
#include <emmintrin.h>
|
||||
#include <smmintrin.h>
|
||||
#include <immintrin.h>
|
||||
#if SIMD_NOTIFY
|
||||
#warning "Using AVX2 extensions."
|
||||
#endif
|
||||
#elif defined USE_SIMD && defined __SSE4_2__
|
||||
#include <emmintrin.h>
|
||||
#include <smmintrin.h>
|
||||
#if SIMD_NOTIFY
|
||||
#warning "Using SSE4.2 extensions."
|
||||
#endif
|
||||
#else
|
||||
//#warning "Using no SIMD extensions."
|
||||
#endif
|
||||
@ -164,6 +172,10 @@ STRUCT(Layer)
|
||||
Layer *p, *p2; // parent layers
|
||||
};
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
//==============================================================================
|
||||
// Essentials
|
||||
@ -352,10 +364,10 @@ static inline __m256i set8ChunkSeeds(int ws, __m256i xs, __m256i zs)
|
||||
|
||||
static inline __m256i mc8NextInt(__m256i* cs, int ws, int mask)
|
||||
{
|
||||
__m256i and = _mm256_set1_epi32(mask);
|
||||
__m256i ret = _mm256_and_si256(and, _mm256_srli_epi32(*cs, 24));
|
||||
__m256i andm = _mm256_set1_epi32(mask);
|
||||
__m256i ret = _mm256_and_si256(andm, _mm256_srli_epi32(*cs, 24));
|
||||
*cs = _mm256_add_epi32(_mm256_set1_epi32(ws), _mm256_mullo_epi32(*cs, _mm256_add_epi32(_mm256_set1_epi32(4150755663), _mm256_mullo_epi32(*cs, _mm256_set1_epi32(1284865837)))));
|
||||
return _mm256_add_epi32(ret, _mm256_and_si256(and, _mm256_cmpgt_epi32(_mm256_set1_epi32(0), ret)));;
|
||||
return _mm256_add_epi32(ret, _mm256_and_si256(andm, _mm256_cmpgt_epi32(_mm256_set1_epi32(0), ret)));
|
||||
}
|
||||
|
||||
static inline __m256i select8Random2(__m256i* cs, int ws, __m256i a1, __m256i a2)
|
||||
@ -431,10 +443,10 @@ static inline __m128i set4ChunkSeeds(int ws, __m128i xs, __m128i zs)
|
||||
|
||||
static inline __m128i mc4NextInt(__m128i* cs, int ws, int mask)
|
||||
{
|
||||
__m128i and = _mm_set1_epi32(mask);
|
||||
__m128i ret = _mm_and_si128(and, _mm_srli_epi32(*cs, 24));
|
||||
__m128i andm = _mm_set1_epi32(mask);
|
||||
__m128i ret = _mm_and_si128(andm, _mm_srli_epi32(*cs, 24));
|
||||
*cs = _mm_add_epi32( _mm_set1_epi32(ws), _mm_mullo_epi32(*cs, _mm_add_epi32(_mm_set1_epi32(4150755663), _mm_mullo_epi32(*cs, _mm_set1_epi32(1284865837)))));
|
||||
return _mm_add_epi32(ret, _mm_and_si128(and, _mm_cmplt_epi32(ret, _mm_set1_epi32(0))));;
|
||||
return _mm_add_epi32(ret, _mm_and_si128(andm, _mm_cmplt_epi32(ret, _mm_set1_epi32(0))));
|
||||
}
|
||||
|
||||
static inline __m128i select4Random2(__m128i* cs, int ws, __m128i a1, __m128i a2)
|
||||
@ -568,4 +580,9 @@ void mapOceanMix(Layer *l, int * __restrict out, int areaX, int areaZ, int areaW
|
||||
|
||||
void mapVoronoiZoom(Layer *l, int * __restrict out, int x, int z, int w, int h);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* LAYER_H_ */
|
||||
|
19
makefile
19
makefile
@ -1,21 +1,30 @@
|
||||
CC = gcc
|
||||
AR = ar
|
||||
ARFLAGS = cr
|
||||
override LDFLAGS = -lm
|
||||
override CFLAGS += -Wall -fwrapv -march=native
|
||||
#override CFLAGS += -DUSE_SIMD
|
||||
|
||||
ifeq ($(OS),Windows_NT)
|
||||
override CFLAGS += -D_WIN32
|
||||
RM = del
|
||||
else
|
||||
override LDFLAGS += -lX11 -pthread
|
||||
#RM = rm
|
||||
endif
|
||||
|
||||
.PHONY : all debug clean
|
||||
.PHONY : all debug libcubiomes clean
|
||||
|
||||
all: CFLAGS += -O3
|
||||
all: CFLAGS += -O3 -march=native
|
||||
all: find_quadhuts find_compactbiomes clean
|
||||
|
||||
debug: CFLAGS += -DDEBUG -O0 -g
|
||||
debug: CFLAGS += -DDEBUG -O0 -ggdb3
|
||||
debug: find_quadhuts find_compactbiomes clean
|
||||
|
||||
libcubiomes: CFLAGS += -O3 -fPIC
|
||||
libcubiomes: layers.o generator.o finders.o util.o
|
||||
$(AR) $(ARFLAGS) libcubiomes.a $^
|
||||
|
||||
find_compactbiomes: find_compactbiomes.o layers.o generator.o finders.o
|
||||
$(CC) -o $@ $^ $(LDFLAGS)
|
||||
|
||||
@ -41,7 +50,9 @@ generator.o: generator.c generator.h
|
||||
layers.o: layers.c layers.h
|
||||
$(CC) -c $(CFLAGS) $<
|
||||
|
||||
util.o: util.c util.h
|
||||
$(CC) -c $(CFLAGS) $<
|
||||
|
||||
clean:
|
||||
rm *.o
|
||||
$(RM) *.o
|
||||
|
||||
|
188
xmapview.c
188
xmapview.c
@ -1,133 +1,10 @@
|
||||
#include "xmapview.h"
|
||||
#include "util.h"
|
||||
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
/* Global biome colour table. */
|
||||
|
||||
|
||||
void setBiomeColour(unsigned char biomeColour[256][3], int biome,
|
||||
unsigned char r, unsigned char g, unsigned char b)
|
||||
{
|
||||
biomeColour[biome][0] = r;
|
||||
biomeColour[biome][1] = g;
|
||||
biomeColour[biome][2] = b;
|
||||
}
|
||||
|
||||
void initBiomeColours(unsigned char biomeColours[256][3])
|
||||
{
|
||||
// This colouring scheme is taken from the AMIDST program:
|
||||
// https://github.com/toolbox4minecraft/amidst
|
||||
// https://sourceforge.net/projects/amidst.mirror/
|
||||
|
||||
memset(biomeColours, 0, 256*3);
|
||||
|
||||
setBiomeColour(biomeColours, ocean, 0, 0, 112);
|
||||
setBiomeColour(biomeColours, plains,141, 179, 96);
|
||||
setBiomeColour(biomeColours, desert, 250, 148, 24);
|
||||
setBiomeColour(biomeColours, mountains, 96, 96, 96);
|
||||
setBiomeColour(biomeColours, forest, 5, 102, 33);
|
||||
setBiomeColour(biomeColours, taiga, 11, 102, 89);
|
||||
setBiomeColour(biomeColours, swamp, 7, 249, 178);
|
||||
setBiomeColour(biomeColours, river, 0, 0, 255);
|
||||
setBiomeColour(biomeColours, hell, 255, 0, 0);
|
||||
setBiomeColour(biomeColours, sky, 128, 128, 255);
|
||||
setBiomeColour(biomeColours, frozen_ocean, 112, 112, 214);
|
||||
setBiomeColour(biomeColours, frozen_river, 160, 160, 255);
|
||||
setBiomeColour(biomeColours, snowy_tundra, 255, 255, 255);
|
||||
setBiomeColour(biomeColours, snowy_mountains, 160, 160, 160);
|
||||
setBiomeColour(biomeColours, mushroom_fields, 255, 0, 255);
|
||||
setBiomeColour(biomeColours, mushroom_field_shore, 160, 0, 255);
|
||||
setBiomeColour(biomeColours, beach, 250, 222, 85);
|
||||
setBiomeColour(biomeColours, desert_hills, 210, 95, 18);
|
||||
setBiomeColour(biomeColours, wooded_hills, 34, 85, 28);
|
||||
setBiomeColour(biomeColours, taiga_hills, 22, 57, 51);
|
||||
setBiomeColour(biomeColours, mountain_edge, 114, 120, 154);
|
||||
setBiomeColour(biomeColours, jungle, 83, 123, 9);
|
||||
setBiomeColour(biomeColours, jungle_hills, 44, 66, 5);
|
||||
setBiomeColour(biomeColours, jungleEdge, 98, 139, 23);
|
||||
setBiomeColour(biomeColours, deep_ocean, 0, 0, 48);
|
||||
setBiomeColour(biomeColours, stone_shore, 162, 162, 132);
|
||||
setBiomeColour(biomeColours, snowy_beach, 250, 240, 192);
|
||||
setBiomeColour(biomeColours, birch_forest, 48, 116, 68);
|
||||
setBiomeColour(biomeColours, birch_forest_hills, 31, 95, 50);
|
||||
setBiomeColour(biomeColours, dark_forest, 64, 81, 26);
|
||||
setBiomeColour(biomeColours, snowy_taiga, 49, 85, 74);
|
||||
setBiomeColour(biomeColours, snowy_taiga_hills, 36, 63, 54);
|
||||
setBiomeColour(biomeColours, giant_tree_taiga, 89, 102, 81);
|
||||
setBiomeColour(biomeColours, giant_tree_taiga_hills, 69, 79, 62);
|
||||
setBiomeColour(biomeColours, wooded_mountains, 80, 112, 80);
|
||||
setBiomeColour(biomeColours, savanna, 189, 178, 95);
|
||||
setBiomeColour(biomeColours, savanna_plateau, 167, 157, 100);
|
||||
setBiomeColour(biomeColours, badlands, 217, 69, 21);
|
||||
setBiomeColour(biomeColours, wooded_badlands_plateau, 176, 151, 101);
|
||||
setBiomeColour(biomeColours, badlands_plateau, 202, 140, 101);
|
||||
|
||||
setBiomeColour(biomeColours, warm_ocean, 0, 0, 172);
|
||||
setBiomeColour(biomeColours, lukewarm_ocean, 0, 0, 144);
|
||||
setBiomeColour(biomeColours, cold_ocean, 32, 32, 112);
|
||||
setBiomeColour(biomeColours, deep_warm_ocean, 0, 0, 80);
|
||||
setBiomeColour(biomeColours, deep_lukewarm_ocean, 0, 0, 64);
|
||||
setBiomeColour(biomeColours, deep_cold_ocean, 32, 32, 56);
|
||||
setBiomeColour(biomeColours, deep_frozen_ocean, 64, 64, 144);
|
||||
|
||||
setBiomeColour(biomeColours, ocean+128, 0, 0, 112);
|
||||
setBiomeColour(biomeColours, plains+128, 141, 179, 96);
|
||||
setBiomeColour(biomeColours, desert+128, 250, 148, 24);
|
||||
setBiomeColour(biomeColours, mountains+128, 96, 96, 96);
|
||||
setBiomeColour(biomeColours, forest+128, 5, 102, 33);
|
||||
setBiomeColour(biomeColours, taiga+128, 11, 102, 89);
|
||||
setBiomeColour(biomeColours, swamp+128, 7, 249, 178);
|
||||
setBiomeColour(biomeColours, river+128, 0, 0, 255);
|
||||
setBiomeColour(biomeColours, hell+128, 255, 0, 0);
|
||||
setBiomeColour(biomeColours, sky+128, 128, 128, 255);
|
||||
setBiomeColour(biomeColours, frozen_ocean+128, 144, 144, 160);
|
||||
setBiomeColour(biomeColours, frozen_river+128, 160, 160, 255);
|
||||
setBiomeColour(biomeColours, snowy_tundra+128, 140, 180, 180);
|
||||
setBiomeColour(biomeColours, snowy_mountains+128, 160, 160, 160);
|
||||
setBiomeColour(biomeColours, mushroom_fields+128, 255, 0, 255);
|
||||
setBiomeColour(biomeColours, mushroom_field_shore+128, 160, 0, 255);
|
||||
setBiomeColour(biomeColours, beach+128, 250, 222, 85);
|
||||
setBiomeColour(biomeColours, desert_hills+128, 210, 95, 18);
|
||||
setBiomeColour(biomeColours, wooded_hills+128, 34, 85, 28);
|
||||
setBiomeColour(biomeColours, taiga_hills+128, 22, 57, 51);
|
||||
setBiomeColour(biomeColours, mountain_edge+128, 114, 120, 154);
|
||||
setBiomeColour(biomeColours, jungle+128, 83, 123, 9);
|
||||
setBiomeColour(biomeColours, jungle_hills+128, 44, 66, 5);
|
||||
setBiomeColour(biomeColours, jungleEdge+128, 98, 139, 23);
|
||||
setBiomeColour(biomeColours, deep_ocean+128, 0, 0, 48);
|
||||
setBiomeColour(biomeColours, stone_shore+128, 162, 162, 132);
|
||||
setBiomeColour(biomeColours, snowy_beach+128, 250, 240, 192);
|
||||
setBiomeColour(biomeColours, birch_forest+128, 48, 116, 68);
|
||||
setBiomeColour(biomeColours, birch_forest_hills+128, 31, 95, 50);
|
||||
setBiomeColour(biomeColours, dark_forest+128, 64, 81, 26);
|
||||
setBiomeColour(biomeColours, snowy_taiga+128, 49, 85, 74);
|
||||
setBiomeColour(biomeColours, snowy_taiga_hills+128, 36, 63, 54);
|
||||
setBiomeColour(biomeColours, giant_tree_taiga+128, 89, 102, 81);
|
||||
setBiomeColour(biomeColours, giant_tree_taiga_hills+128, 69, 79, 62);
|
||||
setBiomeColour(biomeColours, wooded_mountains+128, 80, 112, 80);
|
||||
setBiomeColour(biomeColours, savanna+128, 189, 178, 95);
|
||||
setBiomeColour(biomeColours, savanna_plateau+128, 167, 157, 100);
|
||||
setBiomeColour(biomeColours, badlands+128, 217, 69, 21);
|
||||
setBiomeColour(biomeColours, wooded_badlands_plateau+128, 176, 151, 101);
|
||||
setBiomeColour(biomeColours, badlands_plateau+128, 202, 140, 101);
|
||||
|
||||
setBiomeColour(biomeColours, bamboo_jungle, 118, 142, 20);
|
||||
setBiomeColour(biomeColours, bamboo_jungle_hills, 59, 71, 10);
|
||||
}
|
||||
|
||||
void initBiomeTypeColours(unsigned char biomeColours[256][3])
|
||||
{
|
||||
memset(biomeColours, 0, 256*3);
|
||||
|
||||
setBiomeColour(biomeColours, Oceanic, 0x00, 0x00, 0xa0);
|
||||
setBiomeColour(biomeColours, Warm, 0xff, 0xc0, 0x00);
|
||||
setBiomeColour(biomeColours, Lush, 0x00, 0xa0, 0x00);
|
||||
setBiomeColour(biomeColours, Cold, 0x60, 0x60, 0x60);
|
||||
setBiomeColour(biomeColours, Freezing, 0xff, 0xff, 0xff);
|
||||
}
|
||||
|
||||
|
||||
xwin_t init_x(uint sx, uint sy, const char *titel)
|
||||
{
|
||||
xwin_t w;
|
||||
@ -167,57 +44,6 @@ void close_x(xwin_t w)
|
||||
}
|
||||
|
||||
|
||||
void getBiomeColourMap(uint *colbuf, const unsigned char biomeColour[256][3],
|
||||
const int *ints, const uint sx, const uint sy, const uint pixscale)
|
||||
{
|
||||
uint i, j;
|
||||
int containsInvalidBiomes = 0;
|
||||
|
||||
for(j = 0; j < sy; j++)
|
||||
{
|
||||
for(i = 0; i < sx; i++)
|
||||
{
|
||||
int id = ints[i*sx+j]; //if(id != swamp) id = 100;
|
||||
uint r, g, b;
|
||||
|
||||
if(id < 0 || id >= 256)
|
||||
{
|
||||
// This may happen for some intermediate layers
|
||||
containsInvalidBiomes = 1;
|
||||
r = biomeColour[id&0x7f][0]-40; r = (r>0xff) ? 0x00 : r&0xff;
|
||||
g = biomeColour[id&0x7f][1]-40; g = (g>0xff) ? 0x00 : g&0xff;
|
||||
b = biomeColour[id&0x7f][2]-40; b = (b>0xff) ? 0x00 : b&0xff;
|
||||
}
|
||||
else
|
||||
{
|
||||
if(id < 128) {
|
||||
r = biomeColour[id][0];
|
||||
g = biomeColour[id][1];
|
||||
b = biomeColour[id][2];
|
||||
} else {
|
||||
r = biomeColour[id][0]+40; r = (r>0xff) ? 0xff : r&0xff;
|
||||
g = biomeColour[id][1]+40; g = (g>0xff) ? 0xff : g&0xff;
|
||||
b = biomeColour[id][2]+40; b = (b>0xff) ? 0xff : b&0xff;
|
||||
}
|
||||
}
|
||||
|
||||
uint m, n;
|
||||
for(m = 0; m < pixscale; m++){
|
||||
for(n = 0; n < pixscale; n++){
|
||||
colbuf[(j*pixscale+n) + sy*pixscale*(i*pixscale+m)] =
|
||||
((r&0xff) << 16) + ((g&0xff) << 8) + (b&0xff);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(containsInvalidBiomes)
|
||||
{
|
||||
printf("Warning: Ints contain invalid Biome IDs (Is this an intermediate layer?)\n");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void viewmap(Layer *layer, unsigned char biomeColour[256][3], int areaX, int areaZ, uint areaWidth, uint areaHeight, uint pixscale)
|
||||
{
|
||||
int *ints = allocCache(layer, areaWidth, areaHeight);
|
||||
@ -227,7 +53,7 @@ void viewmap(Layer *layer, unsigned char biomeColour[256][3], int areaX, int are
|
||||
|
||||
// Calculate a hash for the area (useful to verify the accuracy of the map)
|
||||
uint i, hash = 0;
|
||||
for(i = 0; i < areaWidth*areaHeight; i++) hash = hash ^ (i*(ints[i]+1));
|
||||
for (i = 0; i < areaWidth*areaHeight; i++) hash = hash ^ (i*(ints[i]+1));
|
||||
printf("Hash:%3X\n", hash&0xfff);
|
||||
|
||||
// construct the X11 window
|
||||
@ -242,19 +68,19 @@ void viewmap(Layer *layer, unsigned char biomeColour[256][3], int areaX, int are
|
||||
uint *colbuf = (uint *) malloc(sizeof(uint) *
|
||||
areaWidth*areaHeight*pixscale*pixscale);
|
||||
|
||||
getBiomeColourMap(colbuf, biomeColour, ints, areaWidth, areaHeight, pixscale);
|
||||
biomesToImage(colbuf, biomeColour, ints, areaWidth, areaHeight, pixscale, 0);
|
||||
|
||||
XImage *ximg = XCreateImage(w.dis, DefaultVisual(w.dis,0), 24, ZPixmap, 0,
|
||||
(char*)colbuf, areaWidth*pixscale, areaHeight*pixscale, 32, 0);
|
||||
(char*)colbuf, areaWidth*pixscale, areaHeight*pixscale, 24, 0);
|
||||
|
||||
XSetForeground(w.dis, w.gc, 0xf00020);
|
||||
|
||||
// enter the event loop
|
||||
while(1)
|
||||
while (1)
|
||||
{
|
||||
XNextEvent(w.dis, &event);
|
||||
|
||||
if(event.type == ClientMessage)
|
||||
if (event.type == ClientMessage)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
@ -20,11 +20,6 @@ typedef struct xwin_t
|
||||
|
||||
} xwin_t;
|
||||
|
||||
|
||||
void initBiomeColours(unsigned char biomeColours[256][3]);
|
||||
void initBiomeTypeColours(unsigned char biomeColours[256][3]);
|
||||
|
||||
|
||||
xwin_t init_x(uint sx, uint sy, const char *titel);
|
||||
void close_x(xwin_t w);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user