質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
87.20%
C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Unity

Unityは、ユニティテクノロジーが開発したゲームエンジンです。 主にモバイルやブラウザ向けのゲーム製作に利用されていましたが、3Dの重力付きゲームが簡単に作成できることから需要が増え、現在はマルチプラットフォームに対応しています。 言語はC言語/C++で書かれていますが、C#、JavaScript、Booで書かれたコードにも対応しています。

解決済

Unity2D テクスチャブレンド

退会済みユーザー

退会済みユーザー

総合スコア0

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Unity

Unityは、ユニティテクノロジーが開発したゲームエンジンです。 主にモバイルやブラウザ向けのゲーム製作に利用されていましたが、3Dの重力付きゲームが簡単に作成できることから需要が増え、現在はマルチプラットフォームに対応しています。 言語はC言語/C++で書かれていますが、C#、JavaScript、Booで書かれたコードにも対応しています。

1回答

0評価

0クリップ

57閲覧

投稿2019/04/11 15:13

前提・実現したいこと

メッシュに適応しているテクスチャをブレンドするシェーダーを作り、自然な見た目の地形表現をしたい。

該当のソースコード

C#

using System.Collections; using System.Collections.Generic; using UnityEngine; public class World : MonoBehaviour { public int width; public int height; public Tile[,] tiles; public Material material; Mesh mesh; public string seed; public bool randomSeed; public float frequency; public float amplitude; public float lacunarity; public float persistance; public int octaves; Noise noise; private void Awake() { if(randomSeed == true) { int value = Random.Range(-1000, 10000); seed = value.ToString(); } noise = new Noise(seed.GetHashCode(), frequency, amplitude, lacunarity, persistance, octaves); } // Use this for initialization void Start() { CreateTiles(); GenerateMesh(); } // Update is called once per frame void Update() { Graphics.DrawMesh(mesh, Vector3.zero, Quaternion.identity, material, 0); } void CreateTiles() { tiles = new Tile[width, height]; float[,] noiseValues = noise.GetNoiseValues(width, height); for (int i = 0; i < width; i++) { for (int j = 0; j < height; j++) { if(noiseValues[i,j] > 0.5f) { tiles[i, j] = new Tile(Tile.Type.Grass); } else { tiles[i, j] = new Tile(Tile.Type.Dirt); } } } } void GenerateMesh() { MeshData data = new MeshData(tiles); mesh = new Mesh(); // 頂点インデックスのフォーマットを32ビット整数に変更する mesh.indexFormat = UnityEngine.Rendering.IndexFormat.UInt32; mesh.vertices = data.vertices.ToArray(); mesh.triangles = data.triangles.ToArray(); mesh.uv = data.UVs.ToArray(); mesh.RecalculateNormals(); mesh.RecalculateBounds(); } }

C#

using System.Collections; using System.Collections.Generic; using UnityEngine; public class MeshData{ public List<Vector3> vertices; public List<int> triangles; public List<Vector2> UVs; public MeshData(Tile[,] data) { vertices = new List<Vector3>(); triangles = new List<int>(); UVs = new List<Vector2>(); for(int i = 0; i < data.GetLength(0); i++) { for(int j = 0;j < data.GetLength(1); j++) { CreateSquare(data[i, j], i, j); } } } void CreateSquare(Tile tile,int x,int y) { vertices.Add(new Vector3(x + 0, y + 0)); vertices.Add(new Vector3(x + 1, y + 0)); vertices.Add(new Vector3(x + 0, y + 1)); vertices.Add(new Vector3(x + 1, y + 1)); triangles.Add(vertices.Count - 1); triangles.Add(vertices.Count - 3); triangles.Add(vertices.Count - 4); triangles.Add(vertices.Count - 2); triangles.Add(vertices.Count - 1); triangles.Add(vertices.Count - 4); UVs.AddRange(SpriteLoader.instance.GetTileUVs(tile)); } }

C#

using System.Collections; using System.Collections.Generic; using UnityEngine; public class Tile{ public enum Type { Dirt,Grass } public Type type; public Tile(Type type) { this.type = type; } }

C#

using System.Collections; using System.Collections.Generic; using UnityEngine; public class Noise { int seed; float frequency; float amplitude; float lacunarity; float persistance; int octaves; public Noise(int seed,float frequency,float amplitude,float lacunarity,float persistance,int octaves) { this.seed = seed; this.frequency = frequency; this.amplitude = amplitude; this.lacunarity = lacunarity; this.persistance = persistance; this.octaves = octaves; } public float [,] GetNoiseValues(int width,int height) { float[,] noiseValues = new float[width, height]; float max = 0f; float min = float.MaxValue; for(int i = 0; i < width; i++) { for(int j =0; j < height; j++) { noiseValues[i, j] = 0f; float tempA = amplitude; float tempF = frequency; for(int k = 0;k < octaves; k++) { noiseValues[i, j] += Mathf.PerlinNoise((i + seed) / (float)width * frequency, j / (float)height * frequency) * amplitude; frequency *= lacunarity; amplitude *= persistance; } amplitude = tempA; frequency = tempF; if(noiseValues[i,j] > max) { max = noiseValues[i, j]; } if(noiseValues[i,j] < min) { min = noiseValues[i, j]; } } } for (int i = 0; i < width; i++) { for (int j = 0; j < height; j++) { noiseValues[i, j] = Mathf.InverseLerp(max, min, noiseValues[i, j]); } } return noiseValues; } }

C#

using System.Collections; using System.Collections.Generic; using UnityEngine; using System.Linq; public class SpriteLoader : MonoBehaviour { public static SpriteLoader instance; Dictionary<string, Vector2[]> tileUVMap; // Use this for initialization void Awake() { instance = this; tileUVMap = new Dictionary<string, Vector2[]>(); Sprite[] sprites = Resources.LoadAll<Sprite>("World Tiles"); float imageWidth = 0f; float imageHeight = 0f; foreach (Sprite s in sprites) { if (s.rect.x + s.rect.width > imageWidth) imageWidth = s.rect.x + s.rect.width; if (s.rect.y + s.rect.height > imageHeight) imageHeight = s.rect.y + s.rect.height; } foreach (Sprite s in sprites) { Vector2[] uvs = new Vector2[4]; uvs[0] = new Vector2(s.rect.x / imageWidth, s.rect.y / imageHeight); uvs[1] = new Vector2((s.rect.x + s.rect.width) / imageWidth, s.rect.y / imageHeight); uvs[2] = new Vector2(s.rect.x / imageWidth, (s.rect.y + s.rect.height) / imageHeight); uvs[3] = new Vector2((s.rect.x + s.rect.width) / imageWidth, (s.rect.y + s.rect.height) / imageHeight); tileUVMap.Add(s.name, uvs); //Debug.Log(s.name + " :" + uvs[0] + "," + uvs[1] + "," + uvs[2] + "," + uvs[3]); } } // Update is called once per frame void Update() { } public Vector2[] GetTileUVs(Tile tile) { string key = tile.type.ToString(); if (tileUVMap.ContainsKey(key) == true) { return tileUVMap[key]; } else { Debug.LogError("There is no UV map for tile type: " + key); return tileUVMap["Void"]; } } }

試したこと

テクスチャのあるメッシュを生成しましたが、どうやれば目的のシェーダーを作れるのかが分かりませんでした。

イメージ説明
イメージ説明

理想↓
イメージ説明

回答お願いします。

良い質問の評価を上げる

以下のような質問は評価を上げましょう

  • 質問内容が明確
  • 自分も答えを知りたい
  • 質問者以外のユーザにも役立つ

評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

気になる質問をクリップする

クリップした質問は、後からいつでもマイページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

  • プログラミングに関係のない質問
  • やってほしいことだけを記載した丸投げの質問
  • 問題・課題が含まれていない質問
  • 意図的に内容が抹消された質問
  • 過去に投稿した質問と同じ内容の質問
  • 広告と受け取られるような投稿

評価を下げると、トップページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

まだ回答がついていません

会員登録して回答してみよう

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
87.20%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問

同じタグがついた質問を見る

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Unity

Unityは、ユニティテクノロジーが開発したゲームエンジンです。 主にモバイルやブラウザ向けのゲーム製作に利用されていましたが、3Dの重力付きゲームが簡単に作成できることから需要が増え、現在はマルチプラットフォームに対応しています。 言語はC言語/C++で書かれていますが、C#、JavaScript、Booで書かれたコードにも対応しています。