Transformation,Animation and Viewing

4 Transformation,Animation and Viewing

聲明:該代碼來自:Computer Graphics Through OpenGL From Theory to Experiments,僅用作學習參考

4.1 Modeling Transformations

平移、縮放和旋轉,即 OpenGL 的建模轉換,應用于物體以更改其位置和形狀。
Modeling Transformations控制世界坐標系中物體的位置、大小、旋轉

4.1.1 Translation




glFrustum(left, right, bottom, top, near, far)
請注意 OpenGL 的一個小怪癖,即 near 和 far 值在符號上顛倒。
給函數glFrustum輸入near,far為正數,實際上為 z = ? near , z = ? far \text{z}=-\text{near}, \text{z}=-\text{far} z=?near,z=?far

4.1.2 Scaling

the scaling command glScalef(u, v, w) maps each point (x,y,z) of an object to the point (ux vy wz). This has the e ect of stretching objects by a factor of u in the x-direction, v in the y-direction, and w in the z-direction

一個或多個縮放因子為零的縮放轉換稱為退化轉換。雖然并不常見,但偶爾會有一些應用程序會派上用場。
如果w為0那么,將3維物體退化為2維



4.1.3 Rotation



4.2 Composing Modeling Transformations

任務:想要對正方形繞它自己的中心逆時針旋轉45°,如 Figure 4.20(a)所示


如果直接使用glRotatef(45.0, 0.0, 0.0, 1.0)則會得到4.20(b)中的效果,即繞原點逆時針45°,而不是繞物體本身的中心旋轉45°


正確步驟應該是:
(3)glTranslatef(7.5, 7.5, 0.0); // Translate back
(2)glRotatef(45.0, 0.0, 0.0, 1.0); // Rotate about origin.
(1)glTranslatef(-7.5,-7.5, 0.0); // Translate to origin.

在 OpenGL 中,變換矩陣的操作是以堆棧的方式進行的,最新的變換操作會首先應用。也就是說,變換操作的執行順序是從最后一個變換開始,依次向前應用。

4.3 Placing Multiple Objects



在 OpenGL 中,所有的矩陣變換操作會累積在當前的模型視圖矩陣上,并且會影響后續的繪制操作。因此,在你的 drawScene 函數中,所有的變換操作會同時作用于立方體和球體。這些變換會作用于立方體和球體。為了確保球體的變換不受立方體的變換影響,你可以在繪制球體之前重置模型視圖矩陣例如使用glLoadIdentity(); 或者使用 glPushMatrix 和 glPopMatrix 來保存和恢復矩陣狀態。

在創建時,Object1 的局部坐標系與世界坐標系重合。

(1)如果變換 tn 是由函數 glTranslatef(p, q, r) 指定的 translation 變換
則物體所有頂點 V 相對于 object1 的局部坐標系的位置 ( a , b , c ) (a,b,c) (a,b,c) 不會改變。但V在世界坐標系中的位置變為了 ( a + p , b + q , c + r ) (a+p,b+q,c+r) (a+p,b+q,c+r)

(2) 如果變換 tn 是由函數 glRotatef(A, p, q, r) 指定的 rotation 變換
則物體所有頂點 V 相對于 object1 的局部坐標系的位置 ( a , b , c ) (a,b,c) (a,b,c) 不會改變

(3)如果變換 tn 是由函數 glScalef(u, v, w) 指定的 scaling 變換
V 在世界坐標中的位置通過縮放更改為 ( u a , v b , w c ) (ua,vb,wc) (ua,vb,wc)。但是,由于相同的縮放適用于 object1 的局部坐標系的軸,因此 V 相對于該系統的位置 ( a , b , c ) (a,b,c) (a,b,c) 不會再次改變。

例子:
淺藍色為世界坐標系、紅人和藍人有各自的局部坐標系(圖中只畫出了紅人的局部坐標系),對兩個人進行變換,可以看出兩人在世界坐標系中的坐標發生了變換,但是在他們各自的局部坐標系中均為發生變換

