Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Screen Size Qualifiers not work in tns Angular project, only work in js project. #404

Closed
tsonevn opened this Issue Aug 19, 2016 · 19 comments

Comments

Projects
None yet
@tsonevn
Copy link
Contributor

tsonevn commented Aug 19, 2016

From @Arthurisme on August 19, 2016 5:13

I use following names as Screen Size Qualifiers, but none of any one is working in tns angular project:

page.minWH600.html
page.minWH600.css
page.minWH600.ts
page.land.css
page.land.html
page.port.css
page.port.html

So is it because Screen Size Qualifiers not support angular project yet?

Copied from original issue: NativeScript/NativeScript#2604

@tsonevn

This comment has been minimized.

Copy link
Contributor Author

tsonevn commented Aug 19, 2016

Hi @Arthurisme,

Screen Size Qualifiers are still not supported in NativeScript Angular projects. Such a feature would be available for some of the next nativescript-angular versions. As a temporary solution you could use nativescript-orientaion to set different style for the different orientations. Example could be found here.

@tsonevn tsonevn added the feature label Aug 19, 2016

@tsonevn tsonevn removed their assignment Aug 23, 2016

@andy-tai

This comment has been minimized.

Copy link

andy-tai commented Sep 1, 2016

+1 for this issue

@andy-tai

This comment has been minimized.

Copy link

andy-tai commented Sep 8, 2016

so may I guess... the file name resolver works at run time but with Angular 2, the css file name has to be specified at compile time...
example:
@component({
selector: "front",
templateUrl: "pages/front/front.html",
styleUrls: ["pages/front/front-common.css"],
})

the styleUrls cannot be computed at run time...

@echap

This comment has been minimized.

Copy link

echap commented Dec 16, 2016

Any update regarding this ?

This is quite of a key feature 👍

@vakrilov vakrilov self-assigned this Dec 16, 2016

@vakrilov vakrilov added this to the NS 2.6 milestone Dec 16, 2016

@vakrilov

This comment has been minimized.

Copy link
Member

vakrilov commented Dec 16, 2016

Currently we are evaluating how to support that.

The main problem is that this feature cannot work with angular Ahead-Of-Time Compilation as in this case the template should be known at build time, but the screens size and orientation is something only available at runtime.

@vakrilov vakrilov added feature and removed bug labels Dec 16, 2016

@valentinstoychev

This comment has been minimized.

Copy link

valentinstoychev commented Dec 16, 2016

We should evaluate implementing bootstrap-like responsive layout grid as available on the web.

@jlooper

This comment has been minimized.

Copy link

jlooper commented Apr 3, 2017

@vakrilov - community is asking where we are on this topic? ping ping?

@EddyVerbruggen

This comment has been minimized.

Copy link
Member

EddyVerbruggen commented Apr 3, 2017

Just in case someone would only need tablet-specific CSS (like myself) and can't wait for an official solution (like myself), you can do:

const isTablet: boolean = device.deviceType == DeviceType.Tablet;

@Component({
  styleUrls: ['default.css', (isTablet ? 'tablet.css' : 'phone.css')]
})
@anuragd7

This comment has been minimized.

Copy link

anuragd7 commented Apr 19, 2017

Any update on when this feature is likely to be available?

@vakrilov

This comment has been minimized.

Copy link
Member

vakrilov commented Apr 20, 2017

Just an update:
We are still in the process of figuring this out.
The main problem with Angular is supporting Ahead-Of-Time compilation (AOT). AOT happens build-time wile the information about the device (dimensions, orientation, etc) is available runtime. I don't think currently it is possible to tell the angular compiler to compile multiple templates(XML files) for a single component and choose which one to use based on some runtime logic.

@jarrodchesney

This comment has been minimized.

Copy link

jarrodchesney commented Aug 24, 2017

Maybe the solution involves qualifying the selector as well

