Statistics
| Revision:

root / import / ext3D / trunk / install-extension3d / IzPack / src / lib / com / izforge / izpack / installer / GUIInstaller.java @ 15280

History | View | Annotate | Download (18.4 KB)

1
/*
2
 *  $Id: GUIInstaller.java,v 1.1 2006/06/14 07:29:07 cesar Exp $
3
 *  IzPack
4
 *  Copyright (C) 2001-2004 Julien Ponge
5
 *
6
 *  File :               GUIInstaller.java
7
 *  Description :        The graphical installer class.
8
 *  Author's email :     julien@izforge.com
9
 *  Author's Website :   http://www.izforge.com
10
 *
11
 *  This program is free software; you can redistribute it and/or
12
 *  modify it under the terms of the GNU General Public License
13
 *  as published by the Free Software Foundation; either version 2
14
 *  of the License, or any later version.
15
 *
16
 *  This program is distributed in the hope that it will be useful,
17
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
18
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19
 *  GNU General Public License for more details.
20
 *
21
 *  You should have received a copy of the GNU General Public License
22
 *  along with this program; if not, write to the Free Software
23
 *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
24
 */
25
package com.izforge.izpack.installer;
26

    
27
import java.awt.Color;
28
import java.awt.Component;
29
import java.awt.Dimension;
30
import java.awt.GridBagConstraints;
31
import java.awt.GridBagLayout;
32
import java.awt.Insets;
33
import java.awt.Toolkit;
34
import java.awt.event.ActionEvent;
35
import java.awt.event.ActionListener;
36
import java.awt.event.WindowAdapter;
37
import java.awt.event.WindowEvent;
38
import java.io.InputStream;
39
import java.io.ObjectInputStream;
40
import java.lang.reflect.Method;
41
import java.util.List;
42
import java.util.Locale;
43
import java.util.Map;
44
import java.util.TreeMap;
45

    
46
import javax.swing.GrayFilter;
47
import javax.swing.ImageIcon;
48
import javax.swing.JButton;
49
import javax.swing.JComboBox;
50
import javax.swing.JDialog;
51
import javax.swing.JFrame;
52
import javax.swing.JLabel;
53
import javax.swing.JList;
54
import javax.swing.JOptionPane;
55
import javax.swing.JPanel;
56
import javax.swing.ListCellRenderer;
57
import javax.swing.LookAndFeel;
58
import javax.swing.SwingConstants;
59
import javax.swing.UIManager;
60
import javax.swing.plaf.metal.MetalLookAndFeel;
61
import javax.swing.plaf.metal.MetalTheme;
62

    
63
import com.izforge.izpack.GUIPrefs;
64
import com.izforge.izpack.LocaleDatabase;
65
import com.izforge.izpack.util.OsVersion;
66
import com.izforge.izpack.gui.ButtonFactory;
67
import com.izforge.izpack.gui.IzPackMetalTheme;
68
import com.izforge.izpack.gui.LabelFactory;
69

    
70
/**
71
 *  The IzPack graphical installer class.
72
 *
73
 * @author     Julien Ponge
74
 */