///      
// relativePlacement.cpp
//
// This program shows composition of transformations and 
// the relative placement of one object w.r.t another.
//
// Interaction:
// Press the up/down arrow keys to process code statements.
//
// Sumanta Guha.
///#define _USE_MATH_DEFINES #include <cmath>
#include <iostream>#include <GL/glew.h>
#include <GL/freeglut.h> // Globals.
static unsigned int base; // Display lists base index.
static int numVal = 0; // Step index.
static long font = (long)GLUT_BITMAP_8_BY_13; // Font selection.// Routine to draw a bitmap character string.
void writeBitmapString(void *font, char *string)
{char *c;for (c = string; *c != '\0'; c++) glutBitmapCharacter(font, *c);
}// Draw stick figure with a local co-ordinate system.
void drawMan(void)
{float angle;int i;glLineWidth(2.0);glBegin(GL_LINE_LOOP);for (i = 0; i < 20; ++i){angle = 2 * M_PI * i / 20;glVertex2f(0.0 + cos(angle) * 3.0, 7 + sin(angle) * 3.0);}glEnd();glBegin(GL_LINES);glVertex2f(0.0, 4.0);glVertex2f(0.0, -4.0);glVertex2f(0.0, -4.0);glVertex2f(6.0, -10.0);glVertex2f(0.0, -4.0);glVertex2f(-6.0, -10.0);glVertex2f(-6.0, 0.0);glVertex2f(6.0, 0.0);glEnd();glLineWidth(1.0);glRasterPos3f(0.0, 0.0, 0.0);writeBitmapString((void*)font, "O");glRasterPos3f(7.0, 0.0, 0.0);writeBitmapString((void*)font, "x");glRasterPos3f(-1.0, 6.0, 0.0);writeBitmapString((void*)font, "y");
}// Draw local co-ordinates grid.
void drawGrid(void)
{int i;glEnable(GL_LINE_STIPPLE); // Enable line stippling.glLineStipple(1, 0x00FF);glBegin(GL_LINES);for (i = -5; i < 6; ++i){glVertex2f(5 * i, 25.0);glVertex2f(5 * i, -25.0);}for (i = -5; i < 6; ++i){glVertex2f(25.0, 5 * i);glVertex2f(-25.0, 5 * i);}glEnd();glDisable(GL_LINE_STIPPLE); // Disable line stippling.
}// Draw and label world co-ordinate axes.
void drawWorldAxes(void)
{glColor3f(0.0, 1.0, 1.0);glBegin(GL_LINES);glVertex2f(-50.0, 0.0);glVertex2f(50.0, 0.0);glVertex2f(0.0, -50.0);glVertex2f(0.0, 50.0);glEnd();glRasterPos3f(48.0, -2.0, 0.0);writeBitmapString((void*)font, "x");glRasterPos3f(1.0, 48.0, 0.0);writeBitmapString((void*)font, "y");
}// Write fixed messages.
void writeFixedMessages(void)
{glColor3f(0.0, 0.0, 0.0);glRasterPos3f(-15.0, 43.0, 0.0);writeBitmapString((void*)font, "Press the up/down arrow keys!");glColor3f(0.8, 0.8, 0.8);glRasterPos3f(-44.0, -17.0, 0.0);writeBitmapString((void*)font, "glScalef(1.5, 0.75, 1.0);");glRasterPos3f(-44.0, -20.0, 0.0);writeBitmapString((void*)font, "glRotatef(30.0, 0.0, 0.0, 1.0);");glRasterPos3f(-44.0, -23.0, 0.0);writeBitmapString((void*)font, "glTranslatef(10.0, 0.0, 0.0);");glRasterPos3f(-44.0, -26.0, 0.0);writeBitmapString((void*)font, "drawRedMan; // Also draw grid in his local co-ordinate system.");glRasterPos3f(-44.0, -29.0, 0.0);writeBitmapString((void*)font, "glRotatef(45.0, 0.0, 0.0, 1.0);");glRasterPos3f(-44.0, -32.0, 0.0);writeBitmapString((void*)font, "glTranslatef(20.0, 0.0, 0.0);");glRasterPos3f(-44.0, -35.0, 0.0);writeBitmapString((void*)font, "drawBlueMan;");
}// Drawing routine.
void drawScene(void)
{glClear(GL_COLOR_BUFFER_BIT);glLoadIdentity();writeFixedMessages();drawWorldAxes();glColor3f(0.0, 0.0, 0.0);switch (numVal){case 0:goto step0;break;case 1:goto step1;break;case 2:goto step2;break;case 3:goto step3;break;case 4:goto step4;break;case 5:goto step5;break;case 6:goto step6;break;case 7:goto step7;break;default:break;}// Transformation steps.// Text drawing statements are enclosed within push/pop pairs// so that the raster position is w.r.t the identity transform.
step7:// Scale. glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -17.0, 0.0);writeBitmapString((void*)font, "glScalef(1.5, 0.75, 1.0);");glPopMatrix();glScalef(1.5, 0.75, 1.0);step6:// Rotate. glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -20.0, 0.0);writeBitmapString((void*)font, "glRotatef(30.0, 0.0, 0.0, 1.0);");glPopMatrix();glRotatef(30, 0.0, 0.0, 1.0);step5:// Translate.glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -23.0, 0.0);writeBitmapString((void*)font, "glTranslatef(10.0, 0.0, 0.0);");glPopMatrix();glTranslatef(10.0, 0.0, 0.0);step4:// Draw red man.glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -26.0, 0.0);writeBitmapString((void*)font, "drawRedMan; // Also draw grid in his local co-ordinate system.");glPopMatrix();glColor3f(1.0, 0.0, 0.0);glCallList(base);glCallList(base + 1);glColor3f(0.0, 0.0, 0.0);step3:// Rotate.glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -29.0, 0.0);writeBitmapString((void*)font, "glRotatef(45.0, 0.0, 0.0, 1.0);");glPopMatrix();glRotatef(45, 0.0, 0.0, 1.0);step2:// Translate.glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -32.0, 0.0);writeBitmapString((void*)font, "glTranslatef(20.0, 0.0, 0.0);");glPopMatrix();glTranslatef(20.0, 0.0, 0.0);step1:// Draw blue man.glPushMatrix();glLoadIdentity();glRasterPos3f(-44.0, -35.0, 0.0);writeBitmapString((void*)font, "drawBlueMan;");glPopMatrix();glColor3f(0.0, 0.0, 1.0);glCallList(base);step0:glFlush();
}// Initialization routine.
void setup(void)
{base = glGenLists(2);glNewList(base, GL_COMPILE);drawMan();glEndList();glNewList(base + 1, GL_COMPILE);drawGrid();glEndList();glClearColor(1.0, 1.0, 1.0, 0.0);
}// OpenGL window reshape routine.
void resize(int w, int h)
{glViewport(0, 0, w, h);glMatrixMode(GL_PROJECTION);glLoadIdentity();glOrtho(-50.0, 50.0, -50.0, 50.0, -1.0, 1.0);glMatrixMode(GL_MODELVIEW);glLoadIdentity();
}// Keyboard input processing routine.
void keyInput(unsigned char key, int x, int y)
{switch (key){case 27:exit(0);break;break;default:break;}
}// Callback routine for non-ASCII key entry.
void specialKeyInput(int key, int x, int y)
{if (key == GLUT_KEY_UP){if (numVal < 7) numVal++; else numVal = 0;}if (key == GLUT_KEY_DOWN){if (numVal > 0) numVal--; else numVal = 7;}glutPostRedisplay();
}// Routine to output interaction instructions to the C++ window.
void printInteraction(void)
{std::cout << "Interaction:" << std::endl;std::cout << "Press the up/down arrow keys to process code statements." << std::endl;
}// Main routine.
int main(int argc, char **argv)
{printInteraction();glutInit(&argc, argv);glutInitContextVersion(4, 3);glutInitContextProfile(GLUT_COMPATIBILITY_PROFILE);glutInitDisplayMode(GLUT_SINGLE | GLUT_RGBA);glutInitWindowSize(500, 500);glutInitWindowPosition(100, 100);glutCreateWindow("relativePlacement.cpp");glutDisplayFunc(drawScene);glutReshapeFunc(resize);glutKeyboardFunc(keyInput);glutSpecialFunc(specialKeyInput);glewExperimental = GL_TRUE;glewInit();setup();glutMainLoop();
}

