public static OSDMap SerializeAppearance(IAssetClient assetClient, Primitive.TextureEntry texture, byte[] visualParams) { // Fetch all of the texture assets Dictionary <UUID, byte[]> textures = new Dictionary <UUID, byte[]>(); for (int i = 0; i < texture.FaceTextures.Length; i++) { Primitive.TextureEntryFace face = texture.FaceTextures[i]; if (face != null && face.TextureID != AppearanceManager.DEFAULT_AVATAR_TEXTURE && !textures.ContainsKey(face.TextureID)) { // Fetch this texture Asset asset; if (assetClient.TryGetAsset(face.TextureID, "image/x-j2c", out asset)) { textures.Add(face.TextureID, asset.Data); } } } OSDMap assets = new OSDMap(textures.Count); foreach (KeyValuePair <UUID, byte[]> kvp in textures) { assets.Add(kvp.Key.ToString(), OSD.FromBinary(kvp.Value)); } return(new OSDMap { { "texture", texture.GetOSD() }, { "parameters", OSD.FromBinary(visualParams) }, { "assets", assets } }); }
public bool Start(Simian simian) { m_simian = simian; m_httpServer = simian.GetAppModule <IHttpServer>(); m_assetClient = simian.GetAppModule <IAssetClient>(); m_sceneFactory = simian.GetAppModule <ISceneFactory>(); if (m_sceneFactory != null) { m_sceneFactory.OnSceneStart += SceneStartHandler; m_sceneFactory.OnSceneStop += SceneStopHandler; } IConfigSource source = simian.Config; IConfig config = source.Configs["SimianGrid"]; if (config != null) { m_serverUrl = config.GetString("GridService", null); } if (String.IsNullOrEmpty(m_serverUrl)) { m_log.Error("[SimianGrid] config section is missing the GridService URL"); return(false); } return(true); }
public HSProductCommand(AppSettings settings, IOrderCloudClient elevatedOc, ISupplierApiClientHelper apiClientHelper, IAssetClient assetClient) { _oc = elevatedOc; _settings = settings; _apiClientHelper = apiClientHelper; _assetClient = assetClient; }
public void Start(IScene scene) { m_scene = scene; m_httpServer = m_scene.Simian.GetAppModule <IHttpServer>(); if (m_httpServer == null) { m_log.Warn("NewFileAgentInventory requires an IHttpServer"); return; } m_assetClient = m_scene.Simian.GetAppModule <IAssetClient>(); if (m_assetClient == null) { m_log.Warn("NewFileAgentInventory requires an IAssetClient"); return; } m_inventoryClient = m_scene.Simian.GetAppModule <IInventoryClient>(); if (m_inventoryClient == null) { m_log.Warn("NewFileAgentInventory requires an IInventoryClient"); } m_permissions = m_scene.GetSceneModule <LLPermissions>(); //m_scene.Capabilities.AddProtectedResource(m_scene.ID, "NewFileAgentInventory", NewFileAgentInventoryHandler); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "NewFileAgentInventoryVariablePrice", NewFileAgentInventoryVariablePriceHandler); }
public void Start(IScene scene) { m_scene = scene; m_assetClient = m_scene.Simian.GetAppModule <IAssetClient>(); if (m_assetClient == null) { m_log.Warn("Upload requires an IAssetClient"); return; } m_httpServer = m_scene.Simian.GetAppModule <IHttpServer>(); if (m_httpServer == null) { m_log.Warn("Upload requires an IHttpServer"); return; } m_primMesher = m_scene.GetSceneModule <IPrimMesher>(); m_permissions = m_scene.GetSceneModule <LLPermissions>(); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "UploadBakedTexture", UploadBakedTextureHandler); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "UploadBakedTextureData", UploadBakedTextureDataHandler); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "UploadObjectAsset", UploadObjectAssetHandler); }
public void Start(IScene scene) { m_scene = scene; m_httpServer = m_scene.Simian.GetAppModule<IHttpServer>(); if (m_httpServer == null) { m_log.Warn("NewFileAgentInventory requires an IHttpServer"); return; } m_assetClient = m_scene.Simian.GetAppModule<IAssetClient>(); if (m_assetClient == null) { m_log.Warn("NewFileAgentInventory requires an IAssetClient"); return; } m_inventoryClient = m_scene.Simian.GetAppModule<IInventoryClient>(); if (m_inventoryClient == null) { m_log.Warn("NewFileAgentInventory requires an IInventoryClient"); } m_permissions = m_scene.GetSceneModule<LLPermissions>(); //m_scene.Capabilities.AddProtectedResource(m_scene.ID, "NewFileAgentInventory", NewFileAgentInventoryHandler); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "NewFileAgentInventoryVariablePrice", NewFileAgentInventoryVariablePriceHandler); }
public void Start(IScene scene) { m_scene = scene; m_assetClient = m_scene.Simian.GetAppModule<IAssetClient>(); if (m_assetClient == null) { m_log.Warn("Upload requires an IAssetClient"); return; } m_httpServer = m_scene.Simian.GetAppModule<IHttpServer>(); if (m_httpServer == null) { m_log.Warn("Upload requires an IHttpServer"); return; } m_primMesher = m_scene.GetSceneModule<IPrimMesher>(); m_permissions = m_scene.GetSceneModule<LLPermissions>(); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "UploadBakedTexture", UploadBakedTextureHandler); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "UploadBakedTextureData", UploadBakedTextureDataHandler); m_scene.Capabilities.AddProtectedResource(m_scene.ID, "UploadObjectAsset", UploadObjectAssetHandler); }
public void Start(IScene scene) { m_scene = scene; m_scheduler = m_scene.Simian.GetAppModule <IScheduler>(); if (m_scheduler == null) { m_log.Error("OARLoader requires an IScheduler"); return; } m_assetClient = m_scene.Simian.GetAppModule <IAssetClient>(); if (m_assetClient == null) { m_log.Error("OARLoader requires an IAssetClient"); return; } m_primMesher = m_scene.GetSceneModule <IPrimMesher>(); m_terrain = m_scene.GetSceneModule <ITerrain>(); m_regionInfo = m_scene.GetSceneModule <RegionInfo>(); m_udp = m_scene.GetSceneModule <LLUDP>(); m_permissions = m_scene.GetSceneModule <LLPermissions>(); m_scene.AddCommandHandler("loadoar", LoadOARHandler); }
public static BattleriteClient Create( IAssetClient assetClient, IMatchClient matchClient, IPlayerClient playerClient) { return(new BattleriteClient(assetClient, matchClient, playerClient)); }
public PlayerClient Create( IAssetClient assetClient, IRequestUrlBuilder requestUrlBuilder, IRequester requester, JsonSerializerSettings jsonApiSerializerSettings) { return(new PlayerClient(assetClient, requestUrlBuilder, requester, jsonApiSerializerSettings)); }
internal BattleriteClient( IAssetClient assets, IMatchClient matches, IPlayerClient players) { Players = players; Matches = matches; Assets = assets; }
private IAssetClient CreateOrGetAssetClient() { IAssetClient assetClient = null; assetClientFactory.Or(() => new AssetClientFactory()) .MatchSome(factory => assetClient = factory.Create(new HttpClient())); return(assetClient); }
public void Start(IScene scene) { m_assetClient = scene.Simian.GetAppModule<IAssetClient>(); m_terrain = scene.GetSceneModule<ITerrain>(); m_primMesher = scene.GetSceneModule<IPrimMesher>(); m_lslScriptEngine = scene.GetSceneModule<ILSLScriptEngine>(); int implemented = CountMethods(); m_log.Debug("Initializing LSL API with " + implemented + "/" + m_methods.Count + " implemented methods"); }
public void Start(IScene scene) { m_httpServer = scene.Simian.GetAppModule<IHttpServer>(); m_assetClient = scene.Simian.GetAppModule<IAssetClient>(); m_terrain = scene.GetSceneModule<ITerrain>(); m_primMesher = scene.GetSceneModule<IPrimMesher>(); m_lslScriptEngine = scene.GetSceneModule<ILSLScriptEngine>(); m_messaging = scene.GetSceneModule<Messaging>(); m_sounds = scene.GetSceneModule<Sounds>(); }
public void Start(IScene scene) { m_httpServer = scene.Simian.GetAppModule <IHttpServer>(); m_assetClient = scene.Simian.GetAppModule <IAssetClient>(); m_terrain = scene.GetSceneModule <ITerrain>(); m_primMesher = scene.GetSceneModule <IPrimMesher>(); m_lslScriptEngine = scene.GetSceneModule <ILSLScriptEngine>(); m_messaging = scene.GetSceneModule <Messaging>(); m_sounds = scene.GetSceneModule <Sounds>(); }
internal PlayerClient( IAssetClient cachedAssetClient, IRequestUrlBuilder builder, IRequester requester, JsonSerializerSettings jsonApiSerializerSettings) { this.cachedAssetClient = cachedAssetClient; this.requester = requester; this.jsonApiSerializerSettings = jsonApiSerializerSettings; this.builder = builder; }
public void Start(IScene scene) { m_assetClient = scene.Simian.GetAppModule <IAssetClient>(); m_meshCache = scene.Simian.GetAppModule <MeshCache>(); List <string> rendererNames = RenderingLoader.ListRenderers(Util.ExecutingDirectory()); if (rendererNames.Count == 0) { m_log.Error("PrimMesher could not find a valid OpenMetaverse.Rendering.*.dll plugin"); return; } // TODO: Add a config option to allow a preferred renderer to be selected m_renderer = RenderingLoader.LoadRenderer(rendererNames[0]); m_log.Debug(scene.Name + " is meshing prims with " + m_renderer); }
private IPlayerClient CreateOrGetPlayerClient( JsonSerializerSettings jsonSerializerSettings, IRequestUrlBuilder requestUrlBuilder, IRequester requester, IAssetClient assetClient) { IPlayerClient playerClient = null; playerClientFactory.Or(() => new PlayerClientFactory()) .MatchSome( factory => playerClient = factory.Create( assetClient, requestUrlBuilder, requester, jsonSerializerSettings)); return(playerClient); }
public void Start(IScene scene) { m_scene = scene; m_assetClient = m_scene.Simian.GetAppModule<IAssetClient>(); if (m_assetClient == null) { m_log.Error("Can't initialize texture downloads without an IAssetClient"); return; } m_udp = m_scene.GetSceneModule<LLUDP>(); if (m_udp != null) { m_udp.AddPacketHandler(PacketType.RequestImage, RequestImageHandler); m_udp.OnQueueEmpty += QueueEmptyHandler; } }
public void Start(IScene scene) { m_scene = scene; m_assetClient = m_scene.Simian.GetAppModule <IAssetClient>(); if (m_assetClient == null) { m_log.Error("Can't initialize texture downloads without an IAssetClient"); return; } m_udp = m_scene.GetSceneModule <LLUDP>(); if (m_udp != null) { m_udp.AddPacketHandler(PacketType.RequestImage, RequestImageHandler); m_udp.OnQueueEmpty += QueueEmptyHandler; } }
public void Start(IScene scene) { m_scene = scene; m_httpServer = m_scene.Simian.GetAppModule <IHttpServer>(); if (m_httpServer == null) { m_log.Warn("GetTexture requires an IHttpServer"); return; } m_assetClient = m_scene.Simian.GetAppModule <IAssetClient>(); if (m_assetClient == null) { m_log.Warn("GetTexture requires an IAssetClient"); return; } m_scene.Capabilities.AddProtectedResource(m_scene.ID, "GetTexture", GetTextureHandler); }
public void Start(IScene scene) { m_scene = scene; m_httpServer = m_scene.Simian.GetAppModule<IHttpServer>(); if (m_httpServer == null) { m_log.Warn("GetMesh requires an IHttpServer"); return; } m_assetClient = m_scene.Simian.GetAppModule<IAssetClient>(); if (m_assetClient == null) { m_log.Warn("GetMesh requires an IAssetClient"); return; } m_scene.Capabilities.AddProtectedResource(m_scene.ID, "GetMesh", GetMeshHandler); }
public bool Start(Simian simian) { m_simian = simian; m_httpServer = simian.GetAppModule <IHttpServer>(); if (m_httpServer == null) { m_log.Error("StandaloneGridClient requires an IHttpServer"); return(false); } m_sceneFactory = simian.GetAppModule <ISceneFactory>(); if (m_sceneFactory == null) { m_log.Error("StandaloneGridClient requires an ISceneFactory"); return(false); } m_assetClient = simian.GetAppModule <IAssetClient>(); return(true); }
public void Start(IScene scene) { m_scene = scene; m_scheduler = scene.Simian.GetAppModule <IScheduler>(); if (m_scheduler == null) { m_log.Error("XEngine requires an IScheduler"); return; } m_assetClient = scene.Simian.GetAppModule <IAssetClient>(); if (m_assetClient == null) { m_log.Error("XEngine requires an IAssetClient"); return; } // Build the thread pool that will run script events STPStartInfo eventThreadPoolInfo = new STPStartInfo { IdleTimeout = 60 * 1000, MinWorkerThreads = 0, MaxWorkerThreads = 50, ThreadPriority = ThreadPriority.BelowNormal }; m_eventThreadPool = new SmartThreadPool(eventThreadPoolInfo); m_eventThreadPool.Start(); m_running = true; Thread scriptEventsThread = new Thread(ScriptEventsThread); scriptEventsThread.Name = "XEngine (" + m_scene.Name + ")"; scriptEventsThread.IsBackground = true; scriptEventsThread.Start(); }
public void Start(IScene scene) { m_scene = scene; m_assets = m_scene.Simian.GetAppModule <IAssetClient>(); if (m_assets == null) { m_log.Error("Can't initialize asset transfers without an IAssetClient"); return; } m_permissions = m_scene.GetSceneModule <LLPermissions>(); m_udp = m_scene.GetSceneModule <LLUDP>(); if (m_udp != null) { m_udp.AddPacketHandler(PacketType.RequestXfer, RequestXferHandler); m_udp.AddPacketHandler(PacketType.ConfirmXferPacket, ConfirmXferPacketHandler); m_udp.AddPacketHandler(PacketType.AssetUploadRequest, AssetUploadRequestHandler); m_udp.AddPacketHandler(PacketType.SendXferPacket, SendXferPacketHandler); m_udp.AddPacketHandler(PacketType.AbortXfer, AbortXferHandler); m_udp.AddPacketHandler(PacketType.TransferRequest, TransferRequestHandler); } }
public void Start(IScene scene) { m_scene = scene; m_assets = m_scene.Simian.GetAppModule<IAssetClient>(); if (m_assets == null) { m_log.Error("Can't initialize asset transfers without an IAssetClient"); return; } m_permissions = m_scene.GetSceneModule<LLPermissions>(); m_udp = m_scene.GetSceneModule<LLUDP>(); if (m_udp != null) { m_udp.AddPacketHandler(PacketType.RequestXfer, RequestXferHandler); m_udp.AddPacketHandler(PacketType.ConfirmXferPacket, ConfirmXferPacketHandler); m_udp.AddPacketHandler(PacketType.AssetUploadRequest, AssetUploadRequestHandler); m_udp.AddPacketHandler(PacketType.SendXferPacket, SendXferPacketHandler); m_udp.AddPacketHandler(PacketType.AbortXfer, AbortXferHandler); m_udp.AddPacketHandler(PacketType.TransferRequest, TransferRequestHandler); } }
public void Start(IScene scene) { m_scene = scene; m_scheduler = m_scene.Simian.GetAppModule<IScheduler>(); if (m_scheduler == null) { m_log.Error("Inventory requires an IScheduler"); return; } m_inventoryClient = m_scene.Simian.GetAppModule<IInventoryClient>(); if (m_inventoryClient == null) { m_log.Error("Inventory requires an IInventoryClient"); return; } m_assetClient = m_scene.Simian.GetAppModule<IAssetClient>(); if (m_assetClient == null) { m_log.Error("Inventory requires an IAssetClient"); return; } m_primMesher = m_scene.GetSceneModule<IPrimMesher>(); if (m_primMesher == null) { m_log.Error("Inventory requires an IPrimMesher"); return; } m_physics = m_scene.GetSceneModule<IPhysicsEngine>(); m_permissions = m_scene.GetSceneModule<LLPermissions>(); m_udp = m_scene.GetSceneModule<LLUDP>(); if (m_udp != null) { m_udp.AddPacketHandler(PacketType.CreateInventoryItem, CreateInventoryItemHandler); m_udp.AddPacketHandler(PacketType.CreateInventoryFolder, CreateInventoryFolderHandler); m_udp.AddPacketHandler(PacketType.UpdateInventoryItem, UpdateInventoryItemHandler); m_udp.AddPacketHandler(PacketType.UpdateInventoryFolder, UpdateInventoryFolderHandler); m_udp.AddPacketHandler(PacketType.FetchInventoryDescendents, FetchInventoryDescendentsHandler); m_udp.AddPacketHandler(PacketType.FetchInventory, FetchInventoryHandler); m_udp.AddPacketHandler(PacketType.CopyInventoryItem, CopyInventoryItemHandler); m_udp.AddPacketHandler(PacketType.MoveInventoryItem, MoveInventoryItemHandler); m_udp.AddPacketHandler(PacketType.MoveInventoryFolder, MoveInventoryFolderHandler); m_udp.AddPacketHandler(PacketType.RemoveInventoryItem, RemoveInventoryItemHandler); m_udp.AddPacketHandler(PacketType.RemoveInventoryFolder, RemoveInventoryFolderHandler); m_udp.AddPacketHandler(PacketType.PurgeInventoryDescendents, PurgeInventoryDescendentsHandler); m_udp.AddPacketHandler(PacketType.DeRezObject, DeRezObjectHandler); m_udp.AddPacketHandler(PacketType.RezObject, RezObjectHandler); m_udp.AddPacketHandler(PacketType.LinkInventoryItem, LinkInventoryItemHandler); } }
public bool Start(Simian simian) { m_assetClient = simian.GetAppModule<IAssetClient>(); return true; }
public bool Start(Simian simian) { m_simian = simian; m_httpServer = simian.GetAppModule<IHttpServer>(); m_assetClient = simian.GetAppModule<IAssetClient>(); m_sceneFactory = simian.GetAppModule<ISceneFactory>(); if (m_sceneFactory != null) { m_sceneFactory.OnSceneStart += SceneStartHandler; m_sceneFactory.OnSceneStop += SceneStopHandler; } IConfigSource source = simian.Config; IConfig config = source.Configs["SimianGrid"]; if (config != null) m_serverUrl = config.GetString("GridService", null); if (String.IsNullOrEmpty(m_serverUrl)) { m_log.Error("[SimianGrid] config section is missing the GridService URL"); return false; } return true; }
public void Start(IScene scene) { m_assetClient = scene.Simian.GetAppModule<IAssetClient>(); }
public void Start(IScene scene) { m_assetClient = scene.Simian.GetAppModule<IAssetClient>(); m_meshCache = scene.Simian.GetAppModule<MeshCache>(); List<string> rendererNames = RenderingLoader.ListRenderers(Util.ExecutingDirectory()); if (rendererNames.Count == 0) { m_log.Error("PrimMesher could not find a valid OpenMetaverse.Rendering.*.dll plugin"); return; } // TODO: Add a config option to allow a preferred renderer to be selected m_renderer = RenderingLoader.LoadRenderer(rendererNames[0]); m_log.Debug(scene.Name + " is meshing prims with " + m_renderer); }
private bool m_useAntiAliasing = true; // TODO: Make this a config option public bool Start(Simian simian) { m_assetClient = simian.GetAppModule <IAssetClient>(); return(true); }
public AssetController(IAssetClient command) { _command = command; }
/// <summary> /// Builds a composited terrain texture given the region texture /// and heightmap settings /// </summary> /// <param name="heightmap">Terrain heightmap</param> /// <param name="regionInfo">Region information including terrain texture parameters</param> /// <returns>A composited 256x256 RGB texture ready for rendering</returns> /// <remarks>Based on the algorithm described at http://opensimulator.org/wiki/Terrain_Splatting /// </remarks> public static Bitmap Splat(float[] heightmap, UUID[] textureIDs, float[] startHeights, float[] heightRanges, Vector3d regionPosition, IAssetClient assetClient) { Debug.Assert(heightmap.Length == 256 * 256); Debug.Assert(textureIDs.Length == 4); Debug.Assert(startHeights.Length == 4); Debug.Assert(heightRanges.Length == 4); // Swap empty terrain textureIDs with default IDs for (int i = 0; i < textureIDs.Length; i++) { if (textureIDs[i] == UUID.Zero) textureIDs[i] = DEFAULT_TERRAIN_DETAIL[i]; } #region Texture Fetching Bitmap[] detailTexture = new Bitmap[4]; if (assetClient != null) { for (int i = 0; i < 4; i++) { Asset asset; UUID cacheID = UUID.Combine(TEXTURE_CACHE_MAGIC, textureIDs[i]); // Try to fetch a cached copy of the decoded/resized version of this texture if (assetClient.TryGetCachedAsset(cacheID, "image/png", out asset)) { try { using (System.IO.MemoryStream stream = new System.IO.MemoryStream(asset.Data)) detailTexture[i] = (Bitmap)Image.FromStream(stream); } catch (Exception ex) { m_log.Warn("Failed to decode cached terrain texture " + cacheID + " (textureID: " + textureIDs[i] + "): " + ex.Message); } } if (detailTexture[i] == null) { // Try to fetch the original JPEG2000 texture, resize if needed, and cache as PNG if (assetClient.TryGetAsset(textureIDs[i], "image/x-j2c", out asset)) { try { detailTexture[i] = (Bitmap)CSJ2K.J2kImage.FromBytes(asset.Data); } catch (Exception ex) { m_log.Warn("Failed to decode terrain texture " + asset.ID + ": " + ex.Message); } } if (detailTexture[i] != null) { Bitmap bitmap = detailTexture[i]; // Make sure this texture is the correct size, otherwise resize if (bitmap.Width != 256 || bitmap.Height != 256) bitmap = Util.ResizeImage(bitmap, 256, 256); // Save the decoded and resized texture to the cache byte[] data; using (System.IO.MemoryStream stream = new System.IO.MemoryStream()) { bitmap.Save(stream, ImageFormat.Png); data = stream.ToArray(); } assetClient.StoreAsset( new Asset { ContentType = "image/png", CreationDate = DateTime.UtcNow, CreatorID = UUID.Zero, Data = data, ID = cacheID, Local = true, Temporary = true } ); } } } } // Fill in any missing textures with a solid color for (int i = 0; i < 4; i++) { if (detailTexture[i] == null) { // Create a solid color texture for this layer detailTexture[i] = new Bitmap(256, 256, PixelFormat.Format24bppRgb); using (Graphics gfx = Graphics.FromImage(detailTexture[i])) { using (SolidBrush brush = new SolidBrush(DEFAULT_TERRAIN_COLOR[i])) gfx.FillRectangle(brush, 0, 0, 256, 256); } } } #endregion Texture Fetching #region Layer Map float[] layermap = new float[256 * 256]; for (int y = 0; y < 256; y++) { for (int x = 0; x < 256; x++) { float height = heightmap[y * 256 + x]; float pctX = (float)x / 255f; float pctY = (float)y / 255f; // Use bilinear interpolation between the four corners of start height and // height range to select the current values at this position float startHeight = Util.Bilinear( startHeights[0], startHeights[2], startHeights[1], startHeights[3], pctX, pctY); startHeight = Utils.Clamp(startHeight, 0f, 255f); float heightRange = Util.Bilinear( heightRanges[0], heightRanges[2], heightRanges[1], heightRanges[3], pctX, pctY); heightRange = Utils.Clamp(heightRange, 0f, 255f); // Generate two frequencies of perlin noise based on our global position // The magic values were taken from http://opensimulator.org/wiki/Terrain_Splatting Vector3 vec = new Vector3 ( ((float)regionPosition.X + x) * 0.20319f, ((float)regionPosition.Y + y) * 0.20319f, height * 0.25f ); float lowFreq = Perlin.noise2(vec.X * 0.222222f, vec.Y * 0.222222f) * 6.5f; float highFreq = Perlin.turbulence2(vec.X, vec.Y, 2f) * 2.25f; float noise = (lowFreq + highFreq) * 2f; // Combine the current height, generated noise, start height, and height range parameters, then scale all of it float layer = ((height + noise - startHeight) / heightRange) * 4f; if (Single.IsNaN(layer)) layer = 0f; layermap[y * 256 + x] = Utils.Clamp(layer, 0f, 3f); } } #endregion Layer Map #region Texture Compositing Bitmap output = new Bitmap(256, 256, PixelFormat.Format24bppRgb); BitmapData outputData = output.LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.WriteOnly, PixelFormat.Format24bppRgb); unsafe { // Get handles to all of the texture data arrays BitmapData[] datas = new BitmapData[] { detailTexture[0].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[0].PixelFormat), detailTexture[1].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[1].PixelFormat), detailTexture[2].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[2].PixelFormat), detailTexture[3].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[3].PixelFormat) }; int[] comps = new int[] { (datas[0].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3, (datas[1].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3, (datas[2].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3, (datas[3].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3 }; for (int y = 0; y < 256; y++) { for (int x = 0; x < 256; x++) { float layer = layermap[y * 256 + x]; // Select two textures int l0 = (int)Math.Floor(layer); int l1 = Math.Min(l0 + 1, 3); byte* ptrA = (byte*)datas[l0].Scan0 + y * datas[l0].Stride + x * comps[l0]; byte* ptrB = (byte*)datas[l1].Scan0 + y * datas[l1].Stride + x * comps[l1]; byte* ptrO = (byte*)outputData.Scan0 + y * outputData.Stride + x * 3; float aB = *(ptrA + 0); float aG = *(ptrA + 1); float aR = *(ptrA + 2); float bB = *(ptrB + 0); float bG = *(ptrB + 1); float bR = *(ptrB + 2); float layerDiff = layer - l0; // Interpolate between the two selected textures *(ptrO + 0) = (byte)Math.Floor(aB + layerDiff * (bB - aB)); *(ptrO + 1) = (byte)Math.Floor(aG + layerDiff * (bG - aG)); *(ptrO + 2) = (byte)Math.Floor(aR + layerDiff * (bR - aR)); } } for (int i = 0; i < 4; i++) detailTexture[i].UnlockBits(datas[i]); } output.UnlockBits(outputData); // We generated the texture upside down, so flip it output.RotateFlip(RotateFlipType.RotateNoneFlipY); #endregion Texture Compositing return output; }
public bool Start(Simian simian) { m_simian = simian; m_httpServer = simian.GetAppModule<IHttpServer>(); if (m_httpServer == null) { m_log.Error("StandaloneGridClient requires an IHttpServer"); return false; } m_sceneFactory = simian.GetAppModule<ISceneFactory>(); if (m_sceneFactory == null) { m_log.Error("StandaloneGridClient requires an ISceneFactory"); return false; } m_assetClient = simian.GetAppModule<IAssetClient>(); return true; }
/// <summary> /// Builds a composited terrain texture given the region texture /// and heightmap settings /// </summary> /// <param name="heightmap">Terrain heightmap</param> /// <param name="regionInfo">Region information including terrain texture parameters</param> /// <returns>A composited 256x256 RGB texture ready for rendering</returns> /// <remarks>Based on the algorithm described at http://opensimulator.org/wiki/Terrain_Splatting /// </remarks> public static Bitmap Splat(float[] heightmap, UUID[] textureIDs, float[] startHeights, float[] heightRanges, Vector3d regionPosition, IAssetClient assetClient) { Debug.Assert(heightmap.Length == 256 * 256); Debug.Assert(textureIDs.Length == 4); Debug.Assert(startHeights.Length == 4); Debug.Assert(heightRanges.Length == 4); // Swap empty terrain textureIDs with default IDs for (int i = 0; i < textureIDs.Length; i++) { if (textureIDs[i] == UUID.Zero) { textureIDs[i] = DEFAULT_TERRAIN_DETAIL[i]; } } #region Texture Fetching Bitmap[] detailTexture = new Bitmap[4]; if (assetClient != null) { for (int i = 0; i < 4; i++) { Asset asset; UUID cacheID = UUID.Combine(TEXTURE_CACHE_MAGIC, textureIDs[i]); // Try to fetch a cached copy of the decoded/resized version of this texture if (assetClient.TryGetCachedAsset(cacheID, "image/png", out asset)) { try { using (System.IO.MemoryStream stream = new System.IO.MemoryStream(asset.Data)) detailTexture[i] = (Bitmap)Image.FromStream(stream); } catch (Exception ex) { m_log.Warn("Failed to decode cached terrain texture " + cacheID + " (textureID: " + textureIDs[i] + "): " + ex.Message); } } if (detailTexture[i] == null) { // Try to fetch the original JPEG2000 texture, resize if needed, and cache as PNG if (assetClient.TryGetAsset(textureIDs[i], "image/x-j2c", out asset)) { try { detailTexture[i] = (Bitmap)CSJ2K.J2kImage.FromBytes(asset.Data); } catch (Exception ex) { m_log.Warn("Failed to decode terrain texture " + asset.ID + ": " + ex.Message); } } if (detailTexture[i] != null) { Bitmap bitmap = detailTexture[i]; // Make sure this texture is the correct size, otherwise resize if (bitmap.Width != 256 || bitmap.Height != 256) { bitmap = Util.ResizeImage(bitmap, 256, 256); } // Save the decoded and resized texture to the cache byte[] data; using (System.IO.MemoryStream stream = new System.IO.MemoryStream()) { bitmap.Save(stream, ImageFormat.Png); data = stream.ToArray(); } assetClient.StoreAsset( new Asset { ContentType = "image/png", CreationDate = DateTime.UtcNow, CreatorID = UUID.Zero, Data = data, ID = cacheID, Local = true, Temporary = true } ); } } } } // Fill in any missing textures with a solid color for (int i = 0; i < 4; i++) { if (detailTexture[i] == null) { // Create a solid color texture for this layer detailTexture[i] = new Bitmap(256, 256, PixelFormat.Format24bppRgb); using (Graphics gfx = Graphics.FromImage(detailTexture[i])) { using (SolidBrush brush = new SolidBrush(DEFAULT_TERRAIN_COLOR[i])) gfx.FillRectangle(brush, 0, 0, 256, 256); } } } #endregion Texture Fetching #region Layer Map float[] layermap = new float[256 * 256]; for (int y = 0; y < 256; y++) { for (int x = 0; x < 256; x++) { float height = heightmap[y * 256 + x]; float pctX = (float)x / 255f; float pctY = (float)y / 255f; // Use bilinear interpolation between the four corners of start height and // height range to select the current values at this position float startHeight = Util.Bilinear( startHeights[0], startHeights[2], startHeights[1], startHeights[3], pctX, pctY); startHeight = Utils.Clamp(startHeight, 0f, 255f); float heightRange = Util.Bilinear( heightRanges[0], heightRanges[2], heightRanges[1], heightRanges[3], pctX, pctY); heightRange = Utils.Clamp(heightRange, 0f, 255f); // Generate two frequencies of perlin noise based on our global position // The magic values were taken from http://opensimulator.org/wiki/Terrain_Splatting Vector3 vec = new Vector3 ( ((float)regionPosition.X + x) * 0.20319f, ((float)regionPosition.Y + y) * 0.20319f, height * 0.25f ); float lowFreq = Perlin.noise2(vec.X * 0.222222f, vec.Y * 0.222222f) * 6.5f; float highFreq = Perlin.turbulence2(vec.X, vec.Y, 2f) * 2.25f; float noise = (lowFreq + highFreq) * 2f; // Combine the current height, generated noise, start height, and height range parameters, then scale all of it float layer = ((height + noise - startHeight) / heightRange) * 4f; if (Single.IsNaN(layer)) { layer = 0f; } layermap[y * 256 + x] = Utils.Clamp(layer, 0f, 3f); } } #endregion Layer Map #region Texture Compositing Bitmap output = new Bitmap(256, 256, PixelFormat.Format24bppRgb); BitmapData outputData = output.LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.WriteOnly, PixelFormat.Format24bppRgb); unsafe { // Get handles to all of the texture data arrays BitmapData[] datas = new BitmapData[] { detailTexture[0].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[0].PixelFormat), detailTexture[1].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[1].PixelFormat), detailTexture[2].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[2].PixelFormat), detailTexture[3].LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.ReadOnly, detailTexture[3].PixelFormat) }; int[] comps = new int[] { (datas[0].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3, (datas[1].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3, (datas[2].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3, (datas[3].PixelFormat == PixelFormat.Format32bppArgb) ? 4 : 3 }; for (int y = 0; y < 256; y++) { for (int x = 0; x < 256; x++) { float layer = layermap[y * 256 + x]; // Select two textures int l0 = (int)Math.Floor(layer); int l1 = Math.Min(l0 + 1, 3); byte *ptrA = (byte *)datas[l0].Scan0 + y * datas[l0].Stride + x * comps[l0]; byte *ptrB = (byte *)datas[l1].Scan0 + y * datas[l1].Stride + x * comps[l1]; byte *ptrO = (byte *)outputData.Scan0 + y * outputData.Stride + x * 3; float aB = *(ptrA + 0); float aG = *(ptrA + 1); float aR = *(ptrA + 2); float bB = *(ptrB + 0); float bG = *(ptrB + 1); float bR = *(ptrB + 2); float layerDiff = layer - l0; // Interpolate between the two selected textures *(ptrO + 0) = (byte)Math.Floor(aB + layerDiff * (bB - aB)); *(ptrO + 1) = (byte)Math.Floor(aG + layerDiff * (bG - aG)); *(ptrO + 2) = (byte)Math.Floor(aR + layerDiff * (bR - aR)); } } for (int i = 0; i < 4; i++) { detailTexture[i].UnlockBits(datas[i]); } } output.UnlockBits(outputData); // We generated the texture upside down, so flip it output.RotateFlip(RotateFlipType.RotateNoneFlipY); #endregion Texture Compositing return(output); }