Resolved Issue #1223: Android views which have complex backgrounds (i.e. with rounded corners) cannot animate opacity.

This commit is contained in:
Rossen Hristov
2015-12-10 14:55:01 +02:00
parent 0e040cdd6d
commit 700818dd28
11 changed files with 169 additions and 10 deletions

View File

@ -79,6 +79,7 @@
<TypeScriptCompile Include="apps\action-bar-demo\pages\data-binding.ts"> <TypeScriptCompile Include="apps\action-bar-demo\pages\data-binding.ts">
<DependentUpon>data-binding.xml</DependentUpon> <DependentUpon>data-binding.xml</DependentUpon>
</TypeScriptCompile> </TypeScriptCompile>
<TypeScriptCompile Include="apps\animations\opacity.ts" />
<TypeScriptCompile Include="apps\tests\ui\action-bar\ActionBar_NumberAsText.ts" /> <TypeScriptCompile Include="apps\tests\ui\action-bar\ActionBar_NumberAsText.ts" />
<TypeScriptCompile Include="apps\tests\ui\page\modal-page.ts"> <TypeScriptCompile Include="apps\tests\ui\page\modal-page.ts">
<DependentUpon>modal-page.xml</DependentUpon> <DependentUpon>modal-page.xml</DependentUpon>
@ -117,6 +118,12 @@
<Content Include="apps\action-bar-demo\pages\center-view-segmented.xml" /> <Content Include="apps\action-bar-demo\pages\center-view-segmented.xml" />
<Content Include="apps\action-bar-demo\pages\center-view.xml" /> <Content Include="apps\action-bar-demo\pages\center-view.xml" />
<Content Include="apps\action-bar-demo\pages\data-binding.xml" /> <Content Include="apps\action-bar-demo\pages\data-binding.xml" />
<Content Include="apps\animations\opacity.css" />
<Content Include="apps\animations\opacity.xml">
<SubType>Designer</SubType>
</Content>
<Content Include="apps\animations\bkg.png" />
<Content Include="apps\animations\test-icon.png" />
<Content Include="apps\tests\ui\action-bar\ActionBar_NumberAsText.xml" /> <Content Include="apps\tests\ui\action-bar\ActionBar_NumberAsText.xml" />
<Content Include="apps\tests\ui\page\modal-page.xml"> <Content Include="apps\tests\ui\page\modal-page.xml">
<SubType>Designer</SubType> <SubType>Designer</SubType>
@ -2104,7 +2111,7 @@
<SaveServerSettingsInUserFile>False</SaveServerSettingsInUserFile> <SaveServerSettingsInUserFile>False</SaveServerSettingsInUserFile>
</WebProjectProperties> </WebProjectProperties>
</FlavorProperties> </FlavorProperties>
<UserProperties ui_2layouts_2wrap-layout_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2layouts_2grid-layout_2package_1json__JSONSchema="" ui_2layouts_2dock-layout_2package_1json__JSONSchema="" ui_2layouts_2absolute-layout_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2web-view_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2content-view_2package_1json__JSONSchema="http://json.schemastore.org/package" apps_2gallery-app_2package_1json__JSONSchema="http://json.schemastore.org/package" apps_2absolute-layout-demo_2package_1json__JSONSchema="http://json.schemastore.org/package" apps_2editable-text-demo_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2scroll-view_2package_1json__JSONSchema="http://json.schemastore.org/package" /> <UserProperties ui_2scroll-view_2package_1json__JSONSchema="http://json.schemastore.org/package" apps_2editable-text-demo_2package_1json__JSONSchema="http://json.schemastore.org/package" apps_2absolute-layout-demo_2package_1json__JSONSchema="http://json.schemastore.org/package" apps_2gallery-app_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2content-view_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2web-view_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2layouts_2absolute-layout_2package_1json__JSONSchema="http://json.schemastore.org/package" ui_2layouts_2dock-layout_2package_1json__JSONSchema="" ui_2layouts_2grid-layout_2package_1json__JSONSchema="" ui_2layouts_2wrap-layout_2package_1json__JSONSchema="http://json.schemastore.org/package" />
</VisualStudio> </VisualStudio>
</ProjectExtensions> </ProjectExtensions>
</Project> </Project>

BIN
apps/animations/bkg.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 311 B

View File

@ -6,6 +6,7 @@ import animationModule = require("ui/animation");
import colorModule = require("color"); import colorModule = require("color");
import model = require("./model"); import model = require("./model");
import enums = require("ui/enums"); import enums = require("ui/enums");
import frame = require("ui/frame");
var vm = new model.ViewModel(); var vm = new model.ViewModel();
@ -163,3 +164,7 @@ export function onInterrupted(args: observable.EventData) {
}) })
}, 700 * 3); }, 700 * 3);
} }
export function onOpacity(args: observable.EventData) {
frame.topmost().navigate("./opacity");
}

View File

