OpenGL ES之5種紋理翻轉(zhuǎn)策略

最近用GLSL實(shí)現(xiàn)渲染圖片,原始圖片是正常顯示的政冻,但是渲染出來(lái)的是倒置的枚抵,通過(guò)查找許多資料才明白是因?yàn)槭謾C(jī)的(0,0)點(diǎn)在左上角,紋理的(0,0)點(diǎn)在左下角明场,所以才會(huì)產(chǎn)生這樣的問(wèn)題,所以總結(jié)了下面5種紋理翻轉(zhuǎn)方法供大家參考也方便后期查閱李丰。

一苦锨、旋轉(zhuǎn)頂點(diǎn)坐標(biāo)
在頂點(diǎn)著色器中,將頂點(diǎn)坐標(biāo)叉乘一個(gè)180度旋轉(zhuǎn)矩陣趴泌。代碼如下:

  • 頂點(diǎn)著色器

    attribute vec4 position;
    attribute vec2 textCoordinate;
    uniform mat4 rotateMatrix;
    varying lowp vec2 varyTextCoord;
    
    void main()
    {
        varyTextCoord = textCoordinate;
    
        vec4 vPos = position;
        vPos = vPos * rotateMatrix;
    
        gl_Position = vPos;
    }
    
  • 旋轉(zhuǎn)矩陣輸入

    //1. rotate等于shaderv.vsh中的uniform屬性舟舒,rotateMatrix
        GLuint rotate = glGetUniformLocation(self.myPrograme, "rotateMatrix");
    
        //2.獲取渲旋轉(zhuǎn)的弧度
        float radians = 180 * 3.14159f / 180.0f;
    
        //3.求得弧度對(duì)于的sin\cos值
        float s = sin(radians);
        float c = cos(radians);
    
        //4.因?yàn)樵?D課程中用的是橫向量,在OpenGL ES用的是列向量
        /*
         參考Z軸旋轉(zhuǎn)矩陣
         */
        GLfloat zRotation[16] = {
            c,-s,0,0,
            s,c,0,0,
            0,0,1,0,
            0,0,0,1
        };
    
        //5.設(shè)置旋轉(zhuǎn)矩陣
        /*
         glUniformMatrix4fv (GLint location, GLsizei count, GLboolean transpose,  const GLfloat* value)
         location : 對(duì)于shader 中的ID
         count : 個(gè)數(shù)
         transpose : 轉(zhuǎn)置
         value : 指針
         */
        glUniformMatrix4fv(rotate, 1, GL_FALSE, zRotation);
    

二嗜憔、解壓圖片時(shí)改變圖片坐標(biāo)
加載紋理時(shí)秃励,需要解壓圖片,此時(shí)通過(guò)平移縮放改變圖片坐標(biāo)吉捶,即可達(dá)成目的夺鲜。相關(guān)代碼如下:

  • 圖片解壓、平移呐舔、縮放

     //1币励、將 UIImage 轉(zhuǎn)換為 CGImageRef
       CGImageRef spriteImage = [UIImage imageNamed:fileName].CGImage;
    
       //判斷圖片是否獲取成功
       if (!spriteImage) {
           NSLog(@"Failed to load image %@", fileName);
           exit(1);
       }
    
       //2、讀取圖片的大小珊拼,寬和高
       size_t width = CGImageGetWidth(spriteImage);
       size_t height = CGImageGetHeight(spriteImage);
    
       //3.獲取圖片字節(jié)數(shù) 寬*高*4(RGBA)
       GLubyte * spriteData = (GLubyte *) calloc(width * height * 4, sizeof(GLubyte));
    
       //4.創(chuàng)建上下文
       /*
        參數(shù)1:data,指向要渲染的繪制圖像的內(nèi)存地址
        參數(shù)2:width,bitmap的寬度食呻,單位為像素
        參數(shù)3:height,bitmap的高度,單位為像素
        參數(shù)4:bitPerComponent,內(nèi)存中像素的每個(gè)組件的位數(shù)澎现,比如32位RGBA仅胞,就設(shè)置為8
        參數(shù)5:bytesPerRow,bitmap的沒(méi)一行的內(nèi)存所占的比特?cái)?shù)
        參數(shù)6:colorSpace,bitmap上使用的顏色空間   kCGImageAlphaPremultipliedLast:RGBA
        */
       CGContextRef spriteContext = CGBitmapContextCreate(spriteData, width, height, 8, width*4,CGImageGetColorSpace(spriteImage), kCGImageAlphaPremultipliedLast);
    
    
       //5、在CGContextRef上--> 將圖片繪制出來(lái)
       /*
        CGContextDrawImage 使用的是Core Graphics框架剑辫,坐標(biāo)系與UIKit 不一樣干旧。UIKit框架的原點(diǎn)在屏幕的左上角,Core Graphics框架的原點(diǎn)在屏幕的左下角揭斧。
        CGContextDrawImage 
        參數(shù)1:繪圖上下文
        參數(shù)2:rect坐標(biāo)
        參數(shù)3:繪制的圖片
        */
       CGRect rect = CGRectMake(0, 0, width, height);
    
       //6.使用默認(rèn)方式繪制
       CGContextDrawImage(spriteContext, rect, spriteImage);
    
       CGContextTranslateCTM(spriteContext, rect.origin.x, rect.origin.y);
       CGContextTranslateCTM(spriteContext, 0, rect.size.height);//平移
       CGContextScaleCTM(spriteContext, 1.0, -1.0);//縮放
       CGContextTranslateCTM(spriteContext, -rect.origin.x, -rect.origin.y);
       CGContextDrawImage(spriteContext, rect, spriteImage);
    
       //7莱革、畫(huà)圖完畢就釋放上下文
       CGContextRelease(spriteContext);
    

