1 /* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.sdkuilib.internal.repository.sdkman2; 18 19 20 import com.android.prefs.AndroidLocation; 21 22 import org.eclipse.swt.graphics.Point; 23 import org.eclipse.swt.graphics.Rectangle; 24 import org.eclipse.swt.widgets.Monitor; 25 import org.eclipse.swt.widgets.Shell; 26 27 import java.io.File; 28 import java.io.FileInputStream; 29 import java.io.FileOutputStream; 30 import java.io.IOException; 31 import java.util.Properties; 32 33 /** 34 * Utility to save & restore the size and position on a window 35 * using a common config file. 36 */ 37 public class ShellSizeAndPos { 38 39 private static final String SETTINGS_FILENAME = "androidwin.cfg"; //$NON-NLS-1$ 40 private static final String PX = "_px"; //$NON-NLS-1$ 41 private static final String PY = "_py"; //$NON-NLS-1$ 42 private static final String SX = "_sx"; //$NON-NLS-1$ 43 private static final String SY = "_sy"; //$NON-NLS-1$ 44 loadSizeAndPos(Shell shell, String prefix)45 public static void loadSizeAndPos(Shell shell, String prefix) { 46 Properties props = loadProperties(); 47 48 try { 49 int px = Integer.parseInt(props.getProperty(prefix + PX)); 50 int py = Integer.parseInt(props.getProperty(prefix + PY)); 51 int sx = Integer.parseInt(props.getProperty(prefix + SX)); 52 int sy = Integer.parseInt(props.getProperty(prefix + SY)); 53 54 Point p1 = new Point(px, py); 55 Point p2 = new Point(px + sx, py + sy); 56 Rectangle r = new Rectangle(px, py, sy, sy); 57 58 Monitor bestMatch = null; 59 int bestSurface = -1; 60 for (Monitor monitor : shell.getDisplay().getMonitors()) { 61 Rectangle area = monitor.getClientArea(); 62 if (area.contains(p1) && area.contains(p2)) { 63 // The shell is fully visible on this monitor. Just use that. 64 bestMatch = monitor; 65 bestSurface = Integer.MAX_VALUE; 66 break; 67 } else { 68 // Find which monitor displays the largest surface of the window. 69 // We'll use this one to center the window there, to make sure we're not 70 // starting split between several monitors. 71 Rectangle i = area.intersection(r); 72 int surface = i.width * i.height; 73 if (surface > bestSurface) { 74 bestSurface = surface; 75 bestMatch = monitor; 76 } 77 } 78 } 79 80 if (bestMatch != null && bestSurface != Integer.MAX_VALUE) { 81 // Recenter the window on this monitor and make sure it fits 82 Rectangle area = bestMatch.getClientArea(); 83 84 sx = Math.min(sx, area.width); 85 sy = Math.min(sy, area.height); 86 px = area.x + (area.width - sx) / 2; 87 py = area.y + (area.height - sy) / 2; 88 } 89 90 shell.setLocation(px, py); 91 shell.setSize(sx, sy); 92 93 } catch ( Exception e) { 94 // Ignore exception. We could typically get NPE from the getProperty 95 // or NumberFormatException from parseInt calls. Either way, do 96 // nothing if anything goes wrong. 97 } 98 } 99 saveSizeAndPos(Shell shell, String prefix)100 public static void saveSizeAndPos(Shell shell, String prefix) { 101 Properties props = loadProperties(); 102 103 Point loc = shell.getLocation(); 104 Point size = shell.getSize(); 105 106 props.setProperty(prefix + PX, Integer.toString(loc.x)); 107 props.setProperty(prefix + PY, Integer.toString(loc.y)); 108 props.setProperty(prefix + SX, Integer.toString(size.x)); 109 props.setProperty(prefix + SY, Integer.toString(size.y)); 110 111 saveProperties(props); 112 } 113 114 /** 115 * Load properties saved in {@link #SETTINGS_FILENAME}. 116 * If the file does not exists or doesn't load properly, just return an 117 * empty set of properties. 118 */ loadProperties()119 private static Properties loadProperties() { 120 Properties props = new Properties(); 121 FileInputStream fis = null; 122 123 try { 124 String folder = AndroidLocation.getFolder(); 125 File f = new File(folder, SETTINGS_FILENAME); 126 if (f.exists()) { 127 fis = new FileInputStream(f); 128 129 props.load(fis); 130 } 131 } catch (Exception e) { 132 // Ignore 133 } finally { 134 if (fis != null) { 135 try { 136 fis.close(); 137 } catch (IOException e) { 138 } 139 } 140 } 141 142 return props; 143 } 144 saveProperties(Properties props)145 private static void saveProperties(Properties props) { 146 FileOutputStream fos = null; 147 148 try { 149 String folder = AndroidLocation.getFolder(); 150 File f = new File(folder, SETTINGS_FILENAME); 151 fos = new FileOutputStream(f); 152 153 props.store(fos, "## Size and Pos for SDK Manager Windows"); //$NON-NLS-1$ 154 155 } catch (Exception e) { 156 // ignore 157 } finally { 158 if (fos != null) { 159 try { 160 fos.close(); 161 } catch (IOException e) { 162 } 163 } 164 } 165 } 166 } 167