• java操作FFmpeg处理图片


    图片加水印:
    import
    java.awt.Color; import java.awt.Font; import java.awt.Graphics2D; import java.awt.Image; import java.awt.image.BufferedImage; import java.io.File; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import javax.imageio.ImageIO; public class ImageAddWatermarkUtil { public static void imageAddWatermark(String srcFileUrl) { File srcFolder = new File(srcFileUrl); // int i = 0; for (File file : srcFolder.listFiles()) { // File srcImgFile = new File(srcFileUrl);//得到文件 if (file.isFile() && file.getName().endsWith(".jpg")) { Image srcImg = null; try { srcImg = ImageIO.read(file); } catch (IOException e1) { // TODO Auto-generated catch block e1.printStackTrace(); } // 文件转化为图片 int srcImgWidth = srcImg.getWidth(null);// 获取图片的宽 int srcImgHeight = srcImg.getHeight(null);// 获取图片的高 // 加水印 Font font = new Font("微软雅黑", Font.PLAIN, 10); BufferedImage bufImg = new BufferedImage(srcImgWidth, srcImgHeight, BufferedImage.TYPE_INT_RGB); Graphics2D graphics2d = bufImg.createGraphics(); graphics2d.drawImage(srcImg, 0, 0, srcImgWidth, srcImgHeight, null); graphics2d.setColor(Color.WHITE); // 设置水印颜色 graphics2d.setFont(font); // 设置字体 // 设置水印的坐标 String name = file.getName(); String waterMarkContent = name.substring(0, name.indexOf(".")); // System.out.println(getWatermarkLength(waterMarkContent, graphics2d)); int x = srcImgWidth - getWatermarkLength(waterMarkContent, graphics2d) - 3; int y = srcImgHeight - 3; graphics2d.drawString(waterMarkContent, x, y); // 画出水印 graphics2d.dispose(); // 输出图片 FileOutputStream outImgStream = null; try { outImgStream = new FileOutputStream(file); } catch (FileNotFoundException e) { // TODO Auto-generated catch block e.printStackTrace(); } try { ImageIO.write(bufImg, "jpg", outImgStream); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } try { outImgStream.flush(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } try { outImgStream.close(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } } public static int getWatermarkLength(String waterMarkContent, Graphics2D g) { return g.getFontMetrics(g.getFont()).charsWidth(waterMarkContent.toCharArray(), 0, waterMarkContent.length()); } public static void main(String[] args) { } }
    图片合并:

    import
    java.awt.Graphics2D; import java.awt.image.BufferedImage; import java.io.File; import java.io.IOException; import javax.imageio.ImageIO; public class ImageMergeUtil { public static String mergeImage(String srcFileUrl, String size) { // BufferedImage image1 = ImageIO.read(file1); // BufferedImage image2 = ImageIO.read(file2); // String srcFileUrl = "D:\cdv\screenshot-test\image-folder"; int counts = getFileCounts(srcFileUrl); String sizeString[] = size.split("x"); int width = Integer.valueOf(sizeString[0]); int height = Integer.valueOf(sizeString[1]); int totalHeight = 0; if (counts%5==0) totalHeight = height*counts/5; else totalHeight = height*counts/5 + 1; BufferedImage combined = new BufferedImage(width*5,totalHeight, BufferedImage.TYPE_INT_RGB); // paint both images, preserving the alpha channels Graphics2D graphics2d = combined.createGraphics(); File srcFolder = new File(srcFileUrl); int i = 0; for (File file : srcFolder.listFiles()) { if (file.isFile()&&file.getName().endsWith(".jpg")) { BufferedImage fileImage = null; try { fileImage = ImageIO.read(file); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } graphics2d.drawImage(fileImage, width*(i%5), height*(i/5), null); //删除已经加入照片文件 file.delete(); i++; } } // Save as new image File photoWallFolder = new File( srcFileUrl + "\photoWall");// fisrcFileUrl + "\photoWall"; if (!photoWallFolder.exists()) { photoWallFolder.mkdirs(); } File photoWallImage = new File(srcFileUrl + "\photoWall", "photoWall.jpg"); int k = 0; while(photoWallImage.exists()) { photoWallImage = new File(srcFileUrl + "\photoWall", "photoWall-" + String.valueOf(k++) + ".jpg"); } try { ImageIO.write(combined, "JPG", photoWallImage); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } return photoWallImage.getAbsolutePath(); } public static int getFileCounts(String srcFileUrl) { int counts = 0; File fileList[] = new File(srcFileUrl).listFiles(); for (int i = 0; i < fileList.length; i++) { if (fileList[i].isFile()&&fileList[i].getName().endsWith(".jpg")) { counts++; } } //System.out.println(counts); return counts; } public static void main(String[] args) { String srcFileUrl = ""; mergeImage(srcFileUrl, "200x120"); } }

    图片抽帧:

    import java.io.File;
    import java.io.IOException;
    import java.util.ArrayList;
    import java.util.LinkedList;
    import java.util.List;
    
    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    
    public class ScreenShotUtil {
        // private static Logger logger = LoggerFactory.getLogger(ScreenShotUtil.class);
        private static final Logger logger = LoggerFactory.getLogger(ScreenShotController.class);
    
        public static PointScreen shotByTimePoint(String screenshotEXEPath, String srcFileUrl, String timePoint,
                String size, String outUrl) {
    
            List<String> cmd = new LinkedList<String>();
            cmd.add(screenshotEXEPath);
            // cmd.add("-y");
            cmd.add("-i");
            cmd.add(srcFileUrl);
            cmd.add("-ss");
            cmd.add(timePoint);
            // cmd.add("-i");
            // cmd.add(srcFileUrl);
            cmd.add("-t");
            cmd.add("0.001");
            cmd.add("-s");
            cmd.add(size);
            cmd.add("-ignore-black");
            cmd.add(outUrl + "\temp\.jpg");
            // logger.debug("shotByTimePoint: " + cmd);
            // System.out.println(cmd);
            ProcessBuilder pb = new ProcessBuilder();
            pb.command(cmd);
            File imageFolder = new File(outUrl + "\temp");
            imageFolder.mkdirs();
    
            try {
                Process process = pb.start();
                process.waitFor();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
    
            File newImageFile = null;
            for (File imageFile : imageFolder.listFiles()) {
                String imageName = timePoint.replaceAll("[:|.]", "-");
                newImageFile = new File(outUrl, imageName + ".jpg");
                imageFile.renameTo(newImageFile);
                imageFile.delete();
            }
            return new PointScreen(newImageFile.getAbsolutePath(), timePoint);
        }
    
        public static List<PointScreen> shotByKeyFrame(String screenshotEXEPath, String srcFileUrl, String size,
                String outUrl) {
            /**
             * 转场分析抽取若干张图片(输出名称包含百纳秒) snapshot -i oceans-clip.webm -scene_transition 1
             * oceans-clip-%013d.jpg 输出例为 oceans-clip-0000000000123.jpg,
             * oceans-clip-0000000004567.jpg, oceans-clip-0000000089000.jpg
             */
            List<String> cmd = new LinkedList<String>();
            List<PointScreen> pointScreens = new ArrayList<>();
            try {
                cmd.add(screenshotEXEPath);
                cmd.add("-i");
                cmd.add(srcFileUrl);
                cmd.add("-scene_transition");
                cmd.add("1");
                cmd.add("-s");
                cmd.add(size);
                cmd.add("-ignore-black");
                cmd.add(outUrl + "\temp\-%013d.jpg");
    
                ProcessBuilder pb = new ProcessBuilder();
                pb.command(cmd);
                File tempFolder = new File(outUrl + "\temp");
                tempFolder.mkdirs();
    
                // 开始抽帧
                Process process = pb.start();
                process.waitFor();
    
                File newImageFile = null;
                if (tempFolder.listFiles() != null) {
                    for (File imageFile : tempFolder.listFiles()) {
                        String imageNameWithSuffix = imageFile.getName();
                        String timePoint = NanosecondsToTimeUtil
                                .nanosecondsToTime(imageNameWithSuffix.substring(1, imageNameWithSuffix.indexOf(".")));
                        String imageName = timePoint.replaceAll("[:|.]", "-");
                        newImageFile = new File(outUrl, imageName + ".jpg");
                        // System.out.println(newImageFile);
                        imageFile.renameTo(newImageFile);
                        imageFile.delete();
                        pointScreens.add(new PointScreen(newImageFile.getAbsolutePath(), timePoint));
                    }
                }
            } catch (Exception e) {
                logger.info("抽取关键帧报错: " + e.getMessage(), e);
            }
            return pointScreens;
    
        }
    
        public static String photoWall(String screenshotEXEPath, String srcFileUrl, String size, String outFileUrl) {
            shotByKeyFrame(screenshotEXEPath, srcFileUrl, size, outFileUrl);
            ImageAddWatermarkUtil.imageAddWatermark(outFileUrl);
            // ImageMergeUtil.mergeImage(outFileUrl, size);
            return ImageMergeUtil.mergeImage(outFileUrl, size);
        }
    
        public static void main(String[] args) {
            
            // System.out.println(shotByTimePoint(exePath,srcFileUrl,"00:00:00.000",size,outFileUrl));//0时间点截图测试
            // shotByKeyFrame(srcFileUrl, size, outFileUrl);//0关键帧截图测试
    
            // 1.定时截图测试 时间间隔 intervalTime 秒
            // long intervalTime = 10;
            // long videoLength = VideoDuration.getVideoDuration(srcFileUrl);
            // List<PointScreen> pointScreens = new ArrayList<>();
            // for (long i = 0; i <= videoLength; i = i + intervalTime) {
            // timePoint =
            // NanosecondsToTimeUtil.nanosecondsToTime(Long.toString(i*1000*10000));
            // pointScreens.add(ScreenShotUtil.shotByTimePoint(srcFileUrl, timePoint, size,
            // outFileUrl));
            // }
            // for (Iterator<PointScreen> iterator = pointScreens.iterator();
            // iterator.hasNext();) {
            // System.out.println(iterator.next());
            // }
    
            // 2.定点截图
            // List<String> extraParam = new ArrayList<>();
            // extraParam.add("00:01:01.000");
            // extraParam.add("00:02:02.000");
            // extraParam.add("00:03:03.000");
            // extraParam.add("00:14:04.000");
            // for (Iterator<String> iterator = extraParam.iterator(); iterator.hasNext();)
            // ScreenShotUtil.shotByTimePoint(srcFileUrl, iterator.next(), size,
            // outFileUrl);
            // 3.定量截图
    
            // long videoDuration = VideoDuration.getVideoDuration(srcFileUrl);
            // int intervalTime = (int)(videoDuration/(10-1));
            // for (long i = 0; i <= videoDuration; i = i + intervalTime) {
            // String timePoint1 =
            // NanosecondsToTimeUtil.nanosecondsToTime(Long.toString(i*1000*10000));
            // ScreenShotUtil.shotByTimePoint(srcFileUrl, timePoint1, size, outFileUrl);
            // }
    
            // 4.照片墙
            // System.out.println(photoWall(srcFileUrl, size, outFileUrl));
    
        }
    }
    获取视频时间长度:

    import
    java.io.File; import it.sauronsoftware.jave.Encoder; import it.sauronsoftware.jave.EncoderException; import it.sauronsoftware.jave.MultimediaInfo; public class VideoDuration { public static long getVideoDuration(String srcFileUrl) { File source = new File(srcFileUrl); Encoder encoder = new Encoder(); MultimediaInfo mediaInfo = null; try { mediaInfo = encoder.getInfo(source); } catch (EncoderException e) { // TODO Auto-generated catch block e.printStackTrace(); } long duration = mediaInfo.getDuration(); return duration/1000; } public static void main(String[] args) { } }
  • 相关阅读:
    Xcode界面切换动画效果
    Objective—C中的排序及Compare陷阱
    串行口应用
    在windows上搭建C语言开发环境——借助eclipse和MinGW
    Leetcode--Two Sum
    C++语言笔记系列之十六——赋值兼容规则&amp;多继承的二义性
    在Powerdesigner中创建概念数据模型
    数据模型
    数据描述的三个领域
    开启PowerDesigner15工具栏上的被禁用掉的图标
  • 原文地址:https://www.cnblogs.com/liangblog/p/13952465.html
Copyright © 2020-2023  润新知