75
public class GUIInstaller extends InstallerBase
76
{
77

    
78
  /**  The installation data. */
79
  private InstallData installdata;
80

    
81
  /**  The L&F. */
82
  protected String lnf;
83

    
84
  /**
85
   *  The constructor.
86
   *
87
   * @exception  Exception  Description of the Exception
88
   */
89
  public GUIInstaller() throws Exception
90
  {
91
    this.installdata = new InstallData();
92

    
93
    // Loads the installation data
94
    loadInstallData(installdata);
95

    
96
    // add the GUI install data
97
    loadGUIInstallData();
98

    
99
    // Sets up the GUI L&F
100
    loadLookAndFeel();
101

    
102
    // Checks the Java version
103
    checkJavaVersion();
104

    
105
    // Loads the suitable langpack
106
    loadLangPack();
107

    
108
    // create the resource manager (after the language selection!)
109
    ResourceManager.create(this.installdata);
110

    
111
    // We launch the installer GUI
112
    loadGUI();
113
  }
114

    
115
  /**
116
   * Load GUI preference information.
117
   *
118
   * @throws Exception
119
   */
120
  public void loadGUIInstallData() throws Exception
121
  {
122
    InputStream in = GUIInstaller.class.getResourceAsStream("/GUIPrefs");
123
    ObjectInputStream objIn = new ObjectInputStream(in);
124
    this.installdata.guiPrefs = (GUIPrefs) objIn.readObject();
125
    objIn.close();
126
  }
127

    
128
  /**
129
   *  Checks the Java version.
130
   *
131
   * @exception  Exception  Description of the Exception
132
   */
133
  private void checkJavaVersion() throws Exception
134
  {
135
    String version = System.getProperty("java.version");
136
    String required = this.installdata.info.getJavaVersion();
137
    if (version.compareTo(required) < 0)
138
    {
139
      StringBuffer msg = new StringBuffer();
140
      msg.append("The application that you are trying to install requires a ");
141
      msg.append(required);
142
      msg.append(" version or later of the Java platform.\n");
143
      msg.append("You are running a ");
144
      msg.append(version);
145
      msg.append(" version of the Java platform.\n");
146
      msg.append("Please upgrade to a newer version.");
147

    
148
      System.out.println(msg.toString());
149
      JOptionPane.showMessageDialog(null, msg.toString(), "Error",
150
          JOptionPane.ERROR_MESSAGE);
151
      System.exit(1);
152
    }
153
  }
154

    
155
  /**
156
   *  Loads the suitable langpack.
157
   *
158
   * @exception  Exception  Description of the Exception
159
   */
160
  private void loadLangPack() throws Exception
161
  {
162
    // Initialisations
163
    List availableLangPacks = getAvailableLangPacks();
164
    int npacks = availableLangPacks.size();
165
    if (npacks == 0) throw new Exception("no language pack available");
166
    String selectedPack;
167

    
168
    // Dummy Frame
169
    JFrame frame = new JFrame();
170
    frame.setIconImage( new ImageIcon(
171
      this.getClass().getResource( "/img/JFrameIcon.png" )).getImage() );
172

    
173
    Dimension frameSize = frame.getSize();
174
    Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
175
    frame.setLocation((screenSize.width - frameSize.width) / 2,
176
      (screenSize.height - frameSize.height) / 2 - 10);
177

    
178
    // We get the langpack name
179
    if (npacks != 1)
180
    {
181
      LanguageDialog picker = new LanguageDialog(frame, availableLangPacks.toArray());
182
      picker.setSelection(Locale.getDefault().getISO3Country().toLowerCase());
183
      picker.setModal(true);
184
      picker.toFront();
185
      frame.show();
186
      frame.hide();
187
      picker.show();
188

    
189
      selectedPack = (String) picker.getSelection();
190
      if (selectedPack == null) throw new Exception("installation canceled");
191
    }
192
    else
193
      selectedPack = (String) availableLangPacks.get(0);
194

    
195
    // We add an xml data information
196
    this.installdata.xmlData.setAttribute("langpack", selectedPack);
197

    
198
    // We load the langpack
199
    installdata.localeISO3 = selectedPack;
200
    installdata.setVariable(ScriptParser.ISO3_LANG, installdata.localeISO3);
201
    InputStream in = getClass().getResourceAsStream(
202
        "/langpacks/" + selectedPack + ".xml");
203
    this.installdata.langpack = new LocaleDatabase(in);
204
  }
205

    
206
  /**
207
   *  Returns an ArrayList of the available langpacks ISO3 codes.
208
   *
209
   * @return                The available langpacks list.
210
   * @exception  Exception  Description of the Exception
211
   */
212
  private List getAvailableLangPacks() throws Exception
213
  {
214
    // We read from the langpacks file in the jar
215
    InputStream in = getClass().getResourceAsStream("/langpacks.info");
216
    ObjectInputStream objIn = new ObjectInputStream(in);
217
    List available = (List) objIn.readObject();
218
    objIn.close();
219

    
220
    return available;
221
  }
222

    
223
  /**
224
   *  Loads the suitable L&F.
225
   *
226
   * @exception  Exception  Description of the Exception
227
   */
228
  protected void loadLookAndFeel() throws Exception
229
  {
230
    // Do we have any preference for this OS ?
231
    String syskey = "unix";
232
    if (OsVersion.IS_WINDOWS)
233
    {
234
      syskey = "windows";
235
    }
236
    else if (OsVersion.IS_OSX)
237
    {
238
      syskey = "mac";
239
    }
240
    String laf = null;
241
    if (installdata.guiPrefs.lookAndFeelMapping.containsKey(syskey))
242
    {
243
      laf = (String) installdata.guiPrefs.lookAndFeelMapping.get(syskey);
244
    }
245

    
246
    // Let's use the system LAF
247
    // Resolve whether button icons should be used or not.
248
    boolean useButtonIcons = true;
249
    if(installdata.guiPrefs.modifier.containsKey("useButtonIcons") &&
250
      ((String)installdata.guiPrefs.modifier.
251
      get("useButtonIcons")).equalsIgnoreCase("no") )
252
      useButtonIcons = false;
253
    ButtonFactory.useButtonIcons(useButtonIcons);
254
    boolean useLabelIcons = true;
255
    if(installdata.guiPrefs.modifier.containsKey("useLabelIcons") &&
256
      ((String)installdata.guiPrefs.modifier.
257
      get("useLabelIcons")).equalsIgnoreCase("no") )
258
      useLabelIcons = false;
259
    LabelFactory.setUseLabelIcons(useLabelIcons);
260
    if (laf == null)
261
    {
262
      if (!syskey.equals("mac"))
263
      {
264
        String syslaf = UIManager.getSystemLookAndFeelClassName();
265
        UIManager.setLookAndFeel(syslaf);
266
        if (UIManager.getLookAndFeel() instanceof MetalLookAndFeel)
267
        {
268
          MetalLookAndFeel.setCurrentTheme(new IzPackMetalTheme());
269
          ButtonFactory.useHighlightButtons();
270
          // Reset the use button icons state because useHighlightButtons
271
          // make it always true.
272
          ButtonFactory.useButtonIcons(useButtonIcons);
273
          installdata.buttonsHColor = new Color(182, 182, 204);
274
        }
275
      }
276
      lnf = "swing";
277
      return;
278
    }
279

    
280
    // Kunststoff (http://www.incors.org/)
281
    if (laf.equals("kunststoff"))
282
    {
283
      ButtonFactory.useHighlightButtons();
284
      // Reset the use button icons state because useHighlightButtons
285
      // make it always true.
286
      ButtonFactory.useButtonIcons(useButtonIcons);
287
      installdata.buttonsHColor = new Color(255, 255, 255);
288
      Class lafClass = Class
289
          .forName("com.incors.plaf.kunststoff.KunststoffLookAndFeel");
290
      Class mtheme = Class.forName("javax.swing.plaf.metal.MetalTheme");
291
      Class[] params = { mtheme};
292
      Class theme = Class.forName("com.izforge.izpack.gui.IzPackKMetalTheme");
293
      Method setCurrentThemeMethod = lafClass.getMethod("setCurrentTheme", params);
294

    
295
      // We invoke and place Kunststoff as our L&F
296
      LookAndFeel kunststoff = (LookAndFeel) lafClass.newInstance();
297
      MetalTheme ktheme = (MetalTheme) theme.newInstance();
298
      Object[] kparams = { ktheme};
299
      UIManager.setLookAndFeel(kunststoff);
300
      setCurrentThemeMethod.invoke(kunststoff, kparams);
301

    
302
      lnf = "kunststoff";
303
      return;
304
    }
305

    
306
    // Liquid (http://liquidlnf.sourceforge.net/)
307
    if (laf.equals("liquid"))
308
    {
309
      UIManager.setLookAndFeel("com.birosoft.liquid.LiquidLookAndFeel");
310
      lnf = "liquid";
311

    
312
      Map params = (Map)installdata.guiPrefs.lookAndFeelParams.get(laf);
313
      if (params.containsKey("decorate.frames"))
314
      {
315
        String value = (String)params.get("decorate.frames");
316
        if (value.equals("yes"))
317
        {
318
          JFrame.setDefaultLookAndFeelDecorated(true);
319
        }
320
      }
321
      if (params.containsKey("decorate.dialogs"))
322
      {
323
        String value = (String)params.get("decorate.dialogs");
324
        if (value.equals("yes"))
325
        {
326
          JDialog.setDefaultLookAndFeelDecorated(true);
327
        }
328
      }
329

    
330
      return;
331
    }
332

    
333
    // Metouia (http://mlf.sourceforge.net/)
334
    if (laf.equals("metouia"))
335
    {
336
      UIManager.setLookAndFeel("net.sourceforge.mlf.metouia.MetouiaLookAndFeel");
337
      lnf = "metouia";
338
      return;
339
    }
340

    
341
    // JGoodies Looks (http://looks.dev.java.net/)
342
    if (laf.equals("looks"))
343
    {
344
      Map variants = new TreeMap();
345
      variants.put("extwin", "com.jgoodies.plaf.windows.ExtWindowsLookAndFeel");
346
      variants.put("plastic", "com.jgoodies.plaf.plastic.PlasticLookAndFeel");
347
      variants.put("plastic3D", "com.jgoodies.plaf.plastic.Plastic3DLookAndFeel");
348
      variants.put("plasticXP", "com.jgoodies.plaf.plastic.PlasticXPLookAndFeel");
349
      String variant = (String)variants.get("plasticXP");
350

    
351
      Map params = (Map)installdata.guiPrefs.lookAndFeelParams.get(laf);
352
      if (params.containsKey("variant"))
353
      {
354
        String param = (String)params.get("variant");
355
        if (variants.containsKey(param))
356
        {
357
          variant = (String)variants.get(param);
358
        }
359
      }
360

    
361
      UIManager.setLookAndFeel(variant);
362
    }
363
  }
364

    
365
  /**
366
   *  Loads the GUI.
367
   *
368
   * @exception  Exception  Description of the Exception
369
   */
370
  private void loadGUI() throws Exception
371
  {
372
    UIManager.put("OptionPane.yesButtonText", installdata.langpack
373
        .getString("installer.yes"));
374
    UIManager.put("OptionPane.noButtonText", installdata.langpack
375
        .getString("installer.no"));
376
    UIManager.put("OptionPane.cancelButtonText", installdata.langpack
377
        .getString("installer.cancel"));
378

    
379
    String title = installdata.langpack.getString("installer.title")
380
        + this.installdata.info.getAppName();
381
    new InstallerFrame(title, this.installdata);
382
  }
383

    
384
  /**
385
   *  Used to prompt the user for the language.
386
   *
387
   * @author     Julien Ponge
388
   */
389
  private final class LanguageDialog extends JDialog implements ActionListener
390
  {
391

    
392
    /**  The combo box. */
393
    private JComboBox comboBox;
394

    
395
    /**  The ok button. */
396
    private JButton okButton;
397

    
398
    /**
399
     *  The constructor.
400
     *
401
     * @param  items  The items to display in the box.
402
     */
403
    public LanguageDialog(JFrame frame, Object[] items)
404
    {
405
      super(frame);
406

    
407
      try
408
      {
409
        loadLookAndFeel();
410
      }
411
      catch (Exception err)
412
      {
413
        err.printStackTrace();
414
      }
415

    
416
      // We build the GUI
417
      addWindowListener(new WindowHandler());
418
      JPanel contentPane = (JPanel) getContentPane();
419
      setTitle("Language selection");
420
      GridBagLayout layout = new GridBagLayout();
421
      contentPane.setLayout(layout);
422
      GridBagConstraints gbConstraints = new GridBagConstraints();
423
      gbConstraints.anchor = GridBagConstraints.CENTER;
424
      gbConstraints.insets = new Insets(5, 5, 5, 5);
425
      gbConstraints.fill = GridBagConstraints.NONE;
426
      gbConstraints.gridx = 0;
427
      gbConstraints.weightx = 1.0;
428
      gbConstraints.weighty = 1.0;
429

    
430
      ImageIcon img = getImage();
431
      JLabel imgLabel = new JLabel(img);
432
      gbConstraints.gridy = 0;
433
      contentPane.add(imgLabel);
434

    
435
      gbConstraints.fill = GridBagConstraints.HORIZONTAL;
436
      JLabel label1 = new JLabel("Please select your language (ISO3 code)",
437
          SwingConstants.CENTER);
438
      gbConstraints.gridy = 1;
439
      gbConstraints.insets = new Insets(5, 5, 0, 5);
440
      layout.addLayoutComponent(label1, gbConstraints);
441
      contentPane.add(label1);
442
      JLabel label2 = new JLabel("for install instructions:",
443
          SwingConstants.CENTER);
444
      gbConstraints.gridy = 2;
445
      gbConstraints.insets = new Insets(0, 5, 5, 5);
446
      layout.addLayoutComponent(label2, gbConstraints);
447
      contentPane.add(label2);
448
      gbConstraints.insets = new Insets(5, 5, 5, 5);
449

    
450
      comboBox = new JComboBox(items);
451
      comboBox.setRenderer(new FlagRenderer());
452
      gbConstraints.fill = GridBagConstraints.HORIZONTAL;
453
      gbConstraints.gridy = 3;
454
      layout.addLayoutComponent(comboBox, gbConstraints);
455
      contentPane.add(comboBox);
456

    
457
      okButton = new JButton("Ok");
458
      okButton.addActionListener(this);
459
      gbConstraints.fill = GridBagConstraints.NONE;
460
      gbConstraints.gridy = 4;
461
      gbConstraints.anchor = GridBagConstraints.CENTER;
462
      layout.addLayoutComponent(okButton, gbConstraints);
463
      contentPane.add(okButton);
464
      getRootPane().setDefaultButton(okButton);
465

    
466
      // Packs and centers
467
      // Fix for bug "Installer won't show anything on OSX"
468
      if (System.getProperty("mrj.version") == null)
469
        pack();
470
      else
471
        setSize(getPreferredSize());
472

    
473
      Dimension frameSize = getSize();
474
      Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
475
      setLocation((screenSize.width - frameSize.width) / 2,
476
          (screenSize.height - frameSize.height) / 2 - 10);
477
      setResizable(true);
478
    }
479

    
480
    /**
481
     *  Loads an image.
482
     *
483
     * @return    The image icon.
484
     */
485
    public ImageIcon getImage()
486
    {
487
      ImageIcon img;
488
      try
489
      {
490
        img = new ImageIcon(LanguageDialog.class.getResource(
491
            "/res/installer.langsel.img"));
492
      }
493
      catch (NullPointerException err)
494
      {
495
        img = null;
496
      }
497
      return img;
498
    }
499

    
500
    /**
501
     *  Gets the selected object.
502
     *
503
     * @return    The selected item.
504
     */
505
    public Object getSelection()
506
    {
507
      return comboBox.getSelectedItem();
508
    }
509

    
510
    /**
511
     *  Sets the selection.
512
     *
513
     * @param  item  The item to be selected.
514
     */
515
    public void setSelection(Object item)
516
    {
517
      comboBox.setSelectedItem(item);
518
    }
519

    
520
    /**
521
     *  Closer.
522
     *
523
     * @param  e  The event.
524
     */
525
    public void actionPerformed(ActionEvent e)
526
    {
527
      dispose();
528
    }
529

    
530
    /**
531
     *  The window events handler.
532
     *
533
     * @author     Julien Ponge
534
     */
535
    private class WindowHandler extends WindowAdapter
536
    {
537

    
538
      /**
539
       *  We can't avoid the exit here, so don't call exit anywhere else.
540
       *
541
       * @param  e  the event.
542
       */
543
      public void windowClosing(WindowEvent e)
544
      {
545
        System.exit(0);
546
      }
547
    }
548
  }
549

    
550
  /**
551
   *  A list cell renderer that adds the flags on the display.
552
   *
553
   * @author     Julien Ponge
554
   */
555
  private static class FlagRenderer extends JLabel implements ListCellRenderer
556
  {
557

    
558
    /**  Icons cache. */
559
    private TreeMap icons = new TreeMap();
560

    
561
    /**  Grayed icons cache. */
562
    private TreeMap grayIcons = new TreeMap();
563

    
564
    public FlagRenderer()
565
    {
566
      setOpaque(true);
567
    }
568

    
569
    /**
570
     *  Returns a suitable cell.
571
     *
572
     * @param  list          The list.
573
     * @param  value         The object.
574
     * @param  index         The index.
575
     * @param  isSelected    true if it is selected.
576
     * @param  cellHasFocus  Description of the Parameter
577
     * @return               The cell.
578
     */
579
    public Component getListCellRendererComponent(JList list, Object value,
580
        int index, boolean isSelected, boolean cellHasFocus)
581
    {
582
      // We put the label
583
      String iso3 = (String) value;
584
      setText(iso3);
585
      if (isSelected)
586
      {
587
        setForeground(list.getSelectionForeground());
588
        setBackground(list.getSelectionBackground());
589
      }
590
      else
591
      {
592
        setForeground(list.getForeground());
593
        setBackground(list.getBackground());
594
      }
595
      // We put the icon
596
      if (!icons.containsKey(iso3))
597
      {
598
        ImageIcon icon;
599
        icon = new ImageIcon(this.getClass().getResource("/res/flag." + iso3));
600
        icons.put(iso3, icon);
601
        icon = new ImageIcon(GrayFilter.createDisabledImage(icon.getImage()));
602
        grayIcons.put(iso3, icon);
603
      }
604
      if (isSelected || index == -1)
605
        setIcon((ImageIcon) icons.get(iso3));
606
      else
607
        setIcon((ImageIcon) grayIcons.get(iso3));
608

    
609
      // We return
610
      return this;
611
    }
612
  }
613
}