4.4 Modelview Matrix Stack and Isolating Transformations

modelview 矩陣堆棧有助于將轉換應用于多個對象

我們描述的 modelview 矩陣是通過右側的乘法建模轉換來修改的,實際上是 modelview 矩陣堆棧中最上面的一個。這個特定的矩陣稱為當前 modelview 矩陣。事實上,OpenGL 維護了三個不同的矩陣堆棧:modelview、projection 和 texture。glMatrixMode(mode) 命令(其中 mode 為 GL_MODELVIEW、GL_PROJECTION 或 GL_TEXTURE)確定當前處于活動狀態的堆棧。

glPushMatrix() 命令的作用是在 modelview 矩陣堆棧中復制當前(即當前最頂層)矩陣,并將其放置在堆棧頂部;因此,在執行 glPushMatrix() 時,堆棧的兩個頂部矩陣立即相同。另一方面,glPopMatrix() 語句會刪除 modelview 矩陣堆棧的最頂層矩陣,以便下面的矩陣成為當前矩陣。

4.5 Animation

4.5.1 Animation Technicals

Controlling Animation
在 OpenGL 中,有三種簡單的方法可以控制動畫:

  1. 通過鍵盤或鼠標輸入以交互方式,借助其回調例程(callback routine)來調用轉換
  2. 用glutIdelFunc(idle_function)語句調用idle函數,idle 函數在沒有 OpenGL 事件時處于待處理狀態時調用。
  3. 通過指定一個常規定時器函數(稱為定時器函數),并調用 glutTimerFunc(period, 定時器函數, value) 即可實現半自動操作。定時器函數會在執行 glutTimerFunc() 語句后的 period 毫秒被調用,并且會將傳遞給它的參數值作為參數。

