| 
001 /*002  * Copyright 2008-2015 the original author or authors.
 003  *
 004  * Licensed under the Apache License, Version 2.0 (the "License");
 005  * you may not use this file except in compliance with the License.
 006  * You may obtain a copy of the License at
 007  *
 008  *     http://www.apache.org/licenses/LICENSE-2.0
 009  *
 010  * Unless required by applicable law or agreed to in writing, software
 011  * distributed under the License is distributed on an "AS IS" BASIS,
 012  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 013  * See the License for the specific language governing permissions and
 014  * limitations under the License.
 015  */
 016 package griffon.javafx.editors;
 017
 018 import griffon.core.editors.AbstractPropertyEditor;
 019 import griffon.core.formatters.Formatter;
 020 import griffon.core.formatters.ParseException;
 021 import griffon.javafx.formatters.ColorFormatter;
 022 import griffon.metadata.PropertyEditorFor;
 023 import javafx.scene.paint.Color;
 024
 025 import java.util.ArrayList;
 026 import java.util.List;
 027 import java.util.Map;
 028
 029 import static griffon.util.GriffonNameUtils.isBlank;
 030
 031
 032 /**
 033  * @author Andres Almiray
 034  */
 035 @PropertyEditorFor(Color.class)
 036 public class ColorPropertyEditor extends AbstractPropertyEditor {
 037     public static String format(Color color) {
 038         return ColorFormatter.LONG.format(color);
 039     }
 040
 041     @Override
 042     public String getAsText() {
 043         if (null == getValue()) return null;
 044         return isBlank(getFormat()) ? format((Color) getValueInternal()) : getFormattedValue();
 045     }
 046
 047     protected void setValueInternal(Object value) {
 048         if (null == value) {
 049             super.setValueInternal(null);
 050         } else if (value instanceof CharSequence) {
 051             handleAsString(String.valueOf(value).trim());
 052         } else if (value instanceof List) {
 053             handleAsList((List) value);
 054         } else if (value instanceof Map) {
 055             handleAsMap((Map) value);
 056         } else if (value instanceof Number) {
 057             handleAsNumber((Number) value);
 058         } else if (value instanceof Color) {
 059             super.setValueInternal(value);
 060         } else {
 061             throw illegalValue(value, Color.class);
 062         }
 063     }
 064
 065     @Override
 066     protected Formatter<Color> resolveFormatter() {
 067         return !isBlank(getFormat()) ? ColorFormatter.getInstance(getFormat()) : null;
 068     }
 069
 070     private void handleAsString(String str) {
 071         if (isBlank(str)) {
 072             super.setValueInternal(null);
 073             return;
 074         }
 075         try {
 076             super.setValueInternal(ColorFormatter.parseColor(str));
 077         } catch (ParseException e) {
 078             throw illegalValue(str, Color.class, e);
 079         }
 080     }
 081
 082     private void handleAsList(List<?> list) {
 083         if (list.isEmpty()) {
 084             super.setValueInternal(null);
 085             return;
 086         }
 087
 088         List<Object> values = new ArrayList<>();
 089         values.addAll(list);
 090         switch (list.size()) {
 091             case 3:
 092                 values.add(1d);
 093                 break;
 094             case 4:
 095                 // ok
 096                 break;
 097             default:
 098                 throw illegalValue(list, Color.class);
 099         }
 100         for (int i = 0, valuesSize = values.size(); i < valuesSize; i++) {
 101             Object val = values.get(i);
 102             if (val instanceof Number) {
 103                 values.set(i, parse((Number) val));
 104             } else if (val instanceof CharSequence) {
 105                 values.set(i, parse(String.valueOf(val)));
 106             } else {
 107                 throw illegalValue(list, Color.class);
 108             }
 109         }
 110         super.setValueInternal(
 111             new Color(
 112                 (Double) values.get(0),
 113                 (Double) values.get(1),
 114                 (Double) values.get(2),
 115                 (Double) values.get(3)
 116             )
 117         );
 118     }
 119
 120     private void handleAsMap(Map<?, ?> map) {
 121         if (map.isEmpty()) {
 122             super.setValueInternal(null);
 123             return;
 124         }
 125
 126         double r = getMapValue(map, "red", 0d);
 127         double g = getMapValue(map, "green", 0d);
 128         double b = getMapValue(map, "blue", 0d);
 129         double a = getMapValue(map, "alpha", 1d);
 130         super.setValueInternal(new Color(r, g, b, a));
 131     }
 132
 133     private double parse(String val) {
 134         try {
 135             return (Integer.parseInt(String.valueOf(val).trim(), 16) & 0xFF) / 255d;
 136         } catch (NumberFormatException e) {
 137             throw illegalValue(val, Color.class, e);
 138         }
 139     }
 140
 141     private double parse(Number val) {
 142         return val.doubleValue();
 143     }
 144
 145     private double getMapValue(Map<?, ?> map, String key, double defaultValue) {
 146         Object val = map.get(key);
 147         if (null == val) val = map.get(String.valueOf(key.charAt(0)));
 148         if (null == val) {
 149             return defaultValue;
 150         } else if (val instanceof CharSequence) {
 151             return parse(String.valueOf(val));
 152         } else if (val instanceof Number) {
 153             return parse((Number) val);
 154         }
 155         throw illegalValue(map, Color.class);
 156     }
 157
 158     private void handleAsNumber(Number value) {
 159         double c = parse(value);
 160         super.setValueInternal(new Color(c, c, c, 1d));
 161     }
 162 }
 |