@component({
selector: "front-port-minWH600",
...

You could then dynamically create a selector: "front" component that has ng-ifs for <front-port-minWH600> in it and passes through the @Input and @Output

But then you'd need to declare the different versions in the module.

Anyway, This is a solution you could use with out needing native script support built in, it would be a pain though.

@bhavincb

This comment has been minimized.

Copy link
Contributor

bhavincb commented Mar 8, 2018

any new updates to issue?

@fthuin

This comment has been minimized.

Copy link

fthuin commented Mar 15, 2018

As this feature is not yet implemented and it took me a while to figure out how to do it (creating new component for each size didn't look maintainable to me), here is a little explanation. The ternary condition on scss import doesn't work well with webpack for me (because it would mean lazy loaded scss...)

What you can do is:

Create a .scss file for any of the size you want to handle (name them as you want, but let's keep the 'Screen Size Qualifiers' names for this example), which can result for a home component e.g.

home.component.minW640.scss
home.component.minW1080.scss
home.component.minW1440.scss

In each of those files, you wrap all your classes in a specific class, e.g. page-640, page-1080, page-1440

You import all your files inside inside a single scss file, for this example I name it home.component.scss, its content will look like

@import '../../app-common.scss';
@import './home.component.minW640.scss';
@import './home.component.minW1080.scss';
@import './home.component.minW1440.scss';

Inside your component, you can reference home.component.scss as your styleUrls. And you can add programmatically a className on the component you want to change the behavior for each screen size (usually a Page, but in my case a ScrollView)

... html content
    <ScrollView #scrollView>
           ... html content
    </ScrollView>
... html content
import { Component, ElementRef, OnInit, ViewChild } from '@angular/core';
import * as platformModule from 'tns-core-modules/platform';

@Component({
    selector: 'Home',
    moduleId: module.id,
    templateUrl: './home.component.html',
    styleUrls: ['home.component.scss'],
})
export class HomeComponent implements OnInit {
    @ViewChild('scrollView') scrollView: ElementRef;

    constructor() {
        /************************************************************
         * Use the constructor to inject services.
         *************************************************************/
    }

    ngOnInit(): void {
        const className =
            platformModule.screen.mainScreen.widthPixels >= 1440
                ? 'page-1440'
                : platformModule.screen.mainScreen.widthPixels >= 1080
                  ? 'page-1080'
                  : 'page-640';
        const svElement = <ScrollView>this.scrollView.nativeElement;
        svElement.className = className;
    }
}
@vakrilov

This comment has been minimized.

Copy link
Member

vakrilov commented Mar 19, 2018

Hey @fthuin
Thanks for sharing that! It seems like a nice approach. I think the whole thing can even be extracted in a separate directive (similar to ngClass) that will perform the conditional class selection for you. This way you can easily reuse it in many components.

@trojanc

This comment has been minimized.

Copy link

trojanc commented Mar 23, 2018

This is a bit of a problem for me too... I really don't want to change to not using angular :-( and the other suggested "hacky" tricks aren't nice. I need a whole new template for screen sizes, not just minor style changes

@manojdcoder

This comment has been minimized.

Copy link

manojdcoder commented Mar 24, 2018

@trojanc You may try writing a directive that will inject / render right HTML template based on device width.

@vakrilov vakrilov removed this from the NS 2.6 milestone Apr 16, 2018

@vakrilov vakrilov removed their assignment Apr 16, 2018

@lumayara

This comment has been minimized.

Copy link

lumayara commented Apr 16, 2018

Any updates on this issue? Thank you

@manojdcoder

This comment has been minimized.

Copy link

manojdcoder commented Apr 16, 2018

You may achieve this by creating a directive or simple ngIf.

@vakrilov

This comment has been minimized.

Copy link
Member

vakrilov commented Apr 19, 2018

Update: It looks like supporting screen size qualifiers nearly impossible especially now that we have Angular AOT and webpack.

There are a couple of solutions in this tread that you can use now.

Also the same results would be possible when support for CSS media queries is implemented, so you might follow this issue instead.

@vakrilov vakrilov closed this Apr 19, 2018

@wafflebot wafflebot bot removed the feature label Apr 19, 2018

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.
You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.