三峻堰、改變紋素獲取坐標(biāo)
在片元著色器中,改變紋素獲取的y值,即可達(dá)成目的盅视。

  • 片元著色器代碼

    varying lowp vec2 varyTextCoord;
    uniform sampler2D colorMap;
    
    void main()
    {
        //gl_FragColor = texture2D(colorMap, varyTextCoord);
        gl_FragColor = texture2D(colorMap, vec2(varyTextCoord.x,1.0 - varyTextCoord.y));
    }
    

四捐名、改變紋理坐標(biāo)
在頂點(diǎn)著色器中,改變紋理坐標(biāo)的y值闹击,即可達(dá)成目的镶蹋。

  • 頂點(diǎn)著色器代碼

    attribute vec4 position;
    attribute vec2 textCoordinate;
    varying lowp vec2 varyTextCoord;
    
    void main()
    {
        //varyTextCoord = textCoordinate;
        varyTextCoord = vec2(textCoordinate.x,1.0-textCoordinate.y);
        gl_Position = position;
    }
    

五、直接改動(dòng)紋理坐標(biāo)數(shù)組
最復(fù)雜的方法赏半,但是最容易想到的贺归,就是在頂點(diǎn)、紋理坐標(biāo)數(shù)組里改變紋理坐標(biāo)值断箫。

  • 數(shù)組改變代碼

    //前3個(gè)是頂點(diǎn)坐標(biāo)拂酣,后2個(gè)是紋理坐標(biāo)
    //    GLfloat attrArr[] =
    //    {
    //        0.5f, -0.5f, -1.0f,     1.0f, 0.0f,
    //        -0.5f, 0.5f, -1.0f,     0.0f, 1.0f,
    //        -0.5f, -0.5f, -1.0f,    0.0f, 0.0f,
    //
    //        0.5f, 0.5f, -1.0f,      1.0f, 1.0f,
    //        -0.5f, 0.5f, -1.0f,     0.0f, 1.0f,
    //        0.5f, -0.5f, -1.0f,     1.0f, 0.0f,
    //    };
    
        GLfloat attrArr[] =
        {
            0.5f, -0.5f, -1.0f,     1.0f, 1.0f,
            -0.5f, 0.5f, -1.0f,     0.0f, 0.0f,
            -0.5f, -0.5f, -1.0f,    0.0f, 1.0f,
      
            0.5f, 0.5f, -1.0f,      1.0f, 0.0f,
            -0.5f, 0.5f, -1.0f,     0.0f, 0.0f,
            0.5f, -0.5f, -1.0f,     1.0f, 1.0f,
        };
    
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市仲义,隨后出現(xiàn)的幾起案子婶熬,更是在濱河造成了極大的恐慌,老刑警劉巖埃撵,帶你破解...
    沈念sama閱讀 218,525評(píng)論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件赵颅,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡暂刘,警方通過(guò)查閱死者的電腦和手機(jī)饺谬,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,203評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)谣拣,“玉大人募寨,你說(shuō)我怎么就攤上這事≈シⅲ” “怎么了绪商?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,862評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)辅鲸。 經(jīng)常有香客問(wèn)我格郁,道長(zhǎng),這世上最難降的妖魔是什么独悴? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,728評(píng)論 1 294
  • 正文 為了忘掉前任例书,我火速辦了婚禮,結(jié)果婚禮上刻炒,老公的妹妹穿的比我還像新娘决采。我一直安慰自己,他們只是感情好坟奥,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,743評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布树瞭。 她就那樣靜靜地躺著拇厢,像睡著了一般。 火紅的嫁衣襯著肌膚如雪晒喷。 梳的紋絲不亂的頭發(fā)上孝偎,一...
    開(kāi)封第一講書(shū)人閱讀 51,590評(píng)論 1 305
  • 那天错英,我揣著相機(jī)與錄音挤巡,去河邊找鬼驼鹅。 笑死逮栅,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的挨下。 我是一名探鬼主播蒿囤,決...
    沈念sama閱讀 40,330評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼从隆,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼蓝撇!你這毒婦竟也來(lái)了果复?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 39,244評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤渤昌,失蹤者是張志新(化名)和其女友劉穎据悔,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體耘沼,經(jīng)...
    沈念sama閱讀 45,693評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,885評(píng)論 3 336
  • 正文 我和宋清朗相戀三年朱盐,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了群嗤。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,001評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡兵琳,死狀恐怖狂秘,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情躯肌,我是刑警寧澤者春,帶...
    沈念sama閱讀 35,723評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站清女,受9級(jí)特大地震影響钱烟,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜嫡丙,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,343評(píng)論 3 330
  • 文/蒙蒙 一拴袭、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧曙博,春花似錦拥刻、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,919評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)吴汪。三九已至,卻和暖如春蒸眠,著一層夾襖步出監(jiān)牢的瞬間漾橙,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,042評(píng)論 1 270
  • 我被黑心中介騙來(lái)泰國(guó)打工黔宛, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留近刘,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,191評(píng)論 3 370
  • 正文 我出身青樓臀晃,卻偏偏與公主長(zhǎng)得像觉渴,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子徽惋,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,955評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容