001package gwt.material.design.client.base.helper;
002
003/*
004 * #%L
005 * GwtBootstrap3
006 * %%
007 * Copyright (C) 2013 GwtBootstrap3
008 * %%
009 * Licensed under the Apache License, Version 2.0 (the "License");
010 * you may not use this file except in compliance with the License.
011 * You may obtain a copy of the License at
012 * 
013 *      http://www.apache.org/licenses/LICENSE-2.0
014 * 
015 * Unless required by applicable law or agreed to in writing, software
016 * distributed under the License is distributed on an "AS IS" BASIS,
017 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
018 * See the License for the specific language governing permissions and
019 * limitations under the License.
020 * #L%
021 */
022
023import com.google.gwt.dom.client.Style;
024import com.google.gwt.user.client.ui.UIObject;
025
026/**
027 * Helper methods regarding CSS styling of UIObjects.
028 *
029 * @author Sven Jacobs
030 * @author Joshua Godi
031 */
032public final class StyleHelper {
033
034    public static <F extends Enum<? extends Style.HasCssName>> F fromStyleName(final Class<F> enumClass,
035                                                                               final Style.HasCssName styleName) {
036        return EnumHelper.fromStyleName(styleName.getCssName(), enumClass, null);
037    }
038
039    /**
040     * Convenience method for first removing all enum style constants and then adding the single one.
041     *
042     * @see #removeEnumStyleNames(UIObject, Class)
043     * @see #addEnumStyleName(UIObject, Style.HasCssName)
044     */
045    public static <E extends Style.HasCssName, F extends Enum<? extends Style.HasCssName>> void addUniqueEnumStyleName(final UIObject uiObject,
046                                                                                                                       final Class<F> enumClass,
047                                                                                                                       final E style) {
048        removeEnumStyleNames(uiObject, enumClass);
049        addEnumStyleName(uiObject, style);
050    }
051
052    /**
053     * Removes all CSS style names specified by an enum that implements {@link Style.HasCssName} from an UIObject.
054     *
055     * @param uiObject  Object to remove CSS class names from
056     * @param enumClass Enum representing CSS class names
057     * @param <E>       Enum type implementing {@link Style.HasCssName}
058     */
059    public static <E extends Enum<? extends Style.HasCssName>> void removeEnumStyleNames(final UIObject uiObject,
060                                                                                         final Class<E> enumClass) {
061
062        for (final Enum<? extends Style.HasCssName> constant : enumClass.getEnumConstants()) {
063            final String cssClass = ((Style.HasCssName) constant).getCssName();
064
065            if (cssClass != null && !cssClass.isEmpty()) {
066                uiObject.removeStyleName(cssClass);
067            }
068        }
069    }
070
071    /**
072     * Adds enum value style name to UIObject unless style is {@code null}.
073     *
074     * @param uiObject Object to add style to
075     * @param style    Style name
076     */
077    public static <E extends Style.HasCssName> void addEnumStyleName(final UIObject uiObject,
078                                                                     final E style) {
079
080        if (style != null && style.getCssName() != null && !style.getCssName().isEmpty()) {
081            uiObject.addStyleName(style.getCssName());
082        }
083    }
084
085    /**
086     * Removes enum value style name from UIObject unless style is {@code null}.
087     *
088     * @param uiObject Object to remove style from
089     * @param style    Style name
090     */
091    public static <E extends Style.HasCssName> void removeEnumStyleName(final UIObject uiObject,
092                                                                        final E style) {
093
094        if (style != null && style.getCssName() != null && !style.getCssName().isEmpty()) {
095            uiObject.removeStyleName(style.getCssName());
096        }
097    }
098
099    /**
100     * Returns {@code true} if specified style is contained in space-separated list of styles
101     *
102     * @param styleNames Space-separated list of styles
103     * @param style      Style to look for
104     * @return True if contains style
105     */
106    public static boolean containsStyle(final String styleNames,
107                                        final String style) {
108        if (styleNames == null || style == null) {
109            return false;
110        }
111
112        final String[] styles = styleNames.split("\\s");
113
114        for (final String s : styles) {
115            if (style.equals(s)) {
116                return true;
117            }
118        }
119
120        return false;
121    }
122
123    /**
124     * Toggles a style name on a ui object
125     *
126     * @param uiObject    Object to toggle style on
127     * @param toggleStyle whether or not to toggle the style name on the object
128     * @param styleName   Style name
129     */
130    public static void toggleStyleName(final UIObject uiObject,
131                                       final boolean toggleStyle,
132                                       final String styleName) {
133        if (toggleStyle) {
134            uiObject.addStyleName(styleName);
135        } else {
136            uiObject.removeStyleName(styleName);
137        }
138    }
139
140    public static Double getMeasurementValue(String value) {
141        if (value == null) {
142            return null;
143        }
144        try {
145            return Double.parseDouble(value.replaceAll("[^0-9.]", ""));
146        } catch (NumberFormatException ex) {
147            return null;
148        }
149    }
150
151    public static Style.Unit getMeasurementUnit(String value) {
152        if (value == null) {
153            return null;
154        }
155        try {
156            return Style.Unit.valueOf(
157                    value.replaceAll("[-+]?[0-9]*\\.?[0-9]+([eE][-+]?[0-9]+)?", "").toUpperCase());
158        } catch (IllegalArgumentException e) {
159            // Silently catch invalid units
160            return null;
161        }
162    }
163
164    private StyleHelper() {
165    }
166}