Double Buffer
顏色緩沖區是一個空間,通常位于 GPU 內存中,用于存儲光柵像素的 RGBA 值,通常每個 R、G、B 和 A 分別占用 8 位,總計每個像素 32 位。因此,顏色緩沖區保存著單幀的數據,并在該幀被繪制到顯示器時進行讀取。
在雙緩沖系統中,會提供兩個顏色緩沖區的空間,其中一個緩沖區(可查看緩沖區)保存當前顯示在顯示器上的幀,而下一幀則在第二個緩沖區(可繪制緩沖區)中繪制。當在可繪制緩沖區中繪制下一幀完成時,緩沖區會進行交換,這樣下一幀就變為可查看的,同時下一幀的繪制也開始。這個繪制和交換的循環在動畫過程中不斷重復。

可查看緩沖區(Viewable)通常被稱為前緩沖區或主緩沖區,而可繪制緩沖區(Drawable)則被稱為后緩沖區或交換緩沖區。任一緩沖區也被稱為刷新緩沖區。

雙緩沖極大地提高了動畫的質量,因為它能隱藏連續幀之間的過渡。而單緩沖則不然,觀眾會看到下一個幀在包含當前幀的同一個緩沖區中被繪制出來。其結果可能是令人不快的重影,之所以這樣稱呼,是因為在繪制下一個圖像時,之前的圖像仍會殘留。

運動的實現離不開物理,這一塊內容暫時不進行詳細了解

4.6 Viewing Transformation

管理相機位姿(相機在世界坐標系中的位置和朝向)

gluLookAt(eyex, eyey, eyez, centerx, centery, centerz, upx, upy, upz) ,注意這些坐標都是由世界坐標系描述的
模擬 OpenGL 相機第一次移動到位置 eye = (eyex, eyey, eyez),然后指向 center = (centerx, centery, centerz),并且圍繞其視線(line of sight,los)旋轉 連接eye到center的線,以便其向上方向是從 up = (upx, upy, upz)


將glTranslatef(0.0, 0.0, -15.0)替換為 gluLookAt(0.0, 0.0, 15.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0)

