web-dev-qa-db-ja.com

Railsの適切なSCSS資産構造

だから、app/assets/stylesheets/次のようなディレクトリ構造:

   |-dialogs
   |-mixins
   |---buttons
   |---gradients
   |---vendor_support
   |---widgets
   |-pages
   |-structure
   |-ui_elements

各ディレクトリには、複数のsassパーシャル(通常は* .css.scssですが、1つまたは2つの* .css.scss.erb)があります。

私は多くのことを想定しているかもしれませんが、Railsは、*= require_tree . application.cssにありますか?

私は最近、すべての色変数を削除し、それらをルートapp/assets/stylesheetsフォルダー(_colors.css.scss)。次に、ルートにファイルを作成しましたapp/assets/stylesheets次のようなmaster.css.scssというフォルダー:

// Color Palette 
@import "colors";

// Mixins
@import "mixins/buttons/standard_button";
@import "mixins/gradients/table_header_fade";
@import "mixins/vendor_support/rounded_corners";
@import "mixins/vendor_support/rounded_corners_top";
@import "mixins/vendor_support/box_shadow";
@import "mixins/vendor_support/opacity";

Railsがアセットのコンパイルの順序を処理する方法を本当に理解していませんが、それは明らかに私の好みではありません。エラーがスローされ、コンパイルできません。

Undefined variable: "$dialog_divider_color".
  (in /home/blah/app/assets/stylesheets/dialogs/dialog.css.scss.erb)

Undefined mixin 'rounded_corners'.
  (in /home/blah/app/assets/stylesheets/widgets.css.scss)

変数$dialog_divider_colorは_colors.css.scssで明確に定義されており、_master.css.scssは色とすべてのミックスインをインポートしています。しかし、どうやらRailsはそのメモを取得できませんでした。

これらのエラーを修正する方法はありますか、またはすべての変数定義をすべてのミックスインインポートと同様に個々のファイルに戻す必要がありますか?

残念ながら、 this guy は可能だとは思わないようですが、彼が間違っていることを願っています。どんな考えでも大歓迎です。

81
David Savage

CSSの問題は、すべてのファイルを自動的に追加したくないことです。ブラウザがシートをロードして処理する順序は重要です。したがって、常にすべてのcssを明示的にインポートすることになります。

例として、すべての恐ろしい異なるブラウザ実装の代わりにデフォルトの外観を得るために、 normalize.css シートがあるとしましょう。これは、ブラウザーがロードする最初のファイルでなければなりません。このシートをcssインポートのどこかにランダムに含めると、ブラウザーのデフォルトスタイルだけでなく、その前にロードされたすべてのcssファイルで定義されたスタイルも上書きされます。これは、変数とミックスインでも同じです。

Euruko2012で Roy Tomeij によるプレゼンテーションを見た後、管理するCSSがたくさんある場合は、次のアプローチを採用することにしました。

私は通常、このアプローチを使用します。

  1. すべての既存の.cssファイルの名前を.scssに変更します
  2. Application.scssからすべてのコンテンツを削除します

@importディレクティブをapplication.scssに追加し始めます。

Twitters bootstrapと独自のcssシートをいくつか使用している場合、スタイルをリセットするシートがあるため、最初にbootstrap=をインポートする必要があります。 @import "bootstrap/bootstrap.scss";application.scssに追加します。

Bootstrap.scssファイルは次のようになります。

// CSS Reset
@import "reset.scss";

// Core
@import "variables.scss";
@import "mixins.scss";

// Grid system and page structure
@import "scaffolding.scss";

// Styled patterns and elements
@import "type.scss";
@import "forms.scss";
@import "tables.scss";
@import "patterns.scss";

そして、application.scssファイルは次のようになります。

@import "bootstrap/bootstrap.scss";

インポートの順序により、その後インポートされる他の@import "variables.scss";ファイルで.scssでロードされた変数を使用できるようになりました。したがって、これらはbootstrap=フォルダーのtype.scssで使用できますが、my_model.css.scssでも使用できます。

この後、partialsまたはmodulesという名前のフォルダーを作成します。これは、他のほとんどのファイルの場所になります。インポートをapplication.scssファイルに追加するだけで、次のようになります。

@import "bootstrap/bootstrap.scss";
@import "partials/*";

これで、ホームページで記事のスタイルを設定するために少しCSSを作成した場合。 partials/_article.scssを作成するだけで、コンパイルされたapplication.cssに追加されます。インポートの順序のため、任意のbootstrap=独自のscssファイルでミックスインと変数を使用することもできます。

私がこれまでに見つけたこの方法の唯一の欠点は、時々Railsは常にあなたのためにそれをしないので、パーシャル/*.scssファイルの再コンパイルを強制する必要がある場合があります。

次のフォルダー構造を作成します。

+ assets
|
--+ base
| |
| --+ mixins (with subfolders as noted in your question)
|
--+ styles
  |
  --+ ...

フォルダーbaseにファイル「globals.css.scss」を作成します。このファイルで、すべてのインポートを宣言します。

@import 'base/colors';
@import 'base/mixins/...';
@import 'base/mixins/...';

Application.css.scssには、次のものが必要です。

*= require_self
*= depends_on ./base/globals.css.scss
*= require_tree ./styles

最後のステップとして(これは重要です)、@import 'base/globals'変数またはミックスインを使用するすべてのスタイルファイルで。このオーバーヘッドを考慮することもできますが、実際には、すべてのファイルでスタイルの依存関係を宣言する必要があるという考えが気に入っています。もちろん、スタイル定義を追加しないため、globals.css.scssのミックスインと変数のみをインポートすることが重要です。そうしないと、プリコンパイル済みファイルにスタイル定義が複数回含まれてしまいます...

7
emrass

ファイル全体で変数などを使用するには、@ importディレクティブを使用する必要があります。ファイルは指定された順序でインポートされます。

次に、application.cssを使用して、インポートを宣言するファイルを要求します。これは、必要な制御を実現する方法です。

最後に、layout.erbファイルで、使用する「マスター」CSSファイルを指定できます。

例はより役立ちます:

アプリに2つのモジュールがあり、異なるCSSセットが必要だとしましょう: "application"と "admin"

ファイル

|-app/
|-- assets/
|--- stylesheets/
|     // the "master" files that will be called by the layout
|---- application.css
|---- application_admin.css
|
|     // the files that contain styles
|---- config.scss
|---- styles.scss
|---- admin_styles.scss
|
|     // the files that define the imports
|---- app_imports.scss
|---- admin_imports.scss
|
|
|-- views/
|--- layouts/
|---- admin.html.haml
|---- application.html.haml

ファイルは次のようになります。

-------- THE STYLES

-- config.scss
// declare variables and mixins
$font-size: 20px;

--  app_imports.scss
// using imports lets you use variables from `config` in `styles`
@import 'config'
@import 'styles'

-- admin_imports.scss
// for admin module, we import an additional stylesheet
@import 'config'
@import 'styles'
@import 'admin_styles'

-- application.css
// in the master application file, we require the imports
*= require app_imports
*= require some_other_stylesheet_like_a_plugin
*= require_self

-- application_admin.css
// in the master admin file, we require the admin imports
*= require admin_imports
*= require some_other_stylesheet_like_a_plugin
*= require_self


-------- THE LAYOUTS

-- application.html.haml
// in the application layout, we call the master css file
= stylesheet_link_tag "application", media: "all"

--  admin.html.haml
// in the admin layout, we call the admin master css file
= stylesheet_link_tag "application_admin", media: "all"
7
Doug Lee

この質問 によれば、[〜#〜] only [〜#〜]use application.css.sassインポートを定義し、テンプレート間で変数を共有するため。

=>名前の問題だけのようです。

他の方法は、 すべてを含めて、このパイプラインを無効にする です。

3
Coren

私は非常に似た問題を抱えていました。私が役立ったのは、パーシャルをインポートするときに@importステートメントにアンダースコアを挿入することでした。そう

@import "_base";

の代わりに

@import "base";

奇妙なバグかもしれません...

1
Bernát