From a1050db3f34798ae023cdec328de4707dede8df5 Mon Sep 17 00:00:00 2001 From: Rodrigo Braz Monteiro Date: Sun, 1 Jul 2007 02:23:57 +0000 Subject: [PATCH] Re-implemented z rotation on visual typesetting Originally committed to SVN as r1326. --- aegisub/Makefile.am | 1 + aegisub/audio_karaoke.cpp | 1 - aegisub/gl_wrap.cpp | 12 +- aegisub/gl_wrap.h | 3 +- aegisub/video_display.cpp | 6 + aegisub/visual_tool.cpp | 144 +++++++++++++++++------ aegisub/visual_tool.h | 12 ++ aegisub/visual_tool_rotatez.cpp | 200 ++++++++++++++++++++++++++++++++ aegisub/visual_tool_rotatez.h | 63 ++++++++++ 9 files changed, 399 insertions(+), 43 deletions(-) create mode 100644 aegisub/visual_tool_rotatez.cpp create mode 100644 aegisub/visual_tool_rotatez.h diff --git a/aegisub/Makefile.am b/aegisub/Makefile.am index 0b5fe056f..4b21670b7 100644 --- a/aegisub/Makefile.am +++ b/aegisub/Makefile.am @@ -216,6 +216,7 @@ aegisub_SOURCES = \ visual_feature.cpp \ visual_tool.cpp \ visual_tool_cross.cpp \ + visual_tool_rotatez.cpp \ MatroskaParser.c noinst_HEADERS = \ diff --git a/aegisub/audio_karaoke.cpp b/aegisub/audio_karaoke.cpp index e9ec305d4..05585babc 100644 --- a/aegisub/audio_karaoke.cpp +++ b/aegisub/audio_karaoke.cpp @@ -83,7 +83,6 @@ AudioKaraoke::AudioKaraoke(wxWindow *parent) ////////////// // Destructor AudioKaraoke::~AudioKaraoke() { - wxLogDebug(_T("AudioKaraoke destructor")); delete workDiag; } diff --git a/aegisub/gl_wrap.cpp b/aegisub/gl_wrap.cpp index 9ffe75bb0..228a873e7 100644 --- a/aegisub/gl_wrap.cpp +++ b/aegisub/gl_wrap.cpp @@ -81,11 +81,13 @@ PFNGLUNIFORM2FARBPROC glUniform2fARB = NULL; #endif -//////////////// -// GLEW library -//#if __VISUALC__ >= 1200 -//#pragma comment(lib,"glew32.lib") -//#endif +/////////////// +// Constructor +OpenGLWrapper::OpenGLWrapper() { + r1 = g1 = b1 = a1 = 1.0f; + r2 = g2 = b2 = a2 = 1.0f; + lw = 1; +} ///////////// diff --git a/aegisub/gl_wrap.h b/aegisub/gl_wrap.h index b7a3f0b68..3942a3a6d 100644 --- a/aegisub/gl_wrap.h +++ b/aegisub/gl_wrap.h @@ -45,13 +45,14 @@ private: float r2,g2,b2,a2; int lw; - static void Initialize(); static GLuint CreateStandardVertexShader(); static GLuint CreateYV12PixelShader(); static GLuint CreateShaderProgram(GLuint vertex,GLuint pixel); public: + OpenGLWrapper(); + static wxMutex glMutex; void SetLineColour(wxColour col,float alpha=1.0f,int width=1); diff --git a/aegisub/video_display.cpp b/aegisub/video_display.cpp index 5563c1382..1fe6b17c8 100644 --- a/aegisub/video_display.cpp +++ b/aegisub/video_display.cpp @@ -69,6 +69,7 @@ #include "gl_wrap.h" #include "visual_tool.h" #include "visual_tool_cross.h" +#include "visual_tool_rotatez.h" /////// @@ -645,6 +646,11 @@ void VideoDisplay::SetVisualMode(int mode) { delete visual; switch (mode) { case 0: visual = new VisualToolCross(this); break; + //case 1: visual = new VisualToolDrag(this); break; + case 2: visual = new VisualToolRotateZ(this); break; + //case 3: visual = new VisualToolRotateXY(this); break; + //case 4: visual = new VisualToolScale(this); break; + //case 5: visual = new VisualToolClip(this); break; default: visual = NULL; } diff --git a/aegisub/visual_tool.cpp b/aegisub/visual_tool.cpp index 4248d78e4..f1b7071a0 100644 --- a/aegisub/visual_tool.cpp +++ b/aegisub/visual_tool.cpp @@ -63,6 +63,9 @@ VisualTool::VisualTool(VideoDisplay *par) { colour[1] = wxColour(166,247,177); colour[2] = wxColour(255,255,255); colour[3] = wxColour(187,0,0); + + holding = false; + curDiag = NULL; } @@ -72,6 +75,111 @@ VisualTool::~VisualTool() { } +/////////////// +// Mouse event +void VisualTool::OnMouseEvent (wxMouseEvent &event) { + // General variables + mouseX = event.GetX(); + mouseY = event.GetY(); + parent->ConvertMouseCoords(mouseX,mouseY); + parent->GetClientSize(&w,&h); + VideoContext::Get()->GetScriptSize(sw,sh); + frame_n = VideoContext::Get()->GetFrameN(); + SubtitlesGrid *grid = VideoContext::Get()->grid; + bool realTime = Options.AsBool(_T("Video Visual Realtime")); + + // Mouse leaving control + if (event.Leaving()) { + mouseX = -1; + mouseY = -1; + } + + // Transformed mouse x/y + mx = mouseX * sw / w; + my = mouseY * sh / h; + + // Clicks + leftClick = event.ButtonDown(wxMOUSE_BTN_LEFT); + leftDClick = event.LeftDClick(); + shiftDown = event.m_shiftDown; + ctrlDown = event.m_controlDown; + altDown = event.m_altDown; + + // Hold + if (CanHold()) { + // Start holding + if (!holding && event.LeftIsDown()) { + // Get a dialogue + curDiag = GetActiveDialogueLine(); + if (curDiag) { + // Initialize Drag + InitializeHold(); + + // Set flags + holding = true; + parent->CaptureMouse(); + if (realTime) AssLimitToVisibleFilter::SetFrame(frame_n); + } + } + + if (holding) { + // Holding + if (event.LeftIsDown()) { + // Update drag + UpdateHold(); + + if (realTime) { + // Commit + CommitHold(); + grid->editBox->CommitText(true); + grid->CommitChanges(false,true); + } + } + + // Release + else { + // Disable limiting + if (realTime) AssLimitToVisibleFilter::SetFrame(-1); + + // Commit + CommitHold(); + grid->editBox->CommitText(); + grid->ass->FlagAsModified(_("visual typesetting")); + grid->CommitChanges(false,true); + + // Clean up + holding = false; + curDiag = NULL; + parent->ReleaseMouse(); + parent->SetFocus(); + } + } + } + + // Update + Update(); +} + + +//////////////////////////// +// Get active dialogue line +AssDialogue* VisualTool::GetActiveDialogueLine() { + SubtitlesGrid *grid = VideoContext::Get()->grid; + AssDialogue *diag = grid->GetDialogue(grid->editBox->linen); + + // Check if it's within range + if (diag) { + int f1 = VFR_Output.GetFrameAtTime(diag->Start.GetMS(),true); + int f2 = VFR_Output.GetFrameAtTime(diag->End.GetMS(),false); + + // Invisible + if (f1 > frame_n || f2 < frame_n) return NULL; + } + + return diag; +} + + //////////////////////// // Get position of line void VisualTool::GetLinePosition(AssDialogue *diag,int &x, int &y) { @@ -300,39 +408,3 @@ void VisualTool::GetLineClip(AssDialogue *diag,int &x1,int &y1,int &x2,int &y2) } diag->ClearBlocks(); } - - -/////////////// -// Mouse event -void VisualTool::OnMouseEvent (wxMouseEvent &event) { - // Coords - int x = event.GetX(); - int y = event.GetY(); - parent->ConvertMouseCoords(x,y); - parent->GetClientSize(&w,&h); - VideoContext::Get()->GetScriptSize(sw,sh); - frame_n = VideoContext::Get()->GetFrameN(); - - // Hover - if (x != mouseX || y != mouseY) { - mouseX = x; - mouseY = y; - } - - // Mouse leaving control - if (event.Leaving()) { - mouseX = -1; - mouseY = -1; - } - - // Transformed mouse x/y - mx = mouseX * sw / w; - my = mouseY * sh / h; - - // Clicks - leftClick = event.ButtonDown(wxMOUSE_BTN_LEFT); - leftDClick = event.LeftDClick(); - - // Update - Update(); -} diff --git a/aegisub/visual_tool.h b/aegisub/visual_tool.h index 3cdbd70f7..dd4145784 100644 --- a/aegisub/visual_tool.h +++ b/aegisub/visual_tool.h @@ -58,11 +58,17 @@ private: protected: wxColour colour[4]; + bool holding; + AssDialogue *curDiag; + int w,h,sw,sh,mx,my; int frame_n; bool leftClick; bool leftDClick; + bool shiftDown; + bool ctrlDown; + bool altDown; void GetLinePosition(AssDialogue *diag,int &x,int &y); void GetLinePosition(AssDialogue *diag,int &x,int &y,int &orgx,int &orgy); @@ -73,6 +79,12 @@ protected: VideoDisplay *GetParent() { return parent; } + virtual AssDialogue *GetActiveDialogueLine(); + virtual bool CanHold() { return false; } + virtual void InitializeHold() {} + virtual void UpdateHold() {} + virtual void CommitHold() {} + public: int mouseX,mouseY; diff --git a/aegisub/visual_tool_rotatez.cpp b/aegisub/visual_tool_rotatez.cpp new file mode 100644 index 000000000..b6afc9944 --- /dev/null +++ b/aegisub/visual_tool_rotatez.cpp @@ -0,0 +1,200 @@ +// Copyright (c) 2007, Rodrigo Braz Monteiro +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// * Redistributions of source code must retain the above copyright notice, +// this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the following disclaimer in the documentation +// and/or other materials provided with the distribution. +// * Neither the name of the Aegisub Group nor the names of its contributors +// may be used to endorse or promote products derived from this software +// without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +// POSSIBILITY OF SUCH DAMAGE. +// +// ----------------------------------------------------------------------------- +// +// AEGISUB +// +// Website: http://aegisub.cellosoft.com +// Contact: mailto:zeratul@cellosoft.com +// + + +#pragma once + + +/////////// +// Headers +#include "visual_tool_rotatez.h" +#include "gl_text.h" +#include "subs_grid.h" +#include "subs_edit_box.h" +#include "ass_file.h" +#include "ass_dialogue.h" +#include "utils.h" + + +/////////////// +// Constructor +VisualToolRotateZ::VisualToolRotateZ(VideoDisplay *_parent) +: VisualTool(_parent) +{ + _parent->ShowCursor(false); +} + + +////////// +// Update +void VisualToolRotateZ::Update() { + // Render parent + GetParent()->Render(); +} + + +//////// +// Draw +void VisualToolRotateZ::Draw() { + // Get line to draw + AssDialogue *line = GetActiveDialogueLine(); + if (!line) return; + + // Radius + int dx=0,dy=0; + GetLinePosition(line,dx,dy,orgx,orgy); + int radius = (int) sqrt(double((dx-orgx)*(dx-orgx)+(dy-orgy)*(dy-orgy))); + int oRadius = radius; + if (radius < 50) radius = 50; + + // Pivot coordinates + int odx = dx; + int ody = dy; + dx = orgx; + dy = orgy; + + // Rotation + float rz; + GetLineRotation(line,rx,ry,rz); + if (line == curDiag) rz = curAngle; + + // Get scale + float scalX = 100.0f; + float scalY = 100.0f; + GetLineScale(line,scalX,scalY); + + // Get deltas + int deltax = int(cos(rz*3.1415926536/180.0)*radius); + int deltay = int(-sin(rz*3.1415926536/180.0)*radius); + + // Set colours + SetLineColour(colour[0]); + SetFillColour(colour[1],0.3f); + + // Draw pivot + DrawCircle(dx,dy,7); + DrawLine(dx,dy-16,dx,dy+16); + DrawLine(dx-16,dy,dx+16,dy); + + // Set up the projection + glMatrixMode(GL_MODELVIEW); + glPushMatrix(); + glLoadIdentity(); + glTranslatef(dx,dy,-1.0f); + float matrix[16] = { 2500, 0, 0, 0, 0, 2500, 0, 0, 0, 0, 1, 1, 0, 0, 2500, 2500 }; + glMultMatrixf(matrix); + glScalef(1.0f,1.0f,8.0f); + glRotatef(ry,0.0f,-1.0f,0.0f); + glRotatef(rx,-1.0f,0.0f,0.0f); + glScalef(scalX/100.0f,scalY/100.0f,1.0f); + + // Draw the circle + DrawRing(0,0,radius+4,radius-4); + + // Draw markers around circle + int markers = 6; + float markStart = -90.0f / markers; + float markEnd = markStart+(180.0f/markers); + for (int i=0;iStripTag(_T("\\frz")); + curDiag->StripTag(_T("\\fr")); +} + + +/////////////// +// Update hold +void VisualToolRotateZ::UpdateHold() { + // Find angle + float screenAngle = atan2(double(orgy-mouseY*sh/h),double(mouseX*sw/w-orgx)) * 180.0 / 3.1415926535897932; + curAngle = screenAngle - startAngle + origAngle; + while (curAngle < 0.0f) curAngle += 360.0f; + while (curAngle >= 360.0f) curAngle -= 360.0f; + + // Snap + if (shiftDown) { + curAngle = (float)((int)((curAngle+15.0f)/30.0f))*30.0f; + if (curAngle == 360.0f) curAngle = 0.0f; + } +} + + +/////////////// +// Commit hold +void VisualToolRotateZ::CommitHold() { + wxString param = PrettyFloat(wxString::Format(_T("(%0.3f)"),curAngle)); + VideoContext::Get()->grid->editBox->SetOverride(_T("\\frz"),param,0,false); +} diff --git a/aegisub/visual_tool_rotatez.h b/aegisub/visual_tool_rotatez.h new file mode 100644 index 000000000..48db04f65 --- /dev/null +++ b/aegisub/visual_tool_rotatez.h @@ -0,0 +1,63 @@ +// Copyright (c) 2007, Rodrigo Braz Monteiro +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// * Redistributions of source code must retain the above copyright notice, +// this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the following disclaimer in the documentation +// and/or other materials provided with the distribution. +// * Neither the name of the Aegisub Group nor the names of its contributors +// may be used to endorse or promote products derived from this software +// without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +// POSSIBILITY OF SUCH DAMAGE. +// +// ----------------------------------------------------------------------------- +// +// AEGISUB +// +// Website: http://aegisub.cellosoft.com +// Contact: mailto:zeratul@cellosoft.com +// + + +#pragma once + + +/////////// +// Headers +#include "visual_tool.h" + + +///////////////////////// +// Z Rotation tool class +class VisualToolRotateZ : public VisualTool { +private: + float curAngle,startAngle,origAngle; + int orgx,orgy,odx,ody; + float rx,ry; + + bool CanHold() { return true; } + void InitializeHold(); + void UpdateHold(); + void CommitHold(); + +public: + VisualToolRotateZ(VideoDisplay *parent); + + void Update(); + void Draw(); +};