@ -18,6 +18,7 @@
<Button text="In" tap="onSlideIn" width="40" marginLeft="5" marginRight="5" /> <Button text="In" tap="onSlideIn" width="40" marginLeft="5" marginRight="5" />
<Button text="Single" tap="onSingle" width="70" marginLeft="5" marginRight="5" /> <Button text="Single" tap="onSingle" width="70" marginLeft="5" marginRight="5" />
<Button text="Cancel" tap="onCancel" width="70" marginLeft="5" marginRight="5" /> <Button text="Cancel" tap="onCancel" width="70" marginLeft="5" marginRight="5" />
<Button text="Opacity" tap="onOpacity" width="70" marginLeft="5" marginRight="5" />
</StackLayout> </StackLayout>
<StackLayout orientation="horizontal" marginTop="5" marginBottom="5" horizontalAlignment="center" paddingLeft="5" paddingRight="5">> <StackLayout orientation="horizontal" marginTop="5" marginBottom="5" horizontalAlignment="center" paddingLeft="5" paddingRight="5">>

View File

@ -0,0 +1,27 @@
.complex {
width: 45;
height: 45;
margin: 1;
background-image: url('~/bkg.png');
background-repeat:repeat-x;
background-position: 20% 80%;
background-color: lightyellow;
background-size: 25% 50%;
border-radius: 20;
border-width: 4;
border-color: red;
}
.simple {
width: 45;
height: 45;
margin: 1;
border-radius: 20;
background-color: lightgreen;
}
.none {
width: 45;
height: 45;
margin: 1;
}

View File

@ -0,0 +1,53 @@
import observable = require("data/observable");
import pages = require("ui/page");
import view = require("ui/core/view");
import buttonModule = require("ui/button");
import abs = require("ui/layouts/absolute-layout");
import animationModule = require("ui/animation");
import colorModule = require("color");
import model = require("./model");
import enums = require("ui/enums");
import frame = require("ui/frame");
import slider = require("ui/slider");
import wrapLayout = require("ui/layouts/wrap-layout");
var page: pages.Page;
var opacitySlider: slider.Slider;
var red = new colorModule.Color("red");
var green = new colorModule.Color("green");
var container: wrapLayout.WrapLayout;
export function pageLoaded(args: observable.EventData) {
page = <pages.Page>args.object;
opacitySlider = page.getViewById<slider.Slider>("opacitySlider");
container = page.getViewById<wrapLayout.WrapLayout>("container");
}
export function onSetOpacity(args: observable.EventData) {
var newOpacity = opacitySlider.value / 100;
container._eachChildView((childView: view.View) => {
childView.opacity = newOpacity;
return true;
});
}
var animationSet: animationModule.Animation;
export function onAnimateOpacity(args: observable.EventData) {
var newOpacity = opacitySlider.value / 100;
var animationDefinitions = new Array<animationModule.AnimationDefinition>();
container._eachChildView((childView: view.View) => {
animationDefinitions.push({
target: childView,
opacity: newOpacity,
duration: 5000
});
return true;
});
animationSet = new animationModule.Animation(animationDefinitions);
animationSet.play();
}
export function onReset(args: observable.EventData) {
animationSet.cancel();
}

View File

@ -0,0 +1,35 @@
<Page xmlns="http://schemas.nativescript.org/tns.xsd" loaded="pageLoaded" id="opacityPage">
<StackLayout orientation="vertical">
<StackLayout orientation="vertical">
<Label text="opacity" width="180" />
<Slider id="opacitySlider" minValue="0" maxValue="100" width="180" />
<Button text="Set" tap="onSetOpacity"/>
<Button text="Animate" tap="onAnimateOpacity"/>
<Button text="Reset" tap="onReset"/>
</StackLayout>
<WrapLayout orientation="horizontal" id="container">
<StackLayout class="complex"/>
<Button text="Button" class="complex"/>
<Label text="Label" class="complex"/>
<Image src="~/test-icon.png" class="complex"/>
<TextField text="TextField" class="complex"/>
<TextView text="TextView" class="complex"/>
<StackLayout class="simple"/>
<Button text="Button" class="simple"/>
<Label text="Label" class="simple"/>
<Image src="~/test-icon.png" class="simple"/>
<TextField text="TextField" class="simple"/>
<TextView text="TextView" class="simple"/>
<StackLayout class="none"/>
<Button text="Button" class="none"/>
<Label text="Label" class="none"/>
<Image src="~/test-icon.png" class="none"/>
<TextField text="TextField" class="none"/>
<TextView text="TextView" class="none"/>
</WrapLayout>
</StackLayout>
</Page>

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@ -48,6 +48,7 @@
"apps/animations/app.ts", "apps/animations/app.ts",
"apps/animations/main-page.ts", "apps/animations/main-page.ts",
"apps/animations/model.ts", "apps/animations/model.ts",
"apps/animations/opacity.ts",
"apps/connectivity-demo/app.ts", "apps/connectivity-demo/app.ts",
"apps/connectivity-demo/main-page.ts", "apps/connectivity-demo/main-page.ts",
"apps/cuteness.io/app.ts", "apps/cuteness.io/app.ts",
@ -319,9 +320,9 @@
"apps/tests/xml-declaration/mainPage.ts", "apps/tests/xml-declaration/mainPage.ts",
"apps/tests/xml-declaration/mymodule/MyControl.ts", "apps/tests/xml-declaration/mymodule/MyControl.ts",
"apps/tests/xml-declaration/mymodulewithxml/MyControl.ts", "apps/tests/xml-declaration/mymodulewithxml/MyControl.ts",
"apps/tests/xml-declaration/template-builder-tests/template-view.ts",
"apps/tests/xml-declaration/template-builder-tests/event-in-template.ts",
"apps/tests/xml-declaration/template-builder-tests/event-in-codeless-fragment.ts", "apps/tests/xml-declaration/template-builder-tests/event-in-codeless-fragment.ts",
"apps/tests/xml-declaration/template-builder-tests/event-in-template.ts",
"apps/tests/xml-declaration/template-builder-tests/template-view.ts",
"apps/tests/xml-declaration/xml-declaration-tests.ts", "apps/tests/xml-declaration/xml-declaration-tests.ts",
"apps/tests/xml-parser-tests/xml-parser-tests.ts", "apps/tests/xml-parser-tests/xml-parser-tests.ts",
"apps/transforms/app.ts", "apps/transforms/app.ts",