為什么glTranslatef(0.0, 0.0, -15.0)和 gluLookAt(0.0, 0.0, 15.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0) 渲染后效果是一樣的?
原因:使用函數glTranslatef(0.0, 0.0, -15.0)時的情況,相機和物體都在世界坐標系原點,將物體通過函數平移到了相機的視錐體內
使用函數 gluLookAt(0.0, 0.0, 15.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0) 時的情況,物體在世界坐標系原點,將相機平移到了(0,0,15)的位置,物體落到了平移后的相機視錐體內


僅修改相機的center,了解該參數的含義(相機鏡頭指向的點)


僅修改相機的up,了解該參數的含義(攝像機圍繞其視線(z 軸)旋轉,因此其向上方向每次都指向沿向上矢量 (upx, upy, upz))

upx=1,相機up方向朝向x軸正方形
相機從原來朝向基礎上向右旋轉90°

upy為-1,相機up方向朝y軸負方向
相機從原來朝向基礎上向左/右旋轉180°

4.6.1 Understanding the Viewing Transformation

基礎知識鋪墊
點積

點積的一個特別有用的應用是:當想要將給定的向量 v 拆分為 v = v1 +v2 時,其中分量 v1 和 v2 分別平行和垂直于另一個給定的非零向量 u。



將上述點積應用到計算相機的up direction上
將up向量分解為 up 1 \text{up}_1 up1? up 2 \text{up}_2 up2?、其中 up 1 \text{up}_1 up1?與視線los共線, up 2 \text{up}_2 up2?在平面p上,為相機的up direction
相機位置 eye = (eyex,eyey,eyez) \text{eye}=\text{(eyex,eyey,eyez)} eye=(eyex,eyey,eyez)
相機“看向” center = (centerx,centery,centerz) \text{center}=\text{(centerx,centery,centerz)} center=(centerx,centery,centerz)
相機up direction: up 2 = (upx,upy,upz) \text{up}_2=\text{(upx,upy,upz)} up2?=(upx,upy,upz)

例子:計算每個veiwing transformation的相機up direction
gluLookAt(eyex, eyey, eyez, centerx, centery, centerz, upx, upy, upz)
gluLookAt(0.0, 0.0, 5.0, 5.0, 0.0, 0.0, 0.0, 1.0, 1.0)

注意:Collectively, the modeling transformations glTranslatef(), glRot
atef() and glScalef() and the viewing transformation gluLookAt() are called modelview transformations.

4.6.2 Simulating a Viewing Transformation with Modeling Transformations

當我們引入 gluLookAt() 時,我們說它模擬了 OpenGL 相機的運動。這是完全正確的。OpenGL 相機永遠不會在原點處保留其默認姿勢,其鏡頭指向 -z 方向,頂部沿 +y 方向對齊。換句話說,視錐體(或框)保持在它第一次使用 glFrustum()(或 glOrtho())創建的位置。
也就是做第一幀相機坐標系原點和世界坐標系原點重合

實際上,通過將viewing transformation為等效的modeling transformations序列來模擬viewing transformation。


4.6.3 Orientation and Euler Angles

gluLookAt(eyex, eyey, eyez, centerx, centery, centerz, upx, upy, upz)
等價于


相機中心eye在世界坐標系中的坐標eye=(eyex,eyey,eyez),通過glTranslatef(-eyex,eyey,-eyez)將相機中心移到世界坐標系原點

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/67331.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/67331.shtml
英文地址,請注明出處:http://en.pswp.cn/web/67331.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Deepseek的RL算法GRPO解讀

在本文中&#xff0c;我們將深入探討Deepseek采用的策略優化方法GRPO&#xff0c;并順帶介紹一些強化學習&#xff08;Reinforcement Learning, RL&#xff09;的基礎知識&#xff0c;包括PPO等關鍵概念。 策略函數&#xff08;policy&#xff09; 在強化學習中&#xff0c; a…

【python】python基于機器學習與數據分析的二手手機特性關聯與分類預測(源碼+數據集)【獨一無二】

