আমি সি # সহ একটি দ্বীপের মানচিত্রে একটি মাস্ক উত্পন্ন করার জন্য একটি দুর্দান্ত এবং সহজ উপায় অনুসন্ধান করছি।
মূলত আমি পার্লিন শব্দের সাথে উত্পন্ন এলোমেলো উচ্চতা ম্যাপটি ব্যবহার করছি, যেখানে ভূখণ্ডটি জলের চারপাশে নয়।
পরবর্তী পদক্ষেপটি হবে একটি মুখোশ তৈরি করা, কোণ এবং সীমানা কেবল জল কিনা তা নিশ্চিত করা।
তারপরে আমি একটি দ্বীপ পেতে পার্লিন শব্দ শব্দটি থেকে কেবল মুখোশটি বিয়োগ করতে পারি।
এবং বিপরীতে খেলা প্রায় ...
এবং গ্রেডিয়েন্ট বক্ররেখা, আমি যেমন চাই ঠিক তেমন একটি দ্বীপের উচ্চতা ম্যাপটি পেতে পারি ..
(এগুলি অবশ্যই উদাহরণস্বরূপ)
আপনি যেমন দেখতে পাচ্ছেন, দ্বীপের "প্রান্তগুলি" সবেমাত্র কেটে গেছে, রঙের মান খুব বেশি সাদা না হলে এটি কোনও বড় সমস্যা নয়, কারণ আমি গ্রেস্কেলকে কেবল 4 টি স্তরগুলিতে ভাগ করব (জল, বালু, ঘাস এবং শিলা)।
আমার প্রশ্ন হ'ল আমি কীভাবে দ্বিতীয় চিত্রের মতো একটি ভাল চেহারাওয়ালা মুখোশ তৈরি করতে পারি?
হালনাগাদ
আমি এই কৌশলটি পেয়েছি, এটি আমার কাছে একটি দুর্দান্ত সূচনার পয়েন্ট বলে মনে হচ্ছে, তবে আমি নিশ্চিত না যে আমি কীভাবে সুনির্দিষ্টভাবে এটি বাস্তবায়িত করতে পছন্দসই আউটপুট পেতে পারি। http://mrl.nyu.edu/~perlin/experiments/puff/
আপডেট 2
এটি আমার চূড়ান্ত সমাধান।
আমি makeMask()
আমার নরমালাইজেশন লুপটির ভিতরে ফাংশনটি এভাবে প্রয়োগ করেছি :
//normalisation
for( int i = 0; i < width; i++ ) {
for( int j = 0; j < height; j++ ) {
perlinNoise[ i ][ j ] /= totalAmplitude;
perlinNoise[ i ][ j ] = makeMask( width, height, i, j, perlinNoise[ i ][ j ] );
}
}
এবং এটি চূড়ান্ত ফাংশন:
public static float makeMask( int width, int height, int posX, int posY, float oldValue ) {
int minVal = ( ( ( height + width ) / 2 ) / 100 * 2 );
int maxVal = ( ( ( height + width ) / 2 ) / 100 * 10 );
if( getDistanceToEdge( posX, posY, width, height ) <= minVal ) {
return 0;
} else if( getDistanceToEdge( posX, posY, width, height ) >= maxVal ) {
return oldValue;
} else {
float factor = getFactor( getDistanceToEdge( posX, posY, width, height ), minVal, maxVal );
return oldValue * factor;
}
}
private static float getFactor( int val, int min, int max ) {
int full = max - min;
int part = val - min;
float factor = (float)part / (float)full;
return factor;
}
public static int getDistanceToEdge( int x, int y, int width, int height ) {
int[] distances = new int[]{ y, x, ( width - x ), ( height - y ) };
int min = distances[ 0 ];
foreach( var val in distances ) {
if( val < min ) {
min = val;
}
}
return min;
}
এটি চিত্র # 3 এর মতো একটি আউটপুট দেবে।
কোডে কিছুটা পরিবর্তন আনলে আপনি ছবিতে # 2 -> এর মতো আসল আউটপুট পেতে পারেন
public static float makeMask( int width, int height, int posX, int posY, float oldValue ) {
int minVal = ( ( ( height + width ) / 2 ) / 100 * 2 );
int maxVal = ( ( ( height + width ) / 2 ) / 100 * 20 );
if( getDistanceToEdge( posX, posY, width, height ) <= minVal ) {
return 0;
} else if( getDistanceToEdge( posX, posY, width, height ) >= maxVal ) {
return 1;
} else {
float factor = getFactor( getDistanceToEdge( posX, posY, width, height ), minVal, maxVal );
return ( oldValue + oldValue ) * factor;
}
}