View File

@ -159,11 +159,18 @@ export class Animation extends common.Animation implements definition.Animation
case common.Properties.opacity: case common.Properties.opacity:
originalValue1 = nativeView.getAlpha(); originalValue1 = nativeView.getAlpha();
nativeArray = java.lang.reflect.Array.newInstance(floatType, 1); nativeArray = java.lang.reflect.Array.newInstance(floatType, 2);
nativeArray[0] = propertyAnimation.value; nativeArray[0] = originalValue1;
propertyUpdateCallbacks.push(checkAnimation(() => { propertyAnimation.target.opacity = propertyAnimation.value })); nativeArray[1] = propertyAnimation.value;
propertyResetCallbacks.push(checkAnimation(() => { nativeView.setAlpha(originalValue1); })); animator = android.animation.ValueAnimator.ofFloat(nativeArray);
animators.push(android.animation.ObjectAnimator.ofFloat(nativeView, "alpha", nativeArray)); animator.addUpdateListener(new android.animation.ValueAnimator.AnimatorUpdateListener({
onAnimationUpdate(animator: android.animation.ValueAnimator) {
propertyAnimation.target.opacity = (<java.lang.Float>animator.getAnimatedValue()).floatValue();
}
}));
propertyUpdateCallbacks.push(checkAnimation(() => { propertyAnimation.target.opacity = propertyAnimation.value; }));
propertyResetCallbacks.push(checkAnimation(() => { propertyAnimation.target.opacity = originalValue1; }));
animators.push(animator);
break; break;
case common.Properties.backgroundColor: case common.Properties.backgroundColor:

View File

@ -341,6 +341,25 @@ export class ImageStyler implements definition.stylers.Styler {
onBackgroundOrBorderPropertyChanged(view); onBackgroundOrBorderPropertyChanged(view);
} }
//Opacity methods
private static setOpacityProperty(view: view.View, newValue: any) {
ImageStyler._setOpacity(view, newValue);
}
private static resetOpacityProperty(view: view.View, nativeValue: any) {
ImageStyler._setOpacity(view, 1.0);
}
private static _setOpacity(view: view.View, value: any) {
let opacity = float(value);
let nativeView = <android.view.View>view._nativeView;
nativeView.setAlpha(opacity);
let background = nativeView.getBackground();
if (background) {
background.setAlpha(opacity);
}
}
public static registerHandlers() { public static registerHandlers() {
// Use the same handler for all background/border properties // Use the same handler for all background/border properties
// Note: There is no default value getter - the default value is handled in onBackgroundOrBorderPropertyChanged // Note: There is no default value getter - the default value is handled in onBackgroundOrBorderPropertyChanged
@ -352,6 +371,10 @@ export class ImageStyler implements definition.stylers.Styler {
style.registerHandler(style.borderWidthProperty, new stylersCommon.StylePropertyChangedHandler( style.registerHandler(style.borderWidthProperty, new stylersCommon.StylePropertyChangedHandler(
ImageStyler.setBorderWidthProperty, ImageStyler.setBorderWidthProperty,
ImageStyler.resetBorderWidthProperty), "Image"); ImageStyler.resetBorderWidthProperty), "Image");
style.registerHandler(style.opacityProperty, new stylersCommon.StylePropertyChangedHandler(
ImageStyler.setOpacityProperty,
ImageStyler.resetOpacityProperty), "Image");
} }
} }