&#x1f449;博__主&#x1f448;&#xff1a;米碼收割機 &#x1f449;技__能&#x1f448;&#xff1a;C/Python語言 &#x1f449;專__注&#x1f448;&#xff1a;專注主流機器人、人工智能等相關領域的開發、測試技術。 python基于機器學習與數據分析的二手手機特性關聯與…

手撕Diffusion系列 - 第十一期 - lora微調 - 基于Stable Diffusion(代碼)

手撕Diffusion系列 - 第十一期 - lora微調 - 基于Stable Diffusion&#xff08;代碼&#xff09; 目錄 手撕Diffusion系列 - 第十一期 - lora微調 - 基于Stable Diffusion&#xff08;代碼&#xff09;Stable Diffusion 原理圖Stable Diffusion的原理解釋Stable Diffusion 和Di…

前端【8】HTML+CSS+javascript實戰項目----實現一個簡單的待辦事項列表 (To-Do List)

目錄 一、功能需求 二、 HTML 三、CSS 四、js 1、綁定事件與初始設置 2.、綁定事項 &#xff08;1&#xff09;添加操作&#xff1a; &#xff08;2&#xff09;完成操作 &#xff08;3&#xff09;刪除操作 &#xff08;4&#xff09;修改操作 3、完整js代碼 總結…

C++標準線程庫實現優雅退出的方式

目錄 1.通過設置共享退出標記 2.使用std::jthread創建線程 3.定義消息類型的方式 4.注意事項 1.通過設置共享退出標記 定義一個退出變量bool stop false; 表示線程是否應該停止。在主線程中設置標記stoptrue,然后join一直等待&#xff0c;然后線程循環檢測到stop是否為tru…

Java學習教程,從入門到精通,JDBC插入記錄語法及案例(104)

JDBC插入記錄語法及案例 一、JDBC插入記錄語法 在JDBC中&#xff0c;插入記錄主要通過執行SQL的INSERT語句來實現。其基本語法如下&#xff1a; INSERT INTO 表名 (列1, 列2, ..., 列n) VALUES (值1, 值2, ..., 值n);表名&#xff1a;需要插入記錄的表的名稱。列1, 列2, …,…

vue事件總線(原理、優缺點)

目錄 一、原理二、使用方法三、優缺點優點缺點 四、使用注意事項具體代碼參考&#xff1a; 一、原理 在Vue中&#xff0c;事件總線&#xff08;Event Bus&#xff09;是一種可實現任意組件間通信的通信方式。 要實現這個功能必須滿足兩點要求&#xff1a; &#xff08;1&#…

圖像處理之HSV顏色空間

目錄 1 RGB 的局限性 2 HSV 顏色空間 3 RGB與HSV相互轉換 4 HSV顏色模型對圖像的色相、飽和度和明度進行調節 5 演示Demo 5.1 開發環境 5.2 功能介紹 5.3 下載地址 參考 1 RGB 的局限性 RGB 是我們接觸最多的顏色空間&#xff0c;由三個通道表示一幅圖像&#xff0c;分…

DeepSeek是由杭州深度求索人工智能基礎技術研究有限公司(簡稱“深度求索”)發布的一系列人工智能模型

DeepSeek是由杭州深度求索人工智能基礎技術研究有限公司&#xff08;簡稱“深度求索”&#xff09;發布的一系列人工智能模型&#xff0c;其在知識類任務上展現出了卓越的性能。以下是對DeepSeek的詳細介紹&#xff0c;內容雖無法達到10000字&#xff0c;但會盡可能全面且深入地…

【C++高并發服務器WebServer】-9:多線程開發

本文目錄 一、線程概述1.1 線程和進程的區別1.2 線程之間共享和非共享資源1.3 NPTL 二、線程操作2.1 pthread_create2.2 pthread_exit2.3 pthread_join2.4 pthread_detach2.5 patch_cancel2.6 pthread_attr 三、實戰demo四、線程同步五、死鎖六、讀寫鎖七、生產消費者模型 一、…

14-6-1C++STL的list

