protected void OnFrameRemoveClick(object sender, EventArgs e) { BgfBitmap bgfBitmap = SelectedFrame; if (bgfBitmap != null) { uint oldnum = bgfBitmap.Num; int index = dgFrames.Rows.IndexOf(dgFrames.SelectedRows[0]); if (index > -1) { DialogResult = MessageBox.Show(STR_AREYOUSURE, STR_REMOVEFRAME, MessageBoxButtons.YesNo); if (DialogResult == DialogResult.Yes) { if (Program.CurrentFile.IsFrameIndexLinkedInFrameSet(index)) { MessageBox.Show(STR_ERRORSTILLINKED, "Error", MessageBoxButtons.OK); } else { Program.CurrentFile.Frames.Remove(bgfBitmap); // adjust nums for rest for (int i = (int)oldnum - 1; i < Program.CurrentFile.Frames.Count; i++) { Program.CurrentFile.Frames[i].Num--; } } } } } }
protected void OnFrameDownClick(object sender, EventArgs e) { BgfBitmap bgfBitmap = SelectedFrame; if (bgfBitmap != null) { int index = dgFrames.Rows.IndexOf(dgFrames.SelectedRows[0]); if (index < dgFrames.Rows.Count - 1) { // swap listitems BgfBitmap temp = Program.CurrentFile.Frames[index + 1]; Program.CurrentFile.Frames[index + 1] = bgfBitmap; Program.CurrentFile.Frames[index] = temp; // update selection dgFrames.Rows[index + 1].Selected = true; Program.CurrentFile.UpdateFrameIndexInFrameSets(index + 1, -1); Program.CurrentFile.UpdateFrameIndexInFrameSets(index, index + 1); Program.CurrentFile.UpdateFrameIndexInFrameSets(-1, index); // adjust nums Program.CurrentFile.Frames[index + 1].Num++; Program.CurrentFile.Frames[index].Num--; UpdateFrameNums(); } } }
/// <summary> /// Creates RenderInfo for a RoomObject /// </summary> /// <param name="Data"></param> /// <param name="UseViewerFrame"></param> /// <param name="ApplyYOffset"></param> /// <param name="RootHotspotIndex"></param> /// <param name="Quality"></param> /// <param name="ScalePow2"></param> /// <param name="Width"></param> /// <param name="Height"></param> /// <param name="CenterVertical"></param> /// <param name="CenterHorizontal"></param> /// <param name="IsCustomShrink"></param> /// <param name="CustomShrink"></param> public void Refresh( RoomObject Data, bool UseViewerFrame = true, bool ApplyYOffset = true, byte RootHotspotIndex = 0, Real Quality = DEFAULTQUALITY, bool ScalePow2 = false, uint Width = 0, uint Height = 0, bool CenterVertical = false, bool CenterHorizontal = false, bool IsCustomShrink = false, Real CustomShrink = 1.0f) { Clear(); BgfBitmap mainFrame = Data.ViewerFrame; if (!UseViewerFrame) { mainFrame = Data.FrontFrame; } Calculate(Data, mainFrame, UseViewerFrame, ApplyYOffset, RootHotspotIndex, Quality, ScalePow2, Width, Height, CenterVertical, CenterHorizontal, IsCustomShrink, CustomShrink); }
protected void OnFileDialogAddFrameFileOk(object sender, CancelEventArgs e) { // load bitmap from file Bitmap bitmap = new Bitmap(fdAddFrame.FileName); // get pixels byte[] pixelData = BgfBitmap.BitmapToPixelData(bitmap); // create BgfBitmap BgfBitmap bgfBitmap = new BgfBitmap( (uint)Program.CurrentFile.Frames.Count + 1, Program.CurrentFile.Version, (uint)bitmap.Width, (uint)bitmap.Height, 0, 0, new BgfBitmapHotspot[0], false, 0, pixelData); // cleanp temporary bitmap bitmap.Dispose(); // add to frames Program.CurrentFile.Frames.Add(bgfBitmap); }
protected void OnHotspotDownClick(object sender, EventArgs e) { BgfBitmapHotspot bgfHotspot = SelectedHotspot; if (bgfHotspot != null) { int index = dgHotspots.Rows.IndexOf(dgHotspots.SelectedRows[0]); if (index < dgHotspots.Rows.Count - 1) { BgfBitmap bgfBitmap = SelectedFrame; // swap listitems if (bgfBitmap != null) { BgfBitmapHotspot temp = bgfBitmap.HotSpots[index + 1]; bgfBitmap.HotSpots[index + 1] = bgfHotspot; bgfBitmap.HotSpots[index] = temp; // update selection dgHotspots.Rows[index + 1].Selected = true; } } } }
public RenderInfo() { Origin = new V2(0.0f, 0.0f); Size = new V2(0.0f, 0.0f); Bgf = null; HotspotType = HotSpotType.HOTSPOT_NONE; SubOverlay = null; }
protected void OnHotspotAddClick(object sender, EventArgs e) { BgfBitmap bgfBitmap = SelectedFrame; if (bgfBitmap != null) { bgfBitmap.HotSpots.Add(new BgfBitmapHotspot()); } }
protected void OnResizeEnd(object sender, EventArgs e) { BgfBitmap bgfBitmap = SelectedFrame; if (bgfBitmap != null) { Program.ShowFrame(true, bgfBitmap.GetBitmap(), picFrameImage); } }
protected void OnFramesSelectedIndexChanged(object sender, EventArgs e) { if (cbFrames.SelectedItem != null && cbFrames.SelectedItem is BgfBitmap) { BgfBitmap bgfBitmap = (BgfBitmap)cbFrames.SelectedItem; Program.ShowFrame(true, bgfBitmap.GetBitmap(), picBox); } }
protected void OnHotspotAddClick(object sender, EventArgs e) { BgfBitmap bgfBitmap = SelectedFrame; if (bgfBitmap != null) { Program.HasFileChanged = true; bgfBitmap.HotSpots.Add(new BgfBitmapHotspot()); } }
protected void OnFramesSelectionChanged(object sender, EventArgs e) { BgfBitmap bgfBitmap = SelectedFrame; if (bgfBitmap != null) { // set hotspotlist dgHotspots.DataSource = bgfBitmap.HotSpots; // show frame Program.ShowFrame(true, bgfBitmap.GetBitmap(), picFrameImage); } }
/// <summary> /// Swaps in a new image for a given frame, keeping offets, hotspots and group data. /// </summary> /// <param name="sender"></param> /// <param name="e"></param> protected void OnFileDialogChangeFrameFileOk(object sender, CancelEventArgs e) { // Must have a valid frame selected. if (SelectedFrame == null) { return; } int selected_index = (int)SelectedFrame.Num - 1; if (selected_index < 0) { return; } BgfBitmap item = Program.CurrentFile.Frames[selected_index]; // load bitmap from file Bitmap bitmap = new Bitmap(fdChangeFrame.FileName); // get pixels byte[] pixelData = BgfBitmap.BitmapToPixelData(bitmap); // create BgfBitmap BgfBitmap bgfBitmap = new BgfBitmap( item.Num, Program.CurrentFile.Version, (uint)bitmap.Width, (uint)bitmap.Height, item.XOffset, item.YOffset, new BgfBitmapHotspot[0], false, 0, pixelData); // cleanp temporary bitmap bitmap.Dispose(); foreach (BgfBitmapHotspot h in item.HotSpots) { bgfBitmap.HotSpots.Add(h); } Program.HasFileChanged = true; Program.CurrentFile.Frames.RemoveAt(selected_index); Program.CurrentFile.Frames.Insert(selected_index, bgfBitmap); dgFrames.Rows[selected_index].Selected = true; UpdateFrameSetFlow(); }
/// <summary> /// Internal thread loop /// </summary> protected void ThreadProc() { uint version = Program.CurrentFile.Version; Bitmap bitmap; while (IsRunning) { while (Program.BitmapFileQueue.TryDequeue(out string file)) { // load bitmap from file bitmap = new Bitmap(file); // get pixels byte[] pixelData = BgfBitmap.BitmapToPixelData(bitmap); // create BgfBitmap BgfBitmap bgfBitmap = new BgfBitmap( 0, // num determined when adding to list after dequeue version, (uint)bitmap.Width, (uint)bitmap.Height, 0, 0, new BgfBitmapHotspot[0], false, 0, pixelData); // cleanp temporary bitmap bitmap.Dispose(); // enqueue for adding to frames Program.BgfBitmapQueue.Enqueue(bgfBitmap); } // Done IsRunning = false; } }
protected void OnHotspotUpClick(object sender, EventArgs e) { BgfBitmapHotspot bgfHotspot = SelectedHotspot; if (bgfHotspot != null) { int index = dgHotspots.Rows.IndexOf(dgHotspots.SelectedRows[0]); if (index > 0) { Program.HasFileChanged = true; BgfBitmap bgfBitmap = SelectedFrame; // swap listitems BgfBitmapHotspot temp = bgfBitmap.HotSpots[index - 1]; bgfBitmap.HotSpots[index - 1] = bgfHotspot; bgfBitmap.HotSpots[index] = temp; // update selection dgHotspots.Rows[index - 1].Selected = true; } } }
/// <summary> /// Handles the HTTP request /// </summary> /// <param name="context"></param> public void ProcessRequest(HttpContext context) { HttpResponse response = context.Response; // -------------------------------------------------------------------------------------------- // 1) PARSE URL PARAMETERS // -------------------------------------------------------------------------------------------- // read parameters from url-path (see Global.asax): RouteValueDictionary parms = context.Request.RequestContext.RouteData.Values; string parmFile = parms.ContainsKey("file") ? (string)parms["file"] : null; string parmReq = parms.ContainsKey("req") ? (string)parms["req"] : null; string parm1 = parms.ContainsKey("parm1") ? (string)parms["parm1"] : null; string parm2 = parms.ContainsKey("parm2") ? (string)parms["parm2"] : null; string parm3 = parms.ContainsKey("parm3") ? (string)parms["parm3"] : null; BgfCache.Entry entry; // no filename or request type if (String.IsNullOrEmpty(parmFile) || !BgfCache.GetBGF(parmFile, out entry) || String.IsNullOrEmpty(parmReq)) { context.Response.StatusCode = 404; return; } // set cache behaviour context.Response.Cache.SetCacheability(HttpCacheability.Public); context.Response.Cache.VaryByParams["*"] = false; context.Response.Cache.SetLastModified(entry.LastModified); // -------------------------------------------------------------------------------------------- // FRAME IMAGE // -------------------------------------------------------------------------------------------- if (parmReq == "frame") { ushort index; byte palette = 0; Byte.TryParse(parm3, out palette); // try to parse index and palette and validate range if (!UInt16.TryParse(parm2, out index) || index >= entry.Bgf.Frames.Count) { context.Response.StatusCode = 404; return; } // create BMP (256 col) or PNG (32-bit) or return raw pixels (8bit indices) if (parm1 == "bmp") { response.ContentType = "image/bmp"; response.AddHeader( "Content-Disposition", "inline; filename=" + entry.Bgf.Filename + "-" + index.ToString() + ".bmp"); Bitmap bmp = entry.Bgf.Frames[index].GetBitmap(palette); bmp.Save(context.Response.OutputStream, ImageFormat.Bmp); bmp.Dispose(); } else if (parm1 == "png") { response.ContentType = "image/png"; response.AddHeader( "Content-Disposition", "inline; filename=" + entry.Bgf.Filename + "-" + index.ToString() + ".png"); Bitmap bmp = entry.Bgf.Frames[index].GetBitmapA8R8G8B8(palette); bmp.Save(context.Response.OutputStream, ImageFormat.Png); bmp.Dispose(); } else if (parm1 == "bin") { response.ContentType = "application/octet-stream"; response.AddHeader( "Content-Disposition", "attachment; filename=" + entry.Bgf.Filename + "-" + index.ToString() + ".bin"); byte[] pixels = entry.Bgf.Frames[index].PixelData; context.Response.OutputStream.Write(pixels, 0, pixels.Length); } else { context.Response.StatusCode = 404; } } // -------------------------------------------------------------------------------------------- // JSON META DATA // -------------------------------------------------------------------------------------------- else if (parmReq == "meta") { // set response type response.ContentType = "application/json"; response.ContentEncoding = new System.Text.UTF8Encoding(false); response.AddHeader("Content-Disposition", "inline; filename=" + entry.Bgf.Filename + ".json"); // unix timestamp long stamp = (entry.LastModified.Ticks - 621355968000000000) / 10000000; ///////////////////////////////////////////////////////////// response.Write("{\"file\":\""); response.Write(entry.Bgf.Filename); response.Write("\",\"size\":"); response.Write(entry.Size.ToString()); response.Write(",\"modified\":"); response.Write(stamp.ToString()); response.Write(",\"shrink\":"); response.Write(entry.Bgf.ShrinkFactor.ToString()); response.Write(",\"frames\":["); for (int i = 0; i < entry.Bgf.Frames.Count; i++) { BgfBitmap frame = entry.Bgf.Frames[i]; if (i > 0) { response.Write(','); } response.Write("{\"w\":"); response.Write(frame.Width.ToString()); response.Write(",\"h\":"); response.Write(frame.Height.ToString()); response.Write(",\"x\":"); response.Write(frame.XOffset.ToString()); response.Write(",\"y\":"); response.Write(frame.YOffset.ToString()); response.Write(",\"hs\":["); for (int j = 0; j < frame.HotSpots.Count; j++) { BgfBitmapHotspot hs = frame.HotSpots[j]; if (j > 0) { response.Write(','); } response.Write("{\"i\":"); response.Write(hs.Index.ToString()); response.Write(",\"x\":"); response.Write(hs.X.ToString()); response.Write(",\"y\":"); response.Write(hs.Y.ToString()); response.Write('}'); } response.Write("]}"); } response.Write("],\"groups\":["); for (int i = 0; i < entry.Bgf.FrameSets.Count; i++) { BgfFrameSet group = entry.Bgf.FrameSets[i]; if (i > 0) { response.Write(','); } response.Write('['); for (int j = 0; j < group.FrameIndices.Count; j++) { if (j > 0) { response.Write(','); } response.Write(group.FrameIndices[j].ToString()); } response.Write(']'); } response.Write("]}"); } // -------------------------------------------------------------------------------------------- // INVALID // -------------------------------------------------------------------------------------------- else { context.Response.StatusCode = 404; return; } }
protected void Calculate( ObjectBase Data, BgfBitmap MainFrame, bool UseViewerFrame = true, bool ApplyYOffset = true, byte RootHotspotIndex = 0, Real Quality = DEFAULTQUALITY, bool ScalePow2 = false, uint Width = 0, uint Height = 0, bool CenterVertical = false, bool CenterHorizontal = false, bool IsCustomShrink = false, Real CustomShrink = 1.0f) { BgfBitmap mainFrame = MainFrame; BgfFile mainResource = Data.Resource; byte mainColor = Data.ColorTranslation; BgfBitmap subOvFrame; BgfBitmapHotspot subOvHotspot; SubOverlay subOvParent; BgfBitmap subOvParentFrame; BgfBitmapHotspot subOvParentHotspot; bool rootSpotFound = false; // use custom compose root (suboverlay=mainoverlay) // if it's not found, fallback to full compose if (RootHotspotIndex > 0) { SubOverlay subOv = Data.GetSubOverlayByHotspot(RootHotspotIndex); if (subOv != null) { rootSpotFound = true; if (UseViewerFrame) { mainFrame = subOv.ViewerFrame; } else { mainFrame = subOv.FrontFrame; } mainResource = subOv.Resource; mainColor = subOv.ColorTranslation; } } if (mainFrame != null && mainResource != null) { Bgf = mainFrame; BgfColor = mainColor; size.X = (Real)mainFrame.Width / (Real)mainResource.ShrinkFactor; size.Y = (Real)mainFrame.Height / (Real)mainResource.ShrinkFactor; origin.X = (Real)mainFrame.XOffset / (Real)mainResource.ShrinkFactor; origin.Y = (Real)mainFrame.YOffset / (Real)mainResource.ShrinkFactor; MaxShrink = mainResource.ShrinkFactor; // used to calculate the boundingbox V2 min = new V2(Origin.X, Origin.Y); V2 max = new V2(Size.X, Size.Y); if (ApplyYOffset) { if (origin.X > 0.0f) { max.X += origin.X; } if (origin.Y > 0.0f) { max.Y += origin.Y; } } else { max += origin; } Real x, y; // walk suboverlay structure foreach (SubOverlay subOv in Data.CurrentSubOverlays) { if (UseViewerFrame) { subOvFrame = subOv.ViewerFrame; subOvHotspot = subOv.ViewerHotspot; subOvParent = subOv.ViewerParent; } else { subOvFrame = subOv.FrontFrame; subOvHotspot = subOv.FrontHotspot; subOvParent = subOv.FrontParent; } bool isSubRoot = (subOvParent != null && subOvParent.HotSpot == RootHotspotIndex); if (subOv.Resource != null && subOvFrame != null && subOvHotspot != null && (RootHotspotIndex <= 0 || !rootSpotFound || isSubRoot)) { SubOverlay.RenderInfo subOvInfo = new SubOverlay.RenderInfo(); // save subov & bitmap subOvInfo.SubOverlay = subOv; subOvInfo.Bgf = subOvFrame; // calculate the size of this suboverlay subOvInfo.Size.X = (Real)subOvFrame.Width / (Real)subOv.Resource.ShrinkFactor; subOvInfo.Size.Y = (Real)subOvFrame.Height / (Real)subOv.Resource.ShrinkFactor; // update maxshrink if greater if (subOv.Resource.ShrinkFactor > MaxShrink) { MaxShrink = subOv.Resource.ShrinkFactor; } // CASE 1: SubOverlay on mainoverlay if (subOvParent == null || isSubRoot) { // calculate the origin of this suboverlay on the mainoverlay subOvInfo.Origin.X = mainFrame.XOffset + ((Real)subOvHotspot.X) + ((Real)subOvFrame.XOffset); subOvInfo.Origin.Y = mainFrame.YOffset + ((Real)subOvHotspot.Y) + ((Real)subOvFrame.YOffset); subOvInfo.Origin.X /= mainResource.ShrinkFactor; subOvInfo.Origin.Y /= mainResource.ShrinkFactor; // determine type of hotspot if (subOvHotspot.Index < 0) { subOvInfo.HotspotType = HotSpotType.HOTSPOT_UNDER; } else { subOvInfo.HotspotType = HotSpotType.HOTSPOT_OVER; } } // CASE 2: SubOverlay on SubOverlay on MainOverlay else { if (UseViewerFrame) { subOvParentFrame = subOvParent.ViewerFrame; subOvParentHotspot = subOvParent.ViewerHotspot; } else { subOvParentFrame = subOvParent.FrontFrame; subOvParentHotspot = subOvParent.FrontHotspot; } if (subOvParentHotspot != null && subOvParentFrame != null && subOvParent.Resource != null) { // calculate the origin of this suboverlay on the suboverlay on the mainoverlay subOvInfo.Origin.X = (mainFrame.XOffset + (Real)subOvParentHotspot.X + (Real)subOvParentFrame.XOffset) / (Real)mainResource.ShrinkFactor; subOvInfo.Origin.X += ((Real)subOvHotspot.X + (Real)subOvFrame.XOffset) / (Real)subOvParent.Resource.ShrinkFactor; subOvInfo.Origin.Y = (mainFrame.YOffset + (Real)subOvParentHotspot.Y + (Real)subOvParentFrame.YOffset) / (Real)mainResource.ShrinkFactor; subOvInfo.Origin.Y += ((Real)subOvHotspot.Y + (Real)subOvFrame.YOffset) / (Real)subOvParent.Resource.ShrinkFactor; // determine type of nested hotspot if (subOvParentHotspot.Index > 0 && subOvHotspot.Index > 0) { subOvInfo.HotspotType = HotSpotType.HOTSPOT_OVEROVER; } else if (subOvParentHotspot.Index > 0 && subOvHotspot.Index < 0) { subOvInfo.HotspotType = HotSpotType.HOTSPOT_OVERUNDER; } else if (subOvParentHotspot.Index < 0 && subOvHotspot.Index > 0) { subOvInfo.HotspotType = HotSpotType.HOTSPOT_UNDEROVER; } else if (subOvParentHotspot.Index < 0 && subOvHotspot.Index < 0) { subOvInfo.HotspotType = HotSpotType.HOTSPOT_UNDERUNDER; } } } // update max boundingbox if (subOvInfo.Origin.X < min.X) { min.X = subOvInfo.Origin.X; } if (subOvInfo.Origin.Y < min.Y) { min.Y = subOvInfo.Origin.Y; } x = subOvInfo.Origin.X + subOvInfo.Size.X; y = subOvInfo.Origin.Y + subOvInfo.Size.Y; if (x > max.X) { max.X = x; } if (y > max.Y) { max.Y = y; } // save info for this suboverlay SubBgf.Add(subOvInfo); } } // get dimension from boundingbox dimension.X = Math.Abs(max.X - min.X); dimension.Y = Math.Abs(max.Y - min.Y); // move all origins so minimum hits 0/0 // preparation for drawing (pixel origin is 0/0) Translate(-min); // get the center of the dimension box // this is also the center of our image after the translate above V2 bbCenter = dimension * 0.5f; // get the center of the main overlay V2 mainOriginCenter = Origin + (Size * 0.5f); // move the x center of the main overlay to the x center of dimensionbox V2 centerMove = new V2(bbCenter.X - mainOriginCenter.X, 0.0f); Translate(centerMove); // since this moves a part outside the dimension box // we need to add this size of the move to the dimension, // to the right AND left side, so our centering above stays centered // then we remove to the center. V2 center = new V2(Math.Abs(centerMove.X), 0.0f); dimension.X += center.X * 2.0f; Translate(center); // scale so highest resolution resource has 1:1 ratio (no downscale) // or to user provided shrink value Scale(IsCustomShrink ? CustomShrink : (Real)MaxShrink); // user defined sizes if (Width > 0 && Height > 0) { // use user given size V2 userSize = new V2(Width, Height); // scale so we use at least all pixels either from upscaled width or height ScaleToBox(userSize, CenterHorizontal, CenterVertical, !IsCustomShrink); } else { Real maxQuality = Quality * QUALITYBASE; Real ratioX = maxQuality / dimension.X; Real ratioY = maxQuality / dimension.Y; if (ratioX <= ratioY && ratioX < 1.0f) { Scale(ratioX); } else if (ratioX > ratioY && ratioY < 1.0f) { Scale(ratioY); } // scale up to pow2 if set if (ScalePow2) { // get next power of 2 size V2 pow2Size = new V2( MathUtil.NextPowerOf2((uint)System.Math.Ceiling(dimension.X)), MathUtil.NextPowerOf2((uint)System.Math.Ceiling(dimension.Y))); // scale so we use at least all pixels either from upscaled width or height ScaleToBox(pow2Size, CenterHorizontal, CenterVertical, !IsCustomShrink); } } // calculate the world-size (shrink=1) of the composed object from dimension, uv-coordinates and scaling worldsize.X = (uvend.X * dimension.X) / Scaling; worldsize.Y = (uvend.Y * dimension.Y) / Scaling; } }
public void Collect(string PathBgf, string PathPng) { items.Clear(); string[] bgfs = Directory.GetFiles(PathBgf, "*.bgf"); foreach (string sbgf in bgfs) { BgfFile bgfFile = new BgfFile(sbgf); for (int i = 0; i < bgfFile.Frames.Count; i++) { BgfBitmap frame = bgfFile.Frames[i]; // create new item Item item = new Item(); // build file-frame name item.Frame = bgfFile.Filename + "-" + i.ToString(); item.Shrink = bgfFile.ShrinkFactor; // set values from bgf frame item.Bgf = frame; item.BgfWidth = frame.Width; item.BgfHeight = frame.Height; item.BgfRatio = (float)frame.Width / (float)frame.Height; // build png path string pngname = PathPng + "/" + bgfFile.Filename + "-" + i.ToString() + FileExtensions.PNG; if (File.Exists(pngname)) { item.Png = new Bitmap(pngname); item.PngWidth = item.Png.Width; item.PngHeight = item.Png.Height; item.PngRatio = (float)item.Png.Width / (float)item.Png.Height; // scale between bgf and png item.Scale = (float)item.Png.Width / (float)frame.Width; // compare ratio if (item.PngRatio != item.BgfRatio) { item.State = "ERROR"; } else { item.State = "OK"; } } else { item.State = "MISS"; } // add new item items.Add(item); } } gridTextures.DataSource = items; }