[Part I. GIMP基礎功]

[Part II. 一種效果的誕生]
[Part III. Script-Fu的秘密]



24.6 波浪圖,修改成可「單行」執行的 Script-Fu

修改成一行一行可執行的程式碼
  • 本節要將 waves-anim.scm 修改成在 Console 內可一行一行執行的 Scheme 程式碼。
  • waves-anim.scm 完整的程式碼可參考 24.5 節
  • 也可到 GIMP 系統的 scripts 目錄下找到該檔案。
  • 最主要修改的部份是,將「對話框接收輸入變數值」修改成「直接指定輸入變數值」。
  • 先要瞭解,news-text.scm 程式碼的執行流程。


最主要修改的部份
  • 不使用 let* 改用 define
  • 原本的程式使用 let* 定義與指定區域變數值。
  • (let* (()()()...) ()() ...) 這樣的語法括號太多。
  • 若要一行一行分析程式碼的意義,let* 語法,括號有好幾層,分析時,會造成一些干擾。
  • 現在不使用 let* 改用 define 來定義與指定變數值。


捨棄函數 script-fu-waves-anim,直接指定輸入變數值
  • 修改成最多的地方就是下列這兩段部份。
  • (while (condition) (expr1) (expr2) .......),要注意此區塊括號的對齊。
  • 記得要刪除多餘的右括號 ) ,不然會出現錯誤訊息。
  • 修改後的程式碼,不再需要預先定義函數 script-fu-waves-anim ,但是要預先設定變數名稱、變數值 。
(define (script-fu-waves-anim img
drawable
amplitude
wavelength
num-frames
invert)
(let* ((amplitude ......))
(wavelength ......))
(num-frames ......)
(remaining-frames num-frames)
(phase 0)
(phaseshift ......)
(image ......)
(source-layer ......))


(let* (
(waves-layer (car (gimp-layer-copy source-layer TRUE)))
(layer-name (string-append "Frame "
       (number->string
         (- (+ num-frames 2)
            remaining-frames) 10
         )
       " (replace)"))



從下列的程式碼得知變數值的型態與大小
SF-IMAGE       "Image" 0
SF-DRAWABLE "Drawable" 0
SF-ADJUSTMENT _"Amplitude" '(10 1 101 1 10 1 0)
SF-ADJUSTMENT _"Wavelength" '(10 0.1 100 1 10 1 0)
SF-ADJUSTMENT _"Number of frames" '(6 1 512 1 10 0 1)
SF-TOGGLE _"Invert direction" FALSE


以 flat land 平地圖案,作為測試用圖
  • 假設啟動 GIMP 之後沒有開啟任何影像檔。
  • 如此,新出現的影像其 id 為 1
  • 程式碼的開頭加入這幾行,產生測試用圖 。

......
(script-fu-flatland 256 256 80 3.0 4.0 4.0)
......


修改後的程式碼,與測試的結果圖
  • 下面是修改後的程式碼。
  • 為了確保影像 id 為 1 ,請重新啟動 GIMP 。
  • 啟動 GIMP Script-fu Console
  • 將下面的 Scheme 程式碼,全部選取、複製、再貼入 Script-fu Console 文字框,按下 Enter 。
  • 過一會,就會看到結果圖。
(define gradient "Land 1")
(gimp-context-set-gradient gradient)
(script-fu-flatland  256 256 80 3.0 4.0 4.0)
(define img 1) ; 影像 id 需要視"開啟多少影像"而定
(gimp-image-flatten img)
(define drawable (car (gimp-image-active-drawable img)))

(define amplitude 10)
(define wavelength 10)
(define num-frames 6)
(define invert FALSE)
(define amplitude (max 0 amplitude))
(define wavelength (max 0 wavelength))
(define num-frames (max 1 num-frames))
(define remaining-frames num-frames)
(define phase 0)
(define phaseshift (/ 360 num-frames))
(define image (car (gimp-image-duplicate img)))
(define source-layer (car (gimp-image-get-active-layer image)))

(gimp-image-undo-disable image)

(if (= invert TRUE)
(set! phaseshift (- 0 phaseshift)))

(while (> remaining-frames 1)
(define waves-layer (car (gimp-layer-copy source-layer TRUE)))
(define layer-name (string-append "Frame "
(number->string (- (+ num-frames 2)   remaining-frames) 10) " (replace)"))

(gimp-layer-set-lock-alpha waves-layer FALSE)
(gimp-image-add-layer image waves-layer -1)
(gimp-drawable-set-name waves-layer layer-name)

(plug-in-waves RUN-NONINTERACTIVE image waves-layer amplitude phase wavelength 0 FALSE)

(set! remaining-frames (- remaining-frames 1))
(set! phase (- phase phaseshift))
) ;這個右括號屬於 while 迴圈


(gimp-drawable-set-name source-layer "Frame 1")
(plug-in-waves RUN-NONINTERACTIVE image source-layer amplitude phase wavelength 0 FALSE)

(gimp-image-undo-enable image)
(gimp-display-new image)