(一&#xff09;list容器的基本概念 list容器簡介&#xff1a; 1.list是一個雙向鏈表容器&#xff0c;可高效地進行插入刪除元素 2.list不可以隨機存取元素&#xff0c;所以不支持at.(pos)函數與[ ]操作符 &#xff08;二&#xff09;list容器頭部和尾部的操作 list對象的默…

在sortablejs的拖拽排序情況下阻止input拖拽事件

如題 問題 在vue3的elementPlus的table中&#xff0c;通過sortablejs添加了行拖拽功能&#xff0c;但是在行內會有輸入框&#xff0c;此時拖拽輸入框會觸發sortablejs的拖拽功能 解決 基于這個現象&#xff0c;我懷疑是由于拖拽事件未綁定而冒泡到后面的行上從而導致的拖拽…

21.Word:小趙-畢業論文排版?【39】

目錄 題目? NO1.2 NO3.4 NO5.6 NO7.8.9 NO10.11.12 題目 NO1.2 自己的論文當中接收老師的修改&#xff1a;審閱→比較→源文檔&#xff1a;考生文件夾&#xff1a;Word.docx→修訂的文檔&#xff1a;考生文件夾&#xff1a;教師修改→確定→接收→接收所有修訂將合并之…

leetcode_鏈表 876.鏈表的中間節點

876.鏈表的中間節點 給你單鏈表的頭結點 head &#xff0c;請你找出并返回鏈表的中間結點。如果有兩個中間結點&#xff0c;則返回第二個中間結點。思路&#xff1a;快慢指針&#xff0c;創建兩個指針fast和slow&#xff0c;fast指針每次移動兩步&#xff0c;slow指針每次移動…

深度學習 DAY3:NLP發展史及早期的前饋神經網絡(ANN)及多任務學習

NLP發展史 NLP發展脈絡簡要梳理如下&#xff1a; 2001 - Neural language models&#xff08;神經語言模型&#xff09; 2008 - Multi-task learning&#xff08;多任務學習&#xff09; 2013 - Word embeddings&#xff08;詞嵌入&#xff09; 2013 - Neural networks for NL…

全面了解 Web3 AIGC 和 AI Agent 的創新先鋒 MelodAI

不管是在傳統領域還是 Crypto&#xff0c;AI 都是公認的最有前景的賽道。隨著數字內容需求的爆炸式增長和技術的快速迭代&#xff0c;Web3 AIGC&#xff08;AI生成內容&#xff09;和 AI Agent&#xff08;人工智能代理&#xff09;正成為兩大關鍵賽道。 AIGC 通過 AI 技術生成…

54.數字翻譯成字符串的可能性|Marscode AI刷題

1.題目 問題描述 小M獲得了一個任務&#xff0c;需要將數字翻譯成字符串。翻譯規則是&#xff1a;0對應"a"&#xff0c;1對應"b"&#xff0c;依此類推直到25對應"z"。一個數字可能有多種翻譯方法。小M需要一個程序來計算一個數字有多少種不同的…

FileReader使用

FileReader : 讀取文件內容的api&#xff0c;&#xff0c;&#xff0c;在前端處理上傳的文件&#xff0c;&#xff0c;比如預覽圖片 readAsDataURL(file) &#xff1a; 讀取為base64編碼的 data urlreadAsText() &#xff1a; 讀取為文本readAsArrayBuffer() : 讀取為二進制 …

RabbitMQ5-死信隊列

目錄 死信的概念 死信的來源 死信實戰 死信之TTl 死信之最大長度 死信之消息被拒 死信的概念 死信&#xff0c;顧名思義就是無法被消費的消息&#xff0c;一般來說&#xff0c;producer 將消息投遞到 broker 或直接到queue 里了&#xff0c;consumer 從 queue 取出消息進…

JavaScript系列(48)-- 3D渲染引擎實現詳解

JavaScript 3D渲染引擎實現詳解 &#x1f3ae; 今天&#xff0c;讓我們深入探討JavaScript的3D渲染引擎實現。通過WebGL和現代JavaScript技術&#xff0c;我們可以構建一個功能完整的3D渲染系統。 3D渲染基礎概念 &#x1f31f; &#x1f4a1; 小知識&#xff1a;3D渲染引擎的…