- 投稿日:2020-09-15T19:53:28+09:00
【初心者でもわかる】PCとスマホで表示非表示を切り換える共通CSSを作ると効率UP!
どうも7noteです。レスポンシブで表示非表示を切り換える簡単な方法。
「スマホの時はこのブロックを非表示にして、違う場所にこのブロックを表示する」
「スマホの時は改行を非表示にする。」など、レスポンシブサイトを作る際によくあるシチュエーションの対策方法についてまとめていきます。
インライン要素にも対応させますよ。共通のCSSを作成し、出し分け専用のクラスを作る方法。
common.css/* PC専用 */ .pc{ display: block; } .sp{ display: none; } /* スマホ専用 */ @media screen and (max-width:820px) { .pc{ display: none; } .sp{ display: block; } }これだけだと、インライン要素に対応できなくなってしまうので・・・
改common.css.pc{ display: block; } .sp{ display: none; } /* インライン要素の時 */ .pcinline{ display: inline; } .spinline{ display: none; } @media screen and (max-width:820px) { .pc{ display: none; } .sp{ display: block; } /* インライン要素の時 */ .pc{ display: none; } .sp{ display: inline; } }これで、出し分けたい要素に
pc
やspinline
のクラスを付けるだけで簡単に出し分けが可能になります。
CSSで出し分ける際は画面サイズによって切り分けています。SEOに注意!!
一般的にPCとスマホは同じ内容が記載されている定なので、あまりにも出し分けが多くなり、PCとスマホで全然異なる内容になってしまうとSEOに影響がでる可能性があるらしい・・・
デザイン上必要で使う分くらいは大丈夫だろうなと思いますが、必要最低限の使用回数で済むようにCSSで工夫して作れるところはCSSで頑張りたいところ。
他の方法は?
これらの方法はユーザーエージェント(訪問者のデバイスの種類)によって切り分ける方法になります。
開発環境(PC)で確認するには、ユーザーエージェントを切り換えられる拡張機能等が必要になるので注意!まとめ。
これは本当によく使うので常にcommon.cssに入れてます。
ただ、displayがblockやinline以外の要素を出し分けしたい時にたまに困る。無理やり
.hoge.pc { display: flex; }
とか書けば別に問題はないのですが、なんとなく負けた気分になってしまう・・・。せっかく共通化したのに結局個別で指定しているのが腑に落ちない感じが。親要素を1つ追加するとか対策はいろいろあるんですけどね。
いい方法ご存知の方がいればぜひコメントなどで教えてください!おそまつ!
~ Qiitaで毎日投稿中!! ~
【初心者向け】HTML・CSSのちょいテク詰め合わせ
- 投稿日:2020-09-15T18:21:15+09:00
【GAS】HTMLメールで画像をインライン表示させる2つの方法
概要
GASを使えば、アドレス一覧に一斉にメール送信したりできる(一斉送信の記事ではないです)。用途とすればやっぱりメルマガとか?だったらやっぱり、ただのテキストメールじゃなくてHTMLでカッコよく装飾したメールを送りたい!
で、HTMLの書き方なんて分からないから、よくある視覚的にHTMLメールを作れるサービスを使ってテンプレートを作った訳だけど、HTML部分をコピペしても画像が表示されない・・・。
この記事では、HTMLメールで画像をインライン表示させるときの.gs側の記述と.html側の画像部分の記述について、2つの方法を紹介。
前置き...
・使用する画像はGoogleドライブ内にある。
・HTMLファイルの名前は「本文.html」。もちろん任意^^;①画像を添付してインライン表示させる
画像をメールに添付して、本文中にインライン表示させる方法。「コード.gs」がコチラ。
function sendHtmlMailBlob(){ //ドライブ内にある画像をgetBlob var imgA = DriveApp.getFileById('ドライブ内の画像のID').getBlob(); var imgB = DriveApp.getFileById('ドライブ内の画像のID').getBlob(); //本文.htmlをgetContent var html = HtmlService.createHtmlOutputFromFile("本文").getContent(); //宛先と件名 var mail = 'inlinemail@gmail.coi'; var title = 'インラインメール'; //メール送信 MailApp.sendEmail({ to: mail, subject: title, htmlBody: html, inlineImages:{imgA:imgA, imgB:imgB} }); }HTML側、画像部分の記述がコチラ。
<img src="cid=imgA">作成サービスで作ってダウンロードしたコード内に
src=画像の名前
みたいに画像を指定してる部分があるので、src="cid=getBlobした画像の名前"
に書き直してあげればOK!②画像のリンクからインライン表示させる
画像そのものは添付せず、画像のURLからインライン表示させる方法。「コード.gs」がコチラ。
function sendHtmlMailURL(){ //本文.htmlをgetContent var html = HtmlService.createHtmlOutputFromFile("本文").getContent(); //宛先と件名 var mail = 'inlinemail@gmail.coi'; var title = 'インラインメール'; //メール送信 MailApp.sendEmail({ to: mail, subject: title, htmlBody: html, }); }HTML側、画像部分の記述がコチラ。
<img id="source" src="https://drive.google.com/uc?export=view&id=ドライブ内の画像のID">ここでポイントが2つ
・src="共有可能なリンク"
ではダメ。
・画像の共有設定は「リンクを知っている全員」。補足
【画像のID】
ドライブ内の画像の「共有可能なリンク」の、次の部分がIDになる。
https://drive.google.com/file/d/<この部分>/view?usp=sharing
【画像の属性】
HTML部分の記述で画像の属性を省略してるけど、もちろん定義してOK。おしまい
- 投稿日:2020-09-15T16:51:43+09:00
検索ワードが複数あるときまとめてグーグル検索する
検索したいワードが複数あるときまとめてグーグル検索する
何を作りましたか
検索したいワードが複数あるときにそれぞれでコピーしてグーグル検索するのは大変なので、まとめてコピーして検索できるようなコードを書きました。使うのはHTML、Javascriptファイルです。
注)ファイルをHTML、Javascriptに分割していますが、そうするとサーバーのコードが必要になるかもしれません。利用するときはHTMLファイルにコードをまとめて利用しています。
環境
Firefox Browser 80.0.1
Mac OS Catalina 10.15.3HTML ファイル
sample.html<h1>まとめてグーグル検索</h1> <form> <div>検索したい文を入力してください。</div> <div>以下の例のように、改行するとそれぞれの行ごとに検索するよ(タブで開く)</div> <textarea name="textarea" rows="5" cols="30" placeholder="例) あいうえお かきくけこ 東京 寒い"></textarea> <input type="submit" value="Subscribe!"> </form> <h3>以下をコピーして検索してみよう</h3> <ul> <li>白日</li><li>白目</li><li>白曰</li><li>白臼</li><li>白自</li><li>白白</li><li>日白</li><li>日臼</li><li>日自</li><li>日日</li><li>曰白</li><li>曰臼</li><li>曰自</li><li>目曰</li><li>目臼</li><li>目自</li><li>臼白</li><li>臼日</li><li>臼目</li><li>臼曰</li><li>臼自</li><li>自白</li><li>自日</li><li>自目</li><li>自曰</li><li>自臼</li> </ul> <script type="module" src="sample.js"> </script>JSファイル
sample.jsconst searchInput = document.querySelector('textarea'); const form = document.querySelector('form'); form.addEventListener('submit', runEvent); function runEvent(e) { e.preventDefault(e); const searches = divideByLineBreak(searchInput.value); // 行ごとに検索(タブで開く) searches.forEach( search => { window.open('https://www.google.com/search?q=' + search, '_blank') }) // 入力を改行ごとに分割してArrayに格納する function divideByLineBreak (str) { let pos = 0; const searches = []; for (let i = 0; i < str.length; i++) { if (str[i] === '\n') { //console.log('\\n is found.'); searches.push(str.slice(pos, i)); pos = i+1; } // Add code here to replace white space with '+' (future work). } searches.push(str.slice(pos)); return searches; } }その他メモ
- ポップアップがブロックされた(解除するとまとめて開くことができる)
- コンソールに「“(ファイルのURI)” の生成元 “https://www.google.com” へのストレージアクセスが自動的に許可されました。」という警告が出る
- '\n'が一文字として正しく認識されているかが不明。if文で正しく比較できているか。
- 通常、google検索ではand検索時の単語同士が+で繋がれているが、今回の検索ではURIのqに直接書き込んでいるためかホワイトスペースが+に置換されずに検索されていた。
- 投稿日:2020-09-15T14:44:29+09:00
Udemyの人気講座「フルスタック・Webエンジニア講座」を受講してみた(その1)
はじめに
今回はUdemyの講座の1つである、【世界で30万人が受講】フルスタック・Webエンジニア講座(2019最新版)を受講してみる事にしました。
内容としては、以下を学習しながらウェブサイト・ウェブアプリを作成していく、というものになっております。
- HTML5
- CSS
- javascript
- jQuery
- BootStrap4
- WordPress
- PHP
- MySQL
- Python
もちろんこの講座を受けるだけでフルスタックエンジニアになれるとは思っておりません。
今回はフロントエンドの技術を浅く広く体系的に触る事が主な目的です。セクション1から15まである為、概要を記載していきます。
目次
セクション1:はじめに
講座の概要説明と環境セットアップがメイン。
- Chrome
- Brackets(エディター)
- MAMP(ApacheやMySQL等をパッケージしたもの)
セクション2:HTML5
セクション2はHTML。HTMLの説明及び、記載に必要なタグやリンクの挿入等について学習。
以下は学習内容の一例。
- ウェブページの基本構造
- 基本的なタグ
- ヘッダー(見出し)タグ
- パラグラフタグ
- テキストのフォーマット
- リスト
- イメージ
- フォーム
- テーブル
- リンク
- ウェブページを作ってみる
セクション3:CSS
セクション3はCSS。HTMLと同じく、説明及び記載方法等について学習。
以下は学習内容の一例。
- スタイルシート
- インラインCSSと外部CSS
- 各種スタイリング
- インラインCSS
- 内部CSS
- Class・id・span
- Div要素
- Color属性
- Floatレイアウト
- Position属性
- マージン(margin)
- パディング(padding)
- ボーダー(border)
- フォント(Fonts)
おわりに
まだ序盤ですが、動画を見ながら手を動かして実装していくので、理解しやすいという印象です。
9月中に完了するペースで進めていきます。
- 投稿日:2020-09-15T12:03:47+09:00
Django ManyToManyFieldをTemplateに表示
はじめに
今回の記事ではManyToManyFieldで繋いだものをTemplateに表示する方法を書いていきます。
モデルの確認
まずモデルを確認しましょう。
models.pyclass Kadai(models.Model): class Meta: verbose_name = '課題' verbose_name_plural = '課題' kadai_name = models.CharField( verbose_name='課題名', max_length=100, unique=True, ) category_number = models.IntegerField( verbose_name='課題カテゴリ数', default=0, ) kadai_thumbnail = models.ImageField( verbose_name='サムネイル画像', upload_to='media', ) def __str__(self): return self.kadai_name class KadaiCategory(models.Model): class Meta: verbose_name = '課題カテゴリ' verbose_name_plural = '課題カテゴリ' kadai_name = models.ManyToManyField(Kadai) category_name = models.CharField( verbose_name='カテゴリ名', max_length=100, unique=True ) kadai_number = models.IntegerField( verbose_name='課題数', default=0 ) category_thumbnail = models.ImageField( verbose_name='サムネイル画像', upload_to='media', ) def __str__(self): return self.category_nameHTMLファイルの確認
これが全体像ですが、長いので少し短くします。
models.pyclass Kadai(models.Model): class Meta: verbose_name = '課題' verbose_name_plural = '課題' kadai_name = models.CharField( verbose_name='課題名', max_length=100, unique=True, ) . . . def __str__(self): return self.kadai_name class KadaiCategory(models.Model): class Meta: verbose_name = '課題カテゴリ' verbose_name_plural = '課題カテゴリ' kadai_name = models.ManyToManyField(Kadai) category_name = models.CharField( verbose_name='カテゴリ名', max_length=100, unique=True ) . . . def __str__(self): return self.category_nameこれで少しは見やすくなりました。
一応説明しておくと、「Kadai」クラスは課題がいくつかあり、「KadaiCategory」クラスにはカテゴリがいくつかあります。
つまり、「多対多」なのでManyToManyFieldを使っています。
それでは早速Templateの方を見ていきましょう。
このHTMLファイルは、「KadaiCategory」つつながっています。kadai_category.html{% for category in object_list %} <div class="col-4 one-card"> <div class="card" style="width: 18rem;"> <img src="{{ category.category_thumbnail.url }}" height="300" alt="サムネイル画像です。"> <div class="card-body"> <h5 class="card-title">{{ category.category_name }}</h5> <p class="card-text">スキルチェックをして自分のスキルを上げていきましょう!</p> <p>/{{ category.kadai_number }}</p> <a href="#" class="btn btn-primary">Let's Challenge</a> </div> </div> </div> {% endfor %}この状態だとただModelに書かれていることを表示しているだけで、ManyToManyFieldでつながっている「Kadai」クラスのモデルを表示できていません。
ではどのようにしたらManyToManyFielfでつながっている「Kadai」クラスのモデルを表示できるのでしょうか?
答えはこのようにします。kadai_category.html{% for kadai in category.kadai_name.all %} <p>{{ kadai.kadai_name }}</p> {% endfor %}全体像を見てみましょう。
kadai_category.html{% for category in object_list %} <div class="col-4 one-card"> <div class="card" style="width: 18rem;"> <img src="{{ category.category_thumbnail.url }}" height="300" alt="サムネイル画像です。"> <div class="card-body"> <h5 class="card-title">{{ category.category_name }}</h5> <p class="card-text">スキルチェックをして自分のスキルを上げていきましょう!</p> <p>/{{ category.kadai_number }}</p> # ここに追加 {% for kadai in category.kadai_name.all %} <p>{{ kadai.kadai_name }}</p> {% endfor %} <a href="#" class="btn btn-primary">Let's Challenge</a> </div> </div> </div> {% endfor %}書き方を説明します。上の全体像をみつつ理解してください。
{% for カウンタ変数(どんな名前でも良い) in 大きなfor文のカウンタ変数部分.ManyToManyFieldで繋いでいる変数名.all %} <p>{{ カウンタ変数.ManyToManyFieldで繋いだ先の読み込みたいモデルの変数}}</p> {% endfor %}最後に
しっかり伝わっているかわかりませんが、見比べながら自分のプロジェクトに反映させていってください。
- 投稿日:2020-09-15T09:00:09+09:00
React+TypeScriptでcanvasを用いて矩形描画する
React+TypeScriptでCanvasを用いて矩形描画をする関数コンポーネントです。
import React, { useEffect, useRef, memo, FC } from 'react'; type Props = { canvasWidth: number; //canvas幅 canvasHeight: number; //canvas高さ x: number; //矩形始点x y: number; //矩形始点y rectWidth: number; //矩形幅 rectHeight: number; //矩形高さ }; const Canvas: FC<Props> = ({ canvasWidth, canvasHeight, x, y, rectWidth, rectHeight }) => { const canvasRef = useRef(null); const getContext = (): CanvasRenderingContext2D => { const canvas: any = canvasRef.current; return canvas.getContext('2d'); }; useEffect(() => { const ctx = getContext(); ctx.strokeStyle = '#000000'; // 矩形色 ctx.lineWidth = 2; // 矩形線幅 ctx.strokeRect(x, y, rectWidth, rectHeight); // 矩形描画 }, [canvasWidth, canvasHeight, x, y, rectWidth, rectHeight]); return <canvas ref={canvasRef} width={canvasWidth} height={canvasHeight} />; }; export default memo(Canvas);