項目開發步驟
1 界面開發 美顏相機界面構成: 標題 尺寸 關閉方式 位置 可視化
2 創建主函數調用界面方法
3 添加兩個面板 一個是按鈕面板一個是圖片面板 用JPanel
4 添加按鈕到按鈕面吧【注意:此時要用初始化按鈕面板的方法initBtnPanel 并且將按鈕添加到按鈕面板上面 要將按鈕面板傳到方法中】
? ? -? 用一維字符串數組表示按鈕 然后通過for循環遍歷 將按鈕文本添加到按鈕上面 可以獲得按鈕的背景顏色 最后按鈕一定要添加到按鈕面板上
5 添加監聽器 動作監聽器和按鈕監聽器 在按鈕動作監聽器用 e.get~的方法獲取文本信息? 給按鈕也添加監聽器 在添加前先創建對象
6 按鈕功能的實現 用if 和equals?
? ?-? 打開功能的實現
? ? ?先獲取圖片的絕對路徑 用loadImage方法 先讀取文件后ImageIO.read(path)讀取文件的像素點? 定義一個二維數組來儲存圖片? 后用for遍歷圖片的像素點 用image.getRGB(i,j) 將BufferedImage對象Image中指定位置(i,j)的像素顏色取出來儲存到二維數組中? for循環結束后 可輸出圖片加載完成?
? ? ?用文件選擇器打開文件 FileChosser? 打開文件位置null 用if判斷選擇時點了確定按鈕 后獲取所選擇的文件的絕對路徑 然后對圖像處理對象 調用加載圖像的方法將? 轉為像素的二維數組
? -? 原圖功能的實現
? ? ?畫圖片drawImage? 現將像素取出來 然后獲取每個像素點的顏色 將顏色給畫筆【畫筆是從繪制面板傳過來】 后繪制像素點
? ? 在ImageProUI類中獲取顯示圖片畫板的畫筆 然后imageLister對象中ImageUtils對象的畫筆是面板的畫筆【將面板的畫筆賦給它】
? ? 后在按鈕功能實現的地方調用方法
package lfx250220;import javax.swing.*;
import java.awt.*;
import java.awt.image.ImageObserver;
import java.text.AttributedCharacterIterator;public class ImageProUI {//界面開發 先寫一個個方法然后把界面創建出來//創建面板 JPanle//創建一個監聽器ImageLister imageLister=new ImageLister();public void showUI(){JFrame jf= new JFrame();//界面:大小 位置 關閉方式 可視化 布局方式jf.setTitle("美顏相機");jf.setSize(900,900);jf.setLocationRelativeTo(null);jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);//JPanel類 面板 相當于一個容器JPanel btnPanel = new JPanel();JPanel imgPanel = new JPanel();//設置面板屬性btnPanel.setBackground(Color.CYAN);imgPanel.setBackground(Color.BLUE);//設置寬高用到Dimension類 維度Dimension dimension = new Dimension(300,100);btnPanel.setPreferredSize(dimension);//初始化按鈕面板 調用initBtnPanel這個方法initBtnPanel(btnPanel);//布局: 流式布局(JPanel 默認布局) 邊框布局(窗體的默認布局)//將面板添加到窗體上 用BorderLayout布局//BorderLayout布局: 是JFrame 的默認布局管理器 將容器劃分為五個區域//北(BorderLayout.NORTH) 南(BorderLayout.SOUTH) 東(BorderLayout.EAST) 西(BorderLayout.WEST) 中(BorderLayout.CENTER)jf.add(btnPanel,BorderLayout.NORTH);jf.add(imgPanel,BorderLayout.CENTER);//FlowLayout flowLayout = new FlowLayout();//BorderLayout borderLayout = new BorderLayout();//jf.setLayout(flowLayout);//jf.setLayout(borderLayout);jf.setVisible(true);//獲取 顯示圖片的畫板 的畫筆Graphics gra=imgPanel.getGraphics();imageLister.imageUtils.gra=gra;//gra是imageLister對象中imageUtils對象中的畫筆}//初始化按鈕面板//按鈕是要添加到按鈕面板上 所以要把按鈕面板傳過來public void initBtnPanel(JPanel btnPanel){String[] btnTexts = {"打開","保存","原圖","馬賽克","灰度"};//遍歷 將每個按鈕寫出來 然后設置顏色for (int i=0;i< btnTexts.length;i++){JButton btn=new JButton(btnTexts[i]);btn.setBackground(Color.ORANGE);btnPanel.add(btn);btn.addActionListener(imageLister);}String[] btnTexts2={"畫筆","直線","矩形","填充","截圖","馬賽克畫筆"};for (int i=0;i< btnTexts2.length;i++){JButton btn=new JButton(btnTexts2[i]);btn.setBackground(Color.GREEN);btnPanel.add(btn);btn.addActionListener(imageLister);}}public static void main(String[] args) {ImageProUI showui=new ImageProUI();showui.showUI();}
}
package lfx250220;import javax.swing.*;
import javax.swing.filechooser.FileNameExtensionFilter;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;public class ImageLister implements MouseListener, ActionListener {//【注意:函數的調用需要用對象來實現】//圖像處理器ImageUtils imageUtils=new ImageUtils();@Overridepublic void actionPerformed(ActionEvent e) {//按鈕的動作監聽器 獲取按鈕的文本String ac=e.getActionCommand();System.out.println("ac"+ac);//按鈕功能的實現if (ac.equals("打開")){//打開圖片 目的 獲取一張照片的絕對路徑//用文件選擇器將圖片打開//文件過濾器FileNameExtensionFilter filter = new FileNameExtensionFilter("JPG & PNG","jpg", "png");//文件選擇器JFileChooser jfc = new JFileChooser();int state = jfc.showOpenDialog(null);//參數對他的作用是一個位置作用 寫成空就是居中if (state==JFileChooser.APPROVE_OPTION){//選擇時點了確定按鈕//獲取所 選擇的文件的 絕對路徑String path = jfc.getSelectedFile().getAbsolutePath();//圖像處理對象 調用加載圖片的方法 轉為像素的二維數組imageUtils.loadImage(path);}} else if (ac.equals("保存")) {}else if (ac.equals("原圖")) {imageUtils.drawImage();}else if (ac.equals("馬賽克")) {}else if (ac.equals("灰度化")) {}}@Overridepublic void mouseClicked(MouseEvent e) {}@Overridepublic void mousePressed(MouseEvent e) {}@Overridepublic void mouseReleased(MouseEvent e) {}@Overridepublic void mouseEntered(MouseEvent e) {}@Overridepublic void mouseExited(MouseEvent e) {}
}
package lfx250220;import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;public class ImageUtils {//定義一個屬性 儲存圖片的二維數組static int[][] imgArr;//寬度和高度int w;int h;Graphics gra = null;//從繪制面板上將畫筆傳過來//加載圖片public static void loadImage(String path){File file = new File(path);//讀取文件的內容//補充://BufferedImage 可理解為一個包含圖像像素數據的緩沖區 不僅儲存了圖像的像素信息 還包含了圖像的顏色模型 透明度等屬性//也可以把他看成一個二維的像素數組 每個像素都有對應的顏色值//主要作用://圖像讀取與儲存 處理圖像文件一般把BufferedImage當做中間對象 在該項目代碼就是這個作用//圖像編輯與處理 BufferedImage提供豐富的方法來操作圖像的像素 通過修改BufferedImage的像素值 可以是實現各種圖像特效//圖像顯示 Java中 可以將BufferedImage對象繪制到Graohics上下文上 從而在窗口中顯示圖像//ImageIO.read(file)方法嘗試從文件File中讀取圖像 是Java標準庫中用于讀取圖像文件的靜態方法try {BufferedImage image=ImageIO.read(file);//獲取圖片的寬度和高度int w=image.getWidth();int h= image.getHeight();//創建一個空的數組 儲存圖片的像素值imgArr = new int[w][h];//將圖片的像素值復制到數組中for (int i=0;i<w;i++){for (int j=0;j<h;j++){imgArr[i][j]=image.getRGB(i,j);//將BufferedImage對象Image中指定位置(i,j)的像素顏色取出來 并儲存在二維數組}}System.out.println("加載圖片完成");} catch (IOException e) {throw new RuntimeException(e);}}//繪制圖像的方法public void drawImage(){//先將像素取出來for (int i=0;i<w;i++){for (int j=0;j<h;j++){int pixNum = imgArr[i][j];Color color= new Color(pixNum);gra.setColor(color);gra.fillRect(i,j,1,1);//繪制像素點}}}}
補充內容:復盤遇到的問題以及文件選擇器和獲取圖片路徑的方法
?-? 復盤遇到的問題
? ? ?- 1 用for循環遍歷數組的時候 從i= 0 即數組的第一個數開始 并且 i = 數組的長度 這會引起索引越界的問題?
? ? ?-? 2 把按鈕添加到面板上用的方法是初始化按鈕面板 initBtnPanel
? -? 文件選擇器
? ? - JFileChooser 的使用方法
? ? ? ? ? -? 1創建JFileChooser 對象
? ? ? ? ? -? 2顯示文件選擇器的對話框
? ? ? ? ? -? 3 處理用戶的選擇結果? 用if?
package lfx250223;import javax.swing.*;public class JFileChooserExample {public static void main(String[] args) {//使用步驟// 1 創建JFileChooser對象JFileChooser jFileChooser = new JFileChooser();// 2 顯示文件選擇器對話框 位置nullint state = jFileChooser.showOpenDialog(null);// 3 處理用戶的選擇結果if (state==JFileChooser.APPROVE_OPTION){//用戶點擊了 打開 按鈕java.io.File selectedFile = jFileChooser.getSelectedFile();//getSelectedFile() 是JFileCHooser類的一個方法//作用是獲取用戶在文件選擇對話框中選定的文件 該方法會返回一個java.io.File 類的對象 該對象表示用戶所選擇的文件//java.io.File selectedFile:聲明了一個 java.io.File 類型的變量 selectedFile,并把 getSelectedFile() 方法返回的文件對象賦值給它。JOptionPane.showMessageDialog(null,"你選擇的文件是:"+selectedFile.getAbsolutePath());//JOptionPane:這是 Java Swing 庫中的一個類,可用于創建各種對話框,像消息對話框、確認對話框等。//showMessageDialog:這是 JOptionPane 類的一個靜態方法,用于顯示一個消息對話框。//第一個參數 null:表示對話框的父組件,這里傳入 null 意味著對話框會顯示在屏幕中央。//第二個參數:是要顯示的消息內容。selectedFile.getAbsolutePath() 方法會返回所選文件的絕對路徑,把這個路徑和提示信息拼接后作為消息內容顯示在對話框里。}else if (state == JFileChooser.CANCEL_OPTION) {// 用戶點擊了“取消”按鈕JOptionPane.showMessageDialog(null, "你取消了文件選擇。");}}
}
-? 獲取圖片路徑?
? ?在inageUtils中定義一個二維數組 然后用loadImage方法【(String path)】? 定義對象File 然后for遍歷得到文件中圖片的像素點 并且儲存到二維數組中 此時用到的是image.getRGB(i,j)
【詳細代碼看上邊】