使用templateUrl(Angular 7)中的条件在移动模板或桌面模板之间切换 [英] Switch between mobile or desktop template using condition in templateUrl (Angular 7)
问题描述
我想根据屏幕宽度在桌面模板和移动模板之间进行切换,以确保我的应用程序能够响应.我正在尝试执行以下操作:
I want to switch between a desktop and mobile template depending on the screen width to ensure my application is responsive. I am trying to do the following:
@Component({
selector: 'app-root',
templateUrl: "./" + (window.innerWidth < 768) ? "app.component.html" : "app.component.mobile.html",
styleUrls: ['./app.component.css']
})
但是,这不起作用.在屏幕上显示的是字符串"app.component.html"
,而不是模板加载.
However, this is not working. Instead of the template loading, the string, "app.component.html"
, appears on the screen instead.
更有趣的是,如果我使用以下内容:
What is even more interesting is that, if I use the following:
@Component({
selector: 'app-root',
templateUrl: "./" + (false) ? "app.component.html" : "app.component.mobile.html",
styleUrls: ['./app.component.css']
})
页面仍仅显示字符串"app.component.html"
.
是否不支持将条件语句用作@Component
装饰器中templateUrl
字段的值?
Is there no support for using conditional statements as the value for the templateUrl
field in the @Component
decorator?
如果没有,我可以使用什么替代解决方案来实现仍然是模块化并且遵循最佳实践的这种响应水平?
If not, what is an alternative solution I could use to achieve this level of responsiveness that is still modular and follows best practices?
更新:我通过使用ng serve --aot
而不是仅仅使用ng serve
来使其正常工作.但是,我决定不采用这个想法,因为它不会在调整窗口大小时切换模板.
Update: I got this to work by using ng serve --aot
instead of just ng serve
. However, I decided to not go through with this idea because it does not switch templates as the window resizes.
推荐答案
您的方法已关闭.模板是在构建时分配给组件的,而不是在运行时分配的,而Angular会在其宽度足以写入条件关闭的任何窗口存在之前就构建其所有组件.您需要设置逻辑来告诉您的应用何时显示哪个组件.
your approach here is off. Templates are assigned to components at build time, not runtime and Angular will build all of it's components, well before any window exists with a width to write a conditional off of. You need to set up logic to tell your app when to show which component.
这里的最佳做法"(IMO),如果您不能进行响应式设计(请注意:了解受众和应用程序的使用非常重要.我一直尝试选择移动优先响应式设计,但也认识到这并不总是合适的),它有2个组件,并使用路由防护来强制使用正确的组件.
The "best practice" (IMO) here, if you can't do responsive design (note: it's important to understand your audience and how the app will be used. I always try to opt for a mobile first responsive design, but also recognize this isn't always appropriate), is to have 2 components, and use route guards to enforce the correct component.
@Injectable()
export class MobileGuard implements CanActivate {
constructor(
private router: Router
) { }
canActivate() {
if (window.innerWidth >= 768) {
this.router.navigate(['/']);
return false;
}
return true;
}
}
@Injectable()
export class DesktopGuard implements CanActivate {
constructor(
private router: Router
) { }
canActivate() {
if (window.innerWidth < 768) {
this.router.navigate(['/m/']);
return false;
}
return true;
}
}
然后定义您的路由结构,如下所示:
then define your routing structure somewhat like this:
const routes: Routes = [
{
path: '',
component: AppComponent,
canActivate: [DesktopGuard],
children: [... desktop routes ...]
},
{
path: 'm',
component: MobileAppComponent,
canActivate: [MobileGuard],
children: [... mobile routes ...]
}
]
对于组件本身,您的移动组件只是扩展了您的非移动组件,并且具有不同的模板/样式.
as for the components themselves, your mobile component just extends your non mobile component and has a different template / styles associated.
此处的另一种方法是执行以下操作:
an alternative approach here is to do something like this:
export class WrapperAppComponent {
isMobile: boolean;
constructor() {
this.isMobile = window.innerWidth < 768;
}
}
模板如下:
<desktop-app *ngIf="!isMobile"></desktop-app>
<mobile-app *ngIf="isMobile>></mobile-app>
但这不是一个非常可扩展的方法,并且具有相同的组件重复".
but this isn't a very scalable approach and has the same "duplication" of components.
这篇关于使用templateUrl(Angular 7)中的条件在移动模板或桌面模板之间切换的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!