出来混迟早是要还的。
在这一篇中https://www.cnblogs.com/sincoolvip/p/5882817.html,只是简单讲了一下获取apk包的package和launchable-activity名称,可以说是个非常不成熟的鸡肋的东西了。当时花的时间也不多,而且当时雄心壮志的还列了几步计划。
现在看一看,真是要耻笑自己,拖了这么久,今天终于补上,由于本人编程能力非常有限,无数资料都是网上搜搜搜,下来拼拼拼,按需改改改才实现的。在过程中一边熟悉掌握知识点,一边实现个体需求,其实是比较难的,要静下心来做事,
说实话做个东西会帮我一天节省网购至少200元的消费。
程序我优化了,目地是实现打开exe界面可以选择apk包和aapt执行目录,然后输出相关信息,最终的效果:
第二版:
改版后效果,使结果可以复制
这个分几步来列吧。
1、java代码实现
这里我直接帖代码吧,细节不说了。整个拿下去就可以用的,有点长啊,那是因为我只会1个java生成jar.囧~~
1 package p20181214; 2 import java.io.*; 3 import java.util.ArrayList; 4 import java.util.List; 5 import java.util.regex.Matcher; 6 import java.util.regex.Pattern; 7 import java.awt.*; 8 import javax.swing.*; 9 10 import java.awt.event.*; 11 public class YFileChooser implements ActionListener{ 12 JFrame frame=new JFrame("文件选择器实例"); 13 JTabbedPane tabPane=new JTabbedPane();//选项卡布局 14 Container con=new Container();//布局1 15 Container con1=new Container();//布局2 16 JLabel label1=new JLabel("选择aapt目录"); 17 JLabel label2=new JLabel("选择apk文件"); 18 JTextField text1=new JTextField(); 19 JTextField text2=new JTextField(); 20 JButton button1=new JButton("..."); 21 JButton button2=new JButton("..."); 22 JButton button3=new JButton("..."); 23 //放结果 24 JLabel aapt=new JLabel("...."); 25 JLabel apk=new JLabel("..."); 26 JLabel page=new JLabel("..."); 27 JLabel activity=new JLabel("..."); 28 JFileChooser jfc=new JFileChooser();//文件选择器 29 YFileChooser(){ 30 jfc.setCurrentDirectory(new File("d:\"));//文件选择器的初始目录定为d盘 31 //下面两行是取得屏幕的高度和宽度 32 double lx=Toolkit.getDefaultToolkit().getScreenSize().getWidth(); 33 double ly=Toolkit.getDefaultToolkit().getScreenSize().getHeight(); 34 frame.setLocation(new Point((int)(lx/2)-150,(int)(ly/2)-150));//设定窗口出现位置 35 frame.setSize(500,300);//设定窗口大小 36 frame.setVisible(true); 37 frame.setContentPane(tabPane);//设置布局 38 //下面设定标签等的出现位置和高宽 39 label1.setBounds(10,10,150,20); 40 text1.setBounds(100,10,300,20); 41 button1.setBounds(410,10,60,20);//400=上一条100+300 42 button1.setText("选择"); 43 label2.setBounds(10,30,150,20); 44 text2.setBounds(100,30,300,20); 45 button2.setBounds(410,30,60,20); 46 button2.setText("选择"); 47 button3.setBounds(204,70,60,30); 48 button3.setText("获取"); 49 aapt.setBounds(30, 126,300 , 20); 50 apk.setBounds(30, 144,300 , 20); 51 page.setBounds(7, 180,500 , 20); 52 activity.setBounds(7, 200,500 , 20); 53 button1.addActionListener(this);//添加事件处理 54 button2.addActionListener(this);//添加事件处理 55 button3.addActionListener(this);//添加事件处理 56 con.add(label1); 57 con.add(label2); 58 con.add(text1); 59 con.add(text2); 60 con.add(button1); 61 con.add(button2); 62 con.add(button3); 63 con.add(jfc); 64 con.add(aapt); 65 con.add(apk); 66 con.add(page); 67 con.add(activity); 68 tabPane.add("目录/文件选择",con);//添加布局1 69 // tabPane.add("暂无内容",con1);//添加布局2 70 frame.setVisible(true);//窗口可见 71 frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);//使能关闭窗口,结束程序 72 } 73 public void actionPerformed(ActionEvent e){//事件处理 74 /*if(e.getSource().equals(button1)){//判断触发方法的按钮是哪个 75 jfc.setFileSelectionMode(1);//设定只能选择到文件夹 76 int state=jfc.showOpenDialog(null);//此句是打开文件选择器界面的触发语句 77 if(state==1){ 78 return;//撤销则返回 79 } 80 else{ 81 File f=jfc.getSelectedFile();//f为选择到的目录 82 text1.setText(f.getAbsolutePath()); 83 } 84 }*/ 85 if(e.getSource().equals(button1)){//判断触发方法的按钮是哪个 86 jfc.setFileSelectionMode(0);//设定只能选择到文件夹 87 int state=jfc.showOpenDialog(null);//此句是打开文件选择器界面的触发语句 88 if(state==1){ 89 return;//撤销则返回 90 } 91 else{ 92 File f=jfc.getSelectedFile();//f为选择到的目录 93 text1.setText(f.getAbsolutePath()); 94 } 95 } 96 if(e.getSource().equals(button2)){ 97 jfc.setFileSelectionMode(0);//设定只能选择到文件 98 int state=jfc.showOpenDialog(null);//此句是打开文件选择器界面的触发语句 99 if(state==1){ 100 return;//撤销则返回 101 } 102 else{ 103 File f=jfc.getSelectedFile();//f为选择到的文件 104 text2.setText(f.getAbsolutePath()); 105 } 106 } 107 if(e.getSource().equals(button3)) { 108 String aapt1=text1.getText(); 109 String apk1=text2.getText(); 110 System.out.println("aapt="+text1+";apk=="+apk1); 111 //调获取方法 112 //Base base=new Base(); 113 java.util.List<String> list= runCMD(aapt1, " dump badging ", apk1); 114 page.setText("package:"+list.get(0)); 115 activity.setText("activity"+list.get(1)); 116 aapt.setText("aapt.exe目录为:"+aapt1); 117 apk.setText("apk目录为:"+apk1); 118 119 } 120 } 121 public static List<String> runCMD(String aapt,String command,String apk){ 122 InputStream is =null; 123 Process process=null; 124 List<String> slist=new ArrayList<String>(); 125 try { 126 //process =Runtime.getRuntime().exec("cmd.exe /k "+dir+"&cd "+aapt+"& command");//执行doc命令 127 process =Runtime.getRuntime().exec(aapt+command +apk); 128 //后面的所有操作即是读取这个命令的输出结果 129 is = process.getInputStream();//获取执行CMD命令后的信息 130 BufferedReader reader =new BufferedReader(new InputStreamReader(is)); 131 String line =null; 132 StringBuffer sb =new StringBuffer(); 133 while((line = reader.readLine())!=null){ 134 sb.append(line); 135 } 136 //截取package字符串 137 Pattern p =Pattern.compile("package: name(.*?)versionCode"); 138 Matcher m =p.matcher(sb); 139 List<String> list=new ArrayList<String>(); 140 while(m.find()){ 141 list.add(m.group(1)); 142 } 143 for (String str : list) { 144 System.out.println("package"+str); 145 slist.add(str); 146 } 147 148 //截取acvitity字符串,以launchable-activity: name开头, label结尾 获取中间字符串内容 149 Pattern p1 =Pattern.compile("launchable-activity: name(.*?) label"); 150 Matcher m1 =p1.matcher(sb); 151 List<String> list1=new ArrayList<String>(); 152 while(m1.find()){ 153 list1.add(m1.group(1)); 154 } 155 for (String str1 : list1) { 156 System.out.println("activity"+str1); 157 slist.add(str1); 158 } 159 160 } catch (IOException e) { 161 e.printStackTrace(); 162 } finally{ 163 try { 164 process.getOutputStream().close(); 165 is.close(); 166 } catch (IOException e) { 167 e.printStackTrace(); 168 } 169 170 } 171 172 return slist; 173 } 174 public static void main(String[] args) { 175 new YFileChooser(); 176 177 } 178 }
第二版代码
package p20181214; import java.io.*; import java.util.ArrayList; import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; import java.awt.*; import javax.swing.*; import java.awt.event.*; public class YFileChooser implements ActionListener{ JFrame frame=new JFrame("获取apk包的package和activity"); JTabbedPane tabPane=new JTabbedPane();//选项卡布局 Container con=new Container();//布局1 Container con1=new Container();//布局2 JLabel label1=new JLabel("选择aapt文件"); JLabel label2=new JLabel("选择apk文件"); JTextField text1=new JTextField(); JTextField text2=new JTextField(); JButton button1=new JButton("..."); JButton button2=new JButton("..."); JButton button3=new JButton("..."); //放结果 //JLabel aapt=new JLabel("...."); //JLabel apk=new JLabel("..."); //JLabel page=new JLabel("..."); //JLabel activity=new JLabel("..."); JTextArea page_activity=new JTextArea(""); JFileChooser jfc=new JFileChooser();//文件选择器 YFileChooser(){ jfc.setCurrentDirectory(new File("d:\"));//文件选择器的初始目录定为d盘 //下面两行是取得屏幕的高度和宽度 double lx=Toolkit.getDefaultToolkit().getScreenSize().getWidth(); double ly=Toolkit.getDefaultToolkit().getScreenSize().getHeight(); frame.setLocation(new Point((int)(lx/2)-150,(int)(ly/2)-150));//设定窗口出现位置 frame.setSize(500,300);//设定窗口大小 frame.setVisible(true); frame.setContentPane(tabPane);//设置布局 //下面设定标签等的出现位置和高宽 label1.setBounds(10,10,150,20); text1.setBounds(100,10,300,20); button1.setBounds(410,10,60,20);//400=上一条100+300 button1.setText("选择"); label2.setBounds(10,30,150,20); text2.setBounds(100,30,300,20); button2.setBounds(410,30,60,20); button2.setText("选择"); button3.setBounds(204,70,60,30); button3.setText("获取"); // aapt.setBounds(30, 126,300 , 20); // apk.setBounds(30, 144,300 , 20); //page.setBounds(7, 180,500 , 20); //activity.setBounds(7, 200,500 , 20); page_activity.setBounds(7, 126,468 , 200); button1.addActionListener(this);//添加事件处理 button2.addActionListener(this);//添加事件处理 button3.addActionListener(this);//添加事件处理 con.add(label1); con.add(label2); con.add(text1); con.add(text2); con.add(button1); con.add(button2); con.add(button3); con.add(jfc); //con.add(aapt); //con.add(apk); //con.add(page); //con.add(activity); con.add(page_activity); tabPane.add("文件选择",con);//添加布局1 // tabPane.add("暂无内容",con1);//添加布局2 frame.setVisible(true);//窗口可见 frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);//使能关闭窗口,结束程序 } public void actionPerformed(ActionEvent e){//事件处理 /*if(e.getSource().equals(button1)){//判断触发方法的按钮是哪个 jfc.setFileSelectionMode(1);//设定只能选择到文件夹 int state=jfc.showOpenDialog(null);//此句是打开文件选择器界面的触发语句 if(state==1){ return;//撤销则返回 } else{ File f=jfc.getSelectedFile();//f为选择到的目录 text1.setText(f.getAbsolutePath()); } }*/ if(e.getSource().equals(button1)){//判断触发方法的按钮是哪个 jfc.setFileSelectionMode(0);//设定只能选择到文件夹 int state=jfc.showOpenDialog(null);//此句是打开文件选择器界面的触发语句 if(state==1){ return;//撤销则返回 } else{ File f=jfc.getSelectedFile();//f为选择到的目录 text1.setText(f.getAbsolutePath()); } } if(e.getSource().equals(button2)){ jfc.setFileSelectionMode(0);//设定只能选择到文件 int state=jfc.showOpenDialog(null);//此句是打开文件选择器界面的触发语句 if(state==1){ return;//撤销则返回 } else{ File f=jfc.getSelectedFile();//f为选择到的文件 text2.setText(f.getAbsolutePath()); } } if(e.getSource().equals(button3)) { String aapt1=text1.getText(); String apk1=text2.getText(); System.out.println("aapt="+text1+";apk=="+apk1); //调获取方法 //Base base=new Base(); java.util.List<String> list= runCMD(aapt1, " dump badging ", apk1); //page.setText("package:"+list.get(0)); //activity.setText("activity"+list.get(1)); //aapt.setText("aapt.exe目录为:"+aapt1); //apk.setText("apk目录为:"+apk1); page_activity.append("package:"+list.get(0)+" "); page_activity.append("activity:"+list.get(1)); //MJTextArea testarea=new MJTextArea(); } } public static List<String> runCMD(String aapt,String command,String apk){ InputStream is =null; Process process=null; List<String> slist=new ArrayList<String>(); try { //process =Runtime.getRuntime().exec("cmd.exe /k "+dir+"&cd "+aapt+"& command");//执行doc命令 process =Runtime.getRuntime().exec(aapt+command +apk); //后面的所有操作即是读取这个命令的输出结果 is = process.getInputStream();//获取执行CMD命令后的信息 BufferedReader reader =new BufferedReader(new InputStreamReader(is)); String line =null; StringBuffer sb =new StringBuffer(); while((line = reader.readLine())!=null){ sb.append(line); } //截取package字符串 Pattern p =Pattern.compile("package: name(.*?)versionCode"); Matcher m =p.matcher(sb); List<String> list=new ArrayList<String>(); while(m.find()){ list.add(m.group(1)); } for (String str : list) { System.out.println("package"+str); slist.add(str); } //截取acvitity字符串,以launchable-activity: name开头, label结尾 获取中间字符串内容 Pattern p1 =Pattern.compile("launchable-activity: name(.*?) label"); Matcher m1 =p1.matcher(sb); List<String> list1=new ArrayList<String>(); while(m1.find()){ list1.add(m1.group(1)); } for (String str1 : list1) { System.out.println("activity"+str1); slist.add(str1); } } catch (IOException e) { e.printStackTrace(); } finally{ try { process.getOutputStream().close(); is.close(); } catch (IOException e) { e.printStackTrace(); } } return slist; } public static void main(String[] args) { /*try { //UIManager.setLookAndFeel("com.sun.java.swing.plaf.windows.WindowsLookAndFeel"); 使用windows风格 } catch (ClassNotFoundException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InstantiationException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IllegalAccessException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (UnsupportedLookAndFeelException e) { // TODO Auto-generated catch block e.printStackTrace(); } */ new YFileChooser(); } }
2、生成jar
右键点击要导出为jar的java文件,选择export
next下一步继续
默认下一步,继续
在下面界面选择主程序入口文件,点击Browse会自动出来,只要你的java文件有main函数就行
选择好后,Finish,大功告成,我们来手工测试一下生成的jar文件是否有效,这里忽略windows下java环境变量的配置细节
3、通过jar生成exe的可执行文件
引入exe4j工具
链接:https://pan.baidu.com/s/1I1s-duF2xtDj0pm7POT6LQ
提取码:l9nr
使用步骤
a、下载安装后打开exe4j工具,是以下这个长相
b、打开第一步默认不做啥,
上面湖州只有一个License需要填一下,不然后面执行exe后会先弹出提示:
c、选择模式,jar生成Exe,正合我意,点击下一步
d、填写应用名称和存放目录即可下一步
e、这里设置有点多,但不复杂,比较清晰直观,英文也看得非常清晰
f、要选择一下执行机器位数,我的机器是64位,如果不选择生成后的Exe执行后会报错,当然32位机器就不用勾选了。点击下一步
g、本步默认,不作任何更改,直接下一步
h、选择要生成的jar文件及执行主程序
i、选择完jar点击OK,再选择main class的值,打开选择框出来会是默认就能读取到的,选中点击OK,点击"next"
j、选择执行应用程序的jre版本,设置最低和最高版本执行范围。在此范围之外,会报错(具体报什么错没试过)
k、添加执行jre的本地路径,直接点击"next"
l、后面几步默认,不作更改,直接点击"next"
m、上步点击next的时候直接进度条进行执行了,但进度太快,没截到图,直接放结果
测试OK
桌面直接执行测试
最后分享全部源码内容:
链接:https://pan.baidu.com/s/1GoyPvhmsVIBH7kTaLTqeYQ
提取码:k1da
另外推荐一个站长工具:生成ico图标